2015-10-10 18:30:12 +08:00
# include <stdlib.h>
# include <stdio.h>
# include <ctype.h> //tolower
# include <iconv.h>
# include <sys/types.h> //inet_pton
# include <sys/socket.h> //inet_pton
# include <arpa/inet.h> //inet_pton
# include <assert.h>
# include <pthread.h>
# include <unistd.h>
2016-11-21 17:56:59 +08:00
# include <time.h>
2016-12-29 12:15:42 +08:00
# include <sys/prctl.h>
2017-09-10 19:02:28 +08:00
# include <sys/syscall.h>
2015-10-10 18:30:12 +08:00
# include <MESA/MESA_htable.h>
# include <MESA/MESA_list_queue.h>
# include <MESA/MESA_handle_logger.h>
2016-03-28 16:21:36 +08:00
# include <MESA/field_stat2.h>
2015-10-10 18:30:12 +08:00
# include "Maat_rule.h"
# include "Maat_rule_internal.h"
2018-09-24 18:49:18 +08:00
# include "Maat_utils.h"
2015-10-10 18:30:12 +08:00
# include "json2iris.h"
2018-09-21 21:32:09 +08:00
# include "cJSON.h"
2015-10-10 18:30:12 +08:00
# include "dynamic_array.h"
2018-11-27 12:55:52 +08:00
# include "alignment_int64.h"
2015-10-10 18:30:12 +08:00
# include "config_monitor.h"
2015-11-12 18:28:58 +08:00
2015-10-10 18:30:12 +08:00
# include "map_str2int.h"
# include "rulescan.h"
2019-01-05 17:11:20 +08:00
# include "bool_matcher.h"
2017-08-07 17:08:52 +08:00
# include "stream_fuzzy_hash.h"
# include "gram_index_engine.h"
2015-10-10 18:30:12 +08:00
2019-02-22 11:20:34 +06:00
int MAAT_FRAME_VERSION_2_6_20190222 = 1 ;
2015-11-12 18:28:58 +08:00
2016-04-03 12:29:41 +08:00
const char * CHARSET_STRING [ ] = { " NONE " , " gbk " , " big5 " , " unicode " , " utf8 " , " bin " ,
" unicode_ascii_esc " , " unicode_ascii_aligned " , " unicode_ncr_dec " , " unicode_ncr_hex " , " url_encode_gb2312 " , " url_encode_utf8 " , " " } ;
2017-09-10 19:02:28 +08:00
2016-12-26 17:20:59 +08:00
int is_valid_expr_type ( enum MAAT_EXPR_TYPE expr_type )
{
switch ( expr_type )
{
case EXPR_TYPE_STRING :
case EXPR_TYPE_AND :
case EXPR_TYPE_REGEX :
case EXPR_TYPE_OFFSET :
return 1 ;
default :
return 0 ;
}
}
int is_valid_match_method ( enum MAAT_MATCH_METHOD match_method )
{
switch ( match_method )
{
case MATCH_METHOD_SUB :
case MATCH_METHOD_RIGHT :
case MATCH_METHOD_LEFT :
2017-08-07 17:08:52 +08:00
case MATCH_METHOD_COMPLETE :
2016-12-26 17:20:59 +08:00
return 1 ;
default :
return 0 ;
}
}
2018-12-04 23:26:59 +08:00
2019-01-05 17:11:20 +08:00
iconv_t maat_iconv_open ( struct Maat_scanner_t * scanner , enum MAAT_CHARSET to , enum MAAT_CHARSET from )
2015-10-10 18:30:12 +08:00
{
const char * from_s = CHARSET_STRING [ from ] ;
const char * to_s = CHARSET_STRING [ to ] ;
iconv_t cd ;
if ( from = = CHARSET_GBK & & to = = CHARSET_BIG5 )
{
from_s = " gb2312 " ;
}
if ( from > = MAX_CHARSET_NUM | | to > = MAX_CHARSET_NUM )
{
return ( iconv_t ) - 1 ;
}
if ( scanner - > iconv_handle [ to ] [ from ] = = NULL )
{
scanner - > iconv_handle [ to ] [ from ] = iconv_open ( to_s , from_s ) ;
}
cd = scanner - > iconv_handle [ to ] [ from ] ;
return cd ;
}
2016-04-03 12:29:41 +08:00
2019-01-05 17:11:20 +08:00
int iconv_convert ( struct Maat_scanner_t * scanner , enum MAAT_CHARSET from , enum MAAT_CHARSET to , char * src , int srclen , char * dst , int * dstlen )
2015-10-10 18:30:12 +08:00
{
size_t ret ;
int copy_len = 0 ;
char * copy_buf = NULL ;
if ( srclen = = 0 | | src = = NULL )
{
return - 1 ;
}
iconv_t cd = maat_iconv_open ( scanner , to , from ) ;
if ( cd ! = ( iconv_t ) - 1 )
{
char * pInBuff = src ;
size_t iInBuffLen = srclen ;
size_t iOutBuffLen = 10 * iInBuffLen ;
char * pOutBuff = ( char * ) malloc ( iOutBuffLen ) ;
char * pLeftBuff = pOutBuff ;
size_t iLeftLen = iOutBuffLen ;
ret = iconv ( cd , & pInBuff , & iInBuffLen , & pLeftBuff , & iLeftLen ) ;
if ( ret ! = ( size_t ) ( - 1 ) )
{
2016-04-03 12:29:41 +08:00
if ( to = = CHARSET_UNICODE & &
( * ( unsigned short * ) pOutBuff = = 0xFFFE | | * ( unsigned short * ) pOutBuff = = 0XFEFF ) ) //jump unicode 2 bytes BOM, 0xFF 0xFE
2015-10-10 18:30:12 +08:00
{
copy_len = iOutBuffLen - iLeftLen - 2 ;
copy_buf = pOutBuff + 2 ;
}
else
{
copy_len = iOutBuffLen - iLeftLen ;
copy_buf = pOutBuff ;
}
assert ( copy_len < = * dstlen ) ;
* dstlen = copy_len ;
memcpy ( dst , copy_buf , * dstlen ) ;
free ( pOutBuff ) ;
return 1 ;
}
else
{
free ( pOutBuff ) ;
return - 1 ;
}
}
else
{
return - 1 ;
}
}
2016-04-03 12:29:41 +08:00
int URLEncode ( const char * str , const int strSize , char * result , const int resultSize )
{
int i ;
int j = 0 ; //for result index
char ch ;
if ( ( str = = NULL ) | | ( result = = NULL ) | | ( strSize < = 0 ) | | ( resultSize < = 0 ) )
{
return - 1 ;
}
2015-10-10 18:30:12 +08:00
2016-04-03 12:29:41 +08:00
for ( i = 0 ; ( i < strSize ) & & ( j < resultSize ) ; + + i )
{
ch = str [ i ] ;
2016-11-23 16:52:04 +08:00
if ( ( ( ch > = ' A ' ) & & ( ch < = ' Z ' ) ) | |
( ( ch > = ' a ' ) & & ( ch < = ' z ' ) ) | |
( ( ch > = ' 0 ' ) & & ( ch < = ' 9 ' ) ) )
2016-04-03 12:29:41 +08:00
{
result [ j + + ] = ch ;
}
else if ( ch = = ' ' )
{
result [ j + + ] = ' + ' ;
}
else if ( ch = = ' . ' | | ch = = ' - ' | | ch = = ' _ ' | | ch = = ' * ' )
{
result [ j + + ] = ch ;
}
else
{
if ( j + 3 < resultSize )
{
sprintf ( result + j , " %%%02X " , ( unsigned char ) ch ) ;
j + = 3 ;
}
else
{
return - 1 ;
}
}
}
result [ j ] = ' \0 ' ;
return j ;
}
int uni2ascii ( const char * fmt , const char * src , const int srclen , char * dst , const int dstsize )
{
int i = 0 , j = 0 ;
assert ( srclen % 2 = = 0 ) ; //unicode must be 2 bytes aligned.
while ( i < srclen & & j < dstsize )
{
if ( * ( unsigned short * ) ( src + i ) < 0x7f )
{
dst [ j ] = * ( unsigned short * ) ( src + i ) ;
j + + ;
}
else
{
j + = snprintf ( dst + j , dstsize - j , fmt , * ( unsigned short * ) ( src + i ) ) ;
}
i + = 2 ;
}
return j ;
}
2019-01-05 17:11:20 +08:00
int universal_charset_convert ( struct Maat_scanner_t * scanner , enum MAAT_CHARSET from , enum MAAT_CHARSET to , char * src , int srclen , char * dst , int * dstlen )
2016-04-03 12:29:41 +08:00
{
int ret = 0 ;
char * tmp_buff = NULL ;
int tmp_buff_size = 0 ;
MAAT_CHARSET tmp_dst_code = CHARSET_NONE ;
const char * fmt = NULL ;
switch ( to )
{
case CHARSET_GBK :
case CHARSET_BIG5 :
case CHARSET_UNICODE :
case CHARSET_UTF8 :
ret = iconv_convert ( scanner , from , to , src , srclen , dst , dstlen ) ;
return ret ;
break ;
case CHARSET_UNICODE_ASCII_ESC :
tmp_dst_code = CHARSET_UNICODE ;
fmt = " \\ u%x; " ;
break ;
case CHARSET_UNICODE_ASCII_ALIGNED :
tmp_dst_code = CHARSET_UNICODE ;
fmt = " \\ u%04x " ;
break ;
case CHARSET_UNICODE_NCR_DEC :
tmp_dst_code = CHARSET_UNICODE ;
fmt = " &#%u; " ;
break ;
case CHARSET_UNICODE_NCR_HEX :
tmp_dst_code = CHARSET_UNICODE ;
fmt = " &#x%x; " ;
break ;
case CHARSET_URL_ENCODE_GB2312 :
tmp_dst_code = CHARSET_GBK ;
fmt = NULL ;
break ;
case CHARSET_URL_ENCODE_UTF8 :
tmp_dst_code = CHARSET_UTF8 ;
fmt = NULL ;
break ;
default :
return - 1 ;
break ;
}
tmp_buff_size = * dstlen ;
tmp_buff = ( char * ) malloc ( tmp_buff_size ) ;
ret = iconv_convert ( scanner , from , tmp_dst_code , src , srclen , tmp_buff , & tmp_buff_size ) ;
if ( ret < 0 )
{
goto error_out ;
}
if ( fmt ! = NULL )
{
ret = uni2ascii ( fmt , tmp_buff , tmp_buff_size , dst , * dstlen ) ;
}
else
{
ret = URLEncode ( tmp_buff , tmp_buff_size , dst , * dstlen ) ;
}
* dstlen = ret ;
error_out :
free ( tmp_buff ) ;
tmp_buff = NULL ;
return ret ;
}
2017-08-07 17:08:52 +08:00
char * Maat_str_escape ( char * dst , int size , const char * src )
{
int i = 0 , j = 0 ;
int len = strlen ( src ) ;
for ( i = 0 , j = 0 ; i < len & & j < size ; i + + )
{
switch ( src [ i ] )
{
case ' & ' :
dst [ j ] = ' \\ ' ;
dst [ j + 1 ] = ' & ' ;
j + = 2 ;
break ;
case ' ' :
dst [ j ] = ' \\ ' ;
dst [ j + 1 ] = ' b ' ; //space,0x20;
j + = 2 ;
break ;
case ' \\ ' :
dst [ j ] = ' \\ ' ;
dst [ j + 1 ] = ' \\ ' ;
j + = 2 ;
break ;
default :
dst [ j ] = src [ i ] ;
j + + ; //undo the followed i++
break ;
}
}
dst [ j ] = ' \0 ' ;
return dst ;
}
2018-09-24 18:49:18 +08:00
2015-10-10 18:30:12 +08:00
int cnt_maskbits ( struct in6_addr mask )
{
unsigned int i = 0 ;
int bits_cnt = 0 ;
unsigned char * p = ( unsigned char * ) & mask ;
for ( i = 0 ; i < sizeof ( mask ) ; i + + )
{
for ( ; p [ i ] > 0 ; p [ i ] = p [ i ] / 2 )
{
bits_cnt + + ;
}
}
return bits_cnt ;
}
2018-09-21 21:32:09 +08:00
//@param value is a JSON, like {"tags":[{"tag":"location","value":"北京/朝阳/华严北里/甲22号},{"tag":"isp","value":"电信"}]}
int parse_accept_tag ( const char * value , struct rule_tag * * result , void * logger )
{
cJSON * json = NULL , * array = NULL , * tag = NULL , * tmp = NULL ;
struct rule_tag * p = NULL ;
int n_tags = 0 ;
json = cJSON_Parse ( value ) ;
if ( ! json )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" MAAT_OPT_ACCEPT_TAGS Error before: %-200.200s " , cJSON_GetErrorPtr ( ) ) ;
return 0 ;
}
array = cJSON_GetObjectItem ( json , " tags " ) ;
n_tags = cJSON_GetArraySize ( array ) ;
2018-11-27 12:55:52 +08:00
p = ALLOC ( struct rule_tag , n_tags ) ;
2018-09-21 21:32:09 +08:00
for ( int i = 0 ; i < n_tags ; i + + )
{
tag = cJSON_GetArrayItem ( array , i ) ;
tmp = cJSON_GetObjectItem ( tag , " tag " ) ;
p [ i ] . tag_name = _maat_strdup ( tmp - > valuestring ) ;
tmp = cJSON_GetObjectItem ( tag , " value " ) ;
p [ i ] . tag_val = _maat_strdup ( tmp - > valuestring ) ;
}
cJSON_Delete ( json ) ;
* result = p ;
return n_tags ;
}
static int compare_each_tag ( cJSON * tag_obj , const struct rule_tag * accept_tags , int n_accept )
{
const char * tag_name ;
const char * tag_val ;
int n_val ;
cJSON * tab_name_obj = NULL , * tag_vals_array = NULL , * tag_val_obj = NULL ;
int i = 0 , j = 0 , name_matched = 0 ;
tab_name_obj = cJSON_GetObjectItem ( tag_obj , " tag " ) ;
if ( ! tab_name_obj | | tab_name_obj - > type ! = cJSON_String )
{
goto error_out ;
}
tag_name = tab_name_obj - > valuestring ;
tag_vals_array = cJSON_GetObjectItem ( tag_obj , " value " ) ;
if ( ! tag_vals_array | | tag_vals_array - > type ! = cJSON_Array )
{
goto error_out ;
}
n_val = cJSON_GetArraySize ( tag_vals_array ) ;
for ( i = 0 ; i < n_accept ; i + + )
{
if ( 0 ! = strcmp ( accept_tags [ i ] . tag_name , tag_name ) )
{
continue ;
}
name_matched + + ;
2016-02-18 14:53:06 +08:00
2018-09-21 21:32:09 +08:00
for ( j = 0 ; j < n_val ; j + + )
{
tag_val_obj = cJSON_GetArrayItem ( tag_vals_array , j ) ;
if ( ! tag_val_obj | | tag_val_obj - > type ! = cJSON_String )
{
goto error_out ;
}
tag_val = tag_val_obj - > valuestring ;
// compare a/b/c with a/b/c/d is a miss.
if ( strlen ( accept_tags [ i ] . tag_val ) < strlen ( tag_val ) )
{
continue ;
}
// compare a1a2/b1/c1 with a1a2/b/ is a miss.
//make sure the overlap is ended with a '/'
if ( 0 = = strncmp ( accept_tags [ i ] . tag_val , tag_val , strlen ( tag_val ) ) & &
( strlen ( accept_tags [ i ] . tag_val ) = = strlen ( tag_val ) | | accept_tags [ i ] . tag_val [ strlen ( tag_val ) ] = = ' / ' ) )
{
return 1 ;
}
}
}
//no matched name is considered as a
if ( name_matched > 0 )
{
return 0 ;
}
else
{
return 1 ;
}
error_out :
return - 1 ;
}
//@param tag_set likes [{"tag":"location","value":["北京/朝阳/华严北里","上海/浦东/陆家嘴"]},{"tag":"isp","value":["电信","移动"]}]
static int compare_each_tag_set ( cJSON * tag_set , const struct rule_tag * accept_tags , int n_accept )
{
cJSON * tag_obj = NULL ;
int n_tag = 0 , ret = 0 , matched = 0 ;
n_tag = cJSON_GetArraySize ( tag_set ) ;
for ( int i = 0 ; i < n_tag ; i + + )
{
tag_obj = cJSON_GetArrayItem ( tag_set , i ) ;
if ( ! tag_obj | | tag_obj - > type ! = cJSON_Object )
{
goto error_out ;
}
ret = compare_each_tag ( tag_obj , accept_tags , n_accept ) ;
if ( ret < 0 )
{
return - 1 ;
}
if ( ret = = 1 )
{
matched + + ;
}
}
if ( matched = = n_tag )
{
return 1 ;
}
else
{
return 0 ;
}
error_out :
return - 1 ;
}
//@param value {"tag_sets":[[{"tag":"location","value":["北京/朝阳/华严北里","上海/浦东/陆家嘴"]},{"tag":"isp","value":["电信","移动"]}],[{"tag":"location","value":["北京"]},{"tag":"isp","value":["联通"]}]]}
//@return 1 on match, 0 on not match, -1 on error.
static int compare_accept_tag ( const char * value , const struct rule_tag * accept_tags , int n_tags )
{
cJSON * json = NULL ;
cJSON * tag_set_array = NULL , * tag_set = NULL ;
int ret = - 1 , n_set = 0 ;
json = cJSON_Parse ( value ) ;
if ( ! json )
{
goto error_out ;
}
tag_set_array = cJSON_GetObjectItem ( json , " tag_sets " ) ;
if ( ! tag_set_array | | tag_set_array - > type ! = cJSON_Array )
{
goto error_out ;
}
n_set = cJSON_GetArraySize ( tag_set_array ) ;
for ( int i = 0 ; i < n_set ; i + + )
{
tag_set = cJSON_GetArrayItem ( tag_set_array , i ) ;
if ( ! tag_set | | tag_set - > type ! = cJSON_Array )
{
goto error_out ;
}
ret = compare_each_tag_set ( tag_set , accept_tags , n_tags ) ;
if ( ret ! = 0 ) //match or error occurs.
{
break ;
}
}
error_out :
cJSON_Delete ( json ) ;
return ret ;
}
2015-10-10 18:30:12 +08:00
int lqueue_destroy_cb ( void * data , long data_len , void * arg )
{
assert ( 0 ) ;
2018-10-18 19:39:19 +08:00
return 0 ;
2015-10-10 18:30:12 +08:00
}
void * HASH_fetch_by_id ( MESA_htable_handle hash , int id )
{
return MESA_htable_search ( hash , ( unsigned char * ) & ( id ) , sizeof ( id ) ) ;
}
int HASH_add_by_id ( MESA_htable_handle hash , int id , void * data )
{
int ret = 0 ;
ret = MESA_htable_add ( hash
, ( unsigned char * ) & ( id )
, sizeof ( id )
, data ) ;
return ret ;
}
int HASH_delete_by_id ( MESA_htable_handle hash , int id )
{
//destroy function had been initialized when hash create.
int ret = - 1 ;
ret = MESA_htable_del ( hash , ( unsigned char * ) & id , sizeof ( id ) , NULL ) ;
return ret ;
}
2018-11-07 17:12:06 +08:00
MAAT_RULE_EX_DATA rule_ex_data_new ( const struct _head_Maat_rule_t * rule_head , const char * srv_def , const struct compile_ex_data_idx * ex_desc )
{
MAAT_RULE_EX_DATA ad = NULL ;
struct Maat_rule_t rule ;
fill_maat_rule ( & rule , rule_head , srv_def , strlen ( srv_def ) + 1 ) ;
ex_desc - > new_func ( ex_desc - > idx , & rule , srv_def , & ad , ex_desc - > argl , ex_desc - > argp ) ;
return ad ;
}
void rule_ex_data_free ( const struct _head_Maat_rule_t * rule_head , const char * srv_def , MAAT_RULE_EX_DATA * ad , const struct compile_ex_data_idx * ex_desc )
{
struct Maat_rule_t rule ;
fill_maat_rule ( & rule , rule_head , srv_def , strlen ( srv_def ) + 1 ) ;
ex_desc - > free_func ( ex_desc - > idx , & rule , srv_def , ad , ex_desc - > argl , ex_desc - > argp ) ;
return ;
}
2018-12-04 23:26:59 +08:00
int read_expr_table_info ( const char * line , struct Maat_table_desc * table , MESA_htable_handle string2int_map )
2017-08-07 17:08:52 +08:00
{
int j = 0 , ret [ 4 ] = { 0 } ;
char table_type [ 16 ] , src_charset [ 256 ] , dst_charset [ 256 ] , merge [ 4 ] , quick_str_scan [ 32 ] = { 0 } ;
char * token = NULL , * sub_token = NULL , * saveptr ;
2018-12-04 20:12:56 +08:00
struct expr_table_desc * p = & ( table - > expr ) ;
2018-12-05 18:00:55 +08:00
sscanf ( line , " %d \t %s \t %s \t %s \t %s \t %s \t %d \t %s " , & ( table - > table_id )
2018-12-04 20:12:56 +08:00
, table - > table_name [ 0 ]
2017-08-07 17:08:52 +08:00
, table_type
, src_charset
, dst_charset
, merge
, & ( p - > cross_cache_size )
, quick_str_scan ) ;
memset ( ret , 0 , sizeof ( ret ) ) ;
2018-12-04 20:12:56 +08:00
ret [ 0 ] = map_str2int ( string2int_map , str_tolower ( table_type ) , ( int * ) & ( table - > table_type ) ) ;
2018-09-21 21:32:09 +08:00
ret [ 1 ] = map_str2int ( string2int_map , str_tolower ( src_charset ) , ( int * ) & ( p - > src_charset ) ) ;
ret [ 2 ] = map_str2int ( string2int_map , str_tolower ( merge ) , & ( p - > do_charset_merge ) ) ;
2017-08-07 17:08:52 +08:00
if ( strlen ( quick_str_scan ) > 0 )
{
2018-09-21 21:32:09 +08:00
ret [ 3 ] = map_str2int ( string2int_map , str_tolower ( quick_str_scan ) , & ( p - > quick_expr_switch ) ) ;
2017-08-07 17:08:52 +08:00
}
memset ( quick_str_scan , 0 , sizeof ( quick_str_scan ) ) ;
for ( j = 0 ; j < 4 ; j + + )
{
if ( ret [ j ] < 0 )
{
return - 1 ;
}
}
j = 0 ;
for ( token = dst_charset ; ; token = NULL )
{
sub_token = strtok_r ( token , " / " , & saveptr ) ;
if ( sub_token = = NULL )
break ;
2018-09-21 21:32:09 +08:00
ret [ 3 ] = map_str2int ( string2int_map , str_tolower ( sub_token ) , ( int * ) & ( p - > dst_charset [ j ] ) ) ;
2017-08-07 17:08:52 +08:00
if ( ret [ 3 ] > 0 )
{
if ( p - > dst_charset [ j ] = = p - > src_charset )
{
p - > src_charset_in_dst = TRUE ;
}
j + + ;
}
else
{
return - 1 ;
}
}
return 0 ;
}
2018-12-04 23:26:59 +08:00
Maat_table_desc * table_info_new ( int max_thread_num )
2018-12-04 20:12:56 +08:00
{
2018-12-04 23:26:59 +08:00
struct Maat_table_desc * p = ALLOC ( struct Maat_table_desc , 1 ) ;
2018-12-04 20:12:56 +08:00
p - > conj_cnt = 1 ;
return p ;
}
2018-12-04 23:26:59 +08:00
void table_info_free ( struct Maat_table_desc * p )
2018-12-04 20:12:56 +08:00
{
free ( p ) ;
return ;
}
2018-09-24 18:49:18 +08:00
int _read_integer_arrary ( char * string , int * array , int size )
{
char * token = NULL , * sub_token = NULL , * saveptr ;
int i = 0 ;
for ( token = string , i = 0 ; i < size ; token = NULL , i + + )
{
sub_token = strtok_r ( token , " , " , & saveptr ) ;
if ( sub_token = = NULL )
break ;
sscanf ( sub_token , " %d " , array + i ) ;
}
return i ;
}
2018-12-08 17:41:25 +06:00
# define COLUMN_PLUGIN_DESCR_JSON 4
2018-12-05 18:00:55 +08:00
int read_plugin_table_description ( const char * line , struct Maat_table_desc * p )
2018-09-24 18:49:18 +08:00
{
int i = 0 , ret = 0 ;
2018-12-05 18:00:55 +08:00
size_t offset = 0 , len = 0 ;
2018-12-04 20:12:56 +08:00
cJSON * json = NULL , * tmp = NULL , * array_item = NULL ;
2018-09-24 18:49:18 +08:00
char * copy_line = NULL , * plug_info = NULL ;
2018-12-04 20:12:56 +08:00
struct plugin_table_desc * plugin_desc = & ( p - > plugin ) ;
2018-09-24 18:49:18 +08:00
copy_line = _maat_strdup ( line ) ;
2018-12-08 17:41:25 +06:00
ret = get_column_pos ( copy_line , COLUMN_PLUGIN_DESCR_JSON , & offset , & len ) ;
2018-12-05 18:00:55 +08:00
if ( i < 0 )
2018-09-24 18:49:18 +08:00
{
goto error_out ;
}
2018-12-08 17:41:25 +06:00
if ( offset + len < strlen ( copy_line ) )
{
copy_line [ offset + len + 1 ] = ' \0 ' ;
}
2018-12-05 18:00:55 +08:00
plug_info = copy_line + offset ;
2018-09-24 18:49:18 +08:00
2018-12-11 19:52:40 +06:00
if ( NULL = = strchr ( plug_info , ' { ' ) ) //For old version compatible.
2018-09-24 18:49:18 +08:00
{
2018-12-04 20:12:56 +08:00
ret = sscanf ( plug_info , " %d " , & ( plugin_desc - > valid_flag_column ) ) ;
2018-09-24 18:49:18 +08:00
if ( ret = = 0 | | ret = = EOF )
{
2018-12-04 20:12:56 +08:00
plugin_desc - > valid_flag_column = - 1 ;
2018-09-24 18:49:18 +08:00
}
free ( copy_line ) ;
return 0 ;
}
2018-09-24 19:48:18 +08:00
json = cJSON_Parse ( plug_info ) ;
if ( ! json )
2018-09-24 18:49:18 +08:00
{
2018-09-24 19:48:18 +08:00
goto error_out ;
}
2018-12-04 20:12:56 +08:00
tmp = cJSON_GetObjectItem ( json , " key " ) ;
if ( tmp ! = NULL )
{
assert ( tmp - > type = = cJSON_Number ) ;
plugin_desc - > key_column = tmp - > valueint ;
}
2018-09-24 19:48:18 +08:00
tmp = cJSON_GetObjectItem ( json , " valid " ) ;
if ( tmp ! = NULL )
{
2018-12-04 20:12:56 +08:00
assert ( tmp - > type = = cJSON_Number ) ;
plugin_desc - > valid_flag_column = tmp - > valueint ;
2018-09-24 19:48:18 +08:00
}
tmp = cJSON_GetObjectItem ( json , " tag " ) ;
if ( tmp ! = NULL )
{
2018-12-04 20:12:56 +08:00
assert ( tmp - > type = = cJSON_Number ) ;
plugin_desc - > rule_tag_column = tmp - > valueint ;
2018-09-24 19:48:18 +08:00
}
2018-12-04 23:26:59 +08:00
tmp = cJSON_GetObjectItem ( json , " estimate_size " ) ;
if ( tmp ! = NULL )
{
assert ( tmp - > type = = cJSON_Number ) ;
plugin_desc - > estimate_size = tmp - > valueint ;
}
2018-09-24 19:48:18 +08:00
tmp = cJSON_GetObjectItem ( json , " foreign " ) ;
if ( tmp ! = NULL )
{
2018-12-04 20:12:56 +08:00
if ( tmp - > type = = cJSON_String )
{
plugin_desc - > n_foreign = _read_integer_arrary ( tmp - > valuestring , plugin_desc - > foreign_columns , MAX_FOREIGN_CLMN_NUM ) ;
}
else if ( tmp - > type = = cJSON_Array )
{
plugin_desc - > n_foreign = cJSON_GetArraySize ( tmp ) ;
for ( i = 0 ; i < plugin_desc - > n_foreign ; i + + )
{
array_item = cJSON_GetArrayItem ( tmp , i ) ;
assert ( array_item - > type = = cJSON_Number ) ;
plugin_desc - > foreign_columns [ i ] = array_item - > valueint ;
}
}
2018-09-24 19:48:18 +08:00
}
cJSON_Delete ( json ) ;
2018-09-24 18:49:18 +08:00
free ( copy_line ) ;
return 0 ;
error_out :
free ( copy_line ) ;
return - 1 ;
}
2018-12-05 18:00:55 +08:00
int read_table_description ( struct Maat_table_desc * * p_table_info , int num , const char * table_info_path , int max_thread_num , void * logger )
2015-10-10 18:30:12 +08:00
{
FILE * fp = NULL ;
char line [ MAX_TABLE_LINE_SIZE ] ;
2017-08-07 17:08:52 +08:00
int i = 0 , ret = 0 , table_cnt = 0 ;
2018-11-27 12:55:52 +08:00
char table_type_str [ 16 ] = { 0 } , not_care [ 1024 ] = { 0 } , tmp_str [ 32 ] = { 0 } ;
2015-10-10 18:30:12 +08:00
MESA_htable_handle string2int_map = map_create ( ) ;
2018-12-04 23:26:59 +08:00
struct Maat_table_desc * p = NULL ;
struct Maat_table_desc * conj_table = NULL ;
2016-08-30 10:40:05 +08:00
2015-10-10 18:30:12 +08:00
map_register ( string2int_map , " expr " , TABLE_TYPE_EXPR ) ;
map_register ( string2int_map , " ip " , TABLE_TYPE_IP ) ;
map_register ( string2int_map , " compile " , TABLE_TYPE_COMPILE ) ;
map_register ( string2int_map , " plugin " , TABLE_TYPE_PLUGIN ) ;
2017-08-07 17:08:52 +08:00
map_register ( string2int_map , " intval " , TABLE_TYPE_INTERVAL ) ;
2015-11-13 18:08:55 +08:00
map_register ( string2int_map , " digest " , TABLE_TYPE_DIGEST ) ;
2016-02-11 13:57:39 +08:00
map_register ( string2int_map , " expr_plus " , TABLE_TYPE_EXPR_PLUS ) ;
2015-10-10 18:30:12 +08:00
map_register ( string2int_map , " group " , TABLE_TYPE_GROUP ) ;
2017-08-07 17:08:52 +08:00
map_register ( string2int_map , " similar " , TABLE_TYPE_SIMILARITY ) ;
2016-06-17 15:00:28 +08:00
map_register ( string2int_map , " quickoff " , 0 ) ;
map_register ( string2int_map , " quickon " , 1 ) ;
2018-08-08 18:35:53 +08:00
map_register ( string2int_map , " escape " , USER_REGION_ENCODE_ESCAPE ) ;
// map_register(string2int_map,"base64",USER_REGION_ENCODE_BASE64); //NOT supported yet
2016-04-03 12:29:41 +08:00
for ( i = 0 ; i < MAX_CHARSET_NUM ; i + + )
{
if ( strlen ( CHARSET_STRING [ i ] ) > 0 )
{
map_register ( string2int_map , CHARSET_STRING [ i ] , i ) ;
}
else
{
break ;
}
}
2015-10-10 18:30:12 +08:00
map_register ( string2int_map , " yes " , 1 ) ;
map_register ( string2int_map , " no " , 0 ) ;
fp = fopen ( table_info_path , " r " ) ;
if ( fp = = NULL )
{
fprintf ( stderr , " Maat read table info %s error. \n " , table_info_path ) ;
2015-11-13 18:08:55 +08:00
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" Maat read table info %s error. \n " , table_info_path ) ;
2015-10-10 18:30:12 +08:00
}
2016-04-03 12:29:41 +08:00
i = 0 ;
2015-10-10 18:30:12 +08:00
while ( NULL ! = fgets ( line , sizeof ( line ) , fp ) )
{
i + + ;
if ( line [ 0 ] = = ' # ' | | line [ 0 ] = = ' ' | | line [ 0 ] = = ' \t ' | | strlen ( line ) < 4 )
{
continue ;
}
2018-12-04 20:12:56 +08:00
p = table_info_new ( max_thread_num ) ;
2016-05-09 22:02:27 +08:00
2018-12-05 18:00:55 +08:00
ret = sscanf ( line , " %d \t %s \t %s \t %[a-z0-9 \t ] " , & ( p - > table_id )
2016-08-30 10:40:05 +08:00
, p - > table_name [ 0 ]
2017-08-07 17:08:52 +08:00
, table_type_str
, not_care ) ;
2018-08-08 18:35:53 +08:00
if ( ret < 3 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" Maat read table info %s line %d error: not enough column. " , table_info_path , i ) ;
continue ;
}
2018-09-21 21:32:09 +08:00
ret = map_str2int ( string2int_map , str_tolower ( table_type_str ) , ( int * ) & ( p - > table_type ) ) ;
2017-08-07 17:08:52 +08:00
if ( ret < 0 )
2015-10-10 18:30:12 +08:00
{
2017-08-07 17:08:52 +08:00
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" Maat read table info %s line %d error:invalid table type. " , table_info_path , i ) ;
goto error_jump ;
2015-10-10 18:30:12 +08:00
}
2017-08-07 17:08:52 +08:00
switch ( p - > table_type )
2015-10-10 18:30:12 +08:00
{
2017-08-07 17:08:52 +08:00
case TABLE_TYPE_EXPR :
case TABLE_TYPE_EXPR_PLUS :
2018-09-24 18:49:18 +08:00
ret = read_expr_table_info ( line , p , string2int_map ) ;
2017-08-07 17:08:52 +08:00
if ( ret < 0 )
{
2018-09-24 18:49:18 +08:00
fprintf ( stderr , " Maat read table info %s line %d error:illegal column. \n " , table_info_path , i ) ;
2017-08-07 17:08:52 +08:00
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2018-09-24 18:49:18 +08:00
" Maat read table info %s line %d error:illegal column. " , table_info_path , i ) ;
2017-08-07 17:08:52 +08:00
goto error_jump ;
}
2015-10-10 18:30:12 +08:00
break ;
2017-08-07 17:08:52 +08:00
case TABLE_TYPE_PLUGIN :
2018-12-05 18:00:55 +08:00
ret = read_plugin_table_description ( line , p ) ;
2018-09-24 18:49:18 +08:00
if ( ret < 0 )
2015-10-10 18:30:12 +08:00
{
2018-09-24 18:49:18 +08:00
fprintf ( stderr , " Maat read table info %s line %d error:illegal plugin info. \n " , table_info_path , i ) ;
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" Maat read table info %s line %d error:illegal plugin info. " , table_info_path , i ) ;
goto error_jump ;
2015-10-10 18:30:12 +08:00
}
2017-08-07 17:08:52 +08:00
break ;
2018-08-08 18:35:53 +08:00
case TABLE_TYPE_COMPILE :
2018-09-24 12:02:48 +08:00
ret = sscanf ( not_care , " %[a-z0-9] " , tmp_str ) ;
2018-08-08 18:35:53 +08:00
if ( ret > 0 )
{
2018-12-04 20:12:56 +08:00
ret = map_str2int ( string2int_map , str_tolower ( tmp_str ) , ( int * ) & ( p - > compile . user_region_encoding ) ) ;
2018-08-08 18:35:53 +08:00
}
if ( ret ! = 1 )
{
2018-12-04 20:12:56 +08:00
p - > compile . user_region_encoding = USER_REGION_ENCODE_NONE ;
2018-08-08 18:35:53 +08:00
}
2017-08-07 17:08:52 +08:00
default :
break ;
2015-10-10 18:30:12 +08:00
}
2017-08-07 17:08:52 +08:00
2015-10-10 18:30:12 +08:00
if ( p - > table_id > = num )
{
2016-08-30 11:08:32 +08:00
fprintf ( stderr , " Maat read table info %s:%d error: table id %uh > %d. \n " , table_info_path , i , p - > table_id , num ) ;
2015-11-13 18:08:55 +08:00
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" Maat read table info %s line %d error: table id %uh > %d. \n " , table_info_path , i , p - > table_id , num ) ;
2015-10-10 18:30:12 +08:00
goto error_jump ;
}
2016-08-30 10:40:05 +08:00
if ( p_table_info [ p - > table_id ] ! = NULL ) //duplicate table_id,means conjunction table;
2015-10-10 18:30:12 +08:00
{
2016-08-30 10:40:05 +08:00
conj_table = p_table_info [ p - > table_id ] ;
if ( conj_table - > conj_cnt = = MAX_CONJUNCTION_TABLE_NUM )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2016-08-30 11:22:03 +08:00
" Maat read table info %s line %d error:reach tableid %d conjunction upper limit. "
2016-08-30 10:40:05 +08:00
, table_info_path , i , p - > table_id ) ;
goto error_jump ;
}
memcpy ( conj_table - > table_name [ conj_table - > conj_cnt ] , p - > table_name [ 0 ] , MAX_TABLE_NAME_LEN ) ;
conj_table - > conj_cnt + + ;
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
2016-08-30 11:22:03 +08:00
" Maat read table info %s:%d:conjunction %s with %s (id=%d,total=%d). "
2016-08-30 10:40:05 +08:00
, table_info_path , i , p - > table_name [ 0 ]
, conj_table - > table_name [ 0 ] , conj_table - > table_id , conj_table - > conj_cnt ) ;
//use goto to free the conjunctioned table_info
2015-10-10 18:30:12 +08:00
goto error_jump ;
}
2017-08-07 17:08:52 +08:00
2015-10-10 18:30:12 +08:00
p_table_info [ p - > table_id ] = p ;
table_cnt + + ;
continue ;
error_jump :
2018-12-04 20:12:56 +08:00
table_info_free ( p ) ;
2015-10-10 18:30:12 +08:00
p = NULL ;
}
fclose ( fp ) ;
map_destroy ( string2int_map ) ;
return table_cnt ;
}
2019-01-05 17:11:20 +08:00
struct Maat_group_inner_t * create_group_rule ( int group_id )
2015-10-10 18:30:12 +08:00
{
2019-01-05 17:11:20 +08:00
struct Maat_group_inner_t * group = ( struct Maat_group_inner_t * ) malloc ( sizeof ( struct Maat_group_inner_t ) ) ;
2015-10-10 18:30:12 +08:00
group - > group_id = group_id ;
group - > region_cnt = 0 ;
group - > region_boundary = 0 ;
group - > ref_cnt = 0 ;
2017-08-07 17:08:52 +08:00
group - > regions = dynamic_array_create ( 1 , 8 ) ;
2015-10-10 18:30:12 +08:00
group - > compile_shortcut = NULL ;
2017-08-07 17:08:52 +08:00
group - > table_id = 0 ;
group - > group_name = NULL ;
pthread_mutex_init ( & ( group - > mutex ) , NULL ) ;
2015-10-10 18:30:12 +08:00
return group ;
}
2019-01-05 17:11:20 +08:00
void _destroy_group_rule ( struct Maat_group_inner_t * group )
2015-10-10 18:30:12 +08:00
{
2017-08-07 17:08:52 +08:00
dynamic_array_destroy ( group - > regions , free ) ;
2015-10-10 18:30:12 +08:00
group - > region_cnt = 0 ;
group - > region_boundary = 0 ;
2017-08-07 17:08:52 +08:00
group - > regions = NULL ;
2015-10-10 18:30:12 +08:00
group - > ref_cnt = 0 ;
group - > group_id = - 1 ;
2017-08-07 17:08:52 +08:00
group - > table_id = - 1 ;
free ( group - > group_name ) ;
group - > group_name = NULL ;
pthread_mutex_destroy ( & ( group - > mutex ) ) ;
2015-10-10 18:30:12 +08:00
free ( group ) ;
}
2019-01-05 17:11:20 +08:00
void destroy_group_rule ( struct Maat_group_inner_t * group )
2018-07-05 17:20:49 +08:00
{
if ( group - > ref_cnt > 0 | | group - > region_cnt > 0 )
{
return ;
}
2018-11-07 17:12:06 +08:00
_destroy_group_rule ( group ) ;
2018-07-05 17:20:49 +08:00
}
2019-01-05 17:11:20 +08:00
void make_group_set ( struct Maat_compile_inner_t * compile_rule , struct bool_expr * a_set , unsigned char * has_not )
2015-10-10 18:30:12 +08:00
{
int i = 0 , j = 0 ;
2019-01-05 17:11:20 +08:00
a_set - > user_tag = compile_rule ;
struct Maat_group_inner_t * group = NULL ;
2017-08-07 17:08:52 +08:00
assert ( compile_rule - > group_cnt < = MAX_ITEMS_PER_BOOL_EXPR ) ;
for ( i = 0 , j = 0 ; i < compile_rule - > group_boundary & & j < MAX_ITEMS_PER_BOOL_EXPR ; i + + )
2015-10-10 18:30:12 +08:00
{
2019-01-05 17:11:20 +08:00
group = ( struct Maat_group_inner_t * ) dynamic_array_read ( compile_rule - > groups , i ) ;
2015-10-10 18:30:12 +08:00
if ( group = = NULL )
{
continue ;
}
2019-01-05 17:11:20 +08:00
a_set - > items [ j ] . item_id = group - > group_id ;
a_set - > items [ j ] . not_flag = compile_rule - > not_flag [ j ] ;
if ( a_set - > items [ j ] . not_flag )
{
* has_not = 1 ;
}
2015-10-10 18:30:12 +08:00
j + + ;
}
assert ( j = = compile_rule - > group_cnt ) ;
2019-01-05 17:11:20 +08:00
a_set - > item_num = j ;
2015-10-10 18:30:12 +08:00
}
2019-01-05 17:11:20 +08:00
struct compile_walker
{
MESA_lqueue_head update_q ;
long long compile_has_not_flag ;
} ;
2015-10-10 18:30:12 +08:00
void walk_compile_hash ( const uchar * key , uint size , void * data , void * user )
{
2019-01-05 17:11:20 +08:00
struct bool_expr * one_set = NULL ;
struct Maat_compile_inner_t * compile_rule = ( struct Maat_compile_inner_t * ) data ;
struct compile_walker * walker = ( struct compile_walker * ) user ;
unsigned char has_not_flag = 0 ;
MESA_lqueue_head update_q = walker - > update_q ;
2015-10-10 18:30:12 +08:00
if ( compile_rule - > db_c_rule = = NULL )
{
return ;
}
//make sure compile rule's each group has loadded.
if ( ( compile_rule - > group_cnt = = compile_rule - > db_c_rule - > declare_grp_num
| | compile_rule - > db_c_rule - > declare_grp_num = = 0 ) //for compatible old version
2019-01-08 21:25:08 +06:00
& & compile_rule - > group_cnt > 0
& & compile_rule - > group_cnt ! = compile_rule - > not_group_cnt )
2015-10-10 18:30:12 +08:00
{
2019-01-05 17:11:20 +08:00
one_set = ALLOC ( struct bool_expr , 1 ) ;
2015-10-10 18:30:12 +08:00
//reading compile rule is safe in update thread, mutex lock called when modified
2019-01-05 17:11:20 +08:00
make_group_set ( compile_rule , one_set , & has_not_flag ) ;
if ( has_not_flag )
{
walker - > compile_has_not_flag + + ;
}
MESA_lqueue_join_tail ( update_q , & one_set , sizeof ( one_set ) ) ; //put the pointer into queue
2015-10-10 18:30:12 +08:00
}
return ;
}
2019-01-05 17:11:20 +08:00
struct bool_matcher * create_bool_matcher ( MESA_htable_handle compile_hash , int thread_num , void * logger )
2015-10-10 18:30:12 +08:00
{
2019-01-05 17:11:20 +08:00
struct bool_matcher * bm = NULL ;
struct compile_walker walker = { NULL , 0 } ;
walker . update_q = MESA_lqueue_create ( 0 , 0 ) ;
MESA_lqueue_head update_q = walker . update_q ;
2015-10-10 18:30:12 +08:00
long data_size = 0 ;
2019-01-05 17:11:20 +08:00
size_t mem_size = 0 ;
2018-10-18 19:39:19 +08:00
UNUSED MESA_queue_errno_t q_ret = MESA_QUEUE_RET_OK ;
2015-10-10 18:30:12 +08:00
data_size = sizeof ( void * ) ;
2019-01-05 17:11:20 +08:00
struct bool_expr * one_set = NULL ;
struct bool_expr * set_array = NULL ;
2015-10-10 18:30:12 +08:00
int i = 0 ;
2019-01-05 17:11:20 +08:00
MESA_htable_iterate ( compile_hash , walk_compile_hash , & walker ) ;
2015-10-10 18:30:12 +08:00
const long q_cnt = MESA_lqueue_get_count ( update_q ) ;
2018-06-17 20:03:17 +08:00
if ( q_cnt = = 0 )
{
2019-01-05 17:11:20 +08:00
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
2018-10-15 17:23:17 +08:00
" No compile rule to build a bool matcher. " ) ;
2019-01-05 17:11:20 +08:00
MESA_lqueue_destroy ( update_q , lqueue_destroy_cb , NULL ) ;
2018-06-17 20:03:17 +08:00
return NULL ;
}
2019-01-05 17:11:20 +08:00
set_array = ALLOC ( struct bool_expr , q_cnt ) ;
for ( i = 0 ; i < q_cnt ; i + + )
2015-10-10 18:30:12 +08:00
{
2019-01-05 17:11:20 +08:00
q_ret = ( MESA_queue_errno_t ) MESA_lqueue_get_head ( update_q , & one_set , & data_size ) ;
assert ( data_size = = sizeof ( struct bool_expr * ) & & q_ret = = MESA_QUEUE_RET_OK ) ;
set_array [ i ] = * one_set ;
2015-10-10 18:30:12 +08:00
free ( one_set ) ;
one_set = NULL ;
}
2019-01-05 17:11:20 +08:00
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
" build bool matcher start: compile count %ld, NOT-logic count %lld " ,
q_cnt , walker . compile_has_not_flag ) ;
bm = bool_matcher_new ( set_array , q_cnt , thread_num , & mem_size ) ;
if ( bm ! = NULL )
2015-10-10 18:30:12 +08:00
{
2019-01-05 17:11:20 +08:00
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
" build bool matcher use %zu memory " , mem_size ) ;
2015-10-10 18:30:12 +08:00
}
else
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" build bool matcher failed! " ,
2019-01-05 17:11:20 +08:00
q_cnt ) ;
2015-10-10 18:30:12 +08:00
}
free ( set_array ) ;
set_array = NULL ;
2019-01-05 17:11:20 +08:00
MESA_lqueue_destroy ( update_q , lqueue_destroy_cb , NULL ) ;
return bm ;
2015-10-10 18:30:12 +08:00
}
2019-01-05 17:11:20 +08:00
void destroy_bool_matcher ( struct bool_matcher * bm )
2015-10-10 18:30:12 +08:00
{
2019-01-05 17:11:20 +08:00
bool_matcher_free ( bm ) ;
2015-10-10 18:30:12 +08:00
return ;
}
void EMPTY_FREE ( void * p )
{
return ;
}
2019-01-05 17:11:20 +08:00
struct Maat_compile_inner_t * create_compile_rule ( int compile_id )
2015-10-10 18:30:12 +08:00
{
2019-01-05 17:11:20 +08:00
struct Maat_compile_inner_t * p = ALLOC ( struct Maat_compile_inner_t , 1 ) ;
2015-10-10 18:30:12 +08:00
p - > compile_id = compile_id ;
p - > group_cnt = 0 ;
2017-08-07 17:08:52 +08:00
p - > group_boundary = 1 ;
2015-10-10 18:30:12 +08:00
p - > groups = dynamic_array_create ( 1 , 1 ) ;
2018-11-07 17:12:06 +08:00
p - > ads = ALLOC ( MAAT_RULE_EX_DATA , MAX_COMPILE_EX_DATA_NUM ) ;
2015-10-10 18:30:12 +08:00
pthread_rwlock_init ( & ( p - > rwlock ) , NULL ) ;
return p ;
}
2019-01-05 17:11:20 +08:00
void _destroy_compile_rule ( struct Maat_compile_inner_t * compile_rule )
2018-07-05 17:34:06 +08:00
{
2018-12-04 23:26:59 +08:00
const struct Maat_table_desc * table = compile_rule - > ref_table ;
2018-12-04 20:12:56 +08:00
const struct compile_table_desc * compile_desc = & ( table - > compile ) ;
2018-11-07 17:12:06 +08:00
struct db_compile_rule_t * db_compile_rule = compile_rule - > db_c_rule ;
int i = 0 ;
compile_rule - > compile_id = - 1 ;
dynamic_array_destroy ( compile_rule - > groups , NULL ) ;
pthread_rwlock_wrlock ( & ( compile_rule - > rwlock ) ) ;
2018-11-27 12:55:52 +08:00
2018-11-07 17:12:06 +08:00
if ( db_compile_rule ! = NULL )
{
2018-12-04 20:12:56 +08:00
for ( i = 0 ; i < compile_desc - > ex_data_num ; i + + )
2018-11-27 12:55:52 +08:00
{
2018-12-04 20:12:56 +08:00
rule_ex_data_free ( & ( db_compile_rule - > m_rule_head ) , db_compile_rule - > service_defined , compile_rule - > ads + i , compile_desc - > ex_desc + i ) ;
2018-11-27 12:55:52 +08:00
compile_rule - > ads [ i ] = NULL ;
}
2018-11-07 17:12:06 +08:00
free ( db_compile_rule - > service_defined ) ;
free ( db_compile_rule ) ;
compile_rule - > db_c_rule = NULL ;
2018-11-27 12:55:52 +08:00
}
2018-11-07 17:12:06 +08:00
free ( compile_rule - > ads ) ;
pthread_rwlock_unlock ( & ( compile_rule - > rwlock ) ) ;
pthread_rwlock_destroy ( & ( compile_rule - > rwlock ) ) ;
free ( compile_rule ) ;
2018-07-05 17:34:06 +08:00
}
2019-01-05 17:11:20 +08:00
void destroy_compile_rule ( struct Maat_compile_inner_t * p )
2015-10-10 18:30:12 +08:00
{
int i = 0 ;
2019-01-05 17:11:20 +08:00
UNUSED struct Maat_compile_inner_t * p_group = NULL ;
2015-10-10 18:30:12 +08:00
assert ( p - > group_cnt = = 0 ) ;
2017-08-07 17:08:52 +08:00
for ( i = 0 ; i < p - > group_boundary ; i + + )
2015-10-10 18:30:12 +08:00
{
2019-01-05 17:11:20 +08:00
p_group = ( struct Maat_compile_inner_t * ) dynamic_array_read ( p - > groups , i ) ;
2015-10-10 18:30:12 +08:00
assert ( p_group = = NULL ) ;
}
2018-11-07 17:12:06 +08:00
_destroy_compile_rule ( p ) ;
2015-10-10 18:30:12 +08:00
}
scan_rule_t * create_rs_str_rule ( unsigned int sub_type , enum MAAT_MATCH_METHOD match_method , int is_case_sensitive , const char * string , int len , int l_offset , int r_offset )
{
scan_rule_t * p_rule = ( scan_rule_t * ) calloc ( sizeof ( scan_rule_t ) , 1 ) ;
p_rule - > rule_type = RULETYPE_STR ;
p_rule - > sub_type = sub_type ;
p_rule - > string_rule . case_sensitive = is_case_sensitive ;
p_rule - > string_rule . match_mode = 0 ;
p_rule - > string_rule . l_offset = - 1 ;
p_rule - > string_rule . r_offset = - 1 ;
switch ( match_method )
{
2017-08-07 17:08:52 +08:00
case MATCH_METHOD_COMPLETE :
2015-10-10 18:30:12 +08:00
p_rule - > string_rule . match_mode = 1 ;
break ;
case MATCH_METHOD_LEFT :
p_rule - > string_rule . l_offset = - 2 ;
break ;
case MATCH_METHOD_RIGHT :
p_rule - > string_rule . r_offset = - 2 ;
break ;
case MATCH_METHOD_SUB :
p_rule - > string_rule . l_offset = l_offset ;
p_rule - > string_rule . r_offset = r_offset ;
break ;
default :
assert ( 0 ) ;
break ;
}
p_rule - > string_rule . len = len ;
p_rule - > string_rule . str = ( char * ) calloc ( sizeof ( char ) , len ) ;
memcpy ( p_rule - > string_rule . str , string , len ) ;
return p_rule ;
}
void destroy_rs_str_rule ( scan_rule_t * p_rule )
{
free ( p_rule - > string_rule . str ) ;
free ( p_rule ) ;
}
scan_rule_t * create_rs_ip_rule ( unsigned int sub_type , struct db_ip_rule_t * db_ip_rule )
{
scan_rule_t * p_rule = ( scan_rule_t * ) calloc ( sizeof ( scan_rule_t ) , 1 ) ;
if ( db_ip_rule - > addr_type = = 4 )
{
p_rule - > rule_type = RULETYPE_IPv4 ;
memcpy ( & ( p_rule - > ipv4_rule ) , & ( db_ip_rule - > ipv4_rule ) , sizeof ( p_rule - > ipv4_rule ) ) ;
}
else
{
p_rule - > rule_type = RULETYPE_IPv6 ;
memcpy ( & ( p_rule - > ipv6_rule ) , & ( db_ip_rule - > ipv6_rule ) , sizeof ( p_rule - > ipv6_rule ) ) ;
}
p_rule - > sub_type = sub_type ;
return p_rule ;
}
void destroy_rs_ip_rule ( scan_rule_t * p )
{
free ( p ) ;
}
scan_rule_t * create_rs_intval_rule ( unsigned int sub_type , struct db_intval_rule_t * intval_rule )
{
scan_rule_t * p_rule = ( scan_rule_t * ) calloc ( sizeof ( scan_rule_t ) , 1 ) ;
p_rule - > rule_type = RULETYPE_INT ;
p_rule - > sub_type = sub_type ;
p_rule - > interval_rule . lb = intval_rule - > intval . lb ;
p_rule - > interval_rule . ub = intval_rule - > intval . ub ;
return p_rule ;
}
void destroy_rs_intval_rule ( scan_rule_t * p )
{
free ( p ) ;
}
2016-12-28 18:06:34 +08:00
struct op_expr_t * create_op_expr ( unsigned int expr_id , int operation , void * u_para , int table_id )
2015-10-10 18:30:12 +08:00
{
struct op_expr_t * op_expr = NULL ;
op_expr = ( struct op_expr_t * ) calloc ( sizeof ( struct op_expr_t ) , 1 ) ;
2016-06-03 15:10:49 +08:00
op_expr - > no_effect_convert_cnt = 0 ;
2016-06-24 11:49:15 +08:00
op_expr - > convert_failed = 0 ;
2015-10-10 18:30:12 +08:00
op_expr - > p_expr = ( boolean_expr_t * ) calloc ( sizeof ( boolean_expr_t ) , 1 ) ;
op_expr - > p_expr - > expr_id = expr_id ;
op_expr - > p_expr - > operation = operation ;
op_expr - > p_expr - > rnum = 0 ;
op_expr - > p_expr - > rules = NULL ;
op_expr - > p_expr - > tag = u_para ;
2016-12-28 18:06:34 +08:00
op_expr - > table_id = table_id ;
2015-10-10 18:30:12 +08:00
return op_expr ;
}
void destroy_op_expr ( struct op_expr_t * op_expr )
{
unsigned int i = 0 ;
for ( i = 0 ; i < op_expr - > p_expr - > rnum ; i + + )
{
switch ( op_expr - > p_rules [ i ] - > rule_type )
{
case RULETYPE_STR :
case RULETYPE_REG :
destroy_rs_str_rule ( op_expr - > p_rules [ i ] ) ;
break ;
case RULETYPE_IPv4 :
case RULETYPE_IPv6 :
destroy_rs_ip_rule ( op_expr - > p_rules [ i ] ) ;
break ;
case RULETYPE_INT :
destroy_rs_intval_rule ( op_expr - > p_rules [ i ] ) ;
break ;
default :
assert ( 0 ) ;
break ;
}
op_expr - > p_rules [ i ] = NULL ;
}
free ( op_expr - > p_expr ) ;
op_expr - > p_expr = NULL ;
free ( op_expr ) ;
}
void op_expr_add_rule ( struct op_expr_t * op_expr , scan_rule_t * p_rule )
{
int idx = op_expr - > p_expr - > rnum ;
op_expr - > p_rules [ idx ] = p_rule ;
op_expr - > p_expr - > rnum + + ;
2016-12-30 18:07:19 +08:00
op_expr - > rule_type = p_rule - > rule_type ;
2015-10-10 18:30:12 +08:00
return ;
}
2018-12-04 20:12:56 +08:00
GIE_digest_t * create_digest_rule ( unsigned int id , enum GIE_operation op , const char * digest ,
2019-01-05 17:11:20 +08:00
short cfds_lvl , struct Maat_group_inner_t * tag )
2015-11-12 18:28:58 +08:00
{
GIE_digest_t * rule = ( GIE_digest_t * ) calloc ( sizeof ( GIE_digest_t ) , 1 ) ;
2017-08-16 18:23:09 +08:00
int digest_len = 0 ;
2015-11-12 18:28:58 +08:00
rule - > id = id ;
rule - > operation = op ;
if ( digest ! = NULL )
{
2017-08-16 18:23:09 +08:00
digest_len = strlen ( digest ) ;
2017-08-07 17:08:52 +08:00
rule - > sfh = ( char * ) calloc ( sizeof ( char ) , digest_len + 1 ) ;
memcpy ( rule - > sfh , digest , digest_len ) ;
2015-10-10 18:30:12 +08:00
2015-11-12 18:28:58 +08:00
}
2017-08-16 18:23:09 +08:00
rule - > sfh_length = digest_len ;
2015-11-12 18:28:58 +08:00
rule - > cfds_lvl = cfds_lvl ;
rule - > tag = ( void * ) tag ;
return rule ;
}
void destroy_digest_rule ( GIE_digest_t * rule )
{
2017-08-07 17:08:52 +08:00
if ( rule - > sfh ! = NULL )
2015-11-12 18:28:58 +08:00
{
2017-08-07 17:08:52 +08:00
free ( rule - > sfh ) ;
rule - > sfh = NULL ;
2015-11-12 18:28:58 +08:00
}
free ( rule ) ;
rule = NULL ;
return ;
}
2018-12-04 20:12:56 +08:00
2018-12-05 18:00:55 +08:00
struct Maat_table_runtime * table_runtime_new ( const struct Maat_table_desc * table_desc , int max_thread_num )
2018-12-04 20:12:56 +08:00
{
2018-12-05 18:00:55 +08:00
struct Maat_table_runtime * table_rt = ALLOC ( struct Maat_table_runtime , 1 ) ;
table_rt - > table_type = table_desc - > table_type ;
switch ( table_desc - > table_type )
2018-12-04 20:12:56 +08:00
{
case TABLE_TYPE_DIGEST :
case TABLE_TYPE_SIMILARITY :
2018-12-05 18:00:55 +08:00
table_rt - > similar . update_q = MESA_lqueue_create ( 0 , 0 ) ;
2018-12-04 20:12:56 +08:00
break ;
case TABLE_TYPE_PLUGIN :
2018-12-05 18:00:55 +08:00
table_rt - > plugin . cache_lines = dynamic_array_create ( 1 , 1024 ) ;
if ( table_desc - > plugin . have_exdata )
{
table_rt - > plugin . key2ex_hash = wrap_plugin_EX_hash_new ( table_desc - > plugin . estimate_size ,
table_desc - > plugin . ex_desc . key2index_func ) ;
pthread_rwlock_init ( & ( table_rt - > plugin . rwlock ) , NULL ) ;
}
2018-12-04 20:12:56 +08:00
break ;
default :
break ;
}
2018-12-05 18:00:55 +08:00
table_rt - > scan_cnt = alignment_int64_array_alloc ( max_thread_num ) ;
table_rt - > scan_cpu_time = alignment_int64_array_alloc ( max_thread_num ) ;
table_rt - > input_bytes = alignment_int64_array_alloc ( max_thread_num ) ;
table_rt - > stream_num = alignment_int64_array_alloc ( max_thread_num ) ;
table_rt - > hit_cnt = alignment_int64_array_alloc ( max_thread_num ) ;
return table_rt ;
2018-12-04 20:12:56 +08:00
}
2018-12-04 23:26:59 +08:00
void table_runtime_free ( struct Maat_table_runtime * p )
2018-12-04 20:12:56 +08:00
{
long q_cnt = 0 , data_size = 0 ;
int i = 0 ;
UNUSED int q_ret = 0 ;
GIE_digest_t * digest_rule = NULL ;
if ( p = = NULL )
{
return ;
}
switch ( p - > table_type )
{
case TABLE_TYPE_DIGEST :
case TABLE_TYPE_SIMILARITY :
if ( p - > similar . gie_handle ! = NULL )
{
GIE_destory ( p - > similar . gie_handle ) ;
}
if ( p - > similar . update_q ! = NULL )
{
q_cnt = MESA_lqueue_get_count ( p - > similar . update_q ) ;
for ( i = 0 ; i < q_cnt ; i + + )
{
data_size = sizeof ( GIE_digest_t * ) ;
q_ret = ( MESA_queue_errno_t ) MESA_lqueue_get_head ( p - > similar . update_q , & digest_rule , & data_size ) ;
assert ( data_size = = sizeof ( void * ) & & q_ret = = MESA_QUEUE_RET_OK ) ;
destroy_digest_rule ( digest_rule ) ;
}
MESA_lqueue_destroy ( p - > similar . update_q , lqueue_destroy_cb , NULL ) ;
}
break ;
case TABLE_TYPE_PLUGIN :
dynamic_array_destroy ( p - > plugin . cache_lines , free ) ;
p - > plugin . cache_lines = NULL ;
2018-12-04 23:26:59 +08:00
if ( p - > plugin . key2ex_hash ! = NULL )
2018-12-04 20:12:56 +08:00
{
2018-12-04 23:26:59 +08:00
MESA_htable_destroy ( p - > plugin . key2ex_hash , NULL ) ;
2018-12-04 20:12:56 +08:00
}
break ;
default :
break ;
}
alignment_int64_array_free ( p - > scan_cnt ) ;
alignment_int64_array_free ( p - > scan_cpu_time ) ;
alignment_int64_array_free ( p - > input_bytes ) ;
alignment_int64_array_free ( p - > stream_num ) ;
alignment_int64_array_free ( p - > hit_cnt ) ;
free ( p ) ;
return ;
}
2019-01-05 17:11:20 +08:00
struct Maat_scanner_t * create_maat_scanner ( unsigned int version , _Maat_feather_t * feather )
2015-10-10 18:30:12 +08:00
{
2016-06-17 12:11:31 +08:00
int scan_thread_num = feather - > scan_thread_num ;
// int rs_scan_type=feather->rule_scan_type;
2018-12-04 23:26:59 +08:00
struct Maat_table_desc * * pp_table_desc = feather - > p_table_info ;
struct Maat_table_runtime * table_rt = NULL ;
2018-12-04 20:12:56 +08:00
const struct expr_table_desc * expr_desc = NULL ;
2016-06-17 12:11:31 +08:00
int i = 0 , j = 0 ;
unsigned int sub_type = 0 ;
2018-10-18 19:39:19 +08:00
UNUSED int ret = 0 ;
2015-10-10 18:30:12 +08:00
MESA_htable_create_args_t hargs ;
memset ( & hargs , 0 , sizeof ( hargs ) ) ;
2015-11-13 13:33:16 +08:00
hargs . thread_safe = 0 ;
2015-10-10 18:30:12 +08:00
hargs . hash_slot_size = 1024 * 1024 ;
hargs . max_elem_num = 0 ;
2016-03-25 11:55:15 +08:00
hargs . eliminate_type = HASH_ELIMINATE_ALGO_FIFO ;
2015-10-10 18:30:12 +08:00
hargs . expire_time = 0 ;
hargs . key_comp = NULL ;
hargs . key2index = NULL ;
2015-11-13 13:33:16 +08:00
hargs . recursive = 0 ;
2015-10-10 18:30:12 +08:00
// hargs.data_free = _void_destroy_compile_rule;
hargs . data_free = EMPTY_FREE ;
hargs . data_expire_with_condition = NULL ;
2019-01-05 17:11:20 +08:00
struct Maat_scanner_t * scanner = NULL ;
scanner = ALLOC ( struct Maat_scanner_t , 1 ) ;
2015-10-10 18:30:12 +08:00
2017-08-07 17:08:52 +08:00
//Function Maat_cmd_append will access compile_hash in user thread.
hargs . thread_safe = 1 ;
2015-10-10 18:30:12 +08:00
scanner - > compile_hash = MESA_htable_create ( & hargs , sizeof ( hargs ) ) ;
MESA_htable_print_crtl ( scanner - > compile_hash , 0 ) ;
2017-08-07 17:08:52 +08:00
hargs . thread_safe = 1 ;
2015-10-10 18:30:12 +08:00
scanner - > group_hash = MESA_htable_create ( & hargs , sizeof ( hargs ) ) ;
MESA_htable_print_crtl ( scanner - > group_hash , 0 ) ;
2017-08-07 17:08:52 +08:00
hargs . thread_safe = 0 ;
2015-10-10 18:30:12 +08:00
scanner - > region_hash = MESA_htable_create ( & hargs , sizeof ( hargs ) ) ;
2015-12-18 17:51:20 +08:00
MESA_htable_print_crtl ( scanner - > region_hash , 0 ) ;
2016-02-11 13:57:39 +08:00
scanner - > district_map = map_create ( ) ;
2015-10-10 18:30:12 +08:00
scanner - > version = version ;
scanner - > cfg_num = 0 ;
2016-11-23 16:52:04 +08:00
scanner - > dedup_expr_num = 0 ;
2015-10-10 18:30:12 +08:00
scanner - > max_thread_num = scan_thread_num ;
//optimized for CPU cache_alignment 64
2018-11-27 12:55:52 +08:00
scanner - > ref_cnt = alignment_int64_array_alloc ( scan_thread_num ) ;
2018-12-04 20:12:56 +08:00
scanner - > region_update_q = MESA_lqueue_create ( 0 , 0 ) ;
2015-10-10 18:30:12 +08:00
scanner - > region = rulescan_initialize ( scan_thread_num ) ;
2016-06-08 11:16:45 +08:00
//For best performance test:
//1.Do NOT set this option,rulescan return no hit detail as default;
2016-06-17 12:11:31 +08:00
//2.Set necessary STR rule to QUICK;
2016-09-22 17:19:11 +08:00
if ( feather - > rule_scan_type = = 1 )
{
rulescan_set_param ( scanner - > region , RULESCAN_DETAIL_RESULT , NULL , 0 ) ;
}
else if ( feather - > rule_scan_type = = 2 )
{
rulescan_set_param ( scanner - > region , RULESCAN_DETAIL_RESULT , NULL , 0 ) ;
rulescan_set_param ( scanner - > region , RULESCAN_REGEX_GROUP , NULL , 0 ) ;
}
2018-12-04 20:12:56 +08:00
scanner - > tomb_ref = feather - > garbage_q ;
scanner - > region_rslt_buff = ALLOC ( scan_result_t , MAX_SCANNER_HIT_NUM * scan_thread_num ) ;
2015-10-10 18:30:12 +08:00
2016-06-23 16:11:23 +08:00
for ( i = 0 ; i < MAX_TABLE_NUM ; i + + )
2015-11-10 18:29:42 +08:00
{
2018-12-04 20:12:56 +08:00
if ( pp_table_desc [ i ] = = NULL )
2016-06-23 16:11:23 +08:00
{
continue ;
}
2018-12-05 18:00:55 +08:00
table_rt = table_runtime_new ( pp_table_desc [ i ] , feather - > scan_thread_num ) ;
2018-12-04 20:12:56 +08:00
if ( pp_table_desc [ i ] - > table_type = = TABLE_TYPE_EXPR | | pp_table_desc [ i ] - > table_type = = TABLE_TYPE_EXPR_PLUS )
{
expr_desc = & ( pp_table_desc [ i ] - > expr ) ;
if ( expr_desc - > quick_expr_switch = = 1 )
{
for ( j = 0 ; j < MAX_CHARSET_NUM & & pp_table_desc [ i ] - > expr . dst_charset [ j ] ! = CHARSET_NONE ; j + + )
2016-06-17 12:11:31 +08:00
{
2018-12-04 20:12:56 +08:00
sub_type = make_sub_type ( pp_table_desc [ i ] - > table_id , expr_desc - > dst_charset [ j ] , expr_desc - > do_charset_merge ) ;
ret = rulescan_set_param ( scanner - > region , RULESCAN_QUICK_SCAN , & sub_type , sizeof ( sub_type ) ) ;
assert ( ret = = 1 ) ;
if ( expr_desc - > do_charset_merge = = 1 )
2016-06-17 12:11:31 +08:00
{
2018-12-04 20:12:56 +08:00
break ;
2016-06-17 12:11:31 +08:00
}
}
2018-12-04 20:12:56 +08:00
}
2016-06-17 12:11:31 +08:00
}
2018-12-04 23:26:59 +08:00
scanner - > table_rt [ i ] = table_rt ;
2015-11-10 18:29:42 +08:00
}
2015-10-10 18:30:12 +08:00
return scanner ;
}
2019-01-05 17:11:20 +08:00
void destroy_maat_scanner ( struct Maat_scanner_t * scanner )
2015-10-10 18:30:12 +08:00
{
long q_cnt = 0 , data_size = 0 ;
2018-10-18 19:39:19 +08:00
int i = 0 , j = 0 ;
UNUSED int q_ret = 0 ;
2015-10-10 18:30:12 +08:00
struct op_expr_t * op_expr = NULL ;
2017-09-28 20:24:20 +08:00
if ( scanner = = NULL )
{
return ;
}
2015-10-10 18:30:12 +08:00
rulescan_destroy ( scanner - > region ) ;
2018-11-07 17:12:06 +08:00
MESA_htable_destroy ( scanner - > compile_hash , ( void ( * ) ( void * ) ) _destroy_compile_rule ) ;
MESA_htable_destroy ( scanner - > group_hash , ( void ( * ) ( void * ) ) _destroy_group_rule ) ;
2015-10-10 18:30:12 +08:00
MESA_htable_destroy ( scanner - > region_hash , NULL ) ;
2016-02-11 13:57:39 +08:00
map_destroy ( scanner - > district_map ) ;
2016-06-27 18:25:53 +08:00
scanner - > district_map = NULL ;
assert ( scanner - > tmp_district_map = = NULL ) ;
2019-01-08 21:25:08 +06:00
destroy_bool_matcher ( scanner - > bool_matcher_expr_compiler ) ;
2015-10-10 18:30:12 +08:00
q_cnt = MESA_lqueue_get_count ( scanner - > region_update_q ) ;
for ( i = 0 ; i < q_cnt ; i + + )
{
data_size = sizeof ( struct op_expr_t * ) ;
q_ret = ( MESA_queue_errno_t ) MESA_lqueue_get_head ( scanner - > region_update_q , & op_expr , & data_size ) ;
assert ( data_size = = sizeof ( void * ) & & q_ret = = MESA_QUEUE_RET_OK ) ;
destroy_op_expr ( op_expr ) ;
}
MESA_lqueue_destroy ( scanner - > region_update_q , lqueue_destroy_cb , NULL ) ;
free ( scanner - > region_rslt_buff ) ;
scanner - > region_rslt_buff = NULL ;
2018-12-04 20:12:56 +08:00
alignment_int64_array_free ( scanner - > ref_cnt ) ;
2015-10-10 18:30:12 +08:00
scanner - > ref_cnt = NULL ;
for ( i = 0 ; i < MAX_CHARSET_NUM ; i + + )
{
for ( j = 0 ; j < MAX_CHARSET_NUM ; j + + )
{
if ( scanner - > iconv_handle [ i ] [ j ] ! = NULL )
{
iconv_close ( scanner - > iconv_handle [ i ] [ j ] ) ;
}
}
}
2015-11-10 18:29:42 +08:00
for ( i = 0 ; i < MAX_TABLE_NUM ; i + + )
{
2018-12-04 20:12:56 +08:00
table_runtime_free ( scanner - > table_rt [ i ] ) ;
2015-11-10 18:29:42 +08:00
}
2015-10-10 18:30:12 +08:00
free ( scanner ) ;
return ;
}
2015-11-12 18:28:58 +08:00
unsigned int make_sub_type ( unsigned short table_id , enum MAAT_CHARSET charset , int do_charset_merge )
2015-10-10 18:30:12 +08:00
{
unsigned int sub_type = 0 ;
if ( do_charset_merge = = TRUE )
{
sub_type = table_id < < 4 | CHARSET_NONE ;
}
else
{
sub_type = table_id < < 4 | charset ;
}
assert ( sub_type < MAX_SUB_RULETYPE ) ;
return sub_type ;
}
void destroy_ip_expr ( boolean_expr_t * p )
{
free ( p - > rules ) ;
free ( p ) ;
return ;
}
2018-12-04 20:12:56 +08:00
struct _region_stat_t
{
int cfg_num ;
union
{
int expr_rule_cnt ; //expr_type=0,1,3
int ipv4_rule_cnt ;
} ;
union
{
int regex_rule_cnt ; //expr_type=2
int ipv6_rule_cnt ;
} ;
} ;
2016-12-28 18:06:34 +08:00
void count_rs_region ( struct op_expr_t * op_expr , struct _region_stat_t * region_stat , int size )
{
assert ( op_expr - > table_id < size ) ;
int op = 0 ;
if ( op_expr - > p_expr - > operation = = 0 ) //add
{
op = 1 ;
}
else if ( op_expr - > p_expr - > operation = = 1 ) //delete
{
op = - 1 ;
}
else
{
assert ( 0 ) ;
}
region_stat [ op_expr - > table_id ] . cfg_num + = op ;
2016-12-30 18:07:19 +08:00
switch ( op_expr - > rule_type )
2016-12-28 18:06:34 +08:00
{
case RULETYPE_STR :
region_stat [ op_expr - > table_id ] . expr_rule_cnt + = op ;
break ;
case RULETYPE_REG :
region_stat [ op_expr - > table_id ] . regex_rule_cnt + = op ;
break ;
case RULETYPE_INT :
break ;
case RULETYPE_IPv4 :
region_stat [ op_expr - > table_id ] . ipv4_rule_cnt + = op ;
break ;
case RULETYPE_IPv6 :
region_stat [ op_expr - > table_id ] . ipv6_rule_cnt + = op ;
break ;
default :
assert ( 0 ) ;
break ;
}
return ;
}
2015-10-10 18:30:12 +08:00
2019-01-05 17:11:20 +08:00
void rulescan_batch_update ( rule_scanner_t rs_handle , MESA_lqueue_head expr_queue , void * logger , struct Maat_scanner_t * maat_scanner )
2015-10-10 18:30:12 +08:00
{
long i = 0 , data_size = 0 ;
2018-12-04 20:12:56 +08:00
unsigned int j = 0 ;
int ret = 0 ;
2015-10-10 18:30:12 +08:00
unsigned int failed_ids [ MAX_FAILED_NUM ] ;
2018-12-04 20:12:56 +08:00
char failed_info [ 512 ] , * p = NULL ;
2018-10-18 19:39:19 +08:00
UNUSED MESA_queue_errno_t q_ret = MESA_QUEUE_RET_OK ;
2015-10-10 18:30:12 +08:00
memset ( failed_ids , 0 , sizeof ( failed_ids ) ) ;
memset ( failed_info , 0 , sizeof ( failed_info ) ) ;
const long q_cnt = MESA_lqueue_get_count ( expr_queue ) ;
2016-11-21 17:56:59 +08:00
struct timespec start , end ;
unsigned long long update_interval = 0 ;
2016-12-28 18:06:34 +08:00
struct _region_stat_t region_counter [ MAX_TABLE_NUM ] ;
2018-12-04 20:12:56 +08:00
memset ( region_counter , 0 , sizeof ( region_counter ) ) ;
2018-12-04 23:26:59 +08:00
struct Maat_table_runtime * table_rt = NULL ;
2015-10-10 18:30:12 +08:00
if ( q_cnt = = 0 )
{
return ;
}
2018-12-04 20:12:56 +08:00
boolean_expr_t * to_update_expr = ALLOC ( boolean_expr_t , q_cnt ) ;
2015-10-10 18:30:12 +08:00
struct op_expr_t * op_expr = NULL ;
for ( i = 0 ; i < q_cnt ; i + + )
{
data_size = sizeof ( void * ) ;
q_ret = ( MESA_queue_errno_t ) MESA_lqueue_get_head ( expr_queue , & op_expr , & data_size ) ;
assert ( data_size = = sizeof ( void * ) & & q_ret = = MESA_QUEUE_RET_OK ) ;
memcpy ( & ( to_update_expr [ i ] ) , op_expr - > p_expr , sizeof ( boolean_expr_t ) ) ;
//make a whole memory chunk
2018-12-04 20:12:56 +08:00
to_update_expr [ i ] . rules = ALLOC ( scan_rule_t , op_expr - > p_expr - > rnum ) ;
for ( j = 0 ; j < op_expr - > p_expr - > rnum ; j + + )
2015-10-10 18:30:12 +08:00
{
memcpy ( & ( to_update_expr [ i ] . rules [ j ] ) , op_expr - > p_rules [ j ] , sizeof ( scan_rule_t ) ) ;
if ( to_update_expr [ i ] . rules [ j ] . rule_type = = RULETYPE_REG | | to_update_expr [ i ] . rules [ j ] . rule_type = = RULETYPE_STR )
{
to_update_expr [ i ] . rules [ j ] . string_rule . str = ( char * ) calloc ( sizeof ( char ) , to_update_expr [ i ] . rules [ j ] . string_rule . len ) ;
memcpy ( to_update_expr [ i ] . rules [ j ] . string_rule . str
, op_expr - > p_rules [ j ] - > string_rule . str
, to_update_expr [ i ] . rules [ j ] . string_rule . len ) ;
}
}
2018-12-04 20:12:56 +08:00
2016-12-28 18:06:34 +08:00
count_rs_region ( op_expr , region_counter , MAX_TABLE_NUM ) ;
2015-10-10 18:30:12 +08:00
destroy_op_expr ( op_expr ) ;
op_expr = NULL ;
}
2016-11-21 17:39:57 +08:00
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
2016-12-28 18:06:34 +08:00
" rs_handle %p rulescan_update %ld rules. " , rs_handle , q_cnt ) ;
2016-11-21 17:56:59 +08:00
clock_gettime ( CLOCK_MONOTONIC , & start ) ;
2016-12-28 18:06:34 +08:00
ret = rulescan_update ( rs_handle , to_update_expr , q_cnt , failed_ids , MAX_FAILED_NUM ) ;
2016-11-21 17:56:59 +08:00
clock_gettime ( CLOCK_MONOTONIC , & end ) ;
2015-10-10 18:30:12 +08:00
if ( ret ! = 1 )
{
p = failed_info ;
for ( i = 0 ; i < failed_ids [ 0 ] & & i < MAX_FAILED_NUM - 1 & & sizeof ( failed_info ) - ( p - failed_info ) > 10 ; i + + )
{
p + = snprintf ( p , sizeof ( failed_info ) - ( p - failed_info ) , " %d, " , failed_ids [ i + 1 ] ) ;
}
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" rulescan_update error,when batch update %ld rules,regex error %u. " , q_cnt , failed_ids [ 0 ] ) ;
2017-09-21 10:23:04 +08:00
assert ( 0 ) ;
2015-10-10 18:30:12 +08:00
}
2016-11-21 17:56:59 +08:00
update_interval = ( end . tv_sec - start . tv_sec ) * 1000000000 + end . tv_nsec - start . tv_nsec ;
2016-11-21 17:39:57 +08:00
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
2016-12-28 18:06:34 +08:00
" rs_handle %p rulescan_update with %2.2e (%llu) ns. "
, rs_handle
2016-11-21 17:56:59 +08:00
, ( double ) update_interval
, update_interval ) ;
2016-12-28 18:06:34 +08:00
//update scanner's region cnt;
for ( i = 0 ; i < MAX_TABLE_NUM ; i + + )
{
2018-12-04 23:26:59 +08:00
table_rt = maat_scanner - > table_rt [ i ] ;
if ( table_rt = = NULL )
2018-12-04 20:12:56 +08:00
{
continue ;
}
2018-12-04 23:26:59 +08:00
switch ( table_rt - > table_type )
2018-12-04 20:12:56 +08:00
{
case TABLE_TYPE_EXPR :
case TABLE_TYPE_EXPR_PLUS :
2018-12-04 23:26:59 +08:00
table_rt - > expr . expr_rule_cnt + = region_counter [ i ] . expr_rule_cnt ;
table_rt - > expr . regex_rule_cnt + = region_counter [ i ] . regex_rule_cnt ;
assert ( table_rt - > expr . expr_rule_cnt > = 0 ) ;
assert ( table_rt - > expr . regex_rule_cnt > = 0 ) ;
2018-12-04 20:12:56 +08:00
break ;
case TABLE_TYPE_IP :
2018-12-04 23:26:59 +08:00
table_rt - > ip . ipv4_rule_cnt + = region_counter [ i ] . ipv4_rule_cnt ;
table_rt - > ip . ipv6_rule_cnt + = region_counter [ i ] . ipv6_rule_cnt ;
2018-12-04 20:12:56 +08:00
break ;
default :
break ;
}
2018-12-04 23:26:59 +08:00
assert ( table_rt - > origin_rule_num > = 0 ) ;
2016-12-28 18:06:34 +08:00
}
2015-10-10 18:30:12 +08:00
for ( i = 0 ; i < q_cnt ; i + + )
{
2018-12-04 20:12:56 +08:00
for ( j = 0 ; j < to_update_expr [ i ] . rnum ; j + + )
2015-10-10 18:30:12 +08:00
{
if ( to_update_expr [ i ] . rules [ j ] . rule_type = = RULETYPE_REG | | to_update_expr [ i ] . rules [ j ] . rule_type = = RULETYPE_STR )
{
free ( to_update_expr [ i ] . rules [ j ] . string_rule . str ) ;
}
}
free ( to_update_expr [ i ] . rules ) ;
}
free ( to_update_expr ) ;
}
2019-01-05 17:11:20 +08:00
void digest_batch_update ( GIE_handle_t * handle , MESA_lqueue_head update_q , void * logger , struct Maat_scanner_t * maat_scanner , int table_id )
2015-11-10 18:29:42 +08:00
{
long i = 0 , data_size = 0 ;
int ret = 0 ;
GIE_digest_t * digest_rule = NULL ;
GIE_digest_t * * update_array = NULL ;
2018-10-18 19:39:19 +08:00
UNUSED MESA_queue_errno_t q_ret = MESA_QUEUE_RET_OK ;
2015-11-10 18:29:42 +08:00
const long q_cnt = MESA_lqueue_get_count ( update_q ) ;
if ( q_cnt = = 0 )
{
return ;
}
2018-12-04 23:26:59 +08:00
struct Maat_table_runtime * table_rt = maat_scanner - > table_rt [ table_id ] ;
2015-11-10 18:29:42 +08:00
update_array = ( GIE_digest_t * * ) calloc ( sizeof ( GIE_digest_t * ) , q_cnt ) ;
for ( i = 0 ; i < q_cnt ; i + + )
{
data_size = sizeof ( void * ) ;
q_ret = ( MESA_queue_errno_t ) MESA_lqueue_get_head ( update_q , & digest_rule , & data_size ) ;
assert ( data_size = = sizeof ( void * ) & & q_ret = = MESA_QUEUE_RET_OK ) ;
update_array [ i ] = digest_rule ;
digest_rule = NULL ;
}
ret = GIE_update ( handle , update_array , ( int ) q_cnt ) ;
if ( ret ! = ( int ) q_cnt )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" GIE_update error,when batch update %d/%ld rules. " , ret , q_cnt ) ;
2015-10-10 18:30:12 +08:00
2015-11-10 18:29:42 +08:00
}
for ( i = 0 ; i < q_cnt ; i + + )
{
2016-12-28 18:06:34 +08:00
if ( update_array [ i ] - > operation = = GIE_INSERT_OPT )
{
2018-12-04 23:26:59 +08:00
table_rt - > origin_rule_num + + ;
2016-12-28 18:06:34 +08:00
}
else
{
2018-12-04 23:26:59 +08:00
table_rt - > origin_rule_num - - ;
2016-12-28 18:06:34 +08:00
}
2015-11-10 18:29:42 +08:00
destroy_digest_rule ( update_array [ i ] ) ;
update_array [ i ] = NULL ;
}
free ( update_array ) ;
update_array = NULL ;
return ;
}
2019-01-05 17:11:20 +08:00
struct Maat_group_inner_t * add_region_to_group ( struct Maat_group_inner_t * group , int table_id , int region_id , int district_id , int expr_id , enum MAAT_TABLE_TYPE region_type )
2017-08-07 17:08:52 +08:00
{
int i = 0 ;
struct _Maat_region_inner_t * region_rule = NULL ;
for ( i = 0 ; i < group - > region_boundary ; i + + )
{
region_rule = ( struct _Maat_region_inner_t * ) dynamic_array_read ( group - > regions , i ) ;
if ( region_rule = = NULL )
{
continue ;
}
if ( region_rule - > region_id = = region_id )
{
break ;
}
}
if ( i = = group - > region_boundary ) //new region
{
region_rule = ( struct _Maat_region_inner_t * ) malloc ( sizeof ( struct _Maat_region_inner_t ) ) ;
region_rule - > region_id = region_id ;
region_rule - > expr_id_cnt = 1 ;
region_rule - > expr_id_ub = region_rule - > expr_id_lb = expr_id ;
region_rule - > district_id = district_id ;
region_rule - > table_type = region_type ;
region_rule - > table_id = table_id ;
pthread_mutex_lock ( & ( group - > mutex ) ) ;
dynamic_array_write ( group - > regions , group - > region_boundary , region_rule ) ;
group - > region_cnt + + ;
group - > region_boundary + + ;
pthread_mutex_unlock ( & ( group - > mutex ) ) ;
}
else
{
assert ( expr_id = = region_rule - > expr_id_ub + 1 ) ;
region_rule - > expr_id_ub = expr_id ;
region_rule - > expr_id_cnt + + ;
}
2015-10-10 18:30:12 +08:00
return group ;
}
2019-01-05 17:11:20 +08:00
void cancel_last_region_from_group ( struct Maat_group_inner_t * group , int region_id , int expr_id )
2017-08-07 17:08:52 +08:00
{
struct _Maat_region_inner_t * region_rule = NULL ;
pthread_mutex_lock ( & ( group - > mutex ) ) ;
region_rule = ( struct _Maat_region_inner_t * ) dynamic_array_read ( group - > regions , group - > region_boundary - 1 ) ;
assert ( region_rule - > expr_id_ub = = expr_id & & region_rule - > region_id = = region_id ) ;
if ( region_rule - > expr_id_cnt = = 1 )
{
free ( region_rule ) ;
dynamic_array_write ( group - > regions , group - > region_boundary , NULL ) ;
group - > region_cnt - - ;
group - > region_boundary - - ;
}
else
{
region_rule - > expr_id_ub - - ;
region_rule - > expr_id_cnt - - ;
}
pthread_mutex_unlock ( & ( group - > mutex ) ) ;
2017-05-24 13:55:35 +08:00
return ;
}
2019-01-05 17:11:20 +08:00
unsigned int del_region_from_group ( struct Maat_group_inner_t * group , int region_id , unsigned int * output_expr_id , int output_size )
2015-10-10 18:30:12 +08:00
{
int i = 0 , j = 0 ;
2017-08-07 17:08:52 +08:00
struct _Maat_region_inner_t * region_rule = NULL ;
pthread_mutex_lock ( & ( group - > mutex ) ) ;
2015-10-10 18:30:12 +08:00
for ( i = 0 ; i < group - > region_boundary ; i + + )
{
2017-08-07 17:08:52 +08:00
region_rule = ( struct _Maat_region_inner_t * ) dynamic_array_read ( group - > regions , i ) ;
2015-10-10 18:30:12 +08:00
if ( region_rule = = NULL )
{
continue ;
}
if ( region_rule - > region_id = = region_id )
{
2017-08-07 17:08:52 +08:00
dynamic_array_write ( group - > regions , i , NULL ) ;
for ( j = 0 ; j < region_rule - > expr_id_cnt ; j + + )
{
output_expr_id [ j ] = region_rule - > expr_id_lb + j ;
2017-08-17 18:29:01 +08:00
assert ( output_expr_id [ j ] > = 0 ) ;
2017-08-07 17:08:52 +08:00
}
assert ( j < = output_size ) ;
region_rule - > region_id = 0 ;
2015-10-10 18:30:12 +08:00
free ( region_rule ) ;
region_rule = NULL ;
group - > region_cnt - - ;
2017-08-07 17:08:52 +08:00
break ;
2015-10-10 18:30:12 +08:00
}
}
2017-08-07 17:08:52 +08:00
pthread_mutex_unlock ( & ( group - > mutex ) ) ;
2015-10-10 18:30:12 +08:00
return j ;
}
2019-01-05 17:11:20 +08:00
int add_group_to_compile ( struct Maat_compile_inner_t * a_compile_rule , struct Maat_group_inner_t * a_rule_group , int not_flag )
2015-10-10 18:30:12 +08:00
{
int i = 0 , ret = - 1 ;
2017-08-07 17:08:52 +08:00
int write_pos = - 1 ;
2019-01-05 17:11:20 +08:00
struct Maat_group_inner_t * p = NULL ;
2015-10-10 18:30:12 +08:00
pthread_rwlock_wrlock ( & ( a_compile_rule - > rwlock ) ) ;
if ( a_compile_rule - > db_c_rule ! = NULL
& & a_compile_rule - > group_cnt > = a_compile_rule - > db_c_rule - > declare_grp_num
& & a_compile_rule - > db_c_rule - > declare_grp_num ! = 0 )
{
ret = - 1 ;
2017-08-07 17:08:52 +08:00
goto error_out ;
2015-10-10 18:30:12 +08:00
}
2017-08-07 17:08:52 +08:00
for ( i = 0 ; i < a_compile_rule - > group_boundary ; i + + )
2015-10-10 18:30:12 +08:00
{
2019-01-05 17:11:20 +08:00
p = ( struct Maat_group_inner_t * ) dynamic_array_read ( a_compile_rule - > groups , i ) ;
2017-08-07 17:08:52 +08:00
if ( p = = NULL )
2015-10-10 18:30:12 +08:00
{
2017-08-07 17:08:52 +08:00
write_pos = i ;
2015-10-10 18:30:12 +08:00
}
2017-08-07 17:08:52 +08:00
else
2015-10-10 18:30:12 +08:00
{
2017-08-07 17:08:52 +08:00
if ( p - > group_id = = a_rule_group - > group_id ) //duplicate group
{
ret = - 1 ;
goto error_out ;
}
2015-10-10 18:30:12 +08:00
}
2017-08-07 17:08:52 +08:00
}
if ( write_pos < 0 & & a_compile_rule - > group_boundary = = MAX_EXPR_ITEM_NUM )
{
ret = - 1 ;
goto error_out ;
}
if ( write_pos < 0 )
{
write_pos = a_compile_rule - > group_boundary ;
a_compile_rule - > group_boundary + + ;
}
2019-01-05 15:51:08 +08:00
dynamic_array_write ( a_compile_rule - > groups , write_pos , a_rule_group ) ;
if ( not_flag )
{
a_compile_rule - > not_flag [ write_pos ] = 1 ;
2019-01-08 16:09:51 +06:00
a_compile_rule - > not_group_cnt + + ;
2019-01-05 15:51:08 +08:00
}
else
{
a_compile_rule - > not_flag [ write_pos ] = 0 ;
}
2017-08-07 17:08:52 +08:00
a_compile_rule - > group_cnt + + ;
a_rule_group - > ref_cnt + + ;
//member group->compile_shortcut may set to NULL and compile rule pointer repeatly,until rule build finish.
if ( a_rule_group - > ref_cnt = = 1 & & a_compile_rule - > group_cnt = = 1 )
{
a_rule_group - > compile_shortcut = a_compile_rule ;
}
else
{
a_rule_group - > compile_shortcut = NULL ;
}
//update group's shortcut when compile has more than one group.
if ( a_compile_rule - > group_cnt ! = 1 )
{
for ( i = 0 ; i < a_compile_rule - > group_boundary ; i + + )
2015-10-10 18:30:12 +08:00
{
2019-01-05 17:11:20 +08:00
p = ( struct Maat_group_inner_t * ) dynamic_array_read ( a_compile_rule - > groups , i ) ;
2017-08-07 17:08:52 +08:00
if ( p ! = NULL )
2015-10-10 18:30:12 +08:00
{
2017-08-07 17:08:52 +08:00
p - > compile_shortcut = NULL ;
2015-10-10 18:30:12 +08:00
}
}
}
2017-08-07 17:08:52 +08:00
ret = 1 ;
error_out :
2015-10-10 18:30:12 +08:00
pthread_rwlock_unlock ( & ( a_compile_rule - > rwlock ) ) ;
return ret ;
}
2019-01-05 17:11:20 +08:00
struct Maat_group_inner_t * del_group_from_compile ( struct Maat_compile_inner_t * a_compile_rule , int group_id )
2015-10-10 18:30:12 +08:00
{
int i = 0 ;
2019-01-05 17:11:20 +08:00
struct Maat_group_inner_t * group_rule = NULL ;
2015-10-10 18:30:12 +08:00
pthread_rwlock_wrlock ( & ( a_compile_rule - > rwlock ) ) ;
for ( i = 0 ; i < MAAT_MAX_EXPR_ITEM_NUM ; i + + )
{
2019-01-05 17:11:20 +08:00
group_rule = ( struct Maat_group_inner_t * ) dynamic_array_read ( a_compile_rule - > groups , i ) ;
2015-10-10 18:30:12 +08:00
if ( group_rule = = NULL )
{
continue ;
}
if ( group_rule - > group_id = = group_id )
{
group_rule - > ref_cnt - - ;
dynamic_array_write ( a_compile_rule - > groups , i , NULL ) ;
2019-01-08 16:09:51 +06:00
if ( a_compile_rule - > not_flag [ i ] = = 1 )
{
a_compile_rule - > not_group_cnt - - ;
a_compile_rule - > not_flag [ i ] = 0 ;
}
2015-10-10 18:30:12 +08:00
a_compile_rule - > group_cnt - - ;
pthread_rwlock_unlock ( & ( a_compile_rule - > rwlock ) ) ;
return group_rule ;
}
}
pthread_rwlock_unlock ( & ( a_compile_rule - > rwlock ) ) ;
return NULL ;
}
int MAAT_MAGIC = 0xaaaa ;
int sync_region ( MESA_htable_handle region_hash , int region_id , const char * table_name , int is_valid , void * logger )
{
int ret = - 1 ;
if ( is_valid = = TRUE )
{
ret = HASH_add_by_id ( region_hash , region_id , & MAAT_MAGIC ) ;
if ( ret < 0 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2016-06-24 15:25:13 +08:00
" region id %d of table %s is not unique. " , region_id , table_name ) ;
2015-10-10 18:30:12 +08:00
return - 1 ;
}
}
else
{
ret = HASH_delete_by_id ( region_hash , region_id ) ;
if ( ret = = - 1 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2016-06-24 15:25:13 +08:00
" region delete error,id %d in table %s does not exisit. "
2015-10-10 18:30:12 +08:00
, region_id
, table_name ) ;
return - 1 ;
}
}
return 1 ;
}
2019-01-05 17:11:20 +08:00
int get_district_id ( Maat_scanner_t * scanner , const char * district_str )
2016-02-11 13:57:39 +08:00
{
int map_ret = 0 , district_id = - 1 ;
map_ret = map_str2int ( scanner - > district_map , district_str , & district_id ) ;
if ( map_ret < 0 )
{
2016-06-27 18:25:53 +08:00
if ( scanner - > tmp_district_map = = NULL )
{
scanner - > tmp_district_map = map_duplicate ( scanner - > district_map ) ;
}
2016-09-09 15:39:56 +08:00
map_ret = map_str2int ( scanner - > tmp_district_map , district_str , & district_id ) ;
if ( map_ret < 0 )
{
district_id = scanner - > district_num ;
map_register ( scanner - > tmp_district_map , district_str , district_id ) ;
scanner - > district_num + + ;
}
2016-02-11 13:57:39 +08:00
}
return district_id ;
}
2019-01-05 17:11:20 +08:00
int add_expr_rule ( struct Maat_table_desc * table , struct db_str_rule_t * db_rule , struct Maat_scanner_t * scanner , void * logger )
2015-10-10 18:30:12 +08:00
{
unsigned int i = 0 , j = 0 ;
char * p = NULL , * saveptr = NULL , * region_string = NULL ;
int region_str_len = 0 , ret = 0 , k = 0 ;
2016-02-11 13:57:39 +08:00
int expr_id = 0 , district_id = - 1 ;
2018-12-04 20:12:56 +08:00
struct expr_table_desc * expr_desc = & ( table - > expr ) ;
2015-10-10 18:30:12 +08:00
scan_rule_t * p_rule = NULL ;
2019-01-05 17:11:20 +08:00
struct Maat_group_inner_t * group_rule = NULL ;
2015-10-10 18:30:12 +08:00
enum MAAT_CHARSET dst_charset = CHARSET_NONE ;
char * sub_key_array [ MAAT_MAX_EXPR_ITEM_NUM ] ;
int key_left_offset [ MAAT_MAX_EXPR_ITEM_NUM ] = { - 1 } , key_right_offset [ MAAT_MAX_EXPR_ITEM_NUM ] = { - 1 } ;
for ( i = 0 ; i < MAAT_MAX_EXPR_ITEM_NUM ; i + + )
{
key_left_offset [ i ] = - 1 ;
key_right_offset [ i ] = - 1 ;
}
int sub_expr_cnt = 0 ;
struct op_expr_t * op_expr = NULL ;
2019-01-05 17:11:20 +08:00
struct Maat_group_inner_t * u_para = NULL ;
2016-02-11 13:57:39 +08:00
if ( table - > table_type = = TABLE_TYPE_EXPR_PLUS )
{
assert ( strlen ( db_rule - > district ) > 0 ) ;
2018-02-26 18:42:13 +08:00
str_unescape ( db_rule - > district ) ;
2016-02-11 13:57:39 +08:00
district_id = get_district_id ( scanner , db_rule - > district ) ;
}
2019-01-05 17:11:20 +08:00
group_rule = ( struct Maat_group_inner_t * ) HASH_fetch_by_id ( scanner - > group_hash , db_rule - > group_id ) ;
2015-10-10 18:30:12 +08:00
if ( group_rule = = NULL )
{
group_rule = create_group_rule ( db_rule - > group_id ) ;
HASH_add_by_id ( scanner - > group_hash , db_rule - > group_id , group_rule ) ;
}
switch ( db_rule - > expr_type )
{
case EXPR_TYPE_AND :
for ( i = 0 , p = db_rule - > keywords ; ; i + + , p = NULL )
{
if ( i > = MAAT_MAX_EXPR_ITEM_NUM )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2016-08-30 10:40:05 +08:00
" Table %s region cfg %d too many expr. " , table - > table_name [ table - > updating_name ] , db_rule - > region_id ) ;
2015-10-10 18:30:12 +08:00
return - 1 ;
}
sub_key_array [ i ] = strtok_r_esc ( p , ' & ' , & saveptr ) ;
if ( sub_key_array [ i ] = = NULL )
{
break ;
}
2016-06-17 17:08:59 +08:00
sub_key_array [ i ] = str_unescape ( sub_key_array [ i ] ) ;
2015-10-10 18:30:12 +08:00
}
sub_expr_cnt = i ;
break ;
case EXPR_TYPE_OFFSET :
for ( i = 0 , p = db_rule - > keywords ; ; i + + , p = NULL )
{
if ( i > = MAAT_MAX_EXPR_ITEM_NUM )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2016-08-30 10:40:05 +08:00
" Table %s region cfg %d too many expr. " , table - > table_name [ table - > updating_name ] , db_rule - > region_id ) ;
2015-10-10 18:30:12 +08:00
return - 1 ;
}
sub_key_array [ i ] = strtok_r_esc ( p , ' & ' , & saveptr ) ;
if ( sub_key_array [ i ] = = NULL )
{
break ;
}
sscanf ( sub_key_array [ i ] , " %d-%d: " , & ( key_left_offset [ i ] ) , & ( key_right_offset [ i ] ) ) ;
2019-01-27 18:12:41 +06:00
if ( ! ( key_left_offset [ i ] > = 0 & & key_right_offset [ i ] > 0 & & key_left_offset [ i ] < = key_right_offset [ i ] ) )
2015-10-10 18:30:12 +08:00
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2016-08-30 10:40:05 +08:00
" Table %s region cfg %d invalid offset. " , table - > table_name [ table - > updating_name ] , db_rule - > region_id ) ;
2015-10-10 18:30:12 +08:00
return - 1 ;
}
sub_key_array [ i ] = ( char * ) memchr ( sub_key_array [ i ] , ' : ' , strlen ( sub_key_array [ i ] ) ) ;
if ( sub_key_array [ i ] = = NULL )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2019-01-27 18:12:41 +06:00
" Table %s region cfg %d invalid offset keyword format. " , table - > table_name [ table - > updating_name ] , db_rule - > region_id ) ;
2015-10-10 18:30:12 +08:00
return - 1 ;
}
sub_key_array [ i ] + + ; //jump over ':'
2016-06-17 17:08:59 +08:00
sub_key_array [ i ] = str_unescape ( sub_key_array [ i ] ) ;
2015-10-10 18:30:12 +08:00
}
sub_expr_cnt = i ;
break ;
case EXPR_TYPE_REGEX : //it's easy,no need to charset convert
expr_id = scanner - > exprid_generator + + ;
2017-08-07 17:08:52 +08:00
u_para = add_region_to_group ( group_rule , table - > table_id , db_rule - > region_id , district_id , expr_id , TABLE_TYPE_EXPR ) ;
2015-10-10 18:30:12 +08:00
if ( u_para = = NULL )
{
return - 1 ;
}
op_expr = create_op_expr ( expr_id
, 0
2016-12-28 18:06:34 +08:00
, u_para
, table - > table_id ) ;
2015-10-10 18:30:12 +08:00
for ( i = 0 , p = db_rule - > keywords ; ; i + + , p = NULL )
{
if ( i > = MAAT_MAX_EXPR_ITEM_NUM )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2016-08-30 10:40:05 +08:00
" Table %s region cfg %d too many expr. " , table - > table_name [ table - > updating_name ] , db_rule - > region_id ) ;
2015-10-10 18:30:12 +08:00
return - 1 ;
}
sub_key_array [ i ] = strtok_r_esc ( p , ' & ' , & saveptr ) ;
if ( sub_key_array [ i ] = = NULL )
{
break ;
}
2016-06-17 17:08:59 +08:00
sub_key_array [ i ] = str_unescape_and ( sub_key_array [ i ] ) ; //regex remain use str_unescape_and
2015-10-10 18:30:12 +08:00
p_rule = create_rs_str_rule ( make_sub_type ( table - > table_id , CHARSET_NONE , 0 )
, MATCH_METHOD_SUB //not care db_rule->match_method
, db_rule - > is_case_sensitive
, sub_key_array [ i ]
, strlen ( sub_key_array [ i ] )
, - 1
, - 1 ) ;
p_rule - > rule_type = RULETYPE_REG ;
op_expr_add_rule ( op_expr , p_rule ) ;
}
MESA_lqueue_join_tail ( scanner - > region_update_q , & op_expr , sizeof ( void * ) ) ;
return 0 ; //yes,we returned.
break ;
case EXPR_TYPE_STRING :
sub_expr_cnt = 1 ;
sub_key_array [ 0 ] = db_rule - > keywords ;
2016-06-17 17:08:59 +08:00
sub_key_array [ 0 ] = str_unescape ( sub_key_array [ 0 ] ) ;
2015-10-10 18:30:12 +08:00
break ;
default :
break ;
}
for ( k = 0 ; k < sub_expr_cnt ; k + + )
{
if ( strlen ( sub_key_array [ k ] ) = = 0 ) // keyword like "aa&&cc" or "aa&bb&" will cause strlen==0
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" Table %s region cfg %d has an empty sub string. " ,
2016-08-30 10:40:05 +08:00
table - > table_name [ table - > updating_name ] , db_rule - > region_id ) ;
2015-10-10 18:30:12 +08:00
//this sub string will jump over before iconv_convert
}
}
if ( db_rule - > is_hexbin = = FALSE )
{
for ( j = 0 ; j < MAX_CHARSET_NUM ; j + + )
{
2018-12-04 20:12:56 +08:00
dst_charset = expr_desc - > dst_charset [ j ] ;
2015-10-10 18:30:12 +08:00
if ( dst_charset = = CHARSET_NONE )
{
break ;
}
expr_id = scanner - > exprid_generator + + ;
2017-08-07 17:08:52 +08:00
u_para = add_region_to_group ( group_rule , table - > table_id , db_rule - > region_id , district_id , expr_id , table - > table_type ) ;
2015-10-10 18:30:12 +08:00
if ( u_para = = NULL ) //duplicate
{
return - 1 ;
}
op_expr = create_op_expr ( expr_id
, 0 //add
, u_para
2016-12-28 18:06:34 +08:00
, table - > table_id
2015-10-10 18:30:12 +08:00
) ;
for ( k = 0 ; k < sub_expr_cnt ; k + + )
{
if ( strlen ( sub_key_array [ k ] ) = = 0 )
{
continue ;
}
2016-04-03 12:29:41 +08:00
region_str_len = strlen ( sub_key_array [ k ] ) * 8 + 1 ; // 1 byte map to 8 bytes maximum, e.g. "ا" or "\u63221;"
2015-10-10 18:30:12 +08:00
region_string = ( char * ) calloc ( sizeof ( char ) , region_str_len ) ;
2018-12-04 20:12:56 +08:00
if ( expr_desc - > src_charset ! = dst_charset ) //need convert
2015-10-10 18:30:12 +08:00
{
2018-12-04 20:12:56 +08:00
ret = universal_charset_convert ( scanner , expr_desc - > src_charset , dst_charset ,
2015-10-10 18:30:12 +08:00
sub_key_array [ k ] , strlen ( sub_key_array [ k ] ) ,
region_string , & region_str_len ) ;
if ( ret < 0 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" Table %s region cfg %d charset convert from %s to %s failed. " , table - > table_name
, db_rule - > region_id
2018-12-04 20:12:56 +08:00
, CHARSET_STRING [ expr_desc - > src_charset ]
2015-10-10 18:30:12 +08:00
, CHARSET_STRING [ dst_charset ] ) ;
free ( region_string ) ;
2016-06-24 11:49:15 +08:00
op_expr - > convert_failed + + ;
2018-12-04 20:12:56 +08:00
expr_desc - > iconv_err_cnt + + ;
2016-06-24 11:49:15 +08:00
break ;
2015-10-10 18:30:12 +08:00
}
if ( region_str_len = = ( int ) strlen ( sub_key_array [ k ] ) & &
2016-06-03 15:10:49 +08:00
0 = = memcmp ( sub_key_array [ k ] , region_string , region_str_len ) )
2015-10-10 18:30:12 +08:00
{
2016-11-23 16:52:04 +08:00
op_expr - > no_effect_convert_cnt + + ;
2015-10-10 18:30:12 +08:00
}
}
else
{
memcpy ( region_string , sub_key_array [ k ] , strlen ( sub_key_array [ k ] ) ) ;
region_str_len = strlen ( sub_key_array [ k ] ) ;
}
2018-12-04 20:12:56 +08:00
p_rule = create_rs_str_rule ( make_sub_type ( table - > table_id , dst_charset , expr_desc - > do_charset_merge )
2015-10-10 18:30:12 +08:00
, db_rule - > match_method
, db_rule - > is_case_sensitive
, region_string
, region_str_len
, key_left_offset [ k ]
, key_right_offset [ k ] ) ;
op_expr_add_rule ( op_expr , p_rule ) ;
free ( region_string ) ;
region_string = NULL ;
}
2016-06-03 15:10:49 +08:00
//if each sub string's convert take no effect and src charset is one of the dst.
2016-06-24 11:49:15 +08:00
//if any sub expr convert failed
2018-12-04 20:12:56 +08:00
if ( ( TRUE = = expr_desc - > src_charset_in_dst & & op_expr - > no_effect_convert_cnt = = sub_expr_cnt ) | |
2016-06-24 11:49:15 +08:00
op_expr - > convert_failed > 0 )
2016-06-03 15:10:49 +08:00
{
2016-11-23 16:52:04 +08:00
scanner - > dedup_expr_num + + ;
2017-05-24 13:55:35 +08:00
cancel_last_region_from_group ( group_rule , db_rule - > region_id , op_expr - > p_expr - > expr_id ) ;
2016-06-03 15:10:49 +08:00
destroy_op_expr ( op_expr ) ;
2017-08-07 17:08:52 +08:00
//redeem expr_id
scanner - > exprid_generator - - ;
2016-06-03 15:10:49 +08:00
op_expr = NULL ;
}
else
{
MESA_lqueue_join_tail ( scanner - > region_update_q , & op_expr , sizeof ( void * ) ) ;
}
2015-10-10 18:30:12 +08:00
}
}
else
{
expr_id = scanner - > exprid_generator + + ;
2017-08-07 17:08:52 +08:00
u_para = add_region_to_group ( group_rule , table - > table_id , db_rule - > region_id , district_id , expr_id , table - > table_type ) ;
2015-10-10 18:30:12 +08:00
if ( u_para = = NULL )
{
return - 1 ;
}
2019-01-27 19:00:04 +06:00
op_expr = create_op_expr ( expr_id ,
0 , //add
u_para ,
table - > table_id
2015-10-10 18:30:12 +08:00
) ;
for ( k = 0 ; k < sub_expr_cnt ; k + + )
{
2019-01-27 19:00:04 +06:00
region_str_len = strlen ( sub_key_array [ k ] ) + 1 ;
region_string = ALLOC ( char , region_str_len ) ;
region_str_len = hex2bin ( sub_key_array [ k ] , strlen ( sub_key_array [ k ] ) , region_string , region_str_len ) ;
2015-10-10 18:30:12 +08:00
2019-01-27 19:00:04 +06:00
p_rule = create_rs_str_rule ( make_sub_type ( table - > table_id , dst_charset , expr_desc - > do_charset_merge ) ,
db_rule - > match_method ,
db_rule - > is_case_sensitive ,
region_string ,
region_str_len ,
key_left_offset [ k ] ,
key_right_offset [ k ] ) ;
op_expr_add_rule ( op_expr , p_rule ) ;
2015-10-10 18:30:12 +08:00
free ( region_string ) ;
region_string = NULL ;
}
MESA_lqueue_join_tail ( scanner - > region_update_q , & op_expr , sizeof ( void * ) ) ;
}
return 0 ;
}
2019-01-05 17:11:20 +08:00
int add_ip_rule ( struct Maat_table_desc * table , struct db_ip_rule_t * db_ip_rule , struct Maat_scanner_t * scanner , void * logger )
2015-10-10 18:30:12 +08:00
{
2019-01-05 17:11:20 +08:00
struct Maat_group_inner_t * group_rule = NULL ;
2015-10-10 18:30:12 +08:00
scan_rule_t * p_rule = NULL ;
struct op_expr_t * op_expr = NULL ;
2019-01-05 17:11:20 +08:00
struct Maat_group_inner_t * u_para = NULL ;
2016-02-11 13:57:39 +08:00
int expr_id = 0 , district_id = - 1 ;
2015-10-10 18:30:12 +08:00
2019-01-05 17:11:20 +08:00
group_rule = ( struct Maat_group_inner_t * ) HASH_fetch_by_id ( scanner - > group_hash , db_ip_rule - > group_id ) ;
2015-10-10 18:30:12 +08:00
if ( group_rule = = NULL )
{
group_rule = create_group_rule ( db_ip_rule - > group_id ) ;
HASH_add_by_id ( scanner - > group_hash , db_ip_rule - > group_id , group_rule ) ;
}
expr_id = scanner - > exprid_generator + + ;
2017-08-07 17:08:52 +08:00
u_para = add_region_to_group ( group_rule , table - > table_id , db_ip_rule - > region_id , district_id , expr_id , TABLE_TYPE_IP ) ;
2015-10-10 18:30:12 +08:00
if ( u_para = = NULL )
{
return - 1 ;
}
op_expr = create_op_expr ( expr_id
, 0
, u_para
2016-12-28 18:06:34 +08:00
, table - > table_id
2015-10-10 18:30:12 +08:00
) ;
p_rule = create_rs_ip_rule ( make_sub_type ( table - > table_id , CHARSET_NONE , 0 )
, db_ip_rule ) ;
op_expr_add_rule ( op_expr , p_rule ) ;
MESA_lqueue_join_tail ( scanner - > region_update_q , & op_expr , sizeof ( void * ) ) ;
return 0 ;
}
2019-01-05 17:11:20 +08:00
int add_intval_rule ( struct Maat_table_desc * table , struct db_intval_rule_t * intval_rule , struct Maat_scanner_t * scanner , void * logger )
2015-10-10 18:30:12 +08:00
{
2019-01-05 17:11:20 +08:00
struct Maat_group_inner_t * group_rule = NULL ;
2015-10-10 18:30:12 +08:00
scan_rule_t * p_rule = NULL ;
struct op_expr_t * op_expr = NULL ;
2019-01-05 17:11:20 +08:00
struct Maat_group_inner_t * u_para = NULL ;
2016-02-11 13:57:39 +08:00
int expr_id = 0 , district_id = - 1 ;
2019-01-05 17:11:20 +08:00
group_rule = ( struct Maat_group_inner_t * ) HASH_fetch_by_id ( scanner - > group_hash , intval_rule - > group_id ) ;
2015-10-10 18:30:12 +08:00
if ( group_rule = = NULL )
{
group_rule = create_group_rule ( intval_rule - > group_id ) ;
HASH_add_by_id ( scanner - > group_hash , intval_rule - > group_id , group_rule ) ;
}
expr_id = scanner - > exprid_generator + + ;
2017-08-07 17:08:52 +08:00
u_para = add_region_to_group ( group_rule , table - > table_id , intval_rule - > region_id , district_id , expr_id , TABLE_TYPE_INTERVAL ) ;
2015-10-10 18:30:12 +08:00
if ( u_para = = NULL )
{
return - 1 ;
}
op_expr = create_op_expr ( expr_id
, 0
, u_para
2016-12-28 18:06:34 +08:00
, table - > table_id
2015-10-10 18:30:12 +08:00
) ;
p_rule = create_rs_intval_rule ( make_sub_type ( table - > table_id , CHARSET_NONE , 0 )
, intval_rule ) ;
op_expr_add_rule ( op_expr , p_rule ) ;
MESA_lqueue_join_tail ( scanner - > region_update_q , & op_expr , sizeof ( void * ) ) ;
return 0 ;
}
2019-01-05 17:11:20 +08:00
int add_digest_rule ( struct Maat_table_desc * table , struct db_digest_rule_t * db_digest_rule , struct Maat_scanner_t * scanner , void * logger )
2015-11-10 18:29:42 +08:00
{
2019-01-05 17:11:20 +08:00
struct Maat_group_inner_t * group_rule = NULL ;
2015-11-10 18:29:42 +08:00
GIE_digest_t * digest_rule = NULL ;
2019-01-05 17:11:20 +08:00
struct Maat_group_inner_t * u_para = NULL ;
2018-12-04 23:26:59 +08:00
struct Maat_table_runtime * table_rt = scanner - > table_rt [ table - > table_id ] ;
2016-02-11 13:57:39 +08:00
int expr_id = 0 , district_id = - 1 ;
2015-11-10 18:29:42 +08:00
2019-01-05 17:11:20 +08:00
group_rule = ( struct Maat_group_inner_t * ) HASH_fetch_by_id ( scanner - > group_hash , db_digest_rule - > group_id ) ;
2015-11-10 18:29:42 +08:00
if ( group_rule = = NULL )
{
group_rule = create_group_rule ( db_digest_rule - > group_id ) ;
HASH_add_by_id ( scanner - > group_hash , db_digest_rule - > group_id , group_rule ) ;
}
expr_id = scanner - > exprid_generator + + ;
2017-08-16 18:23:09 +08:00
u_para = add_region_to_group ( group_rule , table - > table_id , db_digest_rule - > region_id , district_id , expr_id , TABLE_TYPE_DIGEST ) ;
2015-11-10 18:29:42 +08:00
if ( u_para = = NULL )
{
return - 1 ;
}
2017-08-07 17:08:52 +08:00
if ( table - > table_type = = TABLE_TYPE_SIMILARITY )
{
db_digest_rule - > digest_string = str_unescape ( db_digest_rule - > digest_string ) ;
}
digest_rule = create_digest_rule ( expr_id , GIE_INSERT_OPT
2015-11-10 18:29:42 +08:00
, db_digest_rule - > digest_string
, db_digest_rule - > confidence_degree
, group_rule ) ;
2018-12-04 23:26:59 +08:00
MESA_lqueue_join_tail ( table_rt - > similar . update_q , & digest_rule , sizeof ( void * ) ) ;
2017-08-15 09:14:44 +08:00
scanner - > gie_total_q_size + + ;
2015-11-10 18:29:42 +08:00
return 0 ;
}
2019-01-05 17:11:20 +08:00
int del_region_rule ( struct Maat_table_desc * table , int region_id , int group_id , int rule_type , struct Maat_scanner_t * maat_scanner , void * logger )
2015-10-10 18:30:12 +08:00
{
int i = 0 ;
unsigned int expr_id [ MAAT_MAX_EXPR_ITEM_NUM * MAX_CHARSET_NUM ] = { 0 } ;
int expr_num = 0 ;
2019-01-05 17:11:20 +08:00
struct Maat_group_inner_t * group_rule = NULL ;
2015-10-10 18:30:12 +08:00
struct op_expr_t * op_expr = NULL ;
2015-11-10 18:29:42 +08:00
GIE_digest_t * digest_rule = NULL ;
2019-01-05 17:11:20 +08:00
group_rule = ( struct Maat_group_inner_t * ) HASH_fetch_by_id ( maat_scanner - > group_hash , group_id ) ;
2015-10-10 18:30:12 +08:00
if ( group_rule = = NULL )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" update error,table %s group id %u not exist,while delete region id %d. "
2016-08-30 10:40:05 +08:00
, table - > table_name [ table - > updating_name ]
2015-10-10 18:30:12 +08:00
, group_id
, region_id ) ;
return - 1 ;
}
assert ( group_id = = group_rule - > group_id ) ;
expr_num = del_region_from_group ( group_rule , region_id , expr_id , sizeof ( expr_id ) / sizeof ( unsigned int ) ) ;
if ( expr_num = = 0 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
" region delete error,id %d table %s region not in group id %d. "
, region_id
2016-08-30 10:40:05 +08:00
, table - > table_name [ table - > updating_name ]
2015-10-10 18:30:12 +08:00
, group_id ) ;
return - 1 ;
}
2015-11-10 18:29:42 +08:00
switch ( table - > table_type )
2015-10-10 18:30:12 +08:00
{
2015-11-10 18:29:42 +08:00
case TABLE_TYPE_IP :
case TABLE_TYPE_EXPR :
2016-12-30 18:07:19 +08:00
case TABLE_TYPE_EXPR_PLUS :
2017-08-07 17:08:52 +08:00
case TABLE_TYPE_INTERVAL :
2015-11-10 18:29:42 +08:00
for ( i = 0 ; i < expr_num ; i + + )
{
2016-12-28 18:06:34 +08:00
op_expr = create_op_expr ( expr_id [ i ] , 1 , NULL , table - > table_id ) ; //del expr
2016-12-30 18:07:19 +08:00
op_expr - > rule_type = rule_type ;
2015-11-10 18:29:42 +08:00
MESA_lqueue_join_tail ( maat_scanner - > region_update_q , & op_expr , sizeof ( void * ) ) ;
}
break ;
2017-08-07 17:08:52 +08:00
case TABLE_TYPE_SIMILARITY :
2015-11-10 18:29:42 +08:00
case TABLE_TYPE_DIGEST :
assert ( expr_num = = 1 ) ;
2017-08-07 17:08:52 +08:00
digest_rule = create_digest_rule ( expr_id [ 0 ] , GIE_DELETE_OPT //del digest
2015-11-10 18:29:42 +08:00
, NULL
, 0
, NULL ) ;
2018-12-04 20:12:56 +08:00
MESA_lqueue_join_tail ( maat_scanner - > table_rt [ table - > table_id ] - > similar . update_q , & digest_rule , sizeof ( void * ) ) ;
2017-08-15 09:14:44 +08:00
maat_scanner - > gie_total_q_size + + ;
2015-11-10 18:29:42 +08:00
break ;
default :
assert ( 0 ) ;
break ;
2015-10-10 18:30:12 +08:00
}
if ( group_rule - > region_cnt = = 0 & & group_rule - > region_cnt = = 0 )
{
HASH_delete_by_id ( maat_scanner - > group_hash , group_id ) ;
garbage_bagging ( GARBAGE_GROUP_RULE , group_rule , maat_scanner - > tomb_ref ) ;
2017-12-21 09:36:13 +08:00
2015-10-10 18:30:12 +08:00
}
2018-12-04 20:12:56 +08:00
return 0 ;
2015-10-10 18:30:12 +08:00
}
2019-01-05 17:11:20 +08:00
int add_group_rule ( struct Maat_table_desc * table , struct db_group_rule_t * db_group_rule , struct Maat_scanner_t * scanner , void * logger )
2015-10-10 18:30:12 +08:00
{
2019-01-05 17:11:20 +08:00
struct Maat_group_inner_t * group_rule = NULL ;
struct Maat_compile_inner_t * compile_rule = NULL ;
2015-10-10 18:30:12 +08:00
int ret = 0 ;
2019-01-05 17:11:20 +08:00
group_rule = ( struct Maat_group_inner_t * ) HASH_fetch_by_id ( scanner - > group_hash , db_group_rule - > group_id ) ;
2015-10-10 18:30:12 +08:00
if ( group_rule = = NULL )
{
group_rule = create_group_rule ( db_group_rule - > group_id ) ;
2017-08-07 17:08:52 +08:00
group_rule - > table_id = table - > table_id ;
2019-01-05 15:51:08 +08:00
ret = HASH_add_by_id ( scanner - > group_hash , db_group_rule - > group_id , group_rule ) ;
2015-10-10 18:30:12 +08:00
assert ( ret > = 0 ) ;
}
2019-01-05 17:11:20 +08:00
compile_rule = ( struct Maat_compile_inner_t * ) HASH_fetch_by_id ( scanner - > compile_hash , db_group_rule - > compile_id ) ;
2015-10-10 18:30:12 +08:00
if ( compile_rule = = NULL )
{
compile_rule = create_compile_rule ( db_group_rule - > compile_id ) ;
2019-01-05 15:51:08 +08:00
ret = HASH_add_by_id ( scanner - > compile_hash , db_group_rule - > compile_id , compile_rule ) ;
2015-10-10 18:30:12 +08:00
assert ( ret > = 0 ) ;
}
2019-01-05 15:51:08 +08:00
ret = add_group_to_compile ( compile_rule , group_rule , db_group_rule - > not_flag ) ;
2015-10-10 18:30:12 +08:00
if ( ret < 0 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2018-06-17 20:03:17 +08:00
" update error,add group: %s %d to compile rule %d error, compile rule is full or duplicate group. "
2016-08-30 10:40:05 +08:00
, table - > table_name [ table - > updating_name ]
2015-10-10 18:30:12 +08:00
, db_group_rule - > group_id
, db_group_rule - > compile_id ) ;
return - 1 ;
}
return 0 ;
}
2019-01-05 17:11:20 +08:00
void del_group_rule ( struct Maat_table_desc * table , struct db_group_rule_t * db_group_rule , struct Maat_scanner_t * scanner , void * logger )
2015-10-10 18:30:12 +08:00
{
2019-01-05 17:11:20 +08:00
struct Maat_compile_inner_t * compile_rule = NULL ;
struct Maat_group_inner_t * group_rule = NULL ;
compile_rule = ( struct Maat_compile_inner_t * ) HASH_fetch_by_id ( scanner - > compile_hash , db_group_rule - > compile_id ) ;
2015-10-10 18:30:12 +08:00
if ( compile_rule = = NULL )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" update error,delete %s group rule error : compile id %d does not exisit. "
2016-08-30 10:40:05 +08:00
, table - > table_name [ table - > updating_name ]
2015-10-10 18:30:12 +08:00
, db_group_rule - > compile_id ) ;
return ;
}
group_rule = del_group_from_compile ( compile_rule , db_group_rule - > group_id ) ;
if ( group_rule = = NULL )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" update error,delete %s group rule error : group id %d not in compile id %d. "
2016-08-30 10:40:05 +08:00
, table - > table_name [ table - > updating_name ]
2015-10-10 18:30:12 +08:00
, db_group_rule - > group_id
, db_group_rule - > compile_id ) ;
return ;
}
2018-12-21 20:16:22 +06:00
if ( compile_rule - > group_cnt = = 0 & & compile_rule - > is_valid = = 0 )
2015-10-10 18:30:12 +08:00
{
HASH_delete_by_id ( scanner - > compile_hash , db_group_rule - > compile_id ) ;
garbage_bagging ( GARBAGE_COMPILE_RULE , compile_rule , scanner - > tomb_ref ) ;
}
2016-11-21 15:28:49 +08:00
//Directly delete group id will not destroyp group_rule,it 'll be destroyed when delete this group's last region.
2015-10-10 18:30:12 +08:00
if ( group_rule - > ref_cnt = = 0 & & group_rule - > region_cnt = = 0 )
{
2017-12-21 09:36:13 +08:00
//Directly delete table %s group id %d, do this when delete its last region.
2015-10-10 18:30:12 +08:00
}
return ;
}
2019-01-05 17:11:20 +08:00
int add_compile_rule ( struct Maat_table_desc * table , struct db_compile_rule_t * db_compile_rule , struct Maat_scanner_t * scanner , void * logger )
2015-10-10 18:30:12 +08:00
{
2019-01-05 17:11:20 +08:00
struct Maat_compile_inner_t * compile_rule = NULL ;
2015-10-10 18:30:12 +08:00
struct _head_Maat_rule_t * p_maat_rule_head = & ( db_compile_rule - > m_rule_head ) ;
2018-11-07 17:12:06 +08:00
int i = 0 ;
2019-01-05 17:11:20 +08:00
compile_rule = ( struct Maat_compile_inner_t * ) HASH_fetch_by_id ( scanner - > compile_hash , p_maat_rule_head - > config_id ) ;
2015-10-10 18:30:12 +08:00
if ( compile_rule = = NULL )
{
compile_rule = create_compile_rule ( p_maat_rule_head - > config_id ) ;
HASH_add_by_id ( scanner - > compile_hash , p_maat_rule_head - > config_id , compile_rule ) ;
}
2018-11-07 17:12:06 +08:00
else
2015-10-10 18:30:12 +08:00
{
2018-11-07 17:12:06 +08:00
if ( compile_rule - > db_c_rule ! = NULL ) //duplicate config
{
return - 1 ;
}
2015-10-10 18:30:12 +08:00
}
2018-11-07 17:12:06 +08:00
pthread_rwlock_wrlock ( & ( compile_rule - > rwlock ) ) ;
compile_rule - > ref_table = table ;
2015-10-10 18:30:12 +08:00
compile_rule - > db_c_rule = db_compile_rule ;
2018-12-04 20:12:56 +08:00
for ( i = 0 ; i < table - > compile . ex_data_num ; i + + )
2018-11-07 17:12:06 +08:00
{
2018-12-04 20:12:56 +08:00
compile_rule - > ads [ i ] = rule_ex_data_new ( p_maat_rule_head , db_compile_rule - > service_defined , table - > compile . ex_desc + i ) ;
2018-11-07 17:12:06 +08:00
}
compile_rule - > is_valid = 1 ;
pthread_rwlock_unlock ( & ( compile_rule - > rwlock ) ) ;
2015-10-10 18:30:12 +08:00
return 0 ;
}
2019-01-05 17:11:20 +08:00
int del_compile_rule ( struct Maat_table_desc * table , struct db_compile_rule_t * db_compile_rule , struct Maat_scanner_t * scanner , void * logger )
2015-10-10 18:30:12 +08:00
{
2019-01-05 17:11:20 +08:00
struct Maat_compile_inner_t * compile_rule = NULL ;
compile_rule = ( struct Maat_compile_inner_t * ) HASH_fetch_by_id ( scanner - > compile_hash , db_compile_rule - > m_rule_head . config_id ) ;
2015-10-10 18:30:12 +08:00
if ( compile_rule = = NULL )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" update error,delete %s compile rule error : congfig id %d does not exisit. "
2016-08-30 10:40:05 +08:00
, table - > table_name [ table - > updating_name ]
2015-10-10 18:30:12 +08:00
, db_compile_rule - > m_rule_head . config_id ) ;
return - 1 ;
}
pthread_rwlock_wrlock ( & ( compile_rule - > rwlock ) ) ;
2018-11-07 17:12:06 +08:00
compile_rule - > is_valid = 0 ;
2015-10-10 18:30:12 +08:00
pthread_rwlock_unlock ( & ( compile_rule - > rwlock ) ) ;
if ( compile_rule - > group_cnt = = 0 )
{
HASH_delete_by_id ( scanner - > compile_hash , compile_rule - > compile_id ) ;
garbage_bagging ( GARBAGE_COMPILE_RULE , compile_rule , scanner - > tomb_ref ) ;
}
return 1 ;
}
2019-01-05 17:11:20 +08:00
void update_group_rule ( struct Maat_table_desc * table , const char * table_line , struct Maat_scanner_t * scanner , void * logger )
2015-10-10 18:30:12 +08:00
{
struct db_group_rule_t db_group_rule ;
2018-12-04 23:26:59 +08:00
struct Maat_table_runtime * table_rt = scanner - > table_rt [ table - > table_id ] ;
2015-10-10 18:30:12 +08:00
int ret = 0 ;
2019-01-07 13:35:26 +06:00
memset ( & db_group_rule , 0 , sizeof ( db_group_rule ) ) ;
2019-01-05 15:51:08 +08:00
ret = sscanf ( table_line , " %d \t %d \t %d \t %d " , & ( db_group_rule . group_id ) ,
& ( db_group_rule . compile_id ) ,
& ( db_group_rule . is_valid ) ,
& ( db_group_rule . not_flag ) ) ;
2019-01-18 12:18:58 +06:00
if ( ret ! = 3 & & ret ! = 4 )
2018-11-14 18:36:09 +08:00
{
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
2019-01-05 15:51:08 +08:00
" update error,invalid format of group table %s:%s " ,
table - > table_name [ table - > updating_name ] , table_line ) ;
2018-11-14 18:36:09 +08:00
table - > udpate_err_cnt + + ;
return ;
}
2019-01-18 12:18:58 +06:00
if ( db_group_rule . not_flag ! = 1 ) //compatible to old format that 4th column is op_time
{
db_group_rule . not_flag = 0 ;
}
2015-10-10 18:30:12 +08:00
if ( db_group_rule . is_valid = = FALSE )
{
2019-01-05 15:51:08 +08:00
del_group_rule ( table , & db_group_rule , scanner , logger ) ;
2016-12-15 12:05:48 +08:00
//leave no trace when compatible_group_update calling
if ( table - > table_type = = TABLE_TYPE_GROUP )
{
2018-12-04 23:26:59 +08:00
table_rt - > origin_rule_num - - ;
2019-01-05 15:51:08 +08:00
if ( db_group_rule . not_flag )
{
table_rt - > group . not_flag_group - - ;
}
2016-12-15 12:05:48 +08:00
}
2015-10-10 18:30:12 +08:00
}
else
{
2019-01-05 15:51:08 +08:00
ret = add_group_rule ( table , & db_group_rule , scanner , logger ) ;
2015-10-10 18:30:12 +08:00
if ( ret < 0 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
2019-01-05 15:51:08 +08:00
" duplicate config of group table %s group_id %d compile_id %d. " , table - > table_name [ 0 ] ,
db_group_rule . group_id ,
db_group_rule . compile_id ) ;
2015-10-10 18:30:12 +08:00
}
else
{
//no need to free db_group_rule,it was saved in scanner->compile_hash
2016-12-15 12:05:48 +08:00
if ( table - > table_type = = TABLE_TYPE_GROUP )
{
2018-12-04 23:26:59 +08:00
table_rt - > origin_rule_num + + ;
2019-01-05 15:51:08 +08:00
if ( db_group_rule . not_flag )
{
table_rt - > group . not_flag_group + + ;
}
2016-12-15 12:05:48 +08:00
}
2015-10-10 18:30:12 +08:00
}
}
return ;
}
2019-01-05 17:11:20 +08:00
void compatible_group_udpate ( struct Maat_table_desc * table , int region_id , int compile_id , int is_valid , struct Maat_scanner_t * scanner , void * logger )
2015-10-10 18:30:12 +08:00
{
char virtual_group_line [ 256 ] ;
snprintf ( virtual_group_line , sizeof ( virtual_group_line ) ,
" %d \t %d \t %d " , region_id , compile_id , is_valid ) ;
update_group_rule ( table , virtual_group_line , scanner , logger ) ;
return ;
}
2019-01-05 17:11:20 +08:00
void update_expr_rule ( struct Maat_table_desc * table , const char * table_line , struct Maat_scanner_t * scanner , void * logger , int group_mode_on )
2015-10-10 18:30:12 +08:00
{
2018-11-27 12:55:52 +08:00
struct db_str_rule_t * maat_str_rule = ALLOC ( struct db_str_rule_t , 1 ) ;
2016-12-30 18:07:19 +08:00
int ret = 0 , db_hexbin = 0 , rule_type = 0 ;
2018-12-04 20:12:56 +08:00
const struct expr_table_desc * expr_desc = & ( table - > expr ) ;
2018-12-04 23:26:59 +08:00
struct Maat_table_runtime * table_rt = scanner - > table_rt [ table - > table_id ] ;
2016-02-11 13:57:39 +08:00
switch ( table - > table_type )
2015-10-10 18:30:12 +08:00
{
2016-02-11 13:57:39 +08:00
case TABLE_TYPE_EXPR :
ret = sscanf ( table_line , " %d \t %d \t %s \t %d \t %d \t %d \t %d " , & ( maat_str_rule - > region_id )
, & ( maat_str_rule - > group_id )
, maat_str_rule - > keywords
, ( int * ) & ( maat_str_rule - > expr_type )
, ( int * ) & ( maat_str_rule - > match_method )
, & db_hexbin
, & ( maat_str_rule - > is_valid ) ) ;
if ( ret ! = 7 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2016-11-16 17:30:32 +08:00
" abandon config: invalid format of expr table %s:%s " , table - > table_name [ table - > updating_name ] , table_line ) ;
2016-02-11 13:57:39 +08:00
free ( maat_str_rule ) ;
maat_str_rule = NULL ;
2016-10-08 11:40:57 +08:00
table - > udpate_err_cnt + + ;
2016-02-11 13:57:39 +08:00
return ;
}
break ;
case TABLE_TYPE_EXPR_PLUS :
ret = sscanf ( table_line , " %d \t %d \t %s \t %s \t %d \t %d \t %d \t %d " , & ( maat_str_rule - > region_id )
, & ( maat_str_rule - > group_id )
, maat_str_rule - > district
, maat_str_rule - > keywords
, ( int * ) & ( maat_str_rule - > expr_type )
, ( int * ) & ( maat_str_rule - > match_method )
, & db_hexbin
, & ( maat_str_rule - > is_valid ) ) ;
if ( ret ! = 8 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2016-11-16 17:30:32 +08:00
" abandon config: invalid format of expr_plus table %s:%s " , table - > table_name [ table - > updating_name ] , table_line ) ;
2016-02-11 13:57:39 +08:00
free ( maat_str_rule ) ;
maat_str_rule = NULL ;
2016-10-08 11:40:57 +08:00
table - > udpate_err_cnt + + ;
2016-02-11 13:57:39 +08:00
return ;
}
break ;
default :
assert ( 0 ) ;
break ;
2015-10-10 18:30:12 +08:00
}
switch ( db_hexbin )
{
case 0 :
maat_str_rule - > is_hexbin = FALSE ;
maat_str_rule - > is_case_sensitive = FALSE ;
break ;
case 1 :
maat_str_rule - > is_hexbin = TRUE ;
maat_str_rule - > is_case_sensitive = FALSE ;
break ;
case 2 :
maat_str_rule - > is_hexbin = FALSE ;
maat_str_rule - > is_case_sensitive = TRUE ;
break ;
default :
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2016-12-19 10:14:27 +08:00
" abandon config %d:update error,invalid hexbin value of expr table %s:%s "
, maat_str_rule - > region_id
2016-08-30 10:40:05 +08:00
, table - > table_name [ table - > updating_name ] , table_line ) ;
2016-10-08 11:40:57 +08:00
table - > udpate_err_cnt + + ;
2015-10-10 18:30:12 +08:00
goto error_out ;
}
2016-12-26 17:20:59 +08:00
if ( ! is_valid_match_method ( maat_str_rule - > match_method ) )
2016-12-19 10:14:27 +08:00
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" abandon config %d:update error,invalid match method=%d in expr table %s:%s "
, maat_str_rule - > region_id
, maat_str_rule - > match_method
, table - > table_name [ table - > updating_name ] , table_line ) ;
table - > udpate_err_cnt + + ;
goto error_out ;
}
2016-12-26 17:20:59 +08:00
if ( ! is_valid_expr_type ( maat_str_rule - > expr_type ) )
2016-12-19 10:14:27 +08:00
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" abandon config %d:update error,invalid expr type=%d in expr table %s:%s "
, maat_str_rule - > region_id
, maat_str_rule - > expr_type
, table - > table_name [ table - > updating_name ] , table_line ) ;
table - > udpate_err_cnt + + ;
goto error_out ;
}
2015-10-10 18:30:12 +08:00
ret = sync_region ( scanner - > region_hash
, maat_str_rule - > region_id
2016-08-30 10:40:05 +08:00
, table - > table_name [ table - > updating_name ]
2015-10-10 18:30:12 +08:00
, maat_str_rule - > is_valid , logger ) ;
if ( ret < 0 )
{
2016-10-08 11:40:57 +08:00
table - > udpate_err_cnt + + ;
2015-10-10 18:30:12 +08:00
goto error_out ;
}
if ( group_mode_on = = FALSE ) //for compatible old version
{
compatible_group_udpate ( table
, maat_str_rule - > region_id
, maat_str_rule - > group_id
, maat_str_rule - > is_valid
, scanner
, logger ) ;
maat_str_rule - > group_id = maat_str_rule - > region_id ;
}
if ( maat_str_rule - > is_valid = = FALSE )
{
2016-12-30 18:07:19 +08:00
if ( maat_str_rule - > expr_type = = EXPR_TYPE_REGEX )
{
rule_type = RULETYPE_REG ;
}
else
{
rule_type = RULETYPE_STR ;
}
ret = del_region_rule ( table
, maat_str_rule - > region_id , maat_str_rule - > group_id , rule_type
, scanner , logger ) ;
2018-12-04 20:12:56 +08:00
if ( ret < 0 )
2015-10-10 18:30:12 +08:00
{
2018-12-04 20:12:56 +08:00
table - > udpate_err_cnt + + ;
2015-10-10 18:30:12 +08:00
}
2016-10-08 11:40:57 +08:00
else
{
2018-12-04 23:26:59 +08:00
table_rt - > origin_rule_num - - ;
2016-10-08 11:40:57 +08:00
}
2015-10-10 18:30:12 +08:00
}
else
{
2016-11-16 17:30:32 +08:00
if ( maat_str_rule - > expr_type = = EXPR_TYPE_AND
& & maat_str_rule - > match_method ! = MATCH_METHOD_SUB )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" table %s region cfg %d is EXPR_TYPE_AND,but match method is not MATCH_METHOD_SUB,force fixed. " ,
table - > table_name [ table - > updating_name ] , maat_str_rule - > region_id ) ;
maat_str_rule - > match_method = MATCH_METHOD_SUB ;
}
if ( maat_str_rule - > expr_type = = EXPR_TYPE_STRING
2018-12-04 20:12:56 +08:00
& & expr_desc - > quick_expr_switch = = 1
2016-11-16 17:30:32 +08:00
& & maat_str_rule - > match_method ! = MATCH_METHOD_SUB )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" abandon config: table %s scan mode is quickon, only support MATCH_METHOD_SUB, conflict with match method of region %d. " ,
table - > table_name [ table - > updating_name ] , maat_str_rule - > region_id ) ;
table - > udpate_err_cnt + + ;
goto error_out ;
}
2015-10-10 18:30:12 +08:00
ret = add_expr_rule ( table , maat_str_rule , scanner , logger ) ;
if ( ret < 0 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
2016-08-30 10:40:05 +08:00
" duplicate config of expr table %s region_id=%d "
, table - > table_name [ table - > updating_name ] , maat_str_rule - > region_id ) ;
2016-10-08 11:40:57 +08:00
table - > udpate_err_cnt + + ;
2015-10-10 18:30:12 +08:00
}
else
{
2018-12-04 23:26:59 +08:00
table_rt - > origin_rule_num + + ;
2015-10-10 18:30:12 +08:00
}
2018-12-04 20:12:56 +08:00
2015-10-10 18:30:12 +08:00
}
error_out :
free ( maat_str_rule ) ;
maat_str_rule = NULL ;
}
2019-01-05 17:11:20 +08:00
void update_ip_rule ( struct Maat_table_desc * table , const char * table_line , struct Maat_scanner_t * scanner , void * logger , int group_mode_on )
2015-10-10 18:30:12 +08:00
{
struct db_ip_rule_t * ip_rule = ( struct db_ip_rule_t * ) calloc ( sizeof ( struct db_ip_rule_t ) , 1 ) ;
char src_ip [ 40 ] , mask_src_ip [ 40 ] , dst_ip [ 40 ] , mask_dst_ip [ 40 ] ;
2018-12-04 23:26:59 +08:00
struct Maat_table_runtime * table_rt = scanner - > table_rt [ table - > table_id ] ;
2015-10-10 18:30:12 +08:00
unsigned short i_src_port , i_sport_mask , i_dst_port , i_dport_mask ;
int protocol = 0 , direction = 0 ;
2016-12-30 18:07:19 +08:00
int ret = 0 , rule_type = 0 ;
2015-10-10 18:30:12 +08:00
int ret_array [ 8 ] = { 1 } , i = 0 ;
ret = sscanf ( table_line , " %d \t %d \t %d \t %s \t %s \t %hu \t %hu \t %s \t %s \t %hu \t %hu \t %d \t %d \t %d "
, & ( ip_rule - > region_id )
, & ( ip_rule - > group_id )
, & ( ip_rule - > addr_type )
, src_ip
, mask_src_ip
, & i_src_port
, & i_sport_mask
, dst_ip
, mask_dst_ip
, & i_dst_port
, & i_dport_mask
, & protocol
, & direction
, & ( ip_rule - > is_valid ) ) ;
if ( ret ! = 14 | | ( ip_rule - > addr_type ! = 4 & & ip_rule - > addr_type ! = 6 )
| | protocol > 65535 | | protocol < 0
| | ( direction ! = 0 & & direction ! = 1 ) )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2016-08-30 10:40:05 +08:00
" update error,invalid format of ip table %s:%s "
, table - > table_name [ table - > updating_name ] , table_line ) ;
2016-10-08 11:40:57 +08:00
table - > udpate_err_cnt + + ;
2015-10-10 18:30:12 +08:00
goto error_out ;
}
if ( ip_rule - > addr_type = = 4 )
{
ret_array [ 0 ] = inet_pton ( AF_INET , src_ip , & ( ip_rule - > ipv4_rule . saddr ) ) ;
ip_rule - > ipv4_rule . saddr = ntohl ( ip_rule - > ipv4_rule . saddr ) ;
ret_array [ 1 ] = inet_pton ( AF_INET , mask_src_ip , & ( ip_rule - > ipv4_rule . smask ) ) ;
ip_rule - > ipv4_rule . smask = ntohl ( ip_rule - > ipv4_rule . smask ) ;
ret_array [ 2 ] = inet_pton ( AF_INET , dst_ip , & ( ip_rule - > ipv4_rule . daddr ) ) ;
ip_rule - > ipv4_rule . daddr = ntohl ( ip_rule - > ipv4_rule . daddr ) ;
ret_array [ 3 ] = inet_pton ( AF_INET , mask_dst_ip , & ( ip_rule - > ipv4_rule . dmask ) ) ;
ip_rule - > ipv4_rule . dmask = ntohl ( ip_rule - > ipv4_rule . dmask ) ;
ip_rule - > ipv4_rule . min_sport = i_src_port & i_sport_mask ;
ip_rule - > ipv4_rule . max_sport = ( i_src_port & i_sport_mask ) + ( ~ i_sport_mask ) ;
ip_rule - > ipv4_rule . min_dport = i_dst_port & i_dport_mask ;
ip_rule - > ipv4_rule . max_dport = ( i_dst_port & i_dport_mask ) + ( ~ i_dport_mask ) ;
ip_rule - > ipv4_rule . proto = protocol ;
ip_rule - > ipv4_rule . direction = direction ;
2016-12-30 18:07:19 +08:00
rule_type = RULETYPE_IPv4 ;
2015-10-10 18:30:12 +08:00
}
else
{
ret_array [ 0 ] = inet_pton ( AF_INET6 , src_ip , & ( ip_rule - > ipv6_rule . saddr ) ) ;
ipv6_ntoh ( ip_rule - > ipv6_rule . saddr ) ;
2016-06-08 13:21:23 +08:00
ret_array [ 1 ] = inet_pton ( AF_INET6 , mask_src_ip , & ( ip_rule - > ipv6_rule . smask ) ) ;
ipv6_ntoh ( ip_rule - > ipv6_rule . smask ) ;
2015-10-10 18:30:12 +08:00
ret_array [ 2 ] = inet_pton ( AF_INET6 , dst_ip , & ( ip_rule - > ipv6_rule . daddr ) ) ;
ipv6_ntoh ( ip_rule - > ipv6_rule . daddr ) ;
2016-06-08 13:21:23 +08:00
ret_array [ 3 ] = inet_pton ( AF_INET6 , mask_dst_ip , & ( ip_rule - > ipv6_rule . dmask ) ) ;
ipv6_ntoh ( ip_rule - > ipv6_rule . dmask ) ;
2015-10-10 18:30:12 +08:00
ip_rule - > ipv6_rule . min_sport = i_src_port & i_sport_mask ;
ip_rule - > ipv6_rule . max_sport = ( i_src_port & i_sport_mask ) + ( ~ i_sport_mask ) ;
ip_rule - > ipv6_rule . min_dport = i_dst_port & i_dport_mask ;
ip_rule - > ipv6_rule . max_dport = ( i_dst_port & i_dport_mask ) + ~ ( i_dport_mask ) ;
ip_rule - > ipv6_rule . proto = protocol ;
ip_rule - > ipv6_rule . direction = direction ;
2016-12-30 18:07:19 +08:00
rule_type = RULETYPE_IPv6 ;
2015-10-10 18:30:12 +08:00
}
for ( i = 0 ; i < 4 ; i + + )
{
if ( ret_array [ i ] < = 0 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2016-08-30 10:40:05 +08:00
" update error,invalid format of ip table %s:%s "
, table - > table_name [ table - > updating_name ] , table_line ) ;
2016-10-08 11:40:57 +08:00
table - > udpate_err_cnt + + ;
2015-10-10 18:30:12 +08:00
goto error_out ;
}
}
ret = sync_region ( scanner - > region_hash
, ip_rule - > region_id
2016-08-30 10:40:05 +08:00
, table - > table_name [ table - > updating_name ]
2015-10-10 18:30:12 +08:00
, ip_rule - > is_valid , logger ) ;
if ( ret < 0 )
{
2016-10-08 11:40:57 +08:00
table - > udpate_err_cnt + + ;
2015-10-10 18:30:12 +08:00
goto error_out ;
}
if ( group_mode_on = = FALSE ) //for compatible old version
{
compatible_group_udpate ( table
, ip_rule - > region_id
, ip_rule - > group_id
, ip_rule - > is_valid
, scanner
, logger ) ;
ip_rule - > group_id = ip_rule - > region_id ;
}
if ( ip_rule - > is_valid = = FALSE )
{
2016-12-30 18:07:19 +08:00
ret = del_region_rule ( table
, ip_rule - > region_id , ip_rule - > group_id , rule_type
, scanner , logger ) ;
2018-12-04 20:12:56 +08:00
if ( ret < 0 )
2015-10-10 18:30:12 +08:00
{
2018-12-04 20:12:56 +08:00
table - > udpate_err_cnt + + ;
2015-10-10 18:30:12 +08:00
}
2016-10-08 11:40:57 +08:00
else
{
2018-12-04 23:26:59 +08:00
table_rt - > origin_rule_num - - ;
2016-10-08 11:40:57 +08:00
}
2015-10-10 18:30:12 +08:00
}
else
{
ret = add_ip_rule ( table , ip_rule , scanner , logger ) ;
if ( ret < 0 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
2016-08-30 10:40:05 +08:00
" duplicate config of ip table %s config_id=%d "
, table - > table_name [ table - > updating_name ] , ip_rule - > region_id ) ;
2016-10-08 11:40:57 +08:00
table - > udpate_err_cnt + + ;
2015-10-10 18:30:12 +08:00
}
else
{
2018-12-04 23:26:59 +08:00
table_rt - > origin_rule_num + + ;
2015-10-10 18:30:12 +08:00
}
2018-12-04 20:12:56 +08:00
2015-10-10 18:30:12 +08:00
}
error_out :
free ( ip_rule ) ;
ip_rule = NULL ;
}
2019-01-05 17:11:20 +08:00
void update_intval_rule ( struct Maat_table_desc * table , const char * table_line , struct Maat_scanner_t * scanner , void * logger , int group_mode_on )
2015-10-10 18:30:12 +08:00
{
2018-12-04 20:12:56 +08:00
struct db_intval_rule_t * intval_rule = ALLOC ( struct db_intval_rule_t , 1 ) ;
2018-12-04 23:26:59 +08:00
struct Maat_table_runtime * table_rt = scanner - > table_rt [ table - > table_id ] ;
2015-10-10 18:30:12 +08:00
int ret = 0 ;
ret = sscanf ( table_line , " %d \t %d \t %u \t %u \t %d " , & ( intval_rule - > region_id )
, & ( intval_rule - > group_id )
, & ( intval_rule - > intval . lb )
, & ( intval_rule - > intval . ub )
, & ( intval_rule - > is_valid ) ) ;
if ( ret ! = 5 | | intval_rule - > intval . ub < intval_rule - > intval . lb )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2016-08-30 10:40:05 +08:00
" update error,invalid format of interval table %s:%s "
, table - > table_name [ table - > updating_name ] , table_line ) ;
2016-10-08 11:40:57 +08:00
table - > udpate_err_cnt + + ;
2015-10-10 18:30:12 +08:00
goto error_out ;
}
ret = sync_region ( scanner - > region_hash
, intval_rule - > region_id
2016-08-30 10:40:05 +08:00
, table - > table_name [ table - > updating_name ]
2015-10-10 18:30:12 +08:00
, intval_rule - > is_valid , logger ) ;
if ( ret < 0 )
{
2016-10-08 11:40:57 +08:00
table - > udpate_err_cnt + + ;
2015-10-10 18:30:12 +08:00
goto error_out ;
}
if ( group_mode_on = = FALSE ) //for compatible old version
{
compatible_group_udpate ( table
, intval_rule - > region_id
, intval_rule - > group_id
, intval_rule - > is_valid
, scanner
, logger ) ;
intval_rule - > group_id = intval_rule - > region_id ;
}
if ( intval_rule - > is_valid = = FALSE )
{
2016-12-30 18:07:19 +08:00
ret = del_region_rule ( table
, intval_rule - > region_id , intval_rule - > group_id , RULETYPE_INT
, scanner , logger ) ;
2018-12-04 20:12:56 +08:00
if ( ret < 0 )
2015-10-10 18:30:12 +08:00
{
2018-12-04 20:12:56 +08:00
table - > udpate_err_cnt + + ;
2015-10-10 18:30:12 +08:00
}
2016-10-08 11:40:57 +08:00
else
{
2018-12-04 23:26:59 +08:00
table_rt - > origin_rule_num - - ;
2016-10-08 11:40:57 +08:00
}
2018-12-04 20:12:56 +08:00
2015-10-10 18:30:12 +08:00
}
else
{
ret = add_intval_rule ( table , intval_rule , scanner , logger ) ;
if ( ret < 0 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
2016-08-30 10:40:05 +08:00
" duplicate config of intval table %s config_id=%d "
, table - > table_name [ table - > updating_name ] , intval_rule - > region_id ) ;
2016-10-08 11:40:57 +08:00
table - > udpate_err_cnt + + ;
2015-10-10 18:30:12 +08:00
}
else
{
2018-12-04 23:26:59 +08:00
table_rt - > origin_rule_num + + ;
2015-10-10 18:30:12 +08:00
}
2018-12-04 20:12:56 +08:00
2015-10-10 18:30:12 +08:00
}
error_out :
free ( intval_rule ) ;
intval_rule = NULL ;
}
2019-01-05 17:11:20 +08:00
void update_compile_rule ( struct Maat_table_desc * table , const char * table_line , struct Maat_scanner_t * scanner , const struct rule_tag * tags , int n_tags , void * logger )
2015-10-10 18:30:12 +08:00
{
2018-12-04 20:12:56 +08:00
struct compile_table_desc * compile_desc = & ( table - > compile ) ;
2018-12-04 23:26:59 +08:00
struct Maat_table_runtime * table_rt = scanner - > table_rt [ table - > table_id ] ;
2018-12-04 20:12:56 +08:00
struct db_compile_rule_t * p_compile = ALLOC ( struct db_compile_rule_t , 1 ) ;
2015-10-10 18:30:12 +08:00
struct _head_Maat_rule_t * p_m_rule = & ( p_compile - > m_rule_head ) ;
2018-07-05 17:20:49 +08:00
char user_region [ MAX_TABLE_LINE_SIZE ] = { 0 } ;
2018-09-21 21:32:09 +08:00
char tag_str [ MAX_TABLE_LINE_SIZE ] = { 0 } ;
2015-10-10 18:30:12 +08:00
int ret = 0 ;
p_compile - > declare_grp_num = 0 ;
2018-09-21 21:32:09 +08:00
ret = sscanf ( table_line , " %d \t %d \t %hhd \t %hhd \t %hhd \t %s \t %s \t %d \t %d " , & ( p_m_rule - > config_id )
2015-10-10 18:30:12 +08:00
, & ( p_m_rule - > service_id )
, & ( p_m_rule - > action )
, & ( p_m_rule - > do_blacklist )
, & ( p_m_rule - > do_log )
2018-09-21 21:32:09 +08:00
, tag_str
2015-10-10 18:30:12 +08:00
, user_region
, & ( p_compile - > is_valid )
, & ( p_compile - > declare_grp_num ) ) ;
2018-07-05 18:39:15 +08:00
if ( ( ret ! = 8 & & ret ! = 9 ) | | p_compile - > declare_grp_num > MAAT_MAX_EXPR_ITEM_NUM )
2015-10-10 18:30:12 +08:00
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2016-08-30 10:40:05 +08:00
" update error,invalid format of compile table %s:%s "
2018-09-21 21:32:09 +08:00
, table - > table_name [ table - > updating_name ] , table_line ) ;
2016-10-08 11:40:57 +08:00
table - > udpate_err_cnt + + ;
2018-09-21 21:32:09 +08:00
goto no_save ;
}
if ( n_tags > 0 & & strlen ( tag_str ) > 2 )
{
ret = compare_accept_tag ( tag_str , tags , n_tags ) ;
if ( ret < 0 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" update error,invalid tag format of compile table %s:%s "
, table - > table_name [ table - > updating_name ] , table_line ) ;
table - > udpate_err_cnt + + ;
goto no_save ;
}
if ( ret = = 0 )
{
table - > unmatch_tag_cnt + + ;
goto no_save ;
}
2015-10-10 18:30:12 +08:00
}
2018-12-04 20:12:56 +08:00
switch ( compile_desc - > user_region_encoding )
2018-08-08 18:35:53 +08:00
{
case USER_REGION_ENCODE_ESCAPE :
str_unescape ( user_region ) ;
break ;
default :
break ;
}
2015-10-10 18:30:12 +08:00
p_m_rule - > serv_def_len = strlen ( user_region ) + 1 ;
2018-12-04 20:12:56 +08:00
p_compile - > service_defined = ALLOC ( char , p_m_rule - > serv_def_len ) ;
2015-10-10 18:30:12 +08:00
memcpy ( p_compile - > service_defined , user_region , p_m_rule - > serv_def_len ) ;
2018-08-08 18:35:53 +08:00
2015-10-10 18:30:12 +08:00
if ( p_compile - > is_valid = = FALSE )
{
ret = del_compile_rule ( table , p_compile , scanner , logger ) ;
2018-12-04 23:26:59 +08:00
table_rt - > origin_rule_num - - ;
2018-09-21 21:32:09 +08:00
goto no_save ;
2015-10-10 18:30:12 +08:00
}
else
{
ret = add_compile_rule ( table , p_compile , scanner , logger ) ;
if ( ret < 0 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
2016-08-30 10:40:05 +08:00
" duplicate config of compile table %s config_id=%d "
2018-09-21 21:32:09 +08:00
, table - > table_name [ table - > updating_name ] , p_m_rule - > config_id ) ;
2016-10-08 11:40:57 +08:00
table - > udpate_err_cnt + + ;
2018-09-21 21:32:09 +08:00
goto no_save ;
2015-10-10 18:30:12 +08:00
}
2018-12-04 23:26:59 +08:00
table_rt - > origin_rule_num + + ;
2015-10-10 18:30:12 +08:00
}
2018-09-21 21:32:09 +08:00
return ;
2015-10-10 18:30:12 +08:00
2018-09-21 21:32:09 +08:00
no_save :
free ( p_compile - > service_defined ) ;
p_compile - > service_defined = NULL ;
free ( p_compile ) ;
p_compile = NULL ;
2015-10-10 18:30:12 +08:00
return ;
}
2015-11-10 18:29:42 +08:00
2019-01-05 17:11:20 +08:00
void update_digest_rule ( struct Maat_table_desc * table , const char * table_line , struct Maat_scanner_t * scanner , void * logger , int group_mode_on )
2015-11-10 18:29:42 +08:00
{
2018-12-04 23:26:59 +08:00
struct Maat_table_runtime * table_rt = scanner - > table_rt [ table - > table_id ] ;
2018-12-04 20:12:56 +08:00
struct db_digest_rule_t * digest_rule = ALLOC ( struct db_digest_rule_t , 1 ) ;
2015-11-10 18:29:42 +08:00
int ret = 0 ;
char digest_buff [ MAX_TABLE_LINE_SIZE ] = { ' \0 ' } ;
2017-08-07 17:08:52 +08:00
if ( table - > table_type = = TABLE_TYPE_DIGEST )
{
ret = sscanf ( table_line , " %d \t %d \t %llu \t %s \t %hd \t %d " , & ( digest_rule - > region_id )
2015-11-10 18:29:42 +08:00
, & ( digest_rule - > group_id )
, & ( digest_rule - > orgin_len )
, digest_buff
, & ( digest_rule - > confidence_degree )
, & ( digest_rule - > is_valid ) ) ;
2017-08-07 17:08:52 +08:00
}
else if ( table - > table_type = = TABLE_TYPE_SIMILARITY )
{
digest_rule - > orgin_len = 0 ;
ret = sscanf ( table_line , " %d \t %d \t %s \t %hd \t %d " , & ( digest_rule - > region_id )
, & ( digest_rule - > group_id )
, digest_buff
, & ( digest_rule - > confidence_degree )
, & ( digest_rule - > is_valid ) ) ;
}
else
{
assert ( 0 ) ;
}
2015-11-10 18:29:42 +08:00
digest_rule - > digest_string = digest_buff ;
2017-08-07 17:08:52 +08:00
if ( ! ( ret = = 6 | | ret = = 5 ) | | digest_rule - > confidence_degree > 100 | | digest_rule - > confidence_degree < 0 )
2015-11-10 18:29:42 +08:00
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
2016-08-30 10:40:05 +08:00
" update error,invalid format of digest table %s:%s "
, table - > table_name [ table - > updating_name ] , table_line ) ;
2016-10-08 11:40:57 +08:00
table - > udpate_err_cnt + + ;
2015-11-10 18:29:42 +08:00
goto error_out ;
}
ret = sync_region ( scanner - > region_hash
, digest_rule - > region_id
2016-08-30 10:40:05 +08:00
, table - > table_name [ table - > updating_name ]
2015-11-10 18:29:42 +08:00
, digest_rule - > is_valid , logger ) ;
if ( ret < 0 )
{
2016-10-08 11:40:57 +08:00
table - > udpate_err_cnt + + ;
2015-11-10 18:29:42 +08:00
goto error_out ;
}
if ( group_mode_on = = FALSE ) //for compatible old version
{
compatible_group_udpate ( table
, digest_rule - > region_id
, digest_rule - > group_id
, digest_rule - > is_valid
, scanner
, logger ) ;
digest_rule - > group_id = digest_rule - > region_id ;
}
if ( digest_rule - > is_valid = = FALSE )
{
2016-12-30 18:07:19 +08:00
//digest rule is not build with rulescan, this rule type is useless in count_rs_region funciton.
ret = del_region_rule ( table , digest_rule - > region_id , digest_rule - > group_id , 0 , scanner , logger ) ;
2018-12-04 20:12:56 +08:00
if ( ret < 0 )
2015-11-10 18:29:42 +08:00
{
2018-12-04 20:12:56 +08:00
table - > udpate_err_cnt + + ;
2015-11-10 18:29:42 +08:00
}
2016-10-08 11:40:57 +08:00
else
{
2018-12-04 23:26:59 +08:00
table_rt - > origin_rule_num - - ;
2016-10-08 11:40:57 +08:00
}
2018-12-04 20:12:56 +08:00
2015-11-10 18:29:42 +08:00
}
else
{
ret = add_digest_rule ( table , digest_rule , scanner , logger ) ;
if ( ret < 0 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
2016-08-30 10:40:05 +08:00
" duplicate config of intval table %s config_id=%d "
, table - > table_name [ table - > updating_name ] , digest_rule - > region_id ) ;
2016-10-08 11:40:57 +08:00
table - > udpate_err_cnt + + ;
2015-11-10 18:29:42 +08:00
}
else
{
2018-12-04 23:26:59 +08:00
table_rt - > origin_rule_num + + ;
2015-11-10 18:29:42 +08:00
}
2018-12-04 20:12:56 +08:00
2015-11-10 18:29:42 +08:00
}
error_out :
2015-10-10 18:30:12 +08:00
2015-11-10 18:29:42 +08:00
digest_rule - > digest_string = NULL ;
free ( digest_rule ) ;
digest_rule = NULL ;
}
2018-09-24 18:49:18 +08:00
void garbage_bagging_with_timeout ( enum maat_garbage_type type , void * p , int timeout , MESA_lqueue_head garbage_q )
2015-10-10 18:30:12 +08:00
{
2015-11-10 18:29:42 +08:00
if ( p = = NULL )
{
return ;
}
2015-10-10 18:30:12 +08:00
struct _maat_garbage_t * bag = ( struct _maat_garbage_t * ) malloc ( sizeof ( struct _maat_garbage_t ) ) ;
bag - > raw = p ;
bag - > type = type ;
bag - > create_time = time ( NULL ) ;
bag - > ok_times = 0 ;
2018-09-24 18:49:18 +08:00
bag - > expire_after = timeout ;
2015-10-10 18:30:12 +08:00
MESA_lqueue_join_tail ( garbage_q , & bag , sizeof ( void * ) ) ;
return ;
}
2018-09-24 18:49:18 +08:00
void garbage_bagging ( enum maat_garbage_type type , void * p , MESA_lqueue_head garbage_q )
{
garbage_bagging_with_timeout ( type , p , - 1 , garbage_q ) ;
return ;
}
2017-08-03 18:37:33 +08:00
void garbage_bury ( MESA_lqueue_head garbage_q , int timeout , void * logger )
2015-10-10 18:30:12 +08:00
{
2018-10-18 19:39:19 +08:00
UNUSED MESA_queue_errno_t q_ret = MESA_QUEUE_RET_OK ;
2015-10-10 18:30:12 +08:00
_maat_garbage_t * bag = NULL ;
long data_size = 0 ;
const long q_cnt = MESA_lqueue_get_count ( garbage_q ) ;
2018-09-24 18:49:18 +08:00
int i = 0 , bury_cnt = 0 , ret = 0 ;
2016-02-18 14:53:06 +08:00
long long ref_cnt = 0 ;
2015-10-10 18:30:12 +08:00
int have_timeout = 0 ;
2018-09-24 18:49:18 +08:00
int override_timeout = 0 ;
2015-10-10 18:30:12 +08:00
time_t now = time ( NULL ) ;
for ( i = 0 ; i < q_cnt ; i + + )
{
data_size = sizeof ( void * ) ;
q_ret = ( MESA_queue_errno_t ) MESA_lqueue_get_head ( garbage_q , & bag , & data_size ) ;
assert ( data_size = = sizeof ( void * ) & & q_ret = = MESA_QUEUE_RET_OK ) ;
2018-09-24 18:49:18 +08:00
if ( bag - > expire_after < 0 )
{
override_timeout = timeout ;
}
else
{
override_timeout = bag - > expire_after ;
}
if ( now - bag - > create_time < override_timeout )
2015-10-10 18:30:12 +08:00
{
MESA_lqueue_join_tail ( garbage_q , & bag , sizeof ( void * ) ) ;
continue ;
}
have_timeout = 1 ;
switch ( bag - > type )
{
case GARBAGE_COMPILE_RULE :
destroy_compile_rule ( bag - > compile_rule ) ;
break ;
case GARBAGE_GROUP_RULE :
destroy_group_rule ( bag - > group_rule ) ;
break ;
case GARBAGE_SCANNER :
2019-01-05 17:11:20 +08:00
ref_cnt = alignment_int64_array_sum ( bag - > scanner - > ref_cnt , bag - > scanner - > max_thread_num ) ;
2015-10-10 18:30:12 +08:00
if ( ref_cnt = = 0 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
2019-01-05 17:11:20 +08:00
" scanner %p version %d has no reference peacefully destroyed. " , bag - > scanner , bag - > scanner - > version ) ;
2015-10-10 18:30:12 +08:00
}
else
{
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
2019-01-05 17:11:20 +08:00
" scanner %p version %d force destroyed, ref_cnt %lld. " ,
bag - > scanner , bag - > scanner - > version , ref_cnt ) ;
2015-10-10 18:30:12 +08:00
}
destroy_maat_scanner ( bag - > scanner ) ;
break ;
case GARBAGE_BOOL_MATCHER :
destroy_bool_matcher ( bag - > bool_matcher ) ;
break ;
2016-06-27 18:25:53 +08:00
case GARBAGE_MAP_STR2INT :
map_destroy ( bag - > str2int_map ) ;
break ;
2018-09-24 18:49:18 +08:00
case GARBAGE_FOREIGN_FILE :
ret = system_cmd_rm ( bag - > filename ) ;
if ( ret = = - 1 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
" Foreign content file %s remove failed. " ,
bag - > filename ) ;
}
2018-09-26 19:49:29 +08:00
else
{
MESA_handle_runtime_log ( logger , RLOG_LV_DEBUG , maat_module ,
" Foreign content file %s remove success. " ,
bag - > filename ) ;
}
2018-09-26 19:30:15 +08:00
free ( bag - > filename ) ;
bag - > filename = NULL ;
2018-09-24 18:49:18 +08:00
break ;
2015-10-10 18:30:12 +08:00
default :
assert ( 0 ) ;
}
free ( bag ) ;
bag = NULL ;
bury_cnt + + ;
}
if ( q_cnt > 0 & & have_timeout = = 1 )
{
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
" Garbage queue size %ld, bury %d " ,
q_cnt , bury_cnt ) ;
}
}
2019-01-05 17:11:20 +08:00
void update_plugin_table ( struct Maat_table_desc * table , const char * table_line , Maat_scanner_t * scanner , const struct rule_tag * tags , int n_tags , void * logger )
2015-10-10 18:30:12 +08:00
{
2019-01-24 18:55:38 +06:00
int i = 0 , ret = 1 , matched_tag = 1 ;
2015-10-10 18:30:12 +08:00
unsigned int len = strlen ( table_line ) + 1 ;
2018-12-04 20:12:56 +08:00
struct plugin_table_desc * plugin_desc = & ( table - > plugin ) ;
2018-12-04 23:26:59 +08:00
struct Maat_table_runtime * table_rt = scanner - > table_rt [ table - > table_id ] ;
2015-12-24 17:58:40 +08:00
char * p = NULL ;
2018-09-21 21:32:09 +08:00
char * copy = NULL ;
2018-12-05 18:00:55 +08:00
size_t is_valid_offset = 0 , valid_len = 0 ;
2018-12-24 20:23:48 +06:00
size_t accept_tag_offset = 0 , accept_tag_len = 0 ;
2018-12-04 20:12:56 +08:00
if ( plugin_desc - > rule_tag_column > 0 & & n_tags > 0 )
2018-09-21 21:32:09 +08:00
{
2018-12-24 20:23:48 +06:00
ret = Maat_helper_read_column ( table_line , plugin_desc - > rule_tag_column , & accept_tag_offset , & accept_tag_len ) ;
if ( ret < 0 )
2018-09-21 21:32:09 +08:00
{
2018-12-24 20:23:48 +06:00
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" update error, could not locate tag in column %d of plugin table %s:%s " ,
plugin_desc - > rule_tag_column ,
table - > table_name [ table - > updating_name ] ,
table_line ) ;
table - > udpate_err_cnt + + ;
return ;
2018-09-21 21:32:09 +08:00
}
2018-12-24 20:23:48 +06:00
if ( accept_tag_len > 2 )
2018-09-21 21:32:09 +08:00
{
2018-12-24 20:23:48 +06:00
copy = ALLOC ( char , accept_tag_len + 1 ) ;
memcpy ( copy , table_line + accept_tag_offset , accept_tag_len ) ;
2019-01-24 18:55:38 +06:00
matched_tag = compare_accept_tag ( copy , tags , n_tags ) ;
if ( matched_tag < 0 )
2018-09-21 21:32:09 +08:00
{
MESA_handle_runtime_log ( logger , RLOG_LV_FATAL , maat_module ,
" update error,invalid tag format of plugin table %s:%s "
, table - > table_name [ table - > updating_name ] , table_line ) ;
table - > udpate_err_cnt + + ;
}
2019-01-24 18:55:38 +06:00
if ( matched_tag = = 0 )
2018-09-21 21:32:09 +08:00
{
table - > unmatch_tag_cnt + + ;
}
2018-12-24 20:23:48 +06:00
free ( copy ) ;
copy = NULL ;
2018-09-21 21:32:09 +08:00
}
2019-01-24 18:55:38 +06:00
if ( ! matched_tag )
2018-09-21 21:32:09 +08:00
{
return ;
}
}
2018-12-04 23:26:59 +08:00
table_rt - > plugin . acc_line_num + + ;
2018-12-05 18:00:55 +08:00
if ( plugin_desc - > have_exdata | | plugin_desc - > cb_plug_cnt > 0 )
2015-10-10 18:30:12 +08:00
{
2018-12-05 18:00:55 +08:00
if ( plugin_desc - > have_exdata )
2015-12-24 17:58:40 +08:00
{
2018-12-24 20:23:48 +06:00
ret = Maat_helper_read_column ( table_line , plugin_desc - > valid_flag_column , & is_valid_offset , & valid_len ) ;
2018-12-05 18:00:55 +08:00
pthread_rwlock_wrlock ( & ( table_rt - > plugin . rwlock ) ) ;
if ( atoi ( table_line + is_valid_offset ) = = 1 )
{
plugin_EX_data_new ( table , table_line , table_rt - > plugin . key2ex_hash , logger ) ;
}
else
{
plugin_EX_data_free ( table , table_line , table_rt - > plugin . key2ex_hash , logger ) ;
}
pthread_rwlock_unlock ( & ( table_rt - > plugin . rwlock ) ) ;
}
if ( plugin_desc - > cb_plug_cnt > 0 )
{
for ( i = 0 ; i < plugin_desc - > cb_plug_cnt ; i + + )
{
plugin_desc - > cb_plug [ i ] . update ( table - > table_id , table_line , plugin_desc - > cb_plug [ i ] . u_para ) ;
}
2015-12-24 17:58:40 +08:00
}
2018-12-05 18:00:55 +08:00
2015-12-24 17:58:40 +08:00
}
else
{
2018-12-04 20:12:56 +08:00
p = ALLOC ( char , len ) ;
2015-12-24 17:58:40 +08:00
memcpy ( p , table_line , len ) ;
2018-12-04 23:26:59 +08:00
table_rt - > plugin . cache_size + = len ;
dynamic_array_write ( table_rt - > plugin . cache_lines , table_rt - > plugin . cache_line_num , p ) ;
2018-12-05 18:00:55 +08:00
table_rt - > plugin . cache_line_num + + ;
2015-10-10 18:30:12 +08:00
}
}
2019-01-05 17:11:20 +08:00
void do_scanner_update ( struct Maat_scanner_t * scanner , MESA_lqueue_head garbage_q , int scan_thread_num , void * logger )
2015-11-10 18:29:42 +08:00
{
2019-01-05 17:11:20 +08:00
struct bool_matcher * tmp1 = NULL , * tmp2 = NULL ;
2016-06-27 18:25:53 +08:00
MESA_htable_handle tmp_map = NULL ;
2018-12-04 23:26:59 +08:00
struct Maat_table_runtime * table_rt = NULL ;
2015-11-10 18:29:42 +08:00
int i = 0 ;
long q_cnt ;
GIE_create_para_t para ;
2017-08-07 17:08:52 +08:00
para . gram_value = 7 ;
para . position_accuracy = 10 ;
2015-11-10 18:29:42 +08:00
tmp1 = create_bool_matcher ( scanner - > compile_hash ,
2019-01-05 17:11:20 +08:00
scan_thread_num ,
logger ) ;
2019-01-08 21:25:08 +06:00
tmp2 = scanner - > bool_matcher_expr_compiler ;
2015-11-10 18:29:42 +08:00
//assume pinter = operation is thread safe
2019-01-08 21:25:08 +06:00
scanner - > bool_matcher_expr_compiler = tmp1 ;
2015-11-10 18:29:42 +08:00
if ( tmp2 ! = NULL )
{
garbage_bagging ( GARBAGE_BOOL_MATCHER , tmp2 , garbage_q ) ;
}
2016-11-23 16:52:04 +08:00
MESA_handle_runtime_log ( logger , RLOG_LV_INFO , maat_module ,
" Version %d dedup string rule %lu " , scanner - > version , scanner - > dedup_expr_num ) ;
scanner - > dedup_expr_num = 0 ;
2015-11-10 18:29:42 +08:00
rulescan_batch_update ( scanner - > region ,
scanner - > region_update_q ,
2019-01-05 17:11:20 +08:00
logger ,
scanner ) ;
2015-11-10 18:29:42 +08:00
for ( i = 0 ; i < MAX_TABLE_NUM ; i + + )
{
2018-12-04 23:26:59 +08:00
table_rt = scanner - > table_rt [ i ] ;
if ( table_rt = = NULL )
2016-06-17 15:00:28 +08:00
{
continue ;
}
2018-12-04 23:26:59 +08:00
switch ( table_rt - > table_type )
2015-11-10 18:29:42 +08:00
{
2018-12-04 20:12:56 +08:00
case TABLE_TYPE_DIGEST :
case TABLE_TYPE_SIMILARITY :
2018-12-04 23:26:59 +08:00
q_cnt = MESA_lqueue_get_count ( table_rt - > similar . update_q ) ;
2018-12-04 20:12:56 +08:00
if ( q_cnt = = 0 )
{
continue ;
}
2018-12-04 23:26:59 +08:00
if ( table_rt - > similar . gie_handle = = NULL )
2018-12-04 20:12:56 +08:00
{
2018-12-04 23:26:59 +08:00
if ( table_rt - > table_type = = TABLE_TYPE_SIMILARITY )
2018-12-04 20:12:56 +08:00
{
para . ED_reexamine = 1 ;
para . format = GIE_INPUT_FORMAT_PLAIN ;
}
else
{
para . ED_reexamine = 0 ;
para . format = GIE_INPUT_FORMAT_SFH ;
}
2018-12-04 23:26:59 +08:00
table_rt - > similar . gie_handle = GIE_create ( & para ) ;
2018-12-04 20:12:56 +08:00
}
2018-12-04 23:26:59 +08:00
digest_batch_update ( table_rt - > similar . gie_handle ,
table_rt - > similar . update_q ,
2018-12-04 20:12:56 +08:00
logger ,
scanner ,
i ) ;
break ;
case TABLE_TYPE_PLUGIN :
break ;
default :
break ;
2015-11-10 18:29:42 +08:00
}
2018-12-04 20:12:56 +08:00
2015-11-10 18:29:42 +08:00
}
2017-08-15 09:14:44 +08:00
scanner - > gie_total_q_size = 0 ;
2016-06-27 18:25:53 +08:00
if ( scanner - > tmp_district_map ! = NULL )
{
tmp_map = scanner - > district_map ;
scanner - > district_map = scanner - > tmp_district_map ;
scanner - > tmp_district_map = NULL ;
garbage_bagging ( GARBAGE_MAP_STR2INT , tmp_map , garbage_q ) ;
}
2015-11-10 18:29:42 +08:00
scanner - > last_update_time = time ( NULL ) ;
return ;
}
2018-12-04 23:26:59 +08:00
2017-12-06 18:12:32 +08:00
void maat_start_cb ( long long new_version , int update_type , void * u_para )
2015-10-10 18:30:12 +08:00
{
struct _Maat_feather_t * feather = ( struct _Maat_feather_t * ) u_para ;
2018-12-04 23:26:59 +08:00
struct Maat_table_desc * p_table = NULL ;
2018-12-04 20:12:56 +08:00
struct plugin_table_desc * plugin_desc = NULL ;
2015-10-10 18:30:12 +08:00
int i = 0 , j = 0 ;
2017-12-06 14:41:08 +08:00
feather - > new_version = new_version ;
2017-12-06 18:12:32 +08:00
2015-10-10 18:30:12 +08:00
if ( update_type = = CM_UPDATE_TYPE_FULL )
{
2016-06-17 12:11:31 +08:00
feather - > update_tmp_scanner = create_maat_scanner ( new_version , feather ) ;
2015-10-10 18:30:12 +08:00
MESA_handle_runtime_log ( feather - > logger , RLOG_LV_INFO , maat_module ,
" Full config version %u -> %u update start " ,
feather - > maat_version , new_version ) ;
}
else
{
MESA_handle_runtime_log ( feather - > logger , RLOG_LV_INFO , maat_module ,
" Inc config version %u -> %u update start " ,
feather - > maat_version , new_version ) ;
feather - > maat_version = new_version ;
}
2017-12-06 18:12:32 +08:00
feather - > active_plugin_table_num = 0 ;
2016-06-23 16:11:23 +08:00
for ( i = 0 ; i < MAX_TABLE_NUM ; i + + )
2015-10-10 18:30:12 +08:00
{
p_table = feather - > p_table_info [ i ] ;
2018-12-04 20:12:56 +08:00
plugin_desc = & ( p_table - > plugin ) ;
if ( p_table = = NULL | | p_table - > table_type ! = TABLE_TYPE_PLUGIN | | plugin_desc - > cb_plug_cnt = = 0 )
2015-10-10 18:30:12 +08:00
{
continue ;
}
2017-12-06 18:12:32 +08:00
feather - > active_plugin_table_num + + ;
2018-12-04 20:12:56 +08:00
for ( j = 0 ; j < plugin_desc - > cb_plug_cnt ; j + + )
2015-10-10 18:30:12 +08:00
{
2018-12-04 20:12:56 +08:00
if ( plugin_desc - > cb_plug [ j ] . start ! = NULL )
2016-05-25 11:47:15 +08:00
{
2018-12-04 20:12:56 +08:00
plugin_desc - > cb_plug [ j ] . start ( update_type , plugin_desc - > cb_plug [ j ] . u_para ) ;
2016-05-25 11:47:15 +08:00
}
2015-10-10 18:30:12 +08:00
}
}
return ;
}
2019-01-05 17:11:20 +08:00
long long scanner_rule_num ( struct Maat_scanner_t * scanner )
2015-10-10 18:30:12 +08:00
{
2018-12-04 20:12:56 +08:00
long long total = 0 ;
2018-12-04 23:26:59 +08:00
struct Maat_table_runtime * table_rt = NULL ;
2018-12-04 20:12:56 +08:00
int i = 0 ;
2015-10-10 18:30:12 +08:00
for ( i = 0 ; i < MAX_TABLE_NUM ; i + + )
{
2018-12-04 23:26:59 +08:00
table_rt = scanner - > table_rt [ i ] ;
if ( table_rt ! = NULL )
2015-10-10 18:30:12 +08:00
{
2018-12-04 23:26:59 +08:00
total + = table_rt - > origin_rule_num ;
2015-10-10 18:30:12 +08:00
}
}
2018-12-04 20:12:56 +08:00
return total ;
}
void maat_finish_cb ( void * u_para )
{
struct _Maat_feather_t * feather = ( struct _Maat_feather_t * ) u_para ;
2018-12-04 23:26:59 +08:00
struct Maat_table_desc * p_table = NULL ;
2018-12-04 20:12:56 +08:00
struct plugin_table_desc * plugin_desc = NULL ;
long expr_wait_q_cnt = 0 ;
int i = 0 , j = 0 ;
2017-12-06 18:12:32 +08:00
int call_plugin_table_cnt = 0 ;
2015-10-10 18:30:12 +08:00
for ( i = 0 ; i < MAX_TABLE_NUM ; i + + )
{
p_table = feather - > p_table_info [ i ] ;
2018-12-04 20:12:56 +08:00
if ( p_table = = NULL )
2015-10-10 18:30:12 +08:00
{
continue ;
}
2018-12-04 20:12:56 +08:00
switch ( p_table - > table_type )
2017-12-06 14:41:08 +08:00
{
2018-12-04 20:12:56 +08:00
case TABLE_TYPE_PLUGIN :
plugin_desc = & ( p_table - > plugin ) ;
call_plugin_table_cnt + + ;
if ( call_plugin_table_cnt = = feather - > active_plugin_table_num )
{
feather - > is_last_plugin_table_updating = 1 ;
}
for ( j = 0 ; j < plugin_desc - > cb_plug_cnt ; j + + )
{
if ( plugin_desc - > cb_plug [ j ] . finish ! = NULL )
{
plugin_desc - > cb_plug [ j ] . finish ( plugin_desc - > cb_plug [ j ] . u_para ) ;
}
}
feather - > is_last_plugin_table_updating = 0 ;
break ;
default :
break ;
}
2015-10-10 18:30:12 +08:00
}
2018-12-04 20:12:56 +08:00
2015-10-10 18:30:12 +08:00
if ( feather - > update_tmp_scanner ! = NULL )
{
2018-12-04 20:12:56 +08:00
feather - > update_tmp_scanner - > cfg_num = scanner_rule_num ( feather - > update_tmp_scanner ) ;
2015-11-10 18:29:42 +08:00
do_scanner_update ( feather - > update_tmp_scanner
, feather - > garbage_q
, feather - > scan_thread_num
, feather - > logger ) ;
2015-10-10 18:30:12 +08:00
MESA_handle_runtime_log ( feather - > logger , RLOG_LV_INFO , maat_module ,
" Full config version %u load %d entries complete. " ,
feather - > update_tmp_scanner - > version , feather - > update_tmp_scanner - > cfg_num ) ;
}
2016-05-25 11:47:15 +08:00
else if ( feather - > scanner ! = NULL )
2015-10-10 18:30:12 +08:00
{
2018-12-04 20:12:56 +08:00
feather - > scanner - > cfg_num = scanner_rule_num ( feather - > scanner ) ;
2015-10-10 18:30:12 +08:00
feather - > scanner - > version = feather - > maat_version ;
2017-08-15 09:14:44 +08:00
expr_wait_q_cnt = MESA_lqueue_get_count ( feather - > scanner - > region_update_q ) ;
feather - > postpone_q_size = expr_wait_q_cnt + feather - > scanner - > gie_total_q_size ;
2018-06-17 20:03:17 +08:00
if ( time ( NULL ) - feather - > scanner - > last_update_time > = feather - > effect_interval_ms / 1000 )
2015-10-10 18:30:12 +08:00
{
2015-11-10 18:29:42 +08:00
do_scanner_update ( feather - > scanner
, feather - > garbage_q
, feather - > scan_thread_num
, feather - > logger ) ;
2018-12-04 20:12:56 +08:00
MESA_handle_runtime_log ( feather - > logger , RLOG_LV_INFO , maat_module
, " Inc config version %u build complete, %d entries in total. "
, feather - > scanner - > version , feather - > scanner - > cfg_num ) ;
2017-08-15 09:14:44 +08:00
feather - > postpone_q_size = 0 ;
2015-10-10 18:30:12 +08:00
}
else
{
2018-12-04 20:12:56 +08:00
MESA_handle_runtime_log ( feather - > logger , RLOG_LV_INFO , maat_module ,
2017-09-15 20:00:14 +08:00
" Postpone %d entries of version %u load to rulescan. " ,
2018-12-04 20:12:56 +08:00
feather - > scanner - > cfg_num , feather - > scanner - > version ) ;
2015-10-10 18:30:12 +08:00
}
}
2016-05-25 11:47:15 +08:00
else
{
MESA_handle_runtime_log ( feather - > logger , RLOG_LV_INFO , maat_module ,
2018-12-04 20:12:56 +08:00
" Version %d have no valid scan rules, plugin callback complete. " ,
feather - > maat_version ) ;
2016-05-25 11:47:15 +08:00
}
2017-12-06 14:41:08 +08:00
feather - > new_version = - 1 ;
feather - > active_plugin_table_num = 0 ;
2015-10-10 18:30:12 +08:00
return ;
}
2017-08-09 18:27:08 +08:00
int maat_update_cb ( const char * table_name , const char * line , void * u_para )
2015-10-10 18:30:12 +08:00
{
struct _Maat_feather_t * feather = ( struct _Maat_feather_t * ) u_para ;
2016-08-30 10:40:05 +08:00
int ret = - 1 , i = 0 ;
2015-10-10 18:30:12 +08:00
int table_id = - 1 ;
2019-01-05 17:11:20 +08:00
Maat_scanner_t * scanner = NULL ;
2018-12-04 23:26:59 +08:00
struct Maat_table_desc * p_table = NULL ;
2015-10-10 18:30:12 +08:00
if ( feather - > update_tmp_scanner ! = NULL )
{
scanner = feather - > update_tmp_scanner ;
}
else
{
scanner = feather - > scanner ;
}
ret = map_str2int ( feather - > map_tablename2id , table_name , & table_id ) ;
if ( ret < 0 )
{
MESA_handle_runtime_log ( feather - > logger , RLOG_LV_INFO , maat_module , " update warning,unknown table name %s " , table_name ) ;
2017-08-09 18:27:08 +08:00
return - 1 ;
2015-10-10 18:30:12 +08:00
}
2016-08-30 10:40:05 +08:00
p_table = feather - > p_table_info [ table_id ] ;
for ( i = 0 ; i < p_table - > conj_cnt ; i + + )
{
2016-08-30 11:08:32 +08:00
if ( 0 = = memcmp ( p_table - > table_name [ i ] , table_name , strlen ( table_name ) ) )
2016-08-30 10:40:05 +08:00
{
p_table - > updating_name = i ;
}
}
2016-08-30 11:08:32 +08:00
assert ( i < = p_table - > conj_cnt ) ;
2016-08-30 10:40:05 +08:00
2015-10-10 18:30:12 +08:00
switch ( feather - > p_table_info [ table_id ] - > table_type )
{
case TABLE_TYPE_EXPR :
2016-02-11 13:57:39 +08:00
case TABLE_TYPE_EXPR_PLUS :
2015-10-10 18:30:12 +08:00
update_expr_rule ( feather - > p_table_info [ table_id ] , line , scanner , feather - > logger , feather - > GROUP_MODE_ON ) ;
break ;
case TABLE_TYPE_IP :
update_ip_rule ( feather - > p_table_info [ table_id ] , line , scanner , feather - > logger , feather - > GROUP_MODE_ON ) ;
break ;
2017-08-07 17:08:52 +08:00
case TABLE_TYPE_INTERVAL :
2015-10-10 18:30:12 +08:00
update_intval_rule ( feather - > p_table_info [ table_id ] , line , scanner , feather - > logger , feather - > GROUP_MODE_ON ) ;
break ;
2015-11-10 18:29:42 +08:00
case TABLE_TYPE_DIGEST :
2017-08-07 17:08:52 +08:00
case TABLE_TYPE_SIMILARITY :
2015-11-10 18:29:42 +08:00
update_digest_rule ( feather - > p_table_info [ table_id ] , line , scanner , feather - > logger , feather - > GROUP_MODE_ON ) ;
break ;
2015-10-10 18:30:12 +08:00
case TABLE_TYPE_COMPILE :
2018-09-21 21:32:09 +08:00
update_compile_rule ( feather - > p_table_info [ table_id ] , line , scanner , feather - > accept_tags , feather - > n_tags , feather - > logger ) ;
2015-10-10 18:30:12 +08:00
break ;
case TABLE_TYPE_GROUP :
update_group_rule ( feather - > p_table_info [ table_id ] , line , scanner , feather - > logger ) ;
break ;
case TABLE_TYPE_PLUGIN :
2018-12-04 20:12:56 +08:00
update_plugin_table ( feather - > p_table_info [ table_id ] , line , scanner , feather - > accept_tags , feather - > n_tags , feather - > logger ) ;
2015-10-10 18:30:12 +08:00
default :
break ;
}
2017-08-09 18:27:08 +08:00
return 0 ;
2015-10-10 18:30:12 +08:00
}
void * thread_rule_monitor ( void * arg )
{
struct _Maat_feather_t * feather = ( struct _Maat_feather_t * ) arg ;
2019-01-05 17:11:20 +08:00
struct Maat_scanner_t * old_scanner = NULL ;
2015-10-10 18:30:12 +08:00
long expr_wait_q_cnt = 0 ;
2018-10-18 19:39:19 +08:00
int scan_dir_cnt = 0 ;
2018-12-02 22:50:20 +08:00
int ret = 0 ;
char md5_tmp [ MD5_DIGEST_LENGTH * 2 + 1 ] = { 0 } ;
char tmp_dir [ MAX_TABLE_NAME_LEN ] = { 0 } ;
struct stat attrib ;
2016-12-29 12:15:42 +08:00
char maat_name [ 16 ] ; //Defined by prctl: The name can be up to 16 bytes long,and should
// be null terminated if it contains fewer bytes.
if ( strlen ( feather - > instance_name ) > 0 )
{
snprintf ( maat_name , sizeof ( maat_name ) , " MAAT_%s " , feather - > instance_name ) ;
}
else
{
snprintf ( maat_name , sizeof ( maat_name ) , " MAAT " ) ;
}
2017-01-11 14:39:28 +08:00
ret = prctl ( PR_SET_NAME , ( unsigned long long ) maat_name , NULL , NULL , NULL ) ;
//pthread_setname_np are introduced in glibc2.12
//ret=pthread_setname_np(pthread_self(),maat_name);
2016-12-29 12:15:42 +08:00
assert ( ret > = 0 ) ;
2018-12-16 00:17:37 +06:00
pthread_mutex_lock ( & ( feather - > background_update_mutex ) ) ;
2017-08-22 10:03:38 +08:00
if ( feather - > DEFERRED_LOAD_ON ! = 0 )
2017-08-21 13:59:49 +08:00
{
2017-08-22 10:03:38 +08:00
MESA_handle_runtime_log ( feather - > logger , RLOG_LV_INFO , maat_module ,
" Deferred Loading ON, updating in %s. " , __func__ ) ;
2017-08-21 13:59:49 +08:00
maat_read_full_config ( feather ) ;
}
2018-12-16 00:17:37 +06:00
pthread_mutex_unlock ( & ( feather - > background_update_mutex ) ) ;
2015-10-10 18:30:12 +08:00
while ( feather - > still_working )
{
usleep ( feather - > scan_interval_ms * 1000 ) ;
2016-02-18 09:58:01 +08:00
scan_dir_cnt + + ;
2018-12-16 00:17:37 +06:00
if ( 0 = = pthread_mutex_trylock ( & ( feather - > background_update_mutex ) ) )
2017-08-07 17:08:52 +08:00
{
2018-12-02 22:50:20 +08:00
switch ( feather - > input_mode )
2015-10-10 18:30:12 +08:00
{
2018-12-02 22:50:20 +08:00
case SOURCE_REDIS :
redis_monitor_traverse ( feather - > maat_version ,
& ( feather - > mr_ctx ) ,
maat_start_cb ,
maat_update_cb ,
maat_finish_cb ,
feather ,
feather - > decrypt_key , //Not used.
feather ) ;
break ;
case SOURCE_IRIS_FILE :
config_monitor_traverse ( feather - > maat_version ,
feather - > iris_ctx . inc_dir ,
maat_start_cb ,
maat_update_cb ,
maat_finish_cb ,
feather ,
feather - > decrypt_key ,
feather - > logger ) ;
break ;
case SOURCE_JSON_FILE :
memset ( md5_tmp , 0 , sizeof ( md5_tmp ) ) ;
memset ( tmp_dir , 0 , sizeof ( tmp_dir ) ) ;
stat ( feather - > json_ctx . json_file , & attrib ) ;
if ( attrib . st_ctime ! = feather - > json_ctx . last_md5_time )
{
feather - > json_ctx . last_md5_time = attrib . st_ctime ;
md5_file ( feather - > json_ctx . json_file , md5_tmp ) ;
if ( 0 ! = strcmp ( md5_tmp , feather - > json_ctx . effective_json_md5 ) )
{
ret = json2iris ( feather - > json_ctx . json_file ,
feather - > compile_tn , feather - > group_tn ,
NULL ,
tmp_dir ,
sizeof ( tmp_dir ) ,
feather - > logger ) ;
if ( ret < 0 )
{
MESA_handle_runtime_log ( feather - > logger , RLOG_LV_INFO , maat_module ,
" Maat re-initiate with JSON file %s failed, md5: %s " ,
feather - > json_ctx . json_file ,
md5_tmp ) ;
}
else
{
strcpy ( feather - > json_ctx . effective_json_md5 , md5_tmp ) ;
strcpy ( feather - > json_ctx . iris_file , tmp_dir ) ;
config_monitor_traverse ( 0 ,
feather - > json_ctx . iris_file ,
maat_start_cb ,
maat_update_cb ,
maat_finish_cb ,
feather ,
feather - > decrypt_key ,
feather - > logger ) ;
MESA_handle_runtime_log ( feather - > logger , RLOG_LV_INFO , maat_module ,
" Maat re-initiate with JSON file %s success, md5: %s " ,
feather - > json_ctx . json_file ,
md5_tmp ) ;
}
}
}
break ;
default :
assert ( 0 ) ;
break ;
2018-06-17 20:03:17 +08:00
}
2018-12-02 22:50:20 +08:00
2018-06-17 20:03:17 +08:00
if ( feather - > update_tmp_scanner ! = NULL )
{
old_scanner = feather - > scanner ;
//Some OS doesn't have __sync_lock_test_and_set.
//feather->scanner=__sync_lock_test_and_set(&(feather->scanner),feather->update_tmp_scanner);
feather - > scanner = feather - > update_tmp_scanner ;
if ( old_scanner ! = NULL )
2017-10-14 12:48:14 +08:00
{
2018-06-17 20:03:17 +08:00
if ( feather - > scanner - > version > old_scanner - > version )
{
MESA_handle_runtime_log ( feather - > logger , RLOG_LV_INFO , maat_module ,
" Maat version updated %d -> %d. " ,
old_scanner - > version , feather - > scanner - > version ) ;
}
else
{
MESA_handle_runtime_log ( feather - > logger , RLOG_LV_FATAL , maat_module ,
" Maat version roll back %d -> %d. " ,
old_scanner - > version , feather - > scanner - > version ) ;
}
assert ( old_scanner - > tomb_ref = = feather - > garbage_q ) ;
2018-11-27 12:55:52 +08:00
feather - > zombie_rs_stream + = alignment_int64_array_sum ( old_scanner - > ref_cnt , old_scanner - > max_thread_num ) ;
2018-06-17 20:03:17 +08:00
garbage_bagging ( GARBAGE_SCANNER , old_scanner , feather - > garbage_q ) ;
2017-10-14 12:48:14 +08:00
}
2018-06-17 20:03:17 +08:00
feather - > update_tmp_scanner = NULL ;
feather - > maat_version = feather - > scanner - > version ;
feather - > last_full_version = feather - > scanner - > version ;
2015-10-10 18:30:12 +08:00
}
2018-06-17 20:03:17 +08:00
if ( feather - > scanner ! = NULL )
2015-10-10 18:30:12 +08:00
{
2018-06-17 20:03:17 +08:00
expr_wait_q_cnt = MESA_lqueue_get_count ( feather - > scanner - > region_update_q ) ;
feather - > postpone_q_size = expr_wait_q_cnt + feather - > scanner - > gie_total_q_size ;
if ( feather - > postpone_q_size > 0 & & time ( NULL ) - feather - > scanner - > last_update_time > = feather - > effect_interval_ms / 1000 )
{
do_scanner_update ( feather - > scanner
, feather - > garbage_q
, feather - > scan_thread_num
, feather - > logger ) ;
feather - > postpone_q_size = 0 ;
MESA_handle_runtime_log ( feather - > logger , RLOG_LV_INFO , maat_module ,
" Actual udpate config version %u, %d entries load to rulescan after postpone. " ,
feather - > scanner - > version , feather - > scanner - > cfg_num ) ;
}
2015-10-10 18:30:12 +08:00
}
2018-12-16 00:17:37 +06:00
pthread_mutex_unlock ( & ( feather - > background_update_mutex ) ) ;
2015-10-10 18:30:12 +08:00
}
2017-08-03 18:37:33 +08:00
garbage_bury ( feather - > garbage_q , feather - > effect_interval_ms / 1000 + 10 , feather - > logger ) ;
2018-06-17 20:03:17 +08:00
if ( feather - > stat_on = = 1 & & time ( NULL ) % 2 = = 0 ) //output every 2 seconds
2016-02-10 10:01:18 +08:00
{
maat_stat_output ( feather ) ;
}
2015-10-10 18:30:12 +08:00
}
MESA_htable_destroy ( feather - > map_tablename2id , free ) ;
destroy_maat_scanner ( feather - > scanner ) ;
2018-05-18 21:25:17 +08:00
garbage_bury ( feather - > garbage_q , 0 , feather - > logger ) ;
2018-11-27 14:37:13 +08:00
assert ( 0 = = MESA_lqueue_get_count ( feather - > garbage_q ) ) ;
2015-10-10 18:30:12 +08:00
MESA_lqueue_destroy ( feather - > garbage_q , lqueue_destroy_cb , NULL ) ;
2018-05-18 17:17:26 +08:00
int i = 0 ;
2015-10-10 18:30:12 +08:00
for ( i = 0 ; i < MAX_TABLE_NUM ; i + + )
{
if ( feather - > p_table_info [ i ] = = NULL )
{
continue ;
}
2018-12-04 20:12:56 +08:00
table_info_free ( feather - > p_table_info [ i ] ) ;
2015-10-10 18:30:12 +08:00
feather - > p_table_info [ i ] = NULL ;
}
2018-11-27 12:55:52 +08:00
alignment_int64_array_free ( feather - > thread_call_cnt ) ;
alignment_int64_array_free ( feather - > inner_mid_cnt ) ;
alignment_int64_array_free ( feather - > outer_mid_cnt ) ;
alignment_int64_array_free ( feather - > hit_cnt ) ;
alignment_int64_array_free ( feather - > orphan_group_saving ) ;
2019-01-10 15:46:22 +06:00
alignment_int64_array_free ( feather - > not_grp_hit_cnt ) ;
2018-12-02 22:50:20 +08:00
if ( feather - > input_mode = = SOURCE_REDIS )
2018-11-27 19:53:42 +08:00
{
if ( feather - > mr_ctx . read_ctx )
{
redisFree ( feather - > mr_ctx . read_ctx ) ;
feather - > mr_ctx . read_ctx = NULL ;
}
if ( feather - > mr_ctx . write_ctx )
{
redisFree ( feather - > mr_ctx . write_ctx ) ;
feather - > mr_ctx . write_ctx = NULL ;
}
2017-08-07 17:08:52 +08:00
}
2018-11-27 12:55:52 +08:00
for ( i = 0 ; i < feather - > n_tags ; i + + )
{
free ( feather - > accept_tags [ i ] . tag_name ) ;
free ( feather - > accept_tags [ i ] . tag_val ) ;
}
free ( feather - > accept_tags ) ;
2018-12-23 18:18:19 +06:00
free ( feather - > accept_tags_raw ) ;
2018-11-26 18:41:45 +08:00
if ( feather - > stat_on & & feather - > stat_handle )
{
FS_stop ( & ( feather - > stat_handle ) ) ;
}
2015-10-10 18:30:12 +08:00
free ( feather ) ;
return NULL ;
}
2016-02-10 10:01:18 +08:00