summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
author崔一鸣 <[email protected]>2019-04-17 14:30:11 +0800
committer崔一鸣 <[email protected]>2019-04-17 14:30:11 +0800
commit4333c8d31b65de6d89997d37c752bf5347a026be (patch)
tree2c0a6ca7e17d9ce6e9f502d4eb37cabfb572e4c3
init commit
-rw-r--r--.gitignore1
-rw-r--r--CMakeLists.txt20
-rw-r--r--test/CMakeLists.txt15
-rw-r--r--test/new_http_service/adapter.cpp270
-rw-r--r--test/new_http_service/adapter.h61
-rw-r--r--test/new_http_service/http_service.lua14
-rw-r--r--test/test_coroutine/main.cpp132
-rw-r--r--test/test_coroutine/test.lua54
-rw-r--r--test/test_plugin/http_service.cpp157
-rw-r--r--test/test_plugin/http_service.h51
-rw-r--r--vendor/CMakeLists.txt47
-rw-r--r--vendor/lua-5.3.5.tar.gzbin0 -> 303543 bytes
12 files changed, 822 insertions, 0 deletions
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..75ec3f0
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1 @@
+.vscode/* \ No newline at end of file
diff --git a/CMakeLists.txt b/CMakeLists.txt
new file mode 100644
index 0000000..bbf8ca0
--- /dev/null
+++ b/CMakeLists.txt
@@ -0,0 +1,20 @@
+cmake_minimum_required(VERSION 3.5)
+project(lun_sapp)
+
+set(CMAKE_MODULE_PATH ${PROJECT_SOURCE_DIR}/cmake)
+#include(Version)
+
+set(CMAKE_CXX_STANDARD 11)
+set(CMAKE_C_STANDARD 11)
+set(CMAKE_POSITION_INDEPENDENT_CODE ON)
+set (CMAKE_CXX_FLAGS "-Wall")
+SET(CMAKE_BUILD_TYPE Debug)
+
+add_definitions(-D_GNU_SOURCE)
+
+if (CMAKE_BUILD_TYPE STREQUAL Debug)
+ add_definitions(-DDEBUG)
+endif()
+
+add_subdirectory(vendor)
+add_subdirectory(test) \ No newline at end of file
diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt
new file mode 100644
index 0000000..5797582
--- /dev/null
+++ b/test/CMakeLists.txt
@@ -0,0 +1,15 @@
+### test_coroutine
+add_executable(test_coroutine test_coroutine/main.cpp)
+#target_include_directories(test_coroutine PUBLIC ${CMAKE_CURRENT_LIST_DIR}/include)
+target_link_libraries(test_coroutine lua-static dl)
+
+
+### test_plugin
+add_library(http_service SHARED test_plugin/http_service.cpp)
+#target_include_directories(http_service PUBLIC ${CMAKE_CURRENT_LIST_DIR}/include)
+target_link_libraries(http_service MESA_handle_logger MESA_htable MESA_prof_load)
+
+### new_http_service
+add_library(new_http_service SHARED new_http_service/adapter.cpp)
+#target_include_directories(new_http_service PUBLIC ${CMAKE_CURRENT_LIST_DIR}/include)
+target_link_libraries(new_http_service lua-static dl MESA_handle_logger MESA_htable MESA_prof_load) \ No newline at end of file
diff --git a/test/new_http_service/adapter.cpp b/test/new_http_service/adapter.cpp
new file mode 100644
index 0000000..fb37e32
--- /dev/null
+++ b/test/new_http_service/adapter.cpp
@@ -0,0 +1,270 @@
+#include "adapter.h"
+
+#define LOG_MODULE_NAME "SAPP_LUA"
+#define LUA_SAPP_SYMBOL_MAX 64
+#define LUA_SAPP_PATH_MAX 256
+#define LUA_SAPP_STRING_MAX 2048
+#define LUA_ENTRY_TYPE_NUM 8
+enum lua_entry_type{
+ LUA_ENTRY_TYPE_IP = 0,
+ LUA_ENTRY_TYPE_TCP,
+ LUA_ENTRY_TYPE_UDP,
+ LUA_ENTRY_TYPE_HTTP,
+ LUA_ENTRY_TYPE_TLS,
+ LUA_ENTRY_TYPE_DNS,
+ LUA_ENTRY_TYPE_MAIL,
+ LUA_ENTRY_TYPE_FTP,
+};
+
+
+//TODO:
+// other_regions 有多个, 怎么处理
+// 增加根据region返回header功能
+
+class lua_plug{
+public:
+ std::string file_path;
+ enum lua_entry_type entry_type;
+ int dir;
+ std::unordered_set<std::string> regions;
+ lua_State *lua_state;
+};
+
+static void* g_logger = NULL;
+static std::vector<std::vector<lua_plug>> g_lua_plugs(LUA_ENTRY_TYPE_NUM, std::vector<lua_plug>());
+
+//copy from suricata
+static int lua_push_string_buffer(lua_State *lua_state, const char *input, size_t input_len)
+{
+ if (input_len % 4 != 0) {
+ /* we're using a buffer sized at a multiple of 4 as lua_pushlstring generates
+ * invalid read errors in valgrind otherwise. Adding in a nul to be sure.
+ * Buffer size = len + 1 (for nul) + whatever makes it a multiple of 4 */
+ size_t buflen = input_len + 1 + ((input_len + 1) % 4);
+ char buf[buflen];
+ memset(buf, 0x00, buflen);
+ memcpy(buf, input, input_len);
+ buf[input_len] = '\0';
+ /* return value through lua_state, as a luastring */
+ lua_pushlstring(lua_state, buf, input_len);
+ } else {
+ lua_pushlstring(lua_state, input, input_len);
+ }
+ return 1;
+}
+
+
+static int _get_http_headers(lua_State *lua_state, int status, lua_KContext yieldk_ctx){
+ lua_getglobal(lua_state, "cur_http_sess_ctx");
+ http_sess_ctx *sess_ctx = (http_sess_ctx *)lua_touserdata(lua_state, -1);
+ lua_getglobal(lua_state, "cur_http_sess_dir");
+ int curdir = (int)lua_tonumber(lua_state, -1);
+ lua_pop(lua_state, 2);
+ if(sess_ctx == NULL){
+ //do log
+ std::cout<<"sess_ctx is null"<<std::endl;
+ return 0;
+ }
+ lua_newtable(lua_state);
+ for(auto header : curdir == DIR_C2S ? sess_ctx->request_headers : sess_ctx->response_headers){
+ lua_push_string_buffer(lua_state, header.first.c_str(), header.first.length() + 1);
+ lua_push_string_buffer(lua_state, header.second.c_str(), header.second.length() + 1);
+ lua_settable(lua_state, -3);
+ }
+ //return 1 means one return value
+ return 1;
+}
+
+static int get_http_headers(lua_State *lua_state){
+ lua_yieldk(lua_state, 0, 0, _get_http_headers);
+ return 1;
+}
+
+int regions_parse(char *str, std::unordered_set<std::string>& regions){
+ char *token;
+ char *rest = str;
+ while((token = strtok_r(rest, ",", &rest))){
+ std::string _token = std::string(token);
+ if(_token == "all"){
+ regions.clear();
+ regions.insert(_token);
+ return 0;
+ }
+ regions.insert(_token);
+ }
+ return 0;
+}
+
+static int load_lua_plug(const char *profile){
+ std::unordered_map<std::string, int> type_map = {
+ {"ip", LUA_ENTRY_TYPE_IP},
+ {"tcp", LUA_ENTRY_TYPE_TCP},
+ {"udp", LUA_ENTRY_TYPE_UDP},
+ {"http", LUA_ENTRY_TYPE_HTTP},
+ {"tls", LUA_ENTRY_TYPE_TLS},
+ {"dns", LUA_ENTRY_TYPE_DNS},
+ {"mail", LUA_ENTRY_TYPE_MAIL},
+ {"ftp", LUA_ENTRY_TYPE_FTP}
+ };
+ std::unordered_map<std::string, int> dir_map{
+ {"c2s", DIR_C2S},
+ {"s2c", DIR_S2C},
+ {"all", DIR_DOUBLE}
+ };
+ const char *section = "main";
+ char file_path[LUA_SAPP_PATH_MAX] = "";
+ char entry_type[LUA_SAPP_SYMBOL_MAX] = "";
+ char dir[LUA_SAPP_SYMBOL_MAX] = "";
+ char regions[LUA_SAPP_STRING_MAX] = "";
+ MESA_load_profile_string_def(profile, section, "file_path", file_path, sizeof(file_path), "");
+ MESA_load_profile_string_def(profile, section, "entry_type", entry_type, sizeof(entry_type), "http");
+ MESA_load_profile_string_def(profile, section, "dir", dir, sizeof(dir), "all");
+ MESA_load_profile_string_def(profile, section, "regions", regions, sizeof(regions), "all");
+
+ lua_State *lua_state = luaL_newstate();
+ luaL_openlibs(lua_state);
+ luaL_dofile(lua_state, file_path);
+ lua_register(lua_state, "get_http_headers", get_http_headers);
+ lua_getglobal(lua_state, "main");
+
+ lua_plug plug;
+ plug.file_path = std::string(file_path);
+ plug.entry_type = (enum lua_entry_type)type_map[std::string(entry_type)];
+ plug.dir = dir_map[std::string(dir)];
+ regions_parse(regions, plug.regions);
+ plug.lua_state = lua_state;
+ g_lua_plugs[plug.entry_type].push_back(plug);
+ lua_resume(lua_state, NULL, 0);
+ return 0;
+}
+
+int process_lua_plug_conflist(const char* filename)
+{
+ char lua_plug_conf_path[LUA_SAPP_PATH_MAX] = {0};
+ FILE* fp = fopen(filename, "r");
+ if(fp == NULL){
+ MESA_handle_runtime_log(g_logger, RLOG_LV_FATAL, LOG_MODULE_NAME, "process_conflist() fopen %s error!\n", filename);
+ return -1;
+ }
+ while(feof(fp) == 0){
+ if((fgets(lua_plug_conf_path, LUA_SAPP_PATH_MAX, fp)) == NULL){
+ fclose(fp);
+ fp=NULL;
+ return 0;
+ }
+ if(lua_plug_conf_path[0]=='#'){
+ continue;
+ }
+ int len = strnlen(lua_plug_conf_path, LUA_SAPP_PATH_MAX);
+ lua_plug_conf_path[len - 1] = '\0';
+ load_lua_plug(lua_plug_conf_path);
+ }
+ fclose(fp);
+ fp=NULL;
+ return 0;
+}
+
+static http_sess_ctx* init_http_sess_ctx(){
+ http_sess_ctx *ctx = new http_sess_ctx();
+ return ctx;
+}
+
+static void clear_http_sess_ctx(http_sess_ctx *ctx){
+ delete ctx;
+ ctx = NULL;
+}
+
+static std::string trans_to_binary(unsigned int n){
+ std::string res;
+ while(n){
+ res = std::to_string(n % 2) + res;
+ n /= 2;
+ }
+ return res;
+}
+
+static void output_stack_size(lua_State *lua_state){
+ int n = lua_gettop(lua_state);
+ std::cout<<"stack size is "<<n<<std::endl;
+}
+
+uchar NEW_HTTP_SERVICE_ENTRY(stSessionInfo* session_info, void **param, int thread_seq, struct streaminfo *a_tcp, void *a_packet){
+ uchar rec = PROT_STATE_GIVEME;
+ http_sess_ctx *ctx = (http_sess_ctx*)*param;
+ http_infor *a_http = (http_infor *)(session_info->app_info);
+ //static int header_len = 0;
+ //static int content_len = 0;
+ if(NULL==session_info){
+ return PROT_STATE_DROPME;
+ }
+ if(ctx == NULL){
+ ctx = init_http_sess_ctx();
+ *param = ctx;
+ }
+ std::string prot_flag_str = trans_to_binary(session_info->prot_flag);
+ //MESA_handle_runtime_log(g_logger, RLOG_LV_INFO, HTTP_SERVICE_PLUGNAME,
+ // "call http_service entry, http_state is %02x\n, prot_flag mask is %s : %d", http_state, prot_flag_str.c_str(), prot_flag_str.length() - 1);
+ std::string temp = (a_http->http_state == HTTP_DATA_BEGIN) ? "data begin" : "not data begin";
+ //curdir: request or response
+ uchar curdir = a_http->curdir;
+ switch(session_info->prot_flag)
+ {
+ case HTTP_STATE:
+ case HTTP_CONTENT:
+ break;
+ case HTTP_UNGZIP_CONTENT:
+ //fwrite(session_info->buf, session_info->buflen, 1, service_pme->fp);
+ //fflush(service_pme->fp);
+ break;
+ default:
+ std::string key(http_proto_flag2region(session_info->prot_flag));
+ std::string value((const char*)(session_info->buf), session_info->buflen);
+ if(curdir == DIR_C2S){
+ ctx->request_headers.insert({key, value});
+ }
+ else{
+ ctx->response_headers.insert({key, value});
+ }
+ break;
+ }
+ uchar http_state = a_http->http_state;
+ //header over, resume lua
+ if(http_state == HTTP_DATA_BEGIN){
+ for(auto plug : g_lua_plugs[LUA_ENTRY_TYPE_HTTP]){
+ if(plug.dir == DIR_DOUBLE || plug.dir == curdir){
+ lua_pushlightuserdata(plug.lua_state, (void *)ctx);
+ lua_setglobal(plug.lua_state, "cur_http_sess_ctx");
+ lua_pushinteger(plug.lua_state, curdir);
+ lua_setglobal(plug.lua_state, "cur_http_sess_dir");
+ lua_resume(plug.lua_state, NULL, 0);
+ }
+ }
+ }
+ if(session_info->session_state & SESSION_STATE_CLOSE){
+ clear_http_sess_ctx(ctx);
+ *param = NULL;
+ }
+ return rec;
+}
+
+int NEW_HTTP_SERVICE_INIT(void)
+{
+ g_logger = MESA_create_runtime_log_handle("./log/http/http_service", 10);
+ if(g_logger == NULL){
+ printf("%s init : get log handle error!\n", HTTP_SERVICE_PLUGNAME);
+ return -1;
+ }
+ // get thread num
+ // get all business lua script which register http
+ const char *conflist_path = "./plug/lua/conflist_lua.inf";
+ if(g_lua_plugs[LUA_ENTRY_TYPE_HTTP].size() == 0){
+ process_lua_plug_conflist(conflist_path);
+ }
+ return 0;
+}
+
+void NEW_HTTP_SERVICE_DESTROY(void)
+{
+ return ;
+}
+
diff --git a/test/new_http_service/adapter.h b/test/new_http_service/adapter.h
new file mode 100644
index 0000000..dfdb981
--- /dev/null
+++ b/test/new_http_service/adapter.h
@@ -0,0 +1,61 @@
+/*
+ * HTTP_Service.h
+ *
+ * Created on: 2013-8-19
+ * Author: lishu
+ */
+
+#ifndef HTTP_SERVICE_H_
+#define HTTP_SERVICE_H_
+
+#include <iostream>
+#include <string>
+#include <vector>
+#include <unordered_map>
+#include <unordered_set>
+
+#include <stdio.h>
+#include <string.h>
+#include <pthread.h>
+#include <time.h>
+#include <sys/ioctl.h>
+#include <sys/socket.h>
+#include <arpa/inet.h>
+#include <unistd.h>
+#include <ctype.h>
+#include <stdlib.h>
+#include <regex.h>
+#include "stream.h"
+#include "http.h"
+#include "MESA/MESA_prof_load.h"
+#include "MESA/MESA_handle_logger.h"
+
+extern "C" {
+ #include "lua.h"
+ #include "lualib.h"
+ #include "lauxlib.h"
+}
+#define HTTP_SERVICE_PLUGNAME "new_http_service.so"
+#define LOG_PATH "./log/new_http_service/"
+
+
+class http_sess_ctx{
+public:
+ std::unordered_map<std::string, std::string> request_headers;
+ std::unordered_map<std::string, std::string> response_headers;
+};
+
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+uchar NEW_HTTP_SERVICE_ENTRY(stSessionInfo* session_info, void **param, int thread_seq, struct streaminfo *a_tcp, void *a_packet);
+int NEW_HTTP_SERVICE_INIT(void);
+void NEW_HTTP_SERVICE_DESTROY(void);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* HTTP_SERVICE_H_ */
diff --git a/test/new_http_service/http_service.lua b/test/new_http_service/http_service.lua
new file mode 100644
index 0000000..58f1b81
--- /dev/null
+++ b/test/new_http_service/http_service.lua
@@ -0,0 +1,14 @@
+function main()
+ while true do
+ headers = get_http_request_headers(ctx)
+ for k, v in pairs(headers) do
+ print(k, v)
+ end
+ end
+end
+
+
+function main()
+ headers = get_http_request_headers()
+ content = get_http_content()
+ ---handle \ No newline at end of file
diff --git a/test/test_coroutine/main.cpp b/test/test_coroutine/main.cpp
new file mode 100644
index 0000000..931d562
--- /dev/null
+++ b/test/test_coroutine/main.cpp
@@ -0,0 +1,132 @@
+#include <iostream>
+#include <stdio.h>
+#include <vector>
+#include <unistd.h>
+using namespace std;
+extern "C" {
+ #include "lua.h"
+ #include "lualib.h"
+ #include "lauxlib.h"
+}
+
+static void output_stack_size(lua_State *L){
+ int n = lua_gettop(L);
+ cout<<"stack size is "<<n<<endl;
+}
+
+static void test_coroutine(int argc, char *argv[]){
+ int max_state_num = 10;
+ int max_coroutine_num = 100;
+ if(argc > 2){
+ max_state_num = atoi(argv[1]);
+ max_coroutine_num = atoi(argv[2]);
+ }
+ const char *filename = "../../test/test_coroutine/test.lua";
+ vector<lua_State*> states;
+ for(int i = 0; i < max_state_num; i++){
+ lua_State *L = luaL_newstate();
+ luaL_openlibs(L);
+ luaL_dofile(L, filename);
+ states.push_back(L);
+ }
+ vector<pair<lua_State*, lua_State*>> coroutines;
+ for(auto state : states){
+ int i = 0;
+ for(; i < max_coroutine_num; i++){
+ lua_State* l = lua_newthread(state);
+ int ret = lua_checkstack(state, 1);
+ if(ret != 1)
+ printf("do not have enough space, ret is %d\n", ret);
+ coroutines.push_back({l, state});
+ lua_getglobal(l, "test");
+ //cout<<"after getglobal, size = "<<lua_gettop(l)<<endl;
+ lua_pushinteger(l, i);
+ //cout<<"after pushinterger, size = "<<lua_gettop(l)<<endl;
+ lua_resume(l, state, 1);
+ //cout<<"after resume, size = "<<lua_gettop(L)<<endl;
+ }
+ }
+ sleep(2);
+ cout<<"coroutine size: "<<coroutines.size()<<endl;
+ while(true){
+ for(auto coroutine : coroutines){
+ lua_resume(coroutine.first, coroutine.second, 0);
+ }
+ }
+}
+
+
+static int foo (lua_State *L) {
+ cout<<"call foo"<<endl;
+ output_stack_size(L);
+ lua_Number sum = 0.0;
+ int n = lua_gettop(L);
+ for (int i = 1; i <= n; i++) {
+ if (!lua_isnumber(L, i)) {
+ printf("index %d is not number\n", i);
+ //lua_pushliteral(L, "incorrect argument");
+ //lua_error(L);
+ }
+ sum += lua_tonumber(L, i);
+ }
+ printf("sum is %f\n", sum);
+ lua_pop(L, n);
+ output_stack_size(L);
+ lua_pushnumber(L, sum/n); //first result
+ lua_pushnumber(L, sum); //second result
+ output_stack_size(L);
+ return 2; //number of results
+}
+
+static int foo2(lua_State *L, int n, long int m){
+ cout<<"cpp: after lua_yield"<<endl;
+ return 0;
+}
+
+static int foo1(lua_State *L){
+ output_stack_size(L);
+ /*
+ lua_getglobal(L, "g_http_sess_ctx");
+ output_stack_size(L);
+ int *ctx = (int *)lua_touserdata(L, 1);
+ if(ctx == NULL)
+ cout<<"ctx is null"<<endl;
+ else
+ cout<<"ctx is "<<*ctx<<endl;
+ cout<<"cpp: call foo1"<<endl;
+ */
+ //lua_yieldk(L, 0, 0, foo2);
+}
+
+static void test_lua_CFunction(){
+ const char *filename = "../../test/test_coroutine/test.lua";
+ lua_State *L = luaL_newstate();
+ luaL_openlibs(L);
+ luaL_dofile(L, filename);
+ lua_register(L, "myfoo", foo1);
+ lua_getglobal(L, "lua_call_c");
+ /*
+ output_stack_size(L);
+ lua_getglobal(L, "lua_call_c");
+ output_stack_size(L);
+ int *ctx = (int *)malloc(sizeof(int));
+ *ctx = 3;
+ lua_pushlightuserdata(L, (void *)ctx);
+ output_stack_size(L);
+ lua_setglobal (L, "g_http_sess_ctx");
+ output_stack_size(L);
+ //output_stack_size(L);
+ //lua_pushinteger(L, 2);
+ //lua_pushinteger(L, 3);
+ */
+ lua_resume(L, NULL, 0);
+ cout<<"cpp: atfer lua_call"<<endl;
+ //lua_resume(L, NULL, 0);
+}
+
+
+int main(int argc, char *argv[]){
+ //test_coroutine(argc, argv);
+ test_lua_CFunction();
+ return 0;
+} \ No newline at end of file
diff --git a/test/test_coroutine/test.lua b/test/test_coroutine/test.lua
new file mode 100644
index 0000000..ca340d6
--- /dev/null
+++ b/test/test_coroutine/test.lua
@@ -0,0 +1,54 @@
+
+
+printf = function(s,...)
+ return io.write(s:format(...))
+ end
+
+function test(id)
+ i = 0
+ local j = 1
+ while true do
+ if j % 10000 == 5 and id % 10000 == 5 then
+ printf("call test, coroutine id: %d, local index: %d, global index: %d\n", id, j, i)
+ end
+ j = j + 1
+ i = i + 1
+ coroutine.yield()
+ end
+end
+
+function foo(x)
+ if x % 10000 == 5 then
+ printf("cal foo: x = %d\n", x)
+ end
+ coroutine.yield()
+end
+
+function foo1()
+ print("call foo1")
+ foo(10)
+ return 3
+end
+
+function main()
+ n = 10000000
+ co_list = {}
+ for i = n, 1, -1 do
+ co = coroutine.create(function (i)
+ foo(i)
+ end)
+ table.insert(co_list, co);
+ end
+ while(true) do
+ for i = 1, #co_list do
+ coroutine.resume(co_list[i], i)
+ end
+ end
+end
+
+function lua_call_c()
+
+ printf("lua: call lua_call_c\n")
+ myfoo()
+ printf("lua: after my_foo\n")
+end \ No newline at end of file
diff --git a/test/test_plugin/http_service.cpp b/test/test_plugin/http_service.cpp
new file mode 100644
index 0000000..e3d7984
--- /dev/null
+++ b/test/test_plugin/http_service.cpp
@@ -0,0 +1,157 @@
+/*
+ * HTTP_Service.c
+ *
+ * Created on: 2013-8-19
+ * Author: lishu
+ */
+
+#include <math.h>
+#include <pthread.h>
+#include <time.h>
+#include <arpa/inet.h>
+#include <stdio.h>
+#include <regex.h>
+#include <string>
+#include "http_service.h"
+#include "MESA_handle_logger.h"
+
+int HTTP_SERVICE_VERSION_1_20160412 = 0;
+void http_service_version_1_20160412()
+{
+ //20160412 create project
+}
+
+void* g_log_handle = NULL;
+
+int init_pmeinfo(service_pmeinfo **service_pme, int thread_seq)
+{
+ service_pmeinfo* pme = (service_pmeinfo*)dictator_malloc(thread_seq, sizeof(service_pmeinfo));
+ *service_pme = pme;
+ return 0;
+}
+
+void clear_pmeinfo(service_pmeinfo *service_pme, int thread_seq)
+{
+ if(service_pme!=NULL)
+ {
+ dictator_free(thread_seq, service_pme);
+ }
+ service_pme = NULL;
+}
+
+std::string trans_to_binary(unsigned int n){
+ std::string res;
+ while(n){
+ res = std::to_string(n % 2) + res;
+ n /= 2;
+ }
+ return res;
+}
+
+uchar HTTP_SERVICE_ENTRY(stSessionInfo* session_info, void **param, int thread_seq, struct streaminfo *a_tcp, void *a_packet)
+{
+ uchar rec = PROT_STATE_GIVEME;
+ service_pmeinfo *service_pme = (service_pmeinfo*)*param;
+ http_infor *a_http = (http_infor *)(session_info->app_info);
+ char filename[512] = {0};
+ const char* region = NULL;
+ //static int header_len = 0;
+ //static int content_len = 0;
+
+ uchar http_state = a_http->http_state;
+
+ if(NULL==session_info)
+ {
+ return PROT_STATE_DROPME;
+ }
+
+ if(service_pme == NULL)
+ {
+ if(init_pmeinfo(&service_pme, thread_seq) <0)
+ {
+ return PROT_STATE_DROPME;
+ }
+ *param = service_pme;
+ }
+ std::string prot_flag_str = trans_to_binary(session_info->prot_flag);
+ MESA_handle_runtime_log(g_log_handle, RLOG_LV_INFO, HTTP_SERVICE_PLUGNAME,
+ "call http_service entry, http_state is %02x\n, prot_flag mask is %s : %d", http_state, prot_flag_str.c_str(), prot_flag_str.length() - 1);
+ switch(session_info->prot_flag)
+ {
+ case HTTP_STATE:
+ case HTTP_CONTENT:
+ break;
+ case HTTP_UNGZIP_CONTENT:
+ snprintf(filename, sizeof(filename), "%s/HTTP_%s_%u", LOG_PATH, printaddr(&a_tcp->addr, thread_seq), a_http->http_session_seq);
+ service_pme->fp = fopen(filename, "a+");
+ if(NULL==service_pme->fp)
+ {
+ MESA_handle_runtime_log(g_log_handle, RLOG_LV_FATAL, HTTP_SERVICE_PLUGNAME, "%s file open error.", filename);
+ return PROT_STATE_DROPME;
+ }
+ MESA_handle_runtime_log(g_log_handle, RLOG_LV_DEBUG, HTTP_SERVICE_PLUGNAME, "%s file open.",filename);
+
+ fwrite(session_info->buf, session_info->buflen, 1, service_pme->fp);
+ fflush(service_pme->fp);
+ //content_len += session_info->buflen;
+ //printf("content_len:%d\n", content_len);
+
+ snprintf(filename, sizeof(filename), "%s/HTTP_%s_%u", LOG_PATH, printaddr(&a_tcp->addr, thread_seq), a_http->http_session_seq);
+ MESA_handle_runtime_log(g_log_handle, RLOG_LV_DEBUG, HTTP_SERVICE_PLUGNAME, "%s file close.",filename);
+ fclose(service_pme->fp);
+ break;
+ default:
+ snprintf(filename, sizeof(filename), "%s/HTTP_%s_%u", LOG_PATH, printaddr(&a_tcp->addr, thread_seq), a_http->http_session_seq);
+ service_pme->fp = fopen(filename, "a+");
+ if(NULL==service_pme->fp)
+ {
+ MESA_handle_runtime_log(g_log_handle, RLOG_LV_FATAL, HTTP_SERVICE_PLUGNAME, "%s file open error.", filename);
+ return PROT_STATE_DROPME;
+ }
+ MESA_handle_runtime_log(g_log_handle, RLOG_LV_DEBUG, HTTP_SERVICE_PLUGNAME, "%s file open.",filename);
+
+ region = http_proto_flag2region(session_info->prot_flag);
+
+ fwrite(region, strlen(region), 1, service_pme->fp);
+ fwrite(":", 1, 1, service_pme->fp);
+ fwrite(session_info->buf, session_info->buflen, 1, service_pme->fp);
+ fwrite("\r\n", 2, 1, service_pme->fp);
+ fflush(service_pme->fp);
+ //header_len += session_info->buflen;
+ //printf("header_len:%d\n", header_len);
+
+ snprintf(filename, sizeof(filename), "%s/HTTP_%s_%u", LOG_PATH, printaddr(&a_tcp->addr, thread_seq), a_http->http_session_seq);
+ MESA_handle_runtime_log(g_log_handle, RLOG_LV_DEBUG, HTTP_SERVICE_PLUGNAME, "%s file close.",filename);
+ fclose(service_pme->fp);
+ break;
+ }
+
+ if(session_info->session_state&SESSION_STATE_CLOSE)
+ {
+ if(NULL!=service_pme->fp)
+ {
+
+ service_pme->fp = NULL;
+ }
+ clear_pmeinfo((service_pmeinfo*)*param, thread_seq);
+ *param = NULL;
+ }
+ return rec;
+}
+
+int HTTP_SERVICE_INIT(void)
+{
+ g_log_handle = MESA_create_runtime_log_handle("./log/http/http_service", 10);
+ if(g_log_handle == NULL)
+ {
+ printf("%s init : get log handle error!\n", HTTP_SERVICE_PLUGNAME);
+ return -1;
+ }
+ return 0;
+}
+
+void HTTP_SERVICE_DESTROY(void)
+{
+ return ;
+}
+
diff --git a/test/test_plugin/http_service.h b/test/test_plugin/http_service.h
new file mode 100644
index 0000000..5d0d423
--- /dev/null
+++ b/test/test_plugin/http_service.h
@@ -0,0 +1,51 @@
+/*
+ * HTTP_Service.h
+ *
+ * Created on: 2013-8-19
+ * Author: lishu
+ */
+
+#ifndef HTTP_SERVICE_H_
+#define HTTP_SERVICE_H_
+
+#include <stdio.h>
+#include <string.h>
+#include <pthread.h>
+#include <time.h>
+#include </usr/include/net/if.h>
+#include <sys/ioctl.h>
+#include <sys/socket.h>
+#include </usr/include/linux/sockios.h>
+#include <arpa/inet.h>
+#include <unistd.h>
+#include <ctype.h>
+#include <stdlib.h>
+#include <regex.h>
+
+
+#include "stream.h"
+#include "http.h"
+
+#define HTTP_SERVICE_PLUGNAME "http_service.so"
+#define LOG_PATH "./log/http/"
+
+
+typedef struct service_pmeinfo
+{
+ FILE* fp;
+}service_pmeinfo;
+
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+uchar HTTP_SERVICE_ENTRY(stSessionInfo* session_info, void **param, int thread_seq, struct streaminfo *a_tcp, void *a_packet);
+int HTTP_SERVICE_INIT(void);
+void HTTP_SERVICE_DESTROY(void);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* HTTP_SERVICE_H_ */
diff --git a/vendor/CMakeLists.txt b/vendor/CMakeLists.txt
new file mode 100644
index 0000000..33aea31
--- /dev/null
+++ b/vendor/CMakeLists.txt
@@ -0,0 +1,47 @@
+include(ExternalProject)
+
+### lua-5.3.5
+ExternalProject_Add(lua
+ PREFIX lua
+ URL ${CMAKE_CURRENT_SOURCE_DIR}/lua-5.3.5.tar.gz
+ URL_MD5 184779090118aebdf125fdb1233335ea
+ CONFIGURE_COMMAND cd ./src
+ BUILD_COMMAND make linux
+ INSTALL_COMMAND make install INSTALL_TOP=<INSTALL_DIR>
+ BUILD_IN_SOURCE 1)
+
+ExternalProject_Get_Property(lua INSTALL_DIR)
+file(MAKE_DIRECTORY ${INSTALL_DIR}/include)
+
+add_library(lua-static STATIC IMPORTED GLOBAL)
+set_property(TARGET lua-static PROPERTY IMPORTED_LOCATION ${INSTALL_DIR}/lib/liblua.a)
+set_property(TARGET lua-static PROPERTY INTERFACE_INCLUDE_DIRECTORIES ${INSTALL_DIR}/include)
+
+
+### MESA Framework
+set(MESA_FRAMEWORK_LIB_DIR /opt/MESA/lib)
+set(MESA_FRAMEWORK_INCLUDE_DIR /opt/MESA/include)
+
+add_library(MESA_handle_logger SHARED IMPORTED GLOBAL)
+set_property(TARGET MESA_handle_logger PROPERTY IMPORTED_LOCATION ${MESA_FRAMEWORK_LIB_DIR}/libMESA_handle_logger.so)
+set_property(TARGET MESA_handle_logger PROPERTY INTERFACE_INCLUDE_DIRECTORIES ${MESA_FRAMEWORK_INCLUDE_DIR})
+
+add_library(MESA_prof_load SHARED IMPORTED GLOBAL)
+set_property(TARGET MESA_prof_load PROPERTY IMPORTED_LOCATION ${MESA_FRAMEWORK_LIB_DIR}/libMESA_prof_load.so)
+set_property(TARGET MESA_prof_load PROPERTY INTERFACE_INCLUDE_DIRECTORIES ${MESA_FRAMEWORK_INCLUDE_DIR})
+
+add_library(wiredcfg SHARED IMPORTED GLOBAL)
+set_property(TARGET wiredcfg PROPERTY IMPORTED_LOCATION ${MESA_FRAMEWORK_LIB_DIR}/libwiredcfg.so)
+set_property(TARGET wiredcfg PROPERTY INTERFACE_INCLUDE_DIRECTORIES ${MESA_FRAMEWORK_INCLUDE_DIR})
+
+add_library(MESA_htable SHARED IMPORTED GLOBAL)
+set_property(TARGET MESA_htable PROPERTY IMPORTED_LOCATION ${MESA_FRAMEWORK_LIB_DIR}/libMESA_htable.so)
+set_property(TARGET MESA_htable PROPERTY INTERFACE_INCLUDE_DIRECTORIES ${MESA_FRAMEWORK_INCLUDE_DIR})
+
+add_library(maatframe SHARED IMPORTED GLOBAL)
+set_property(TARGET maatframe PROPERTY IMPORTED_LOCATION ${MESA_FRAMEWORK_LIB_DIR}/libmaatframe.so)
+set_property(TARGET maatframe PROPERTY INTERFACE_INCLUDE_DIRECTORIES ${MESA_FRAMEWORK_INCLUDE_DIR})
+
+add_library(MESA_field_stat SHARED IMPORTED GLOBAL)
+set_property(TARGET MESA_field_stat PROPERTY IMPORTED_LOCATION ${MESA_FRAMEWORK_LIB_DIR}/libMESA_field_stat2.so)
+set_property(TARGET MESA_field_stat PROPERTY INTERFACE_INCLUDE_DIRECTORIES ${MESA_FRAMEWORK_INCLUDE_DIR}) \ No newline at end of file
diff --git a/vendor/lua-5.3.5.tar.gz b/vendor/lua-5.3.5.tar.gz
new file mode 100644
index 0000000..90c0027
--- /dev/null
+++ b/vendor/lua-5.3.5.tar.gz
Binary files differ