修改action判断逻辑

This commit is contained in:
崔一鸣
2019-06-04 13:25:44 +08:00
parent 1fa7a0673f
commit f89c0cf902
3 changed files with 89 additions and 42 deletions

View File

@@ -6,9 +6,9 @@
struct kni_maat_handle; struct kni_maat_handle;
enum kni_action{ enum kni_action{
KNI_ACTION_UNKNOWN = 0, KNI_ACTION_NONE = 0x00,
KNI_ACTION_INTERCEPT, KNI_ACTION_INTERCEPT = 0x02,
KNI_ACTION_BYPASS, KNI_ACTION_BYPASS = 0x80,
}; };
struct kni_maat_handle* kni_maat_init(const char* profile, void *logger); struct kni_maat_handle* kni_maat_init(const char* profile, void *logger);

View File

@@ -171,6 +171,7 @@ static struct pme_info* pme_info_new(const struct streaminfo *stream, int thread
pmeinfo->stream = (struct streaminfo*)stream; pmeinfo->stream = (struct streaminfo*)stream;
pmeinfo->start_time = time(NULL); pmeinfo->start_time = time(NULL);
pmeinfo->logger = logger; pmeinfo->logger = logger;
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_TOT_STM], 0, FS_OP_ADD, 1);
return pmeinfo; return pmeinfo;
} }
@@ -467,7 +468,6 @@ static char* add_cmsg_to_packet(struct pme_info *pmeinfo, struct pkt_info *pktin
static int send_to_tfe(struct kni_marsio_handle *handle, char *raw_data, int raw_len, int thread_seq, int tfe_id){ static int send_to_tfe(struct kni_marsio_handle *handle, char *raw_data, int raw_len, int thread_seq, int tfe_id){
void *logger = g_kni_handle->local_logger; void *logger = g_kni_handle->local_logger;
KNI_LOG_DEBUG(logger, "send packet to tfe%d", tfe_id);
marsio_buff_t *tx_buffs[BURST_MAX]; marsio_buff_t *tx_buffs[BURST_MAX];
unsigned int ret = 1; unsigned int ret = 1;
//TODO: marsio配置文件: 2500 //TODO: marsio配置文件: 2500
@@ -498,6 +498,7 @@ static char pending_opstate(const struct streaminfo *stream, struct pme_info *pm
//pending_opstate 不是syn, bypass这个流 //pending_opstate 不是syn, bypass这个流
KNI_LOG_ERROR(logger, "pending opstate: not syn"); KNI_LOG_ERROR(logger, "pending opstate: not syn");
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_NO_SYN_EXP], 0, FS_OP_ADD, 1); FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_NO_SYN_EXP], 0, FS_OP_ADD, 1);
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_STM], 0, FS_OP_ADD, 1);
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_PKT], 0, FS_OP_ADD, 1); FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_PKT], 0, FS_OP_ADD, 1);
//异常情况不需要等tfe release, 直接释放 //异常情况不需要等tfe release, 直接释放
pmeinfo->tfe_release = 1; pmeinfo->tfe_release = 1;
@@ -525,14 +526,28 @@ static char data_opstate(const struct streaminfo *stream, struct pme_info *pmein
void *logger = g_kni_handle->local_logger; void *logger = g_kni_handle->local_logger;
char *buf = (char*)pktinfo->iphdr; char *buf = (char*)pktinfo->iphdr;
int len = pktinfo->ip_totlen; int len = pktinfo->ip_totlen;
if(pmeinfo->action == KNI_ACTION_INTERCEPT){ char stream_addr[KNI_SYMBOL_MAX] = "";
send_to_tfe(g_kni_handle->marsio_handle, buf, len, thread_seq, pmeinfo->tfe_id); int ret;
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_INTCP_PKT], 0, FS_OP_ADD, 1); kni_stream_addr_trans((struct ipaddr*)(&stream->addr), stream_addr, sizeof(stream_addr));
return APP_STATE_DROPPKT | APP_STATE_GIVEME; //保证pmeinfo->action只有KNI_ACTION_NONE KNI_ACTION_INTERCEPT KNI_ACTION_BYPASS三种情况
} switch (pmeinfo->action){
if(pmeinfo->action == KNI_ACTION_BYPASS){ case KNI_ACTION_NONE:
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_PKT], 0, FS_OP_ADD, 1); break;
return APP_STATE_FAWPKT | APP_STATE_GIVEME; case KNI_ACTION_INTERCEPT:
ret = send_to_tfe(g_kni_handle->marsio_handle, buf, len, thread_seq, pmeinfo->tfe_id);
if(ret < 0){
KNI_LOG_ERROR(logger, "Failed at send continue packet to tfe%d, stream_addr is %s", pmeinfo->tfe_id, stream_addr);
}
else{
KNI_LOG_DEBUG(logger, "Succeed at send continue packet to tfe%d, stream_addr is %s", pmeinfo->tfe_id, stream_addr);
}
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_INTCP_PKT], 0, FS_OP_ADD, 1);
return APP_STATE_DROPPKT | APP_STATE_GIVEME;
case KNI_ACTION_BYPASS:
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_PKT], 0, FS_OP_ADD, 1);
return APP_STATE_FAWPKT | APP_STATE_GIVEME;
default:
break;
} }
//TODO: client hello如果跨包怎么办client hello后面一个包先到这个包该丢掉还是bypass //TODO: client hello如果跨包怎么办client hello后面一个包先到这个包该丢掉还是bypass
//此时 action = KNI_ACTION_UNKNOWN, 说明还没收到第一个数据包 //此时 action = KNI_ACTION_UNKNOWN, 说明还没收到第一个数据包
@@ -546,21 +561,21 @@ static char data_opstate(const struct streaminfo *stream, struct pme_info *pmein
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_PKT], 0, FS_OP_ADD, 1); FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_PKT], 0, FS_OP_ADD, 1);
return APP_STATE_FAWPKT | APP_STATE_GIVEME; return APP_STATE_FAWPKT | APP_STATE_GIVEME;
} }
//第一个数据包: 如果从第一个数据包判断不出协议,直接返回,后续包也不要了 //单向流, bypass and dropme
//单向流, 直接bypass
if(stream->dir != DIR_DOUBLE){ if(stream->dir != DIR_DOUBLE){
KNI_LOG_INFO(logger, "stream dir is %d, bypass", stream->dir); KNI_LOG_INFO(logger, "dir is %d, bypass, stream addr is %s", stream->dir, stream_addr);
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_STM], 0, FS_OP_ADD, 1);
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_PKT], 0, FS_OP_ADD, 1); FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_PKT], 0, FS_OP_ADD, 1);
pmeinfo->tfe_release = 1; pmeinfo->tfe_release = 1;
return APP_STATE_FAWPKT | APP_STATE_DROPME; return APP_STATE_FAWPKT | APP_STATE_DROPME;
} }
//三次握手成功才算一个流
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_TOT_STM], 0, FS_OP_ADD, 1);
struct protocol_identify_result *result = ALLOC(struct protocol_identify_result, 1); struct protocol_identify_result *result = ALLOC(struct protocol_identify_result, 1);
protocol_identify(stream, pktinfo->data, pktinfo->data_len, result); protocol_identify(stream, pktinfo->data, pktinfo->data_len, result);
pmeinfo->protocol = result->protocol; pmeinfo->protocol = result->protocol;
//第一个数据包: 如果从第一个数据包判断不出协议, bypass and dropme
if(pmeinfo->protocol == KNI_PROTOCOL_UNKNOWN){ if(pmeinfo->protocol == KNI_PROTOCOL_UNKNOWN){
KNI_LOG_INFO(logger, "Failed at protocol_identify, protocol is %d\n", pmeinfo->protocol); KNI_LOG_INFO(logger, "Failed at protocol_identify, bypass and dropme, stream addr is %s\n",
pmeinfo->protocol, stream_addr);
FREE(&result); FREE(&result);
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_PKT], 0, FS_OP_ADD, 1); FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_PKT], 0, FS_OP_ADD, 1);
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_STM], 0, FS_OP_ADD, 1); FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_STM], 0, FS_OP_ADD, 1);
@@ -579,19 +594,11 @@ static char data_opstate(const struct streaminfo *stream, struct pme_info *pmein
} }
pmeinfo->action = get_action((struct ipaddr*)(&stream->addr), result->domain, result->domain_len, thread_seq, &(pmeinfo->policy_id)); pmeinfo->action = get_action((struct ipaddr*)(&stream->addr), result->domain, result->domain_len, thread_seq, &(pmeinfo->policy_id));
//输出maat拦截日志 //输出maat拦截日志
char stream_addr[KNI_SYMBOL_MAX] = "";
kni_stream_addr_trans((struct ipaddr*)(&stream->addr), stream_addr, sizeof(stream_addr));
char domain_str[KNI_DOMAIN_MAX] = ""; char domain_str[KNI_DOMAIN_MAX] = "";
memcpy(domain_str, result->domain, result->domain_len); memcpy(domain_str, result->domain, result->domain_len);
KNI_LOG_DEBUG(logger, "get_action: %s, %s, policy_id = %d, action = %s", KNI_LOG_DEBUG(logger, "get_action: %s, %s, policy_id = %d, action = %s",
stream_addr, domain_str, pmeinfo->policy_id, pmeinfo->action == KNI_ACTION_BYPASS ? "bypass" : "intercept"); stream_addr, domain_str, pmeinfo->policy_id, pmeinfo->action == KNI_ACTION_BYPASS ? "bypass" : "intercept");
FREE(&result); FREE(&result);
//如果是bypass
if(pmeinfo->action == KNI_ACTION_BYPASS){
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_PKT], 0, FS_OP_ADD, 1);
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_STM], 0, FS_OP_ADD, 1);
return APP_STATE_FAWPKT | APP_STATE_GIVEME;
}
//TODO: 这块比较奇怪, 收到client hello, 但是没有syn/ack包, 直接bypass了 //TODO: 这块比较奇怪, 收到client hello, 但是没有syn/ack包, 直接bypass了
if(pmeinfo->client_tcpopt == NULL || pmeinfo->server_tcpopt == NULL){ if(pmeinfo->client_tcpopt == NULL || pmeinfo->server_tcpopt == NULL){
KNI_LOG_ERROR(logger, "Failed at intercept, %s, %s", pmeinfo->client_tcpopt == NULL ? "no syn" : "", KNI_LOG_ERROR(logger, "Failed at intercept, %s, %s", pmeinfo->client_tcpopt == NULL ? "no syn" : "",
@@ -602,27 +609,60 @@ static char data_opstate(const struct streaminfo *stream, struct pme_info *pmein
pmeinfo->tfe_release = 1; pmeinfo->tfe_release = 1;
return APP_STATE_FAWPKT | APP_STATE_DROPME; return APP_STATE_FAWPKT | APP_STATE_DROPME;
} }
//action = KNI_ACTION_INTERCEPT, 带上控制信息发送给qq, 要修改ip, tcp的校验和 switch(pmeinfo->action){
buf = add_cmsg_to_packet(pmeinfo, pktinfo, &len); case KNI_ACTION_BYPASS:
send_to_tfe(g_kni_handle->marsio_handle, buf, len, thread_seq, pmeinfo->tfe_id); FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_PKT], 0, FS_OP_ADD, 1);
FREE(&buf); FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_STM], 0, FS_OP_ADD, 1);
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_INTCP_PKT], 0, FS_OP_ADD, 1); return APP_STATE_FAWPKT | APP_STATE_GIVEME;
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_INTCP_STM], 0, FS_OP_ADD, 1); case KNI_ACTION_INTERCEPT:
return APP_STATE_DROPPKT | APP_STATE_GIVEME; //action = KNI_ACTION_INTERCEPT, 带上控制信息发送给qq, 要修改ip, tcp的校验和
buf = add_cmsg_to_packet(pmeinfo, pktinfo, &len);
ret = send_to_tfe(g_kni_handle->marsio_handle, buf, len, thread_seq, pmeinfo->tfe_id);
if(ret < 0){
KNI_LOG_ERROR(logger, "Failed at send first packet to tfe%d, stream_trace_id is %s", pmeinfo->tfe_id, pmeinfo->stream_trace_id);
}
else{
KNI_LOG_DEBUG(logger, "Succeed at send first packet to tfe%d, stream_trace_id is %s", pmeinfo->tfe_id, pmeinfo->stream_trace_id);
}
FREE(&buf);
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_INTCP_PKT], 0, FS_OP_ADD, 1);
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_INTCP_STM], 0, FS_OP_ADD, 1);
return APP_STATE_DROPPKT | APP_STATE_GIVEME;
default:
//action非法bypass and dropme
KNI_LOG_ERROR(logger, "Action %d is Invalid, policy_id is %d, bypass(dropme)", pmeinfo->action, pmeinfo->policy_id);
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_PKT], 0, FS_OP_ADD, 1);
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_STM], 0, FS_OP_ADD, 1);
pmeinfo->tfe_release = 1;
return APP_STATE_FAWPKT | APP_STATE_DROPME;
}
} }
static char close_opstate(const struct streaminfo *stream, struct pme_info *pmeinfo, struct pkt_info *pktinfo, int thread_seq){ static char close_opstate(const struct streaminfo *stream, struct pme_info *pmeinfo, struct pkt_info *pktinfo, int thread_seq){
//close 数据也要发送给tfe //close 数据也要发送给tfe
//void *logger = g_kni_handle->logger; void *logger = g_kni_handle->local_logger;
char *buf = (char*)pktinfo->iphdr; char *buf = (char*)pktinfo->iphdr;
char stream_addr[KNI_SYMBOL_MAX] = "";
kni_stream_addr_trans((struct ipaddr*)(&stream->addr), stream_addr, sizeof(stream_addr));
int len = pktinfo->ip_totlen; int len = pktinfo->ip_totlen;
if(pmeinfo->action == KNI_ACTION_INTERCEPT){ int ret;
send_to_tfe(g_kni_handle->marsio_handle, buf, len, thread_seq, pmeinfo->tfe_id); switch(pmeinfo->action){
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_INTCP_PKT], 0, FS_OP_ADD, 1); case KNI_ACTION_INTERCEPT:
return APP_STATE_DROPPKT | APP_STATE_DROPME; ret =send_to_tfe(g_kni_handle->marsio_handle, buf, len, thread_seq, pmeinfo->tfe_id);
if(ret < 0){
KNI_LOG_ERROR(logger, "Failed at send last packet to tfe%d, stream addr is %s",
pmeinfo->tfe_id, stream_addr);
}
else{
KNI_LOG_DEBUG(logger, "Succeed at send last packet to tfe%d, stream addr is %s",
pmeinfo->tfe_id, stream_addr);
}
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_INTCP_PKT], 0, FS_OP_ADD, 1);
return APP_STATE_DROPPKT | APP_STATE_DROPME;
default:
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_PKT], 0, FS_OP_ADD, 1);
return APP_STATE_FAWPKT | APP_STATE_DROPME;
} }
FS_operate(g_kni_fs_handle->handle, g_kni_fs_handle->fields[KNI_FIELD_BYP_PKT], 0, FS_OP_ADD, 1);
return APP_STATE_FAWPKT | APP_STATE_DROPME;
} }
//从syn包开始回调 //从syn包开始回调

View File

@@ -3,7 +3,13 @@
extern int g_iThreadNum; extern int g_iThreadNum;
int g_maat_default_action = -1;
/* 关于没有命中配置情况下的默认配置
1. g_maat_default_action = KNI_ACTION_INTERCEPT policy_id = 0
2. 如果maat的编译配置表中有policy_id = 0的配置则将 g_maat_default_action设为对应的action, policy_id = 0
*/
int g_maat_default_action = KNI_ACTION_INTERCEPT;
struct kni_maat_handle{ struct kni_maat_handle{
Maat_feather_t feather; Maat_feather_t feather;
@@ -191,11 +197,12 @@ int kni_maat_scan_ip(struct kni_maat_handle *handle, struct ipaddr *addr, int th
} }
int action = maat_process_scan_result(handle, ret, result, policy_id); int action = maat_process_scan_result(handle, ret, result, policy_id);
//for debug /*for debug
char stream_addr[KNI_SYMBOL_MAX] = ""; char stream_addr[KNI_SYMBOL_MAX] = "";
kni_stream_addr_trans(addr, stream_addr, sizeof(stream_addr)); kni_stream_addr_trans(addr, stream_addr, sizeof(stream_addr));
KNI_LOG_DEBUG(logger, "maat_scan_ip, %s, policy_id = %d, action = %s\n", KNI_LOG_DEBUG(logger, "maat_scan_ip, %s, policy_id = %d, action = %s\n",
stream_addr, *policy_id, action == KNI_ACTION_BYPASS ? "bypss" : "intercept"); stream_addr, *policy_id, action == KNI_ACTION_BYPASS ? "bypss" : "intercept");
*/
return action; return action;
} }