From: Tom Peters (thopeter) Date: Thu, 27 Apr 2017 17:26:08 +0000 (-0400) Subject: Merge pull request #867 in SNORT/snort3 from appid_syncup_291042_final to master X-Git-Tag: 3.0.0-233~17 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=be1d9b138e56153eb78df948d6efc4fe082ff428;p=thirdparty%2Fsnort3.git Merge pull request #867 in SNORT/snort3 from appid_syncup_291042_final to master Squashed commit of the following: commit c577f7ef36e3088d5605dc3ab7cc17f5e3b15da9 Author: davis mcpherson Date: Thu Apr 6 15:08:23 2017 -0400 miscellaneous cleanups and fixit fixes implement helper functions to return client/service detected status for the pop3 & imap detectors the index returned for the matched pattern is +1 the actual index value (0 means no match), the index was not being decremented before use in certain cases and this patch fixes those implement unit test to verify the appid api functions implement service detector to use for reg test scenarios dead code cleanup refactor to improve testability and eliminate service_util.h, add unit tests for app_info_table delete dead code, generic config functionality no longer required as detectors can now save this state in the class instance add unit tests for AppIdDetector class refactor appid_session to rename struct HttpSession to class AppIdHttpSession and move it and associated functions to a separate file appid_http_session.[h|cc] refactor unit test code to improve reuse of mocking and common initialization functions streamline processing of version strings add appid api unit test to verify consumption of HA state info generated by the produce HA state api method fix memory leak in changes to version handling code when version string was not saved to session status object fix memory leaks in appid unit tests document utility functions per review comments and uncrustify update copyright notices to conform with cisco standard for imap & pop3 custom pattern matching use (pattern array size + 1) to indicate no match instead of 0. this eliminates need for 'cooked index' that must be decremented on return from find_all function of pattern matcher. fix pop3, imap, and kerberos detectors such that the client & server side detectors both use the client appid detector id to store and lookup the common data structures shared by each. --- diff --git a/src/network_inspectors/appid/CMakeLists.txt b/src/network_inspectors/appid/CMakeLists.txt index 15c0e28ed..8a0ba0bb1 100644 --- a/src/network_inspectors/appid/CMakeLists.txt +++ b/src/network_inspectors/appid/CMakeLists.txt @@ -70,6 +70,8 @@ set ( SP_APPID_SOURCES service_plugins/service_ntp.h service_plugins/service_radius.cc service_plugins/service_radius.h + service_plugins/service_regtest.cc + service_plugins/service_regtest.h service_plugins/service_rexec.cc service_plugins/service_rexec.h service_plugins/service_rfb.cc @@ -98,7 +100,6 @@ set ( SP_APPID_SOURCES service_plugins/service_timbuktu.h service_plugins/service_tns.cc service_plugins/service_tns.h - service_plugins/service_util.h ) set ( DP_APPID_SOURCES @@ -123,8 +124,6 @@ set ( DP_APPID_SOURCES ) set ( UTIL_APPID_SOURCES - appid_utils/appid_utils.cc - appid_utils/appid_utils.h appid_utils/fw_avltree.cc appid_utils/fw_avltree.h appid_utils/ip_funcs.cc @@ -148,6 +147,8 @@ set ( APPID_SOURCES appid_detector.h appid_discovery.cc appid_discovery.h + appid_http_session.cc + appid_http_session.h appid_session.cc appid_session.h appid_inspector.cc diff --git a/src/network_inspectors/appid/Makefile.am b/src/network_inspectors/appid/Makefile.am index c2809336c..50d807b06 100644 --- a/src/network_inspectors/appid/Makefile.am +++ b/src/network_inspectors/appid/Makefile.am @@ -87,6 +87,8 @@ service_plugins/service_ntp.cc \ service_plugins/service_ntp.h \ service_plugins/service_radius.cc \ service_plugins/service_radius.h \ +service_plugins/service_regtest.cc \ +service_plugins/service_regtest.h \ service_plugins/service_rexec.cc \ service_plugins/service_rexec.h \ service_plugins/service_rfb.cc \ @@ -114,12 +116,9 @@ service_plugins/service_tftp.h \ service_plugins/service_timbuktu.cc \ service_plugins/service_timbuktu.h \ service_plugins/service_tns.cc \ -service_plugins/service_tns.h \ -service_plugins/service_util.h +service_plugins/service_tns.h util_file_list = \ -appid_utils/appid_utils.cc \ -appid_utils/appid_utils.h \ appid_utils/fw_avltree.cc \ appid_utils/fw_avltree.h \ appid_utils/ip_funcs.cc \ @@ -142,6 +141,8 @@ appid_detector.cc \ appid_detector.h \ appid_discovery.cc \ appid_discovery.h \ +appid_http_session.cc \ +appid_http_session.h \ appid_session.cc \ appid_session.h \ appid_inspector.cc \ diff --git a/src/network_inspectors/appid/app_info_table.cc b/src/network_inspectors/appid/app_info_table.cc index f5f82b593..d3bf7ce46 100644 --- a/src/network_inspectors/appid/app_info_table.cc +++ b/src/network_inspectors/appid/app_info_table.cc @@ -29,15 +29,9 @@ #include "appid_config.h" #include "appid_api.h" - +#include "appid_inspector.h" #include "log/messages.h" #include "main/snort_debug.h" -#include "service_plugins/service_util.h" - -#define MAX_TABLE_LINE_LEN 1024 -#define CONF_SEPARATORS "\t\n\r" -#define MIN_MAX_TP_FLOW_DEPTH 1 -#define MAX_MAX_TP_FLOW_DEPTH 1000000 static AppInfoTable app_info_table; static AppInfoTable app_info_service_table; @@ -47,7 +41,15 @@ static AppInfoNameTable app_info_name_table; static AppId next_custom_appid = SF_APPID_DYNAMIC_MIN; static AppInfoTable custom_app_info_table; -static inline char* strdupToLower(const char* source) +#define MAX_TABLE_LINE_LEN 1024 +static const char* CONF_SEPARATORS = "\t\n\r"; +static const int MIN_MAX_TP_FLOW_DEPTH = 1; +static const int MAX_MAX_TP_FLOW_DEPTH = 1000000; +static const char* APP_CONFIG_FILE = "appid.conf"; +static const char* USR_CONFIG_FILE = "userappid.conf"; +const char* APP_MAPPING_FILE = "appMapping.data"; + +static inline char* strdup_to_lower(const char* source) { char* dest = snort_strdup(source); char* lcd = dest; @@ -73,7 +75,7 @@ static AppInfoTableEntry* find_app_info_by_name(const char* app_name) { AppInfoTableEntry* entry = nullptr; AppInfoNameTable::iterator app; - const char* search_name = strdupToLower(app_name); + const char* search_name = strdup_to_lower(app_name); app = app_info_name_table.find(search_name); if ( app != app_info_name_table.end() ) @@ -83,14 +85,21 @@ static AppInfoTableEntry* find_app_info_by_name(const char* app_name) return entry; } -static void add_entry_to_app_info_hash(const char* app_name, AppInfoTableEntry* entry) +static bool add_entry_to_app_info_name_table(const char* app_name, AppInfoTableEntry* entry) { + bool added = true; + if ( !is_existing_entry(entry) ) app_info_name_table[app_name] = entry; else + { WarningMessage( "App name, \"%s\"is a duplicate existing entry will be shared by each detector.\n", app_name); + added = false; + } + + return added; } static AppId get_static_app_info_entry(AppId appid) @@ -145,12 +154,12 @@ AppInfoTableEntry* AppInfoManager::add_dynamic_app_entry(const char* app_name) if (!entry) { entry = new AppInfoTableEntry(next_custom_appid++, snort_strdup(app_name)); - entry->app_name_key = strdupToLower(app_name); + entry->app_name_key = strdup_to_lower(app_name); entry->serviceId = entry->appId; entry->clientId = entry->appId; entry->payloadId = entry->appId; custom_app_info_table[entry->appId] = entry; - add_entry_to_app_info_hash(entry->app_name_key, entry); + add_entry_to_app_info_name_table(entry->app_name_key, entry); } return entry; @@ -160,7 +169,6 @@ void AppInfoManager::cleanup_appid_info_table() { for (auto& kv: app_info_table) delete(kv.second); - app_info_table.erase(app_info_table.begin(), app_info_table.end()); for (auto& kv: custom_app_info_table) @@ -225,9 +233,9 @@ void AppInfoManager::set_app_info_active(AppId appId) WarningMessage("AppInfo: AppId %d has no entry in application info table\n", appId); } -void AppInfoManager::load_appid_config(AppIdModuleConfig* mod_config, const char* path) +void AppInfoManager::load_appid_config(AppIdModuleConfig* config, const char* path) { - char buf[1024]; + char buf[MAX_TABLE_LINE_LEN]; unsigned line = 0; FILE* config_file = fopen(path, "r"); @@ -271,8 +279,8 @@ void AppInfoManager::load_appid_config(AppIdModuleConfig* mod_config, const char if (!(strcasecmp(conf_key, "max_tp_flow_depth"))) { int max_tp_flow_depth = atoi(conf_val); - if (max_tp_flow_depth < MIN_MAX_TP_FLOW_DEPTH || max_tp_flow_depth > - MAX_MAX_TP_FLOW_DEPTH) + if (max_tp_flow_depth < MIN_MAX_TP_FLOW_DEPTH + || max_tp_flow_depth > MAX_MAX_TP_FLOW_DEPTH) { ParseWarning(WARN_CONF, "AppId: invalid max_tp_flow_depth %d, must be between %d and %d\n.", @@ -283,7 +291,7 @@ void AppInfoManager::load_appid_config(AppIdModuleConfig* mod_config, const char DebugFormat(DEBUG_APPID, "AppId: setting max thirdparty inspection flow depth to %d packets.\n", max_tp_flow_depth); - mod_config->max_tp_flow_depth = max_tp_flow_depth; + config->max_tp_flow_depth = max_tp_flow_depth; } } else if (!(strcasecmp(conf_key, "tp_allow_probes"))) @@ -293,7 +301,7 @@ void AppInfoManager::load_appid_config(AppIdModuleConfig* mod_config, const char DebugMessage(DEBUG_APPID, "AppId: TCP probes will be analyzed by NAVL.\n"); - mod_config->tp_allow_probes = 1; + config->tp_allow_probes = 1; } } else if (!(strcasecmp(conf_key, "tp_client_app"))) @@ -315,7 +323,7 @@ void AppInfoManager::load_appid_config(AppIdModuleConfig* mod_config, const char if (!(strcasecmp(conf_val, "disabled"))) { DebugMessage(DEBUG_APPID, "AppId: disabling safe search enforcement.\n"); - mod_config->disable_safe_search = 1; + config->safe_search_enabled = false; } } else if (!(strcasecmp(conf_key, "ssl_squelch"))) @@ -346,7 +354,7 @@ void AppInfoManager::load_appid_config(AppIdModuleConfig* mod_config, const char { DebugMessage(DEBUG_APPID, "AppId: HTTP UserID collection disabled.\n"); - mod_config->chp_userid_disabled = 1; + config->chp_userid_disabled = true; continue; } } @@ -356,7 +364,7 @@ void AppInfoManager::load_appid_config(AppIdModuleConfig* mod_config, const char { DebugMessage(DEBUG_APPID, "AppId: HTTP Body header reading disabled.\n"); - mod_config->chp_body_collection_disabled = 1; + config->chp_body_collection_disabled = 1; continue; } } @@ -365,7 +373,7 @@ void AppInfoManager::load_appid_config(AppIdModuleConfig* mod_config, const char if (!(strcasecmp(conf_val, "disabled"))) { DebugMessage(DEBUG_APPID, "AppId: FTP userID disabled.\n"); - mod_config->ftp_userid_disabled = 1; + config->ftp_userid_disabled = 1; continue; } } @@ -391,10 +399,10 @@ void AppInfoManager::load_appid_config(AppIdModuleConfig* mod_config, const char { if (!(strcasecmp(conf_val, "disabled"))) { - mod_config->referred_appId_disabled = 1; + config->referred_appId_disabled = true; continue; } - else if (!mod_config->referred_appId_disabled) + else if (!config->referred_appId_disabled) { char referred_app_list[4096]; int referred_app_index = snprintf(referred_app_list, 4096, "%d ", atoi( @@ -415,19 +423,19 @@ void AppInfoManager::load_appid_config(AppIdModuleConfig* mod_config, const char } else if (!(strcasecmp(conf_key, "rtmp_max_packets"))) { - mod_config->rtmp_max_packets = atoi(conf_val); + config->rtmp_max_packets = atoi(conf_val); } else if (!(strcasecmp(conf_key, "mdns_user_report"))) { - mod_config->mdns_user_reporting = atoi(conf_val); + config->mdns_user_reporting = atoi(conf_val) ? true : false; } else if (!(strcasecmp(conf_key, "dns_host_report"))) { - mod_config->dns_host_reporting = atoi(conf_val); + config->dns_host_reporting = atoi(conf_val) ? true : false; } else if (!(strcasecmp(conf_key, "chp_body_max_bytes"))) { - mod_config->chp_body_collection_max = atoi(conf_val); + config->chp_body_collection_max = atoi(conf_val); } else if (!(strcasecmp(conf_key, "ignore_thirdparty_appid"))) { @@ -446,12 +454,12 @@ void AppInfoManager::load_appid_config(AppIdModuleConfig* mod_config, const char if (!(strcasecmp(conf_val, "disabled"))) { DebugMessage(DEBUG_APPID, "AppId: disabling internal HTTP/2 detection.\n"); - mod_config->http2_detection_enabled = false; + config->http2_detection_enabled = false; } else if (!(strcasecmp(conf_val, "enabled"))) { DebugMessage(DEBUG_APPID, "AppId: enabling internal HTTP/2 detection.\n"); - mod_config->http2_detection_enabled = true; + config->http2_detection_enabled = true; } else { @@ -547,10 +555,10 @@ void AppInfoManager::init_appid_info_table(AppIdModuleConfig* mod_config) snortName = snort_strdup(token); entry = new AppInfoTableEntry(appId, app_name); - entry->snortId = add_appid_protocol_reference(snortName); + entry->snortId = AppIdInspector::get_inspector()->add_appid_protocol_reference(snortName); snort_free(snortName); snortName = nullptr; - entry->app_name_key = strdupToLower(app_name); + entry->app_name_key = strdup_to_lower(app_name); entry->serviceId = serviceId; entry->clientId = clientId; entry->payloadId = payloadId; @@ -564,17 +572,10 @@ void AppInfoManager::init_appid_info_table(AppIdModuleConfig* mod_config) if ((appId = get_static_app_info_entry(entry->payloadId))) app_info_payload_table[appId] = entry; - add_entry_to_app_info_hash(entry->app_name_key, entry); + add_entry_to_app_info_name_table(entry->app_name_key, entry); } fclose(tableFile); - /* Configuration defaults. */ - mod_config->rtmp_max_packets = 15; - mod_config->mdns_user_reporting = 1; - mod_config->dns_host_reporting = 1; - mod_config->max_tp_flow_depth = 5; - mod_config->http2_detection_enabled = false; - snprintf(filepath, sizeof(filepath), "%s/odp/%s", mod_config->app_detector_dir, APP_CONFIG_FILE); load_appid_config (mod_config, filepath); diff --git a/src/network_inspectors/appid/appid_api.cc b/src/network_inspectors/appid/appid_api.cc index 41a3b297e..779f76c33 100644 --- a/src/network_inspectors/appid/appid_api.cc +++ b/src/network_inspectors/appid/appid_api.cc @@ -24,7 +24,7 @@ #endif #include "appid_api.h" - +#include "appid_http_session.h" #include "app_info_table.h" #include "thirdparty_appid_utils.h" #include "service_plugins/service_bootp.h" @@ -56,7 +56,7 @@ AppId AppIdApi::get_service_app_id(AppIdSession* asd) AppId AppIdApi::get_port_service_app_id(AppIdSession* asd) { if (asd) - return asd->portServiceAppId; + return asd->port_service_id; return APP_ID_NONE; } @@ -169,13 +169,15 @@ bool AppIdApi::is_appid_inspecting_session(AppIdSession* asd) { return true; } + if (asd->client_disco_state != APPID_DISCO_STATE_FINISHED && - (!asd->get_session_flags(APPID_SESSION_CLIENT_DETECTED) || + (!asd->is_client_detected() || (asd->service_disco_state != APPID_DISCO_STATE_STATEFUL && asd->get_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS)))) { return true; } + if (asd->tp_app_id == APP_ID_SSH && asd->payload_app_id != APP_ID_SFTP && asd->session_packet_count < MAX_SFTP_PACKET_COUNT) { @@ -194,6 +196,7 @@ char* AppIdApi::get_user_name(AppIdSession* asd, AppId* service, bool* isLoginSu userName = asd->username; *service = asd->username_service; *isLoginSuccessful = asd->get_session_flags(APPID_SESSION_LOGIN_SUCCEEDED) ? true : false; + //FIXIT-L: what is this ownership transfer about, doesn't smell right... asd->username = nullptr; //transfer ownership to caller. return userName; } @@ -227,12 +230,12 @@ APPID_FLOW_TYPE AppIdApi::get_flow_type(AppIdSession* asd) } void AppIdApi::get_service_info(AppIdSession* asd, char** serviceVendor, char** serviceVersion, - RNAServiceSubtype** serviceSubtype) + AppIdServiceSubtype** serviceSubtype) { if (asd) { - *serviceVendor = asd->serviceVendor; - *serviceVersion = asd->serviceVersion; + *serviceVendor = asd->service_vendor; + *serviceVersion = asd->service_version; *serviceSubtype = asd->subtype; } else @@ -492,33 +495,32 @@ char* AppIdApi::get_netbios_name(AppIdSession* asd) uint32_t AppIdApi::produce_ha_state(Flow* flow, uint8_t* buf) { + assert(flow); + assert(buf); AppIdSessionHA* appHA = (AppIdSessionHA*)buf; AppIdSession* asd = (AppIdSession*)(flow->get_flow_data(AppIdSession::flow_id)); - if ( get_flow_type(asd) != APPID_FLOW_TYPE_NORMAL ) - asd = nullptr; - if ( asd ) + if ( asd && ( get_flow_type(asd) == APPID_FLOW_TYPE_NORMAL ) ) { appHA->flags = APPID_HA_FLAGS_APP; if (is_third_party_appid_available(asd->tpsession)) appHA->flags |= APPID_HA_FLAGS_TP_DONE; - if (asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (asd->is_service_detected()) appHA->flags |= APPID_HA_FLAGS_SVC_DONE; if (asd->get_session_flags(APPID_SESSION_HTTP_SESSION)) appHA->flags |= APPID_HA_FLAGS_HTTP; appHA->appId[0] = asd->tp_app_id; - appHA->appId[1] = asd->serviceAppId; + appHA->appId[1] = asd->service_app_id; appHA->appId[2] = asd->client_service_app_id; - appHA->appId[3] = asd->portServiceAppId; + appHA->appId[3] = asd->port_service_id; appHA->appId[4] = asd->payload_app_id; appHA->appId[5] = asd->tp_payload_app_id; appHA->appId[6] = asd->client_app_id; appHA->appId[7] = asd->misc_app_id; } else - { memset(appHA->appId, 0, sizeof(appHA->appId)); - } + return sizeof(*appHA); } @@ -535,19 +537,19 @@ uint32_t AppIdApi::consume_ha_state(Flow* flow, const uint8_t* buf, uint8_t, IpP { asd = new AppIdSession(proto, ip, port); flow->set_flow_data(asd); - asd->serviceAppId = appHA->appId[1]; - if (asd->serviceAppId == APP_ID_FTP_CONTROL) + asd->service_app_id = appHA->appId[1]; + if (asd->service_app_id == APP_ID_FTP_CONTROL) { asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED | APPID_SESSION_NOT_A_SERVICE | APPID_SESSION_SERVICE_DETECTED); - if (!AddFTPServiceState(asd)) - { + if ( !ServiceDiscovery::add_ftp_service_state(*asd) ) asd->set_session_flags(APPID_SESSION_CONTINUE); - } + asd->service_disco_state = APPID_DISCO_STATE_STATEFUL; } else asd->service_disco_state = APPID_DISCO_STATE_FINISHED; + asd->client_disco_state = APPID_DISCO_STATE_FINISHED; if (thirdparty_appid_module) thirdparty_appid_module->session_state_set(asd->tpsession, TP_STATE_HA); @@ -559,14 +561,14 @@ uint32_t AppIdApi::consume_ha_state(Flow* flow, const uint8_t* buf, uint8_t, IpP asd->set_session_flags(APPID_SESSION_NO_TPI); } if (appHA->flags & APPID_HA_FLAGS_SVC_DONE) - asd->set_session_flags(APPID_SESSION_SERVICE_DETECTED); + asd->set_service_detected(); if (appHA->flags & APPID_HA_FLAGS_HTTP) asd->set_session_flags(APPID_SESSION_HTTP_SESSION); asd->tp_app_id = appHA->appId[0]; - asd->serviceAppId = appHA->appId[1]; + asd->service_app_id = appHA->appId[1]; asd->client_service_app_id = appHA->appId[2]; - asd->portServiceAppId = appHA->appId[3]; + asd->port_service_id = appHA->appId[3]; asd->payload_app_id = appHA->appId[4]; asd->tp_payload_app_id = appHA->appId[5]; asd->client_app_id = appHA->appId[6]; @@ -623,15 +625,14 @@ uint32_t AppIdApi::get_dns_ttl(AppIdSession* asd) return 0; } -bool is_http_inspection_done(AppIdSession* asd) +bool AppIdApi::is_http_inspection_done(AppIdSession* asd) { bool done = true; if ( asd && ( asd->common.flow_type == APPID_FLOW_TYPE_NORMAL ) && - !is_third_party_appid_done(asd->tpsession) ) + !is_third_party_appid_done(asd->tpsession) ) done = false; return done; } - diff --git a/src/network_inspectors/appid/appid_api.h b/src/network_inspectors/appid/appid_api.h index fb87cf3d4..a0aa85fe8 100644 --- a/src/network_inspectors/appid/appid_api.h +++ b/src/network_inspectors/appid/appid_api.h @@ -26,10 +26,6 @@ enum class IpProtocol : uint8_t; -#define APP_MAPPING_FILE "appMapping.data" -#define APP_CONFIG_FILE "appid.conf" -#define USR_CONFIG_FILE "userappid.conf" - #define APPID_SESSION_RESPONDER_MONITORED (1ULL << 0) #define APPID_SESSION_INITIATOR_MONITORED (1ULL << 1) #define APPID_SESSION_SPECIAL_MONITORED (1ULL << 2) @@ -100,9 +96,9 @@ enum APPID_FLOW_TYPE APPID_FLOW_TYPE_TMP }; -struct RNAServiceSubtype +struct AppIdServiceSubtype { - RNAServiceSubtype* next; + AppIdServiceSubtype* next; const char* service; const char* vendor; const char* version; @@ -204,7 +200,7 @@ public: uint64_t get_appid_session_attribute(AppIdSession*, uint64_t flag); APPID_FLOW_TYPE get_flow_type(AppIdSession*); void get_service_info(AppIdSession*, char** serviceVendor, char** serviceVersion, - RNAServiceSubtype**); + AppIdServiceSubtype**); short get_service_port(AppIdSession*); SfIp* get_service_ip(AppIdSession*); SfIp* get_initiator_ip(AppIdSession*); diff --git a/src/network_inspectors/appid/appid_config.cc b/src/network_inspectors/appid/appid_config.cc index c1d38f8b0..6dd1ee6b7 100644 --- a/src/network_inspectors/appid/appid_config.cc +++ b/src/network_inspectors/appid/appid_config.cc @@ -31,7 +31,6 @@ #include "app_info_table.h" #include "appid_session.h" #include "thirdparty_appid_utils.h" -#include "appid_utils/appid_utils.h" #ifdef USE_RNA_CONFIG #include "appid_utils/network_set.h" #endif @@ -46,7 +45,12 @@ #define MAX_DISPLAY_SIZE 65536 #define MAX_LINE 2048 -uint32_t app_id_netmasks[33]; +uint32_t app_id_netmasks[33] = +{ 0x00000000, 0x80000000, 0xC0000000, 0xE0000000, 0xF0000000, 0xF8000000, 0xFC000000, + 0xFE000000, 0xFF000000, 0xFF800000, 0xFFC00000, 0xFFE00000, 0xFFF00000, 0xFFF80000, + 0xFFFC0000, 0xFFFE0000, 0xFFFF0000, 0xFFFF8000, 0xFFFFC000, 0xFFFFE000, 0xFFFFF000, + 0xFFFFF800, 0xFFFFFC00, 0xFFFFFE00, 0xFFFFFF00, 0xFFFFFF80, 0xFFFFFFC0, 0xFFFFFFE0, + 0xFFFFFFF0, 0xFFFFFFF8, 0xFFFFFFFC, 0xFFFFFFFE, 0xFFFFFFFF }; struct PortList { @@ -54,8 +58,6 @@ struct PortList uint16_t port; }; -static THREAD_LOCAL SF_LIST appid_custom_configs; - int16_t snortId_for_unsynchronized; int16_t snortId_for_ftp_data; int16_t snortId_for_http2; @@ -114,53 +116,6 @@ AppIdConfig::~AppIdConfig() cleanup(); } -void AppidConfigElement::add_generic_config_element(const char* name, void* data) -{ - AppidConfigElement* ce; - - ce = (AppidConfigElement*)snort_calloc(sizeof(AppidConfigElement)); - ce->name = snort_strdup(name); - ce->value = data; - sflist_add_tail(&appid_custom_configs, ce); -} - -void* AppidConfigElement::find_generic_config_element(const char* name) -{ - AppidConfigElement* ce; - SF_LNODE* next; - - // Search a module's configuration by its name - for (ce = (AppidConfigElement*)sflist_first(&appid_custom_configs, &next); - ce != nullptr; - ce = (AppidConfigElement*)sflist_next(&next)) - { - if (strcmp(ce->name, name) == 0) - return ce->value; - } - - return nullptr; -} - -void AppidConfigElement::remove_generic_config_element(const char* name) -{ - SF_LNODE* iter; - AppidConfigElement* ce; - - // Search a module's configuration by its name - for (ce = (AppidConfigElement*)sflist_first(&appid_custom_configs, &iter); - ce != nullptr; - ce = (AppidConfigElement*)sflist_next(&iter)) - { - if (strcmp(ce->name, name) == 0) - { - snort_free(ce->name); - snort_free(ce); - sflist_remove_node(&appid_custom_configs, iter); - break; - } - } -} - void AppIdConfig::read_port_detectors(const char* files) { int rval; @@ -604,6 +559,74 @@ void AppIdConfig::process_config_directive(char* toklist[], int /* reload */) } } +static int strip(char* data) +{ + int size; + char* idx; + + idx = data; + size = 0; + + while (*idx) + { + if ((*idx == '\n') || (*idx == '\r')) + { + *idx = 0; + break; + } + if (*idx == '\t') + { + *idx = ' '; + } + size++; + idx++; + } + + return size; +} + +#define MAX_TOKS 256 +static int tokenize(char* data, char* toklist[]) +{ + char** ap; + int argcount = 0; + int i = 0; + char* tok; + int drop_further = 0; + + for (ap = (char**)toklist; ap < &toklist[MAX_TOKS] && (*ap = strsep(&data, " ")) != nullptr; ) + { + if (**ap != '\0') + { + ap++; + argcount++; + } + } + + *ap = nullptr; + + /* scan for comments */ + while (i < argcount) + { + tok = toklist[i]; + + if (tok[0] == '#' && !drop_further) + { + argcount = i; + drop_further = 1; + } + + if (drop_further) + { + toklist[i] = nullptr; + } + + i++; + } + + return argcount; +} + int AppIdConfig::load_analysis_config(const char* config_file, int reload, int instance_id) { FILE* fp; @@ -645,7 +668,7 @@ int AppIdConfig::load_analysis_config(const char* config_file, int reload, int i while (fgets(linebuffer, MAX_LINE, fp) != nullptr) { line++; - AppIdUtils::strip(linebuffer); + strip(linebuffer); cptr = linebuffer; while (isspace((int)*cptr)) @@ -654,7 +677,7 @@ int AppIdConfig::load_analysis_config(const char* config_file, int reload, int i if (*cptr && (*cptr != '#') && (*cptr != 0x0a)) { memset(toklist, 0, sizeof(toklist)); - num_toks = AppIdUtils::tokenize(cptr, toklist); + num_toks = tokenize(cptr, toklist); if (num_toks < 2) { fclose(fp); @@ -706,16 +729,16 @@ int AppIdConfig::load_analysis_config(const char* config_file, int reload, int i #endif -void AppIdConfig::set_safe_search_enforcement(int enabled) +void AppIdConfig::set_safe_search_enforcement(bool enabled) { - DEBUG_WRAP(DebugFormat(DEBUG_APPID, " Safe Search Enforcement enabled = %d.\n",enabled); ); - mod_config->disable_safe_search = enabled ? 0 : 1; + DEBUG_WRAP(DebugFormat(DEBUG_APPID, + " Safe Search Enforcement enabled = %d.\n", enabled); ); + mod_config->safe_search_enabled = enabled; } bool AppIdConfig::init_appid( ) { map_app_names_to_snort_ids(); - AppIdUtils::init_netmasks(app_id_netmasks); app_info_mgr.init_appid_info_table(mod_config); #ifdef USE_RNA_CONFIG load_analysis_config(mod_config->conf_file, 0, mod_config->instance_id); diff --git a/src/network_inspectors/appid/appid_config.h b/src/network_inspectors/appid/appid_config.h index ededb3cdd..ae8259150 100644 --- a/src/network_inspectors/appid/appid_config.h +++ b/src/network_inspectors/appid/appid_config.h @@ -52,24 +52,6 @@ struct PortExclusion ip::snort_in6_addr netmask; }; -// Modules can use this generic data structure to store their configuration. -// All such generic configurations are stored in genericConfigList. Modules -// are responsible for populating the configuration in init() and cleaning it -// up in clean() function. -// -// Currently, IMAP, PO3 and MDNS use this data structure. Lua modules currently -// do not have any configuration. They can use this data structure in the future, -// if needed. -struct AppidConfigElement -{ - char* name; ///< Module name - void* value; ///< Module configuration data - - static void add_generic_config_element(const char* name, void* pData); - static void* find_generic_config_element(const char* name); - static void remove_generic_config_element(const char* name); -}; - struct AppIdSessionLogFilter { AppIdSessionLogFilter() @@ -109,19 +91,18 @@ public: bool dump_ports = false; AppIdSessionLogFilter session_log_filter; - // FIXIT-L configs below not set from appid preproc config, should they be? - uint32_t disable_safe_search = 0; - uint32_t dns_host_reporting = 0; - uint32_t referred_appId_disabled = 0; - uint32_t rtmp_max_packets = 0; - uint32_t mdns_user_reporting = 0; + bool safe_search_enabled = true; + bool dns_host_reporting = true; + bool referred_appId_disabled = false; + bool mdns_user_reporting = true; + bool chp_userid_disabled = false; + bool http2_detection_enabled = false; uint32_t ftp_userid_disabled = 0; - uint32_t chp_userid_disabled = 0; uint32_t chp_body_collection_disabled = 0; uint32_t chp_body_collection_max = 0; - uint32_t max_tp_flow_depth = 0; + uint32_t rtmp_max_packets = 15; + uint32_t max_tp_flow_depth = 5; uint32_t tp_allow_probes = 0; - bool http2_detection_enabled = false; }; typedef std::array AppIdPortExclusions; @@ -135,7 +116,7 @@ public: bool init_appid(); void cleanup(); void show(); - void set_safe_search_enforcement(int enabled); + void set_safe_search_enforcement(bool enabled); AppId get_port_service_id(IpProtocol, uint16_t port); unsigned max_service_info = 0; diff --git a/src/network_inspectors/appid/appid_detector.cc b/src/network_inspectors/appid/appid_detector.cc index c96ad449d..49d3f5972 100644 --- a/src/network_inspectors/appid/appid_detector.cc +++ b/src/network_inspectors/appid/appid_detector.cc @@ -26,6 +26,7 @@ #include "appid_detector.h" #include "appid_config.h" +#include "appid_http_session.h" #include "app_info_table.h" #include "lua_detector_api.h" #include "protocols/packet.h" @@ -60,23 +61,6 @@ int AppIdDetector::initialize() return APPID_SUCCESS; } -void AppIdDetector::activate() -{ -} - -int AppIdDetector::validate(AppIdDiscoveryArgs&) -{ - return APPID_SUCCESS; -} - -void AppIdDetector::clean() -{ -} - -void AppIdDetector::register_appid(AppId, unsigned) -{ -} - void* AppIdDetector::data_get(AppIdSession* asd) { return asd->get_flow_data(flow_data_index); @@ -93,7 +77,7 @@ void AppIdDetector::add_info(AppIdSession* asd, const char* info) asd->hsession->url = snort_strdup(info); } -void AppIdDetector::add_user(AppIdSession* asd, const char* username, AppId appId, int success) +void AppIdDetector::add_user(AppIdSession* asd, const char* username, AppId appId, bool success) { if (asd->username) snort_free(asd->username); @@ -126,7 +110,7 @@ void AppIdDetector::add_app(AppIdSession* asd, AppId service_id, AppId id, const asd->client_version = snort_strdup(version); } - asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + asd->set_client_detected(); asd->client_service_app_id = service_id; asd->client_app_id = id; } diff --git a/src/network_inspectors/appid/appid_detector.h b/src/network_inspectors/appid/appid_detector.h index b18bd6e97..9e416cd03 100644 --- a/src/network_inspectors/appid/appid_detector.h +++ b/src/network_inspectors/appid/appid_detector.h @@ -71,7 +71,11 @@ class AppIdDiscoveryArgs public: AppIdDiscoveryArgs(const uint8_t* data, uint16_t size, int dir, AppIdSession* asd, Packet* p) : data(data), size(size), dir(dir), asd(asd), pkt(p) - { } + { + config = asd->config; + session_logging_enabled = asd->session_logging_enabled; + session_logging_id = asd->session_logging_id; + } const uint8_t* data; uint16_t size; @@ -105,29 +109,67 @@ public: virtual int initialize(); virtual void do_custom_init() = 0; - virtual void activate(); - virtual int validate(AppIdDiscoveryArgs&); - virtual void clean(); - virtual void register_appid(AppId, unsigned extractsInfo); + virtual int validate(AppIdDiscoveryArgs&) = 0; + virtual void register_appid(AppId, unsigned extractsInfo) = 0; virtual void* data_get(AppIdSession*); virtual int data_add(AppIdSession*, void*, AppIdFreeFCN); virtual void add_info(AppIdSession*, const char*); - virtual void add_user(AppIdSession*, const char*, AppId, int); + virtual void add_user(AppIdSession*, const char*, AppId, bool); virtual void add_payload(AppIdSession*, AppId); virtual void add_app(AppIdSession*, AppId, AppId, const char*); -public: // FIXIT-M - make this protected: + const std::string& get_name() const + { + return name; + } + + unsigned get_minimum_matches() const + { + return minimum_matches; + } + + void set_minimum_matches(unsigned minimumMatches = 0) + { + minimum_matches = minimumMatches; + } + + unsigned int get_precedence() const + { + return precedence; + } + + unsigned get_flow_data_index() const + { + return flow_data_index; + } + + bool is_custom_detector() const + { + return custom_detector; + } + + void set_custom_detector(bool isCustom = false) + { + this->custom_detector = isCustom; + } + + AppIdDiscovery& get_handler() const + { + return *handler; + } + +protected: AppIdDiscovery* handler = nullptr; std::string name; bool enabled = true; + bool custom_detector = false; IpProtocol proto = IpProtocol::PROTO_NOT_SET; unsigned minimum_matches = 0; unsigned int precedence = 0; bool provides_user = false; unsigned flow_data_index = 0; unsigned detectorType = DETECTOR_TYPE_NOT_SET; - bool isCustom = false; AppIdFlowContentPatterns tcp_patterns; AppIdFlowContentPatterns udp_patterns; @@ -135,7 +177,6 @@ public: // FIXIT-M - make this protected: ServiceDetectorPorts service_ports; }; - #if defined(WORDS_BIGENDIAN) #define LETOHS(p) BYTE_SWAP_16(*((uint16_t*)(p))) #define LETOHL(p) BYTE_SWAP_32(*((uint32_t*)(p))) diff --git a/src/network_inspectors/appid/appid_discovery.cc b/src/network_inspectors/appid/appid_discovery.cc index c97b3cd4e..41182b626 100644 --- a/src/network_inspectors/appid/appid_discovery.cc +++ b/src/network_inspectors/appid/appid_discovery.cc @@ -26,15 +26,16 @@ #include "appid_discovery.h" #include "appid_config.h" -#include "appid_module.h" +#include "appid_detector.h" #include "app_forecast.h" +#include "appid_http_session.h" +#include "app_info_table.h" #include "appid_inspector.h" +#include "appid_module.h" #include "appid_session.h" -#include "appid_detector.h" -#include "app_info_table.h" -#include "host_port_app_cache.h" #include "appid_utils/ip_funcs.h" #include "appid_utils/network_set.h" +#include "host_port_app_cache.h" #include "thirdparty_appid_utils.h" #include "service_plugins/service_discovery.h" #include "client_plugins/client_discovery.h" @@ -46,13 +47,10 @@ #include "protocols/packet.h" #include "protocols/tcp.h" -ProfileStats tpPerfStats; - AppIdDiscovery::AppIdDiscovery() { tcp_patterns = new SearchTool("ac_full"); udp_patterns = new SearchTool("ac_full"); - http_matchers = HttpPatternMatchers::get_instance(); } AppIdDiscovery::~AppIdDiscovery() @@ -105,8 +103,7 @@ void AppIdDiscovery::register_detector(std::string name, AppIdDetector* cd, IpP } void AppIdDiscovery::add_pattern_data(AppIdDetector* detector, SearchTool* st, int position, const - uint8_t* const pattern, - unsigned size, unsigned nocase, int* count) + uint8_t* const pattern, unsigned size, unsigned nocase, int* count) { AppIdPatternMatchNode* pd = (AppIdPatternMatchNode*)snort_calloc( sizeof(AppIdPatternMatchNode)); @@ -120,16 +117,14 @@ void AppIdDiscovery::add_pattern_data(AppIdDetector* detector, SearchTool* st, i } void AppIdDiscovery::register_tcp_pattern(AppIdDetector* detector, const uint8_t* const pattern, - unsigned size, - int position, unsigned nocase) + unsigned size, int position, unsigned nocase) { int* count = &tcp_pattern_count; add_pattern_data(detector, tcp_patterns, position, pattern, size, nocase, count); } void AppIdDiscovery::register_udp_pattern(AppIdDetector* detector, const uint8_t* const pattern, - unsigned size, - int position, unsigned nocase) + unsigned size, int position, unsigned nocase) { int* count = &udp_pattern_count; add_pattern_data(detector, udp_patterns, position, pattern, size, nocase, count); @@ -278,8 +273,8 @@ static inline bool is_special_session_monitored(const Packet* p) return false; } - -static bool set_network_attributes(AppIdSession* asd, Packet* p, IpProtocol& protocol, int& direction ) +static bool set_network_attributes(AppIdSession* asd, Packet* p, IpProtocol& protocol, + int& direction) { if (asd) { @@ -346,7 +341,7 @@ static bool is_packet_ignored(AppIdSession* asd, Packet* p, int& direction) else if ( p->is_rebuilt() && !p->flow->is_proxied() ) { if ( direction == APP_ID_FROM_INITIATOR && - asd && asd->hsession && asd->hsession->get_offsets_from_rebuilt ) + asd && asd->hsession && asd->hsession->get_offsets_from_rebuilt ) { HttpPatternMatchers::get_instance()->get_http_offsets(p, asd->hsession); if (asd->session_logging_enabled) @@ -365,134 +360,148 @@ static bool is_packet_ignored(AppIdSession* asd, Packet* p, int& direction) return false; } -static uint64_t is_session_monitored(const Packet* p, int dir, AppIdSession* asd) +static uint64_t is_session_monitored(AppIdSession& asd, const Packet* p, int dir) { uint64_t flags = 0; uint64_t flow_flags = APPID_SESSION_DISCOVER_APP; flow_flags |= (dir == APP_ID_FROM_INITIATOR) ? APPID_SESSION_INITIATOR_SEEN : APPID_SESSION_RESPONDER_SEEN; - if ( asd ) + + flow_flags |= asd.common.flags; + // FIXIT-M - the 2.x purpose of this check is stop monitoring a flow after a + // reload if the flow ip addresses are no longer configured to be + // monitored... this may not apply in snort++, find out and fix + // accordingly + if ( asd.common.policyId != asd.config->appIdPolicyId ) { - flow_flags |= asd->common.flags; - if ( asd->common.policyId != asd->config->appIdPolicyId ) + if (check_port_exclusion(p, dir == APP_ID_FROM_RESPONDER)) { - if (check_port_exclusion(p, dir == APP_ID_FROM_RESPONDER)) - { - flow_flags |= APPID_SESSION_INITIATOR_SEEN | APPID_SESSION_RESPONDER_SEEN | - APPID_SESSION_INITIATOR_CHECKED | APPID_SESSION_RESPONDER_CHECKED; - flow_flags &= ~(APPID_SESSION_INITIATOR_MONITORED | - APPID_SESSION_RESPONDER_MONITORED); - return flow_flags; - } - if (dir == APP_ID_FROM_INITIATOR) - { - if (asd->get_session_flags(APPID_SESSION_INITIATOR_CHECKED)) - { - flags = get_ipfuncs_flags(p, false); - if (flags & IPFUNCS_HOSTS_IP) - flow_flags |= APPID_SESSION_INITIATOR_MONITORED; - else - flow_flags &= ~APPID_SESSION_INITIATOR_MONITORED; - } - - if (asd->get_session_flags(APPID_SESSION_RESPONDER_CHECKED)) - { - flags = get_ipfuncs_flags(p, true); - if (flags & IPFUNCS_HOSTS_IP) - flow_flags |= APPID_SESSION_RESPONDER_MONITORED; - else - flow_flags &= ~APPID_SESSION_RESPONDER_MONITORED; - } - } - else - { - if (asd->get_session_flags(APPID_SESSION_RESPONDER_CHECKED)) - { - flags = get_ipfuncs_flags(p, false); - if (flags & IPFUNCS_HOSTS_IP) - flow_flags |= APPID_SESSION_RESPONDER_MONITORED; - else - flow_flags &= ~APPID_SESSION_RESPONDER_MONITORED; - } - - if (asd->get_session_flags(APPID_SESSION_INITIATOR_CHECKED)) - { - flags = get_ipfuncs_flags(p, true); - if (flags & IPFUNCS_HOSTS_IP) - flow_flags |= APPID_SESSION_INITIATOR_MONITORED; - else - flow_flags &= ~APPID_SESSION_INITIATOR_MONITORED; - } - } - } - - if (asd->get_session_flags(APPID_SESSION_BIDIRECTIONAL_CHECKED) == - APPID_SESSION_BIDIRECTIONAL_CHECKED) + flow_flags |= APPID_SESSION_INITIATOR_SEEN | APPID_SESSION_RESPONDER_SEEN | + APPID_SESSION_INITIATOR_CHECKED | APPID_SESSION_RESPONDER_CHECKED; + flow_flags &= ~(APPID_SESSION_INITIATOR_MONITORED | + APPID_SESSION_RESPONDER_MONITORED); return flow_flags; - + } if (dir == APP_ID_FROM_INITIATOR) { - if (!asd->get_session_flags(APPID_SESSION_INITIATOR_CHECKED)) + if (asd.get_session_flags(APPID_SESSION_INITIATOR_CHECKED)) { flags = get_ipfuncs_flags(p, false); - flow_flags |= APPID_SESSION_INITIATOR_CHECKED; if (flags & IPFUNCS_HOSTS_IP) flow_flags |= APPID_SESSION_INITIATOR_MONITORED; - if (flags & IPFUNCS_USER_IP) - flow_flags |= APPID_SESSION_DISCOVER_USER; - if (flags & IPFUNCS_APPLICATION) - flow_flags |= APPID_SESSION_DISCOVER_APP; - if (is_special_session_monitored(p)) - flow_flags |= APPID_SESSION_SPECIAL_MONITORED; + else + flow_flags &= ~APPID_SESSION_INITIATOR_MONITORED; } - if (!(flow_flags & APPID_SESSION_DISCOVER_APP) - && !asd->get_session_flags(APPID_SESSION_RESPONDER_CHECKED)) + if (asd.get_session_flags(APPID_SESSION_RESPONDER_CHECKED)) { flags = get_ipfuncs_flags(p, true); - if (flags & IPFUNCS_CHECKED) - flow_flags |= APPID_SESSION_RESPONDER_CHECKED; if (flags & IPFUNCS_HOSTS_IP) flow_flags |= APPID_SESSION_RESPONDER_MONITORED; - if (flags & IPFUNCS_APPLICATION) - flow_flags |= APPID_SESSION_DISCOVER_APP; - if (is_special_session_monitored(p)) - flow_flags |= APPID_SESSION_SPECIAL_MONITORED; + else + flow_flags &= ~APPID_SESSION_RESPONDER_MONITORED; } } else { - if (!asd->get_session_flags(APPID_SESSION_RESPONDER_CHECKED)) + if (asd.get_session_flags(APPID_SESSION_RESPONDER_CHECKED)) { flags = get_ipfuncs_flags(p, false); - flow_flags |= APPID_SESSION_RESPONDER_CHECKED; if (flags & IPFUNCS_HOSTS_IP) flow_flags |= APPID_SESSION_RESPONDER_MONITORED; - if (flags & IPFUNCS_APPLICATION) - flow_flags |= APPID_SESSION_DISCOVER_APP; - if (is_special_session_monitored(p)) - flow_flags |= APPID_SESSION_SPECIAL_MONITORED; + else + flow_flags &= ~APPID_SESSION_RESPONDER_MONITORED; } - if (!(flow_flags & APPID_SESSION_DISCOVER_APP) - && !asd->get_session_flags(APPID_SESSION_INITIATOR_CHECKED)) + if (asd.get_session_flags(APPID_SESSION_INITIATOR_CHECKED)) { flags = get_ipfuncs_flags(p, true); - if (flags & IPFUNCS_CHECKED) - flow_flags |= APPID_SESSION_INITIATOR_CHECKED; if (flags & IPFUNCS_HOSTS_IP) flow_flags |= APPID_SESSION_INITIATOR_MONITORED; - if (flags & IPFUNCS_USER_IP) - flow_flags |= APPID_SESSION_DISCOVER_USER; - if (flags & IPFUNCS_APPLICATION) - flow_flags |= APPID_SESSION_DISCOVER_APP; - if (is_special_session_monitored(p)) - flow_flags |= APPID_SESSION_SPECIAL_MONITORED; + else + flow_flags &= ~APPID_SESSION_INITIATOR_MONITORED; } } } - else if (check_port_exclusion(p, false)) + + if (asd.get_session_flags(APPID_SESSION_BIDIRECTIONAL_CHECKED) == + APPID_SESSION_BIDIRECTIONAL_CHECKED) + return flow_flags; + + if (dir == APP_ID_FROM_INITIATOR) + { + if (!asd.get_session_flags(APPID_SESSION_INITIATOR_CHECKED)) + { + flags = get_ipfuncs_flags(p, false); + flow_flags |= APPID_SESSION_INITIATOR_CHECKED; + if (flags & IPFUNCS_HOSTS_IP) + flow_flags |= APPID_SESSION_INITIATOR_MONITORED; + if (flags & IPFUNCS_USER_IP) + flow_flags |= APPID_SESSION_DISCOVER_USER; + if (flags & IPFUNCS_APPLICATION) + flow_flags |= APPID_SESSION_DISCOVER_APP; + if (is_special_session_monitored(p)) + flow_flags |= APPID_SESSION_SPECIAL_MONITORED; + } + + if (!(flow_flags & APPID_SESSION_DISCOVER_APP) + && !asd.get_session_flags(APPID_SESSION_RESPONDER_CHECKED)) + { + flags = get_ipfuncs_flags(p, true); + if (flags & IPFUNCS_CHECKED) + flow_flags |= APPID_SESSION_RESPONDER_CHECKED; + if (flags & IPFUNCS_HOSTS_IP) + flow_flags |= APPID_SESSION_RESPONDER_MONITORED; + if (flags & IPFUNCS_APPLICATION) + flow_flags |= APPID_SESSION_DISCOVER_APP; + if (is_special_session_monitored(p)) + flow_flags |= APPID_SESSION_SPECIAL_MONITORED; + } + } + else + { + if (!asd.get_session_flags(APPID_SESSION_RESPONDER_CHECKED)) + { + flags = get_ipfuncs_flags(p, false); + flow_flags |= APPID_SESSION_RESPONDER_CHECKED; + if (flags & IPFUNCS_HOSTS_IP) + flow_flags |= APPID_SESSION_RESPONDER_MONITORED; + if (flags & IPFUNCS_APPLICATION) + flow_flags |= APPID_SESSION_DISCOVER_APP; + if (is_special_session_monitored(p)) + flow_flags |= APPID_SESSION_SPECIAL_MONITORED; + } + + if (!(flow_flags & APPID_SESSION_DISCOVER_APP) + && !asd.get_session_flags(APPID_SESSION_INITIATOR_CHECKED)) + { + flags = get_ipfuncs_flags(p, true); + if (flags & IPFUNCS_CHECKED) + flow_flags |= APPID_SESSION_INITIATOR_CHECKED; + if (flags & IPFUNCS_HOSTS_IP) + flow_flags |= APPID_SESSION_INITIATOR_MONITORED; + if (flags & IPFUNCS_USER_IP) + flow_flags |= APPID_SESSION_DISCOVER_USER; + if (flags & IPFUNCS_APPLICATION) + flow_flags |= APPID_SESSION_DISCOVER_APP; + if (is_special_session_monitored(p)) + flow_flags |= APPID_SESSION_SPECIAL_MONITORED; + } + } + + return flow_flags; +} + +static uint64_t is_session_monitored(const Packet* p, int dir) +{ + uint64_t flags = 0; + uint64_t flow_flags = APPID_SESSION_DISCOVER_APP; + + flow_flags |= (dir == APP_ID_FROM_INITIATOR) ? + APPID_SESSION_INITIATOR_SEEN : APPID_SESSION_RESPONDER_SEEN; + + if (check_port_exclusion(p, false)) { flow_flags |= APPID_SESSION_INITIATOR_SEEN | APPID_SESSION_RESPONDER_SEEN | APPID_SESSION_INITIATOR_CHECKED | APPID_SESSION_RESPONDER_CHECKED; @@ -548,22 +557,67 @@ static uint64_t is_session_monitored(const Packet* p, int dir, AppIdSession* asd return flow_flags; } +static void lookup_appid_by_host_port(AppIdSession* asd, Packet* p, IpProtocol protocol, + int direction) +{ + HostPortVal* hv = nullptr; + uint16_t port = 0; + const SfIp* ip = nullptr; + asd->scan_flags |= SCAN_HOST_PORT_FLAG; + if (direction == APP_ID_FROM_INITIATOR) + { + ip = p->ptrs.ip_api.get_dst(); + port = p->ptrs.dp; + } + else + { + ip = p->ptrs.ip_api.get_src(); + port = p->ptrs.sp; + } + if ((hv = HostPortCache::find(ip, port, protocol))) + { + switch (hv->type) + { + case 1: + asd->client_app_id = hv->appId; + asd->client_disco_state = APPID_DISCO_STATE_FINISHED; + break; + case 2: + asd->payload_app_id = hv->appId; + break; + default: + asd->service_app_id = hv->appId; + asd->sync_with_snort_id(hv->appId, p); + asd->service_disco_state = APPID_DISCO_STATE_FINISHED; + asd->client_disco_state = APPID_DISCO_STATE_FINISHED; + asd->set_session_flags(APPID_SESSION_SERVICE_DETECTED); + if (thirdparty_appid_module) + thirdparty_appid_module->session_delete(asd->tpsession, 1); + + asd->tpsession = nullptr; + } + } +} + void AppIdDiscovery::do_application_discovery(Packet* p) { IpProtocol protocol = IpProtocol::PROTO_NOT_SET; - AppId client_app_id = 0; - AppId payload_app_id = 0; bool isTpAppidDiscoveryDone = false; int direction = 0; AppIdSession* asd = (AppIdSession*)p->flow->get_flow_data(AppIdSession::flow_id); - if( !set_network_attributes(asd, p, protocol, direction) ) + if ( !set_network_attributes(asd, p, protocol, direction) ) return; if ( is_packet_ignored(asd, p, direction) ) return; - uint64_t flow_flags = is_session_monitored(p, direction, asd); + uint64_t flow_flags; + if (asd) + flow_flags = is_session_monitored(*asd, p, direction); + else + flow_flags = is_session_monitored(p, direction); + if ( !( flow_flags & (APPID_SESSION_DISCOVER_APP | APPID_SESSION_SPECIAL_MONITORED) ) ) { if ( !asd ) @@ -615,9 +669,9 @@ void AppIdDiscovery::do_application_discovery(Packet* p) asd->session_packet_count++; if (direction == APP_ID_FROM_INITIATOR) - asd->stats.initiatorBytes += p->pkth->pktlen; + asd->stats.initiator_bytes += p->pkth->pktlen; else - asd->stats.responderBytes += p->pkth->pktlen; + asd->stats.responder_bytes += p->pkth->pktlen; asd->common.flags = flow_flags; asd->common.policyId = asd->config->appIdPolicyId; @@ -625,11 +679,11 @@ void AppIdDiscovery::do_application_discovery(Packet* p) if (asd->get_session_flags(APPID_SESSION_IGNORE_FLOW)) { if ( asd->session_logging_enabled && - !asd->get_session_flags(APPID_SESSION_IGNORE_FLOW_LOGGED) ) + !asd->get_session_flags(APPID_SESSION_IGNORE_FLOW_LOGGED) ) { asd->set_session_flags(APPID_SESSION_IGNORE_FLOW_LOGGED); LogMessage("AppIdDbg %s Ignoring connection with service %d\n", - asd->session_logging_id, asd->serviceAppId); + asd->session_logging_id, asd->service_app_id); } return; @@ -664,47 +718,8 @@ void AppIdDiscovery::do_application_discovery(Packet* p) } /*HostPort based AppId. */ - if (!(asd->scan_flags & SCAN_HOST_PORT_FLAG)) - { - HostPortVal* hv = nullptr; - uint16_t port = 0; - const SfIp* ip = nullptr; - - asd->scan_flags |= SCAN_HOST_PORT_FLAG; - if (direction == APP_ID_FROM_INITIATOR) - { - ip = p->ptrs.ip_api.get_dst(); - port = p->ptrs.dp; - } - else - { - ip = p->ptrs.ip_api.get_src(); - port = p->ptrs.sp; - } - - if ((hv = HostPortCache::find(ip, port, protocol))) - { - switch (hv->type) - { - case 1: - asd->client_app_id = hv->appId; - asd->client_disco_state = APPID_DISCO_STATE_FINISHED; - break; - case 2: - asd->payload_app_id = hv->appId; - break; - default: - asd->serviceAppId = hv->appId; - asd->sync_with_snort_id(hv->appId, p); - asd->service_disco_state = APPID_DISCO_STATE_FINISHED; - asd->client_disco_state = APPID_DISCO_STATE_FINISHED; - asd->set_session_flags(APPID_SESSION_SERVICE_DETECTED); - if (thirdparty_appid_module) - thirdparty_appid_module->session_delete(asd->tpsession, 1); - asd->tpsession = nullptr; - } - } - } + if ( !(asd->scan_flags & SCAN_HOST_PORT_FLAG) ) + lookup_appid_by_host_port(asd, p, protocol, direction); asd->check_app_detection_restart(); @@ -731,10 +746,10 @@ void AppIdDiscovery::do_application_discovery(Packet* p) // All protocols other than TCP and UDP come straight here. default: { - asd->portServiceAppId = asd->config->get_port_service_id(protocol, p->ptrs.sp); + asd->port_service_id = asd->config->get_port_service_id(protocol, p->ptrs.sp); if (asd->session_logging_enabled) LogMessage("AppIdDbg %s port service %d\n", - asd->session_logging_id, asd->portServiceAppId); + asd->session_logging_id, asd->port_service_id); asd->set_session_flags(APPID_SESSION_PORT_SERVICE_DONE); } break; @@ -746,7 +761,7 @@ void AppIdDiscovery::do_application_discovery(Packet* p) * - Port service didn't find anything (and we haven't yet either). * - We haven't hit the max packets allowed for detector sequence matches. * - Packet has data (we'll ignore 0-sized packets in sequencing). */ - if ( (asd->portServiceAppId <= APP_ID_NONE) + if ( (asd->port_service_id <= APP_ID_NONE) && (asd->length_sequence.sequence_cnt < LENGTH_SEQUENCE_CNT_MAX) && (p->dsize > 0)) { @@ -755,8 +770,8 @@ void AppIdDiscovery::do_application_discovery(Packet* p) asd->length_sequence.sequence_cnt++; asd->length_sequence.sequence[index].direction = direction; asd->length_sequence.sequence[index].length = p->dsize; - asd->portServiceAppId = find_length_app_cache(&asd->length_sequence); - if (asd->portServiceAppId > APP_ID_NONE) + asd->port_service_id = find_length_app_cache(&asd->length_sequence); + if (asd->port_service_id > APP_ID_NONE) asd->set_session_flags(APPID_SESSION_PORT_SERVICE_DONE); } @@ -764,16 +779,17 @@ void AppIdDiscovery::do_application_discovery(Packet* p) if (asd->get_session_flags(APPID_SESSION_REXEC_STDERR)) { ServiceDiscovery::get_instance().identify_service(asd, p, direction); - if (asd->serviceAppId == APP_ID_DNS && + if (asd->service_app_id == APP_ID_DNS && asd->config->mod_config->dns_host_reporting && asd->dsession && asd->dsession->host ) { size_t size = asd->dsession->host_len; + AppId client_app_id = APP_ID_NONE, payload_app_id = APP_ID_NONE; dns_host_scan_hostname((const uint8_t*)asd->dsession->host, size, &client_app_id, &payload_app_id); asd->set_client_app_id_data(client_app_id, nullptr); } - else if (asd->serviceAppId == APP_ID_RTMP) + else if (asd->service_app_id == APP_ID_RTMP) asd->examine_rtmp_metadata(); else if (asd->get_session_flags(APPID_SESSION_SSL_SESSION) && asd->tsession) asd->examine_ssl_metadata(p); @@ -781,12 +797,12 @@ void AppIdDiscovery::do_application_discovery(Packet* p) // FIXIT-M - snort 2.x has added a check for midstream pickup to this if, do we need that? else if (protocol != IpProtocol::TCP || !p->dsize || (p->packet_flags & PKT_STREAM_ORDER_OK)) { - // FIXIT-M commented out assignment causes analysis warning - /*isTpAppidDiscoveryDone = */ - ServiceDiscovery::get_instance().do_service_discovery(*asd, protocol, direction, - client_app_id, payload_app_id, p); - isTpAppidDiscoveryDone = ClientDiscovery::get_instance().do_client_discovery(*asd, - direction, p); + if (asd->service_disco_state != APPID_DISCO_STATE_FINISHED) + isTpAppidDiscoveryDone = + ServiceDiscovery::get_instance().do_service_discovery(*asd, p, direction); + if (asd->client_disco_state != APPID_DISCO_STATE_FINISHED) + isTpAppidDiscoveryDone = + ClientDiscovery::get_instance().do_client_discovery(*asd, p, direction); asd->set_session_flags(APPID_SESSION_ADDITIONAL_PACKET); } else @@ -799,35 +815,34 @@ void AppIdDiscovery::do_application_discovery(Packet* p) } } - AppId serviceAppId = asd->pick_service_app_id(); - payload_app_id = asd->pick_payload_app_id(); + AppId service_app_id = asd->pick_service_app_id(); + AppId payload_app_id = asd->pick_payload_app_id(); - if (serviceAppId > APP_ID_NONE) + if (service_app_id > APP_ID_NONE) { if (asd->get_session_flags(APPID_SESSION_DECRYPTED)) { if (asd->misc_app_id == APP_ID_NONE) - asd->update_encrypted_app_id(serviceAppId); + asd->update_encrypted_app_id(service_app_id); } // FIXIT-M Need to determine what api to use for this _dpd function #if 1 UNUSED(isTpAppidDiscoveryDone); #else - else if (isTpAppidDiscoveryDone && isSslServiceAppId(serviceAppId) && + else if (isTpAppidDiscoveryDone && isSslServiceAppId(service_app_id) && _dpd.isSSLPolicyEnabled(nullptr)) asd->set_session_flags(APPID_SESSION_CONTINUE); #endif } - p->flow->set_application_ids(serviceAppId, asd->pick_client_app_id(), payload_app_id, + p->flow->set_application_ids(service_app_id, asd->pick_client_app_id(), payload_app_id, asd->pick_misc_app_id()); /* Set the field that the Firewall queries to see if we have a search engine. */ if (asd->search_support_type == UNKNOWN_SEARCH_ENGINE && payload_app_id > APP_ID_NONE) { uint flags = AppInfoManager::get_instance().get_app_info_flags(payload_app_id, - APPINFO_FLAG_SEARCH_ENGINE | - APPINFO_FLAG_SUPPORTED_SEARCH); + APPINFO_FLAG_SEARCH_ENGINE | APPINFO_FLAG_SUPPORTED_SEARCH); asd->search_support_type = (flags & APPINFO_FLAG_SEARCH_ENGINE) ? ((flags & APPINFO_FLAG_SUPPORTED_SEARCH) ? SUPPORTED_SEARCH_ENGINE : @@ -849,19 +864,19 @@ void AppIdDiscovery::do_application_discovery(Packet* p) } } - if ( serviceAppId != APP_ID_NONE ) + if ( service_app_id != APP_ID_NONE ) { - if ( payload_app_id != APP_ID_NONE && payload_app_id != asd->pastIndicator) + if ( payload_app_id != APP_ID_NONE && payload_app_id != asd->past_indicator) { - asd->pastIndicator = payload_app_id; + asd->past_indicator = payload_app_id; check_session_for_AF_indicator(p, direction, (ApplicationId)payload_app_id); } - if (asd->payload_app_id == APP_ID_NONE && asd->pastForecast != serviceAppId && - asd->pastForecast != APP_ID_UNKNOWN) + if (asd->payload_app_id == APP_ID_NONE && asd->past_forecast != service_app_id && + asd->past_forecast != APP_ID_UNKNOWN) { - asd->pastForecast = check_session_for_AF_forecast(asd, p, direction, - (ApplicationId)serviceAppId); + asd->past_forecast = check_session_for_AF_forecast(asd, p, direction, + (ApplicationId)service_app_id); } } } diff --git a/src/network_inspectors/appid/appid_discovery.h b/src/network_inspectors/appid/appid_discovery.h index 820d816b3..dbbf80f38 100644 --- a/src/network_inspectors/appid/appid_discovery.h +++ b/src/network_inspectors/appid/appid_discovery.h @@ -29,13 +29,21 @@ #include "search_engines/search_tool.h" #include "flow/flow.h" -class HttpPatternMatchers; class AppIdSession; class AppIdDetector; class ServiceDetector; struct ServiceDetectorPort; struct Packet; +#define SCAN_HTTP_VIA_FLAG (1<<0) +#define SCAN_HTTP_USER_AGENT_FLAG (1<<1) +#define SCAN_HTTP_HOST_URL_FLAG (1<<2) +#define SCAN_SSL_HOST_FLAG (1<<4) +#define SCAN_HOST_PORT_FLAG (1<<5) +#define SCAN_HTTP_VENDOR_FLAG (1<<6) +#define SCAN_HTTP_XWORKINGWITH_FLAG (1<<7) +#define SCAN_HTTP_CONTENT_TYPE_FLAG (1<<8) + struct AppIdPatternMatchNode { AppIdPatternMatchNode* next = nullptr; @@ -76,6 +84,17 @@ public: static void do_application_discovery(Packet* p); + AppIdDetectors* get_tcp_detectors() + { + return &tcp_detectors; + } + + AppIdDetectors* get_udp_detectors() + { + return &udp_detectors; + } + +protected: AppIdDetectors tcp_detectors; AppIdDetectors udp_detectors; SearchTool* tcp_patterns = nullptr; @@ -83,7 +102,6 @@ public: SearchTool* udp_patterns = nullptr; int udp_pattern_count = 0; AppIdPatternMatchNode* pattern_data_list = nullptr; - HttpPatternMatchers* http_matchers; }; #endif diff --git a/src/network_inspectors/appid/appid_http_event_handler.cc b/src/network_inspectors/appid/appid_http_event_handler.cc index ab634511f..e2a1d250a 100644 --- a/src/network_inspectors/appid/appid_http_event_handler.cc +++ b/src/network_inspectors/appid/appid_http_event_handler.cc @@ -29,6 +29,7 @@ #include +#include "appid_http_session.h" #include "appid_module.h" #include "appid_session.h" #include "utils/util.h" @@ -66,7 +67,7 @@ void HttpEventHandler::handle(DataEvent& event, Flow* flow) direction = event_type == REQUEST_EVENT ? APP_ID_FROM_INITIATOR : APP_ID_FROM_RESPONDER; if (!session->hsession) - session->hsession = (decltype(session->hsession))snort_calloc(sizeof(HttpSession)); + session->hsession = new AppIdHttpSession(session); if (direction == APP_ID_FROM_INITIATOR) { @@ -167,7 +168,7 @@ void HttpEventHandler::handle(DataEvent& event, Flow* flow) session->scan_flags |= SCAN_HTTP_VIA_FLAG; } - session->process_http_packet(direction); + session->hsession->process_http_packet(direction); session->set_session_flags(APPID_SESSION_SERVICE_DETECTED | APPID_SESSION_HTTP_SESSION); if (direction == APP_ID_FROM_INITIATOR) appid_stats.http_flows++; diff --git a/src/network_inspectors/appid/appid_http_session.cc b/src/network_inspectors/appid/appid_http_session.cc new file mode 100644 index 000000000..a308d0624 --- /dev/null +++ b/src/network_inspectors/appid/appid_http_session.cc @@ -0,0 +1,674 @@ +//-------------------------------------------------------------------------- +// Copyright (C) 2016-2017 Cisco and/or its affiliates. All rights reserved. +// +// This program is free software; you can redistribute it and/or modify it +// under the terms of the GNU General Public License Version 2 as published +// by the Free Software Foundation. You may not use, modify or distribute +// this program under any other version of the GNU General Public License. +// +// This program is distributed in the hope that it will be useful, but +// WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// General Public License for more details. +// +// You should have received a copy of the GNU General Public License along +// with this program; if not, write to the Free Software Foundation, Inc., +// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +//-------------------------------------------------------------------------- + +// appid_inspector.cc author davis mcpherson +// Created on: Apr 19, 2017 + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#include "appid_http_session.h" + +#include "appid_config.h" +#include "appid_module.h" +#include "appid_session.h" +#include "app_info_table.h" +#include "thirdparty_appid_utils.h" +#include "profiler/profiler.h" + +static const char* httpFieldName[ NUMBER_OF_PTYPES ] = // for use in debug messages +{ + "useragent", + "host", + "referer", + "uri", + "cookie", + "req_body", + "content_type", + "location", + "body", +}; + +ProfileStats httpPerfStats; + +AppIdHttpSession::AppIdHttpSession(AppIdSession* asd) + : asd(asd) +{ + http_matchers = HttpPatternMatchers::get_instance(); +} + +AppIdHttpSession::~AppIdHttpSession() +{ + snort_free(body); + snort_free(content_type); + snort_free(cookie); + snort_free(host); + snort_free(location); + snort_free(referer); + snort_free(req_body); + snort_free(response_code); + snort_free(server); + snort_free(uri); + snort_free(url); + snort_free(useragent); + snort_free(via); + snort_free(x_working_with); + delete xffAddr; + + if (new_field_contents) + for ( unsigned i = 0; i < NUMBER_OF_PTYPES; i++) + if (nullptr != new_field[i]) + snort_free(new_field[i]); +} + +void AppIdHttpSession::free_chp_matches(MatchedCHPAction** ppmatches, unsigned max_matches) +{ + for (unsigned i = 0; i <= max_matches; i++) + { + if (ppmatches[i]) + { + http_matchers->free_matched_chp_actions(ppmatches[i]); + ppmatches[i] = nullptr; + } + } +} + +int AppIdHttpSession::initial_chp_sweep(char** chp_buffers, uint16_t* chp_buffer_lengths, + MatchedCHPAction** ppmatches) +{ + CHPApp* cah = nullptr; + CHPTallyAndActions chp; + chp.matches = *ppmatches; + + for (unsigned i = 0; i <= MAX_KEY_PATTERN; i++) + { + ppmatches[i] = nullptr; + if (chp_buffers[i] && chp_buffer_lengths[i]) + http_matchers->scan_key_chp((PatternType)i, chp_buffers[i], chp_buffer_lengths[i], + chp); + } + + if (chp.match_tally.empty()) + { + free_chp_matches(ppmatches, MAX_KEY_PATTERN); + return 0; + } + + int longest = 0; + for (auto& item: chp.match_tally) + { + // Only those items with key_pattern_countdown field reduced to zero are a full match + if (item.key_pattern_countdown) + continue; + if (longest < item.key_pattern_length_sum) + { + // We've found a new longest pattern set + longest = item.key_pattern_length_sum; + cah = item.chpapp; + } + } + + if ( !cah ) + { + free_chp_matches(ppmatches, MAX_KEY_PATTERN); + return 0; + } + + /*************************************************************** + candidate has been chosen and it is pointed to by cah + we will preserve any match sets until the calls to scanCHP() + ***************************************************************/ + for (unsigned i = 0; i < NUMBER_OF_PTYPES; i++) + { + ptype_scan_counts[i] = cah->ptype_scan_counts[i]; + ptype_req_counts[i] = cah->ptype_req_counts[i] + + cah->ptype_rewrite_insert_used[i]; + if (i > 3 && !cah->ptype_scan_counts[i] + && !asd->get_session_flags(APPID_SESSION_SPDY_SESSION)) + { + asd->clear_session_flags(APPID_SESSION_CHP_INSPECTING); + if (thirdparty_appid_module) + thirdparty_appid_module->session_attr_clear(asd->tpsession, + TP_ATTR_CONTINUE_MONITORING); + } + } + chp_candidate = cah->appIdInstance; + app_type_flags = cah->app_type_flags; + num_matches = cah->num_matches; + num_scans = cah->num_scans; + + if (thirdparty_appid_module) + { + if ((ptype_scan_counts[CONTENT_TYPE_PT])) + thirdparty_appid_module->session_attr_set(asd->tpsession, + TP_ATTR_COPY_RESPONSE_CONTENT); + else + thirdparty_appid_module->session_attr_clear(asd->tpsession, + TP_ATTR_COPY_RESPONSE_CONTENT); + + if ((ptype_scan_counts[LOCATION_PT])) + thirdparty_appid_module->session_attr_set(asd->tpsession, + TP_ATTR_COPY_RESPONSE_LOCATION); + else + thirdparty_appid_module->session_attr_clear(asd->tpsession, + TP_ATTR_COPY_RESPONSE_LOCATION); + + if ((ptype_scan_counts[BODY_PT])) + thirdparty_appid_module->session_attr_set(asd->tpsession, TP_ATTR_COPY_RESPONSE_BODY); + else + thirdparty_appid_module->session_attr_clear(asd->tpsession, + TP_ATTR_COPY_RESPONSE_BODY); + } + + return 1; +} + +void AppIdHttpSession::process_chp_buffers() +{ + char* version = nullptr; + + char* chp_buffers[NUMBER_OF_PTYPES] = + { + useragent, + host, + referer, + uri, + cookie, + req_body, + content_type, + location, + body, + }; + + uint16_t chp_buffer_lengths[NUMBER_OF_PTYPES] = + { + useragent_buflen, + host_buflen, + referer_buflen, + uri_buflen, + cookie_buflen, + req_body_buflen, + content_type_buflen, + location_buflen, + body_buflen, + }; + + char* chp_rewritten[NUMBER_OF_PTYPES] = + { + nullptr,nullptr,nullptr, + nullptr,nullptr,nullptr, + nullptr,nullptr,nullptr + }; + + MatchedCHPAction* chp_matches[NUMBER_OF_PTYPES] = + { + nullptr,nullptr,nullptr, + nullptr,nullptr,nullptr, + nullptr,nullptr,nullptr + }; + + if ( chp_hold_flow ) + chp_finished = false; + + if ( !chp_candidate ) + { + // remove artifacts from previous matches before we start again. + for (unsigned i = 0; i < NUMBER_OF_PTYPES; i++) + if (new_field[i]) + { + snort_free(new_field[i]); + new_field[i] = nullptr; + } + + if ( !initial_chp_sweep(chp_buffers, chp_buffer_lengths, chp_matches) ) + chp_finished = true; // this is a failure case. + } + + if ( !chp_finished && chp_candidate ) + { + char* user = nullptr; + + for (unsigned i = 0; i < NUMBER_OF_PTYPES; i++) + { + if ( !ptype_scan_counts[i] ) + continue; + + if ( chp_buffers[i] && chp_buffer_lengths[i] ) + { + int found_in_buffer = 0; + AppId ret = http_matchers->scan_chp((PatternType)i, chp_buffers[i], + chp_buffer_lengths[i], chp_matches[i], &version, &user, + &chp_rewritten[i], &found_in_buffer, this, asd->config->mod_config); + chp_matches[i] = nullptr; // freed by scanCHP() + total_found += found_in_buffer; + if (!ret || found_in_buffer < ptype_req_counts[i]) + { + // No match at all or the required matches for the field was NOT made + if (!num_matches) + { + // num_matches == 0 means: all must succeed + // give up early + chp_candidate = 0; + break; + } + } + } + else if ( !num_matches ) + { + // num_matches == 0 means: all must succeed give up early + chp_candidate = 0; + break; + } + + // Decrement the expected scan count toward 0. + ptype_scan_counts[i] = 0; + num_scans--; + // if we have reached the end of the list of scans (which have something to do), then + // num_scans == 0 + if (num_scans == 0) + { + // we finished the last scan + // either the num_matches value was zero and we failed early-on or we need to check + // for the min. + if (num_matches && + total_found < num_matches) + { + // There was a minimum scans match count (num_matches != 0) + // And we did not reach that minimum + chp_candidate = 0; + break; + } + // All required matches were met. + chp_finished = true; + break; + } + } + + free_chp_matches(chp_matches, NUMBER_OF_PTYPES); + + if ( !chp_candidate ) + { + chp_finished = true; + if ( version ) + { + snort_free(version); + version = nullptr; + } + + if ( user ) + { + snort_free(user); + user = nullptr; + } + + for (unsigned i = 0; i < NUMBER_OF_PTYPES; i++) + { + if (nullptr != chp_rewritten[i]) + { + snort_free(chp_rewritten[i]); + chp_rewritten[i] = nullptr; + } + } + memset(ptype_scan_counts, 0, NUMBER_OF_PTYPES * sizeof(int)); + + // Make it possible for other detectors to run. + skip_simple_detect = false; + return; + } + + if (chp_candidate && chp_finished) + { + AppId chp_final = chp_alt_candidate ? chp_alt_candidate + : CHP_APPIDINSTANCE_TO_ID(chp_candidate); + + if (app_type_flags & APP_TYPE_SERVICE) + asd->set_service_appid_data(chp_final, nullptr, version); + + if (app_type_flags & APP_TYPE_CLIENT) + asd->set_client_app_id_data(chp_final, version); + + if ( app_type_flags & APP_TYPE_PAYLOAD ) + asd->set_payload_app_id_data((ApplicationId)chp_final, version); + + if ( version ) + version = nullptr; + + if ( user ) + { + asd->username = user; + user = nullptr; + if (app_type_flags & APP_TYPE_SERVICE) + asd->username_service = chp_final; + else + asd->username_service = asd->service_app_id; + asd->set_session_flags(APPID_SESSION_LOGIN_SUCCEEDED); + } + + for (unsigned i = 0; i < NUMBER_OF_PTYPES; i++) + if ( chp_rewritten[i] ) + { + if (asd->session_logging_enabled) + LogMessage("AppIdDbg %s rewritten %s: %s\n", asd->session_logging_id, + httpFieldName[i], chp_rewritten[i]); + if (new_field[i]) + snort_free(new_field[i]); + new_field[i] = chp_rewritten[i]; + new_field_contents = true; + chp_rewritten[i] = nullptr; + } + + chp_candidate = 0; + //if we're doing safesearch rewrites, we want to continue to hold the flow + if (!get_offsets_from_rebuilt) + chp_hold_flow = 0; + asd->scan_flags &= ~SCAN_HTTP_VIA_FLAG; + asd->scan_flags &= ~SCAN_HTTP_USER_AGENT_FLAG; + asd->scan_flags &= ~SCAN_HTTP_HOST_URL_FLAG; + memset(ptype_scan_counts, 0, + NUMBER_OF_PTYPES * sizeof(ptype_scan_counts[0])); + } + else /* if we have a candidate, but we're not finished */ + { + if ( user ) + { + snort_free(user); + user = nullptr; + } + + for (unsigned i = 0; i < NUMBER_OF_PTYPES; i++) + if (nullptr != chp_rewritten[i]) + { + snort_free(chp_rewritten[i]); + chp_rewritten[i] = nullptr; + } + } + } +} + +int AppIdHttpSession::process_http_packet(int direction) +{ + Profile http_profile_context(httpPerfStats); + constexpr auto RESPONSE_CODE_LENGTH = 3; + int size; + AppId service_id = APP_ID_NONE; + AppId client_id = APP_ID_NONE; + AppId payload_id = APP_ID_NONE; + + // For fragmented HTTP headers, do not process if none of the fields are set. + // These fields will get set when the HTTP header is reassembled. + if ((!useragent) && (!host) && (!referer) && (!uri)) + { + if (!skip_simple_detect) + asd->clear_http_flags(); + + return 0; + } + + if (direction == APP_ID_FROM_RESPONDER && + !asd->get_session_flags(APPID_SESSION_RESPONSE_CODE_CHECKED)) + { + if (response_code) + { + asd->set_session_flags(APPID_SESSION_RESPONSE_CODE_CHECKED); + if (response_code_buflen != RESPONSE_CODE_LENGTH) + { + if (asd->session_logging_enabled) + LogMessage("AppIdDbg %s bad http response code.\n", asd->session_logging_id); + asd->reset_session_data(); + return 0; + } + } +#if RESPONSE_CODE_PACKET_THRESHHOLD + else if (++(response_code_packets) == RESPONSE_CODE_PACKET_THRESHHOLD) + { + set_session_flags(APPID_SESSION_RESPONSE_CODE_CHECKED); + /* didn't receive response code in first X packets. Stop processing this session */ + asd->reset_session_data(); + if (asd->session_logging_enabled) + LogMessage("AppIdDbg %s no response code received\n", asd->session_logging_id); + return 0; + } +#endif + } + + if (asd->service_app_id == APP_ID_NONE) + asd->service_app_id = APP_ID_HTTP; + + if (asd->session_logging_enabled) + LogMessage("AppIdDbg %s chp_finished %d chp_hold_flow %d\n", asd->session_logging_id, + chp_finished, chp_hold_flow); + + if (!chp_finished || chp_hold_flow) + process_chp_buffers(); + + if (!skip_simple_detect) // true if processCHP found match + { + if (!asd->get_session_flags(APPID_SESSION_APP_REINSPECT)) + { + // Scan Server Header for Vendor & Version + // FIXIT-M: Should we be checking the scan_flags even when + // thirdparty_appid_module is off? + if ((thirdparty_appid_module && (asd->scan_flags & SCAN_HTTP_VENDOR_FLAG) && + server) || (!thirdparty_appid_module && server)) + { + if (asd->service_app_id == APP_ID_NONE || asd->service_app_id == APP_ID_HTTP) + { + AppIdServiceSubtype* local_subtype = nullptr; + AppIdServiceSubtype** tmpSubtype; + char* vendorVersion = nullptr; + char* vendor = nullptr; + + http_matchers->get_server_vendor_version((uint8_t*)server, + strlen(server), &vendorVersion, &vendor, &asd->subtype); + if (vendor || vendorVersion) + { + if (asd->service_vendor) + { + snort_free(asd->service_vendor); + asd->service_vendor = nullptr; + } + if (asd->service_version) + { + snort_free(asd->service_version); + asd->service_version = nullptr; + } + if (vendor) + asd->service_vendor = vendor; + if (vendorVersion) + asd->service_version = vendorVersion; + asd->scan_flags &= ~SCAN_HTTP_VENDOR_FLAG; + } + if (local_subtype) + { + for (tmpSubtype = &asd->subtype; *tmpSubtype; tmpSubtype = + &(*tmpSubtype)->next) + ; + + *tmpSubtype = local_subtype; + } + } + } + + if (is_webdav) + { + if (asd->session_logging_enabled and asd->payload_app_id != APP_ID_WEBDAV) + LogMessage("AppIdDbg %s data is webdav\n", asd->session_logging_id); + asd->set_payload_app_id_data(APP_ID_WEBDAV, nullptr); + } + + // Scan User-Agent for Browser types or Skype + if ((asd->scan_flags & SCAN_HTTP_USER_AGENT_FLAG) && asd->client_app_id <= APP_ID_NONE + && useragent && useragent_buflen) + { + char* version = nullptr; + + http_matchers->identify_user_agent((uint8_t*)useragent, useragent_buflen, + &service_id, &client_id, &version); + if (asd->session_logging_enabled && service_id > APP_ID_NONE && + service_id != APP_ID_HTTP && asd->service_app_id != service_id) + LogMessage("AppIdDbg %s User Agent is service %d\n", asd->session_logging_id, + service_id); + asd->set_service_appid_data(service_id, nullptr, nullptr); + if (asd->session_logging_enabled && client_id > APP_ID_NONE && + client_id != APP_ID_HTTP && asd->client_app_id != client_id) + LogMessage("AppIdDbg %s User Agent is client %d\n", asd->session_logging_id, + client_id); + asd->set_client_app_id_data(client_id, version); + asd->scan_flags &= ~SCAN_HTTP_USER_AGENT_FLAG; + snort_free(version); + } + + /* Scan Via Header for squid */ + if (!asd->is_payload_appid_set() && (asd->scan_flags & SCAN_HTTP_VIA_FLAG) && via && + (size = strlen(via)) > 0) + { + payload_id = http_matchers->get_appid_by_pattern((uint8_t*)via, size, nullptr); + if (asd->session_logging_enabled && payload_id > APP_ID_NONE && + asd->payload_app_id != payload_id) + LogMessage("AppIdDbg %s VIA is data %d\n", asd->session_logging_id, + payload_id); + asd->set_payload_app_id_data((ApplicationId)payload_id, nullptr); + asd->scan_flags &= ~SCAN_HTTP_VIA_FLAG; + } + } + + /* Scan X-Working-With HTTP header */ + // FIXIT-M: Should we be checking the scan_flags even when + // thirdparty_appid_module is off? + if ((thirdparty_appid_module && (asd->scan_flags & SCAN_HTTP_XWORKINGWITH_FLAG) && + x_working_with) || (!thirdparty_appid_module && x_working_with)) + { + AppId appId; + char* version = nullptr; + + appId = http_matchers->scan_header_x_working_with((uint8_t*)x_working_with, + strlen(x_working_with), &version); + if ( appId ) + { + if (direction == APP_ID_FROM_INITIATOR) + { + if (asd->session_logging_enabled && client_id > APP_ID_NONE && client_id != + APP_ID_HTTP && asd->client_app_id != client_id) + LogMessage("AppIdDbg %s X is client %d\n", asd->session_logging_id, appId); + + asd->set_client_app_id_data(appId, version); + } + else + { + if (asd->session_logging_enabled && service_id > APP_ID_NONE && service_id != + APP_ID_HTTP && asd->service_app_id != service_id) + LogMessage("AppIdDbg %s X is service %d\n", asd->session_logging_id, + appId); + asd->set_service_appid_data(appId, nullptr, version); + } + asd->scan_flags &= ~SCAN_HTTP_XWORKINGWITH_FLAG; + } + + snort_free(version); + } + + // Scan Content-Type Header for multimedia types and scan contents + // FIXIT-M: Should we be checking the scan_flags even when + // thirdparty_appid_module is off? + if ((thirdparty_appid_module && (asd->scan_flags & SCAN_HTTP_CONTENT_TYPE_FLAG) + && content_type && !asd->is_payload_appid_set()) + || (!thirdparty_appid_module && !asd->is_payload_appid_set() && content_type)) + { + payload_id = http_matchers->get_appid_by_content_type((uint8_t*)content_type, + strlen(content_type)); + if (asd->session_logging_enabled && payload_id > APP_ID_NONE + && asd->payload_app_id != payload_id) + LogMessage("AppIdDbg %s Content-Type is data %d\n", asd->session_logging_id, + payload_id); + asd->set_payload_app_id_data((ApplicationId)payload_id, nullptr); + asd->scan_flags &= ~SCAN_HTTP_CONTENT_TYPE_FLAG; + } + + if (asd->scan_flags & SCAN_HTTP_HOST_URL_FLAG) + { + AppId referredPayloadAppId = 0; + char* version = nullptr; + + if ( http_matchers->get_appid_from_url(host, url, &version, referer, &client_id, + &service_id, &payload_id, &referredPayloadAppId, 0) ) + { + // do not overwrite a previously-set client or service + if (asd->client_app_id <= APP_ID_NONE) + { + if (asd->session_logging_enabled && client_id > APP_ID_NONE && client_id != + APP_ID_HTTP && asd->client_app_id != client_id) + LogMessage("AppIdDbg %s URL is client %d\n", asd->session_logging_id, + client_id); + asd->set_client_app_id_data(client_id, nullptr); + } + + if (asd->service_app_id <= APP_ID_NONE) + { + if (asd->session_logging_enabled && service_id > APP_ID_NONE && service_id != + APP_ID_HTTP && asd->service_app_id != service_id) + LogMessage("AppIdDbg %s URL is service %d\n", asd->session_logging_id, + service_id); + asd->set_service_appid_data(service_id, nullptr, nullptr); + } + + // DO overwrite a previously-set data + if (asd->session_logging_enabled && payload_id > APP_ID_NONE && + asd->payload_app_id != payload_id) + LogMessage("AppIdDbg %s URL is data %d\n", asd->session_logging_id, + payload_id); + asd->set_payload_app_id_data((ApplicationId)payload_id, version); + asd->set_referred_payload_app_id_data(referredPayloadAppId); + } + + asd->scan_flags &= ~SCAN_HTTP_HOST_URL_FLAG; + snort_free(version); + } + + if (asd->client_app_id == APP_ID_APPLE_CORE_MEDIA) + { + AppInfoTableEntry* entry; + + if (asd->tp_payload_app_id > APP_ID_NONE) + { + entry = asd->app_info_mgr->get_app_info_entry(asd->tp_payload_app_id); + // only move tpPayloadAppId to client if its got a client_app_id + if (entry && entry->clientId > APP_ID_NONE) + { + asd->misc_app_id = asd->client_app_id; + asd->client_app_id = asd->tp_payload_app_id; + } + } + else if (asd->payload_app_id > APP_ID_NONE) + { + entry = asd->app_info_mgr->get_app_info_entry(asd->payload_app_id); + // only move payload_app_id to client if it has a ClientAppid + if (entry && entry->clientId > APP_ID_NONE) + { + asd->misc_app_id = asd->client_app_id; + asd->client_app_id = asd->payload_app_id; + } + } + } + + asd->clear_http_flags(); + } // end DON'T skip_simple_detect + + return 0; +} + diff --git a/src/network_inspectors/appid/appid_http_session.h b/src/network_inspectors/appid/appid_http_session.h new file mode 100644 index 000000000..f40e05762 --- /dev/null +++ b/src/network_inspectors/appid/appid_http_session.h @@ -0,0 +1,109 @@ +//-------------------------------------------------------------------------- +// Copyright (C) 2014-2017 Cisco and/or its affiliates. All rights reserved. +// Copyright (C) 2005-2013 Sourcefire, Inc. +// +// This program is free software; you can redistribute it and/or modify it +// under the terms of the GNU General Public License Version 2 as published +// by the Free Software Foundation. You may not use, modify or distribute +// this program under any other version of the GNU General Public License. +// +// This program is distributed in the hope that it will be useful, but +// WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// General Public License for more details. +// +// You should have received a copy of the GNU General Public License along +// with this program; if not, write to the Free Software Foundation, Inc., +// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +//-------------------------------------------------------------------------- + +// appid_inspector.h author davis mcpherson +// Created on: Apr 19, 2017 + +#ifndef APPID_HTTP_SESSION_H +#define APPID_HTTP_SESSION_H + +#include "appid_api.h" +#include "application_ids.h" +#include "detector_plugins/http_url_patterns.h" +#include "flow/flow.h" +#include "sfip/sf_ip.h" + +class AppIdSession; + +#define RESPONSE_CODE_PACKET_THRESHHOLD 0 + +// These values are used in Lua code as raw numbers. Do NOT reassign new values. +#define APP_TYPE_SERVICE 0x1 +#define APP_TYPE_CLIENT 0x2 +#define APP_TYPE_PAYLOAD 0x4 + +class AppIdHttpSession +{ +public: + AppIdHttpSession(AppIdSession*); + ~AppIdHttpSession(); + + int process_http_packet(int); + + AppIdSession* asd = nullptr; + char* host = nullptr; + uint16_t host_buflen = 0; + char* url = nullptr; + char* uri = nullptr; + uint16_t uri_buflen = 0; + char* via = nullptr; + char* useragent = nullptr; + uint16_t useragent_buflen = 0; + char* response_code = nullptr; + uint16_t response_code_buflen = 0; + char* referer = nullptr; + uint16_t referer_buflen = 0; + char* cookie = nullptr; + uint16_t cookie_buflen = 0; + char* content_type = nullptr; + uint16_t content_type_buflen = 0; + char* location = nullptr; + uint16_t location_buflen = 0; + char* body = nullptr; + uint16_t body_buflen = 0; + char* req_body = nullptr; + uint16_t req_body_buflen = 0; + char* server = nullptr; + char* x_working_with = nullptr; + char* new_field[HTTP_FIELD_MAX + 1] = { nullptr }; + uint16_t new_field_len[HTTP_FIELD_MAX + 1] = { 0 }; + uint16_t fieldOffset[HTTP_FIELD_MAX + 1] = { 0 }; + uint16_t fieldEndOffset[HTTP_FIELD_MAX + 1] = { 0 }; + bool new_field_contents = false; + bool is_webdav = false; + bool chp_finished = false; + AppId chp_candidate = APP_ID_NONE; + AppId chp_alt_candidate = APP_ID_NONE; + int chp_hold_flow = 0; + int ptype_req_counts[NUMBER_OF_PTYPES] = { 0 }; + int total_found = 0; + unsigned app_type_flags = 0; + int num_matches = 0; + int num_scans = 0; + int get_offsets_from_rebuilt = 0; + bool skip_simple_detect = false; + SfIp* xffAddr = nullptr; + const char** xffPrecedence = nullptr; + unsigned numXffFields = 0; + int ptype_scan_counts[NUMBER_OF_PTYPES] = { 0 }; + +#if RESPONSE_CODE_PACKET_THRESHHOLD + unsigned response_code_packets = 0; +#endif + +private: + int initial_chp_sweep(char**, uint16_t*, MatchedCHPAction**); + void process_chp_buffers(); + void free_chp_matches(MatchedCHPAction** ppmatches, unsigned max_matches); + + HttpPatternMatchers* http_matchers = nullptr; +}; + +#endif + diff --git a/src/network_inspectors/appid/appid_inspector.cc b/src/network_inspectors/appid/appid_inspector.cc index 613570d97..1728f9fd0 100644 --- a/src/network_inspectors/appid/appid_inspector.cc +++ b/src/network_inspectors/appid/appid_inspector.cc @@ -44,9 +44,11 @@ #include "detector_plugins/detector_sip.h" #include "detector_plugins/detector_pattern.h" #include "log/messages.h" +#include "main/snort_config.h" #include "managers/inspector_manager.h" #include "protocols/packet.h" #include "profiler/profiler.h" +#include "target_based/snort_protocols.h" THREAD_LOCAL AppIdStatistics* appid_stats_manager = nullptr; @@ -98,6 +100,16 @@ AppIdStatistics* AppIdInspector::get_stats_manager() return appid_stats_manager; } +int16_t AppIdInspector::add_appid_protocol_reference(const char* protocol) +{ + static std::mutex apr_mutex; + + apr_mutex.lock(); + int16_t id = snort_conf->proto_ref->add(protocol); + apr_mutex.unlock(); + return id; +} + bool AppIdInspector::configure(SnortConfig*) { assert(!active_config); diff --git a/src/network_inspectors/appid/appid_inspector.h b/src/network_inspectors/appid/appid_inspector.h index 21ee424c8..88fd02efa 100644 --- a/src/network_inspectors/appid/appid_inspector.h +++ b/src/network_inspectors/appid/appid_inspector.h @@ -44,6 +44,7 @@ public: void eval(Packet*) override; AppIdConfig* get_appid_config(); AppIdStatistics* get_stats_manager(); + int16_t add_appid_protocol_reference(const char* protocol); private: const AppIdModuleConfig* config = nullptr; diff --git a/src/network_inspectors/appid/appid_module.cc b/src/network_inspectors/appid/appid_module.cc index c0d17f285..a166dd7e0 100644 --- a/src/network_inspectors/appid/appid_module.cc +++ b/src/network_inspectors/appid/appid_module.cc @@ -25,6 +25,8 @@ #include "appid_module.h" +#include + #include "log/messages.h" #include "profiler/profiler.h" #include "utils/util.h" diff --git a/src/network_inspectors/appid/appid_session.cc b/src/network_inspectors/appid/appid_session.cc index d16d10b5f..66ea42cd0 100644 --- a/src/network_inspectors/appid/appid_session.cc +++ b/src/network_inspectors/appid/appid_session.cc @@ -27,6 +27,15 @@ #include +#include "app_forecast.h" +#include "appid_http_session.h" +#include "appid_inspector.h" +#include "app_info_table.h" +#include "appid_module.h" +#include "appid_stats.h" +#include "appid_utils/ip_funcs.h" +#include "service_plugins/service_ssl.h" +#include "thirdparty_appid_utils.h" #include "log/messages.h" #include "main/snort_config.h" #include "profiler/profiler.h" @@ -36,25 +45,26 @@ #include "target_based/snort_protocols.h" #include "time/packet_time.h" -#include "appid_inspector.h" -#include "app_forecast.h" -#include "app_info_table.h" -#include "appid_module.h" -#include "appid_stats.h" -#include "appid_utils/ip_funcs.h" -#include "client_plugins/client_detector.h" -#include "detector_plugins/detector_dns.h" -#include "detector_plugins/http_url_patterns.h" -#include "service_plugins/service_ssl.h" -#include "service_plugins/service_util.h" -#include "thirdparty_appid_utils.h" - -ProfileStats httpPerfStats; - unsigned AppIdSession::flow_id = 0; THREAD_LOCAL AppIdFlowData* AppIdSession::fd_free_list = nullptr; THREAD_LOCAL uint32_t AppIdSession::appid_flow_data_id = 0; +const uint8_t* service_strstr(const uint8_t* haystack, unsigned haystack_len, + const uint8_t* needle, unsigned needle_len) +{ + const uint8_t* h_end = haystack + haystack_len; + + for (const uint8_t* p = haystack; h_end-p >= (int)needle_len; p++) + { + if (memcmp(p, needle, needle_len) == 0) + { + return p; + } + } + + return nullptr; +} + void AppIdSession::set_session_logging_state(const Packet* pkt, int direction) { if (config->mod_config->session_log_filter.log_all_sessions) @@ -102,7 +112,7 @@ AppIdSession* AppIdSession::allocate_session(const Packet* p, IpProtocol proto, AppIdSession* asd = new AppIdSession(proto, ip, port); asd->flow = p->flow; - asd->stats.firstPktsecond = p->pkth->ts.tv_sec; + asd->stats.first_packet_second = p->pkth->ts.tv_sec; asd->set_session_logging_state(p, direction); asd->snort_id = snortId_for_unsynchronized; p->flow->set_flow_data(asd); @@ -127,12 +137,11 @@ AppIdSession::AppIdSession(IpProtocol proto, const SfIp* ip, uint16_t port) length_sequence.sequence_cnt = 0; memset(length_sequence.sequence, '\0', sizeof(length_sequence.sequence)); session_logging_id[0] = '\0'; - http_matchers = HttpPatternMatchers::get_instance(); } AppIdSession::~AppIdSession() { - if ( !in_expected_cache) + if ( !in_expected_cache ) { AppIdStatistics* stats_mgr = AppIdInspector::get_inspector()->get_stats_manager(); if ( stats_mgr ) @@ -144,19 +153,29 @@ AppIdSession::~AppIdSession() { ServiceDiscoveryState* sds = AppIdServiceState::get(&service_ip, protocol, service_port, is_decrypted()); - if( sds ) + if ( sds ) { - sds->invalid_client_count += STATE_ID_INCONCLUSIVE_SERVICE_WEIGHT; if (flow->server_ip.fast_eq6(service_ip)) - sds->set_service_id_failed(this, &flow->client_ip); + sds->set_service_id_failed(this, &flow->client_ip, + STATE_ID_INCONCLUSIVE_SERVICE_WEIGHT); else - sds->set_service_id_failed(this, &flow->server_ip); + sds->set_service_id_failed(this, &flow->server_ip, + STATE_ID_INCONCLUSIVE_SERVICE_WEIGHT); } } } - delete_shared_data(); + if (thirdparty_appid_module) + { + thirdparty_appid_module->session_delete(tpsession, 0); + tpsession = nullptr; + } + + delete_session_data(); free_flow_data(); + service_candidates.clear(); + client_candidates.clear(); + snort_free(firewall_early_data); } // FIXIT-L X Move this to somewhere more generally available/appropriate. @@ -201,7 +220,7 @@ AppIdSession* AppIdSession::create_future_session(const Packet* ctrlPkt, const S // FIXIT-M 2.9.x set_application_protocol_id_expected has several new parameters, need to look // into what is required to support those here. if ( Stream::set_application_protocol_id_expected(ctrlPkt, type, proto, cliIp, cliPort, srvIp, - srvPort, app_id, asd) ) + srvPort, app_id, asd) ) { sfip_ntop(cliIp, src_ip, sizeof(src_ip)); sfip_ntop(srvIp, dst_ip, sizeof(dst_ip)); @@ -228,21 +247,21 @@ AppIdSession* AppIdSession::create_future_session(const Packet* ctrlPkt, const S return asd; } -void AppIdSession::reinit_shared_data() +void AppIdSession::reinit_session_data() { misc_app_id = APP_ID_NONE; //data - if (isSslServiceAppId(tp_app_id)) + if ( is_service_over_ssl(tp_app_id) ) { payload_app_id = referred_payload_app_id = tp_payload_app_id = APP_ID_NONE; clear_session_flags(APPID_SESSION_CONTINUE); - if (payload_version) + if ( payload_version ) { snort_free(payload_version); payload_version = nullptr; } - if (hsession && hsession->url) + if ( hsession && hsession->url ) { snort_free(hsession->url); hsession->url = nullptr; @@ -250,18 +269,18 @@ void AppIdSession::reinit_shared_data() } //service - if (!get_session_flags(APPID_SESSION_STICKY_SERVICE)) + if ( !get_session_flags(APPID_SESSION_STICKY_SERVICE) ) { - tp_app_id = serviceAppId = portServiceAppId = APP_ID_NONE; - if (serviceVendor) + tp_app_id = service_app_id = port_service_id = APP_ID_NONE; + if ( service_vendor ) { - snort_free(serviceVendor); - serviceVendor = nullptr; + snort_free(service_vendor); + service_vendor = nullptr; } - if (serviceVersion) + if ( service_version ) { - snort_free(serviceVersion); - serviceVersion = nullptr; + snort_free(service_version); + service_version = nullptr; } service_ip.clear(); @@ -273,7 +292,7 @@ void AppIdSession::reinit_shared_data() //client client_app_id = client_service_app_id = APP_ID_NONE; - if (client_version) + if ( client_version ) { snort_free(client_version); client_version = nullptr; @@ -364,7 +383,7 @@ void AppIdSession::check_app_detection_restart() return; AppId serviceAppId = pick_service_app_id(); - bool isSsl = isSslServiceAppId(serviceAppId); + bool isSsl = is_service_over_ssl(serviceAppId); // A session could either: // 1. Start off as SSL - captured with isSsl flag, OR @@ -373,12 +392,12 @@ void AppIdSession::check_app_detection_restart() if (get_session_flags(APPID_SESSION_ENCRYPTED) || isSsl) { set_session_flags(APPID_SESSION_DECRYPTED); - encrypted.serviceAppId = serviceAppId; - encrypted.payloadAppId = pick_payload_app_id(); - encrypted.ClientAppId = pick_client_app_id(); - encrypted.miscAppId = pick_misc_app_id(); - encrypted.referredAppId = pick_referred_payload_app_id(); - reinit_shared_data(); + encrypted.service_app_id = serviceAppId; + encrypted.payload_app_id = pick_payload_app_id(); + encrypted.client_app_id = pick_client_app_id(); + encrypted.misc_app_id = pick_misc_app_id(); + encrypted.referred_app_id = pick_referred_payload_app_id(); + reinit_session_data(); if (session_logging_enabled) LogMessage("AppIdDbg %s SSL decryption is available, restarting app Detection\n", session_logging_id); @@ -386,7 +405,7 @@ void AppIdSession::check_app_detection_restart() // APPID_SESSION_ENCRYPTED is set upon receiving a command which upgrades the session to // SSL. Next packet after the command will have encrypted traffic. In the case of a // session which starts as SSL, current packet itself is encrypted. Set the special flag - // APPID_SESSION_APP_REINSPECT_SSL which allows reinspection of this pcaket. + // APPID_SESSION_APP_REINSPECT_SSL which allows reinspection of this packet. if (isSsl) set_session_flags(APPID_SESSION_APP_REINSPECT_SSL); } @@ -440,14 +459,14 @@ void AppIdSession::update_encrypted_app_id(AppId serviceAppId) } } -void AppIdSession::set_client_app_id_data(AppId id, char** version) +void AppIdSession::set_client_app_id_data(AppId id, char* version) { - if (id <= APP_ID_NONE || id == APP_ID_HTTP) + if ( id <= APP_ID_NONE || id == APP_ID_HTTP ) return; - if (id != client_app_id) + if ( id != client_app_id ) { - if (client_app_id) + if ( client_app_id ) { unsigned prev_priority = app_info_mgr->get_app_info_priority(client_app_id); unsigned curr_priority = app_info_mgr->get_app_info_priority(id); @@ -458,23 +477,16 @@ void AppIdSession::set_client_app_id_data(AppId id, char** version) client_app_id = id; - if (client_version) + if ( client_version ) snort_free(client_version); - - if (version && *version) - { - client_version = *version; - *version = nullptr; - } - else - client_version = nullptr; + if (version) + client_version = snort_strdup(version); } - else if (version && *version) + else if ( version ) { - if (client_version) + if ( client_version ) snort_free(client_version); - client_version = *version; - *version = nullptr; + client_version = snort_strdup(version); } } @@ -526,33 +538,36 @@ void AppIdSession::examine_ssl_metadata(Packet* p) void AppIdSession::examine_rtmp_metadata() { - AppId serviceAppId = 0; - AppId client_app_id = 0; - AppId payload_app_id = 0; - AppId referredPayloadAppId = 0; + AppId service_id = APP_ID_NONE; + AppId client_id = APP_ID_NONE; + AppId payload_id = APP_ID_NONE; + AppId referred_payload_id = APP_ID_NONE; char* version = nullptr; - if (!hsession) - hsession = (HttpSession*)snort_calloc(sizeof(HttpSession)); + if ( !hsession ) + hsession = new AppIdHttpSession(this); - if (hsession->url) + if ( hsession->url ) { - if (((http_matchers->get_appid_from_url(nullptr, hsession->url, &version, - hsession->referer, &client_app_id, &serviceAppId, - &payload_app_id, &referredPayloadAppId, 1)) || - (http_matchers->get_appid_from_url(nullptr, hsession->url, &version, - hsession->referer, &client_app_id, &serviceAppId, - &payload_app_id, &referredPayloadAppId, 0))) == 1) + HttpPatternMatchers* http_matchers = HttpPatternMatchers::get_instance(); + + if ( ( ( http_matchers->get_appid_from_url(nullptr, hsession->url, &version, + hsession->referer, &client_id, &service_id, + &payload_id, &referred_payload_id, 1) ) + || + ( http_matchers->get_appid_from_url(nullptr, hsession->url, &version, + hsession->referer, &client_id, &service_id, + &payload_id, &referred_payload_id, 0) ) ) ) { /* do not overwrite a previously-set client or service */ if (client_app_id <= APP_ID_NONE) - set_client_app_id_data(client_app_id, nullptr); - if (serviceAppId <= APP_ID_NONE) - set_service_appid_data(serviceAppId, nullptr, nullptr); + set_client_app_id_data(payload_id, nullptr); + if (service_app_id <= APP_ID_NONE) + set_service_appid_data(service_id, nullptr, nullptr); /* DO overwrite a previously-set data */ set_payload_app_id_data((ApplicationId)payload_app_id, nullptr); - set_referred_payload_app_id_data(referredPayloadAppId); + set_referred_payload_app_id_data(referred_payload_id); } } } @@ -566,14 +581,14 @@ void AppIdSession::set_referred_payload_app_id_data(AppId id) referred_payload_app_id = id; } -void AppIdSession::set_payload_app_id_data(ApplicationId id, char** version) +void AppIdSession::set_payload_app_id_data(ApplicationId id, char* version) { - if (id <= APP_ID_NONE) + if ( id <= APP_ID_NONE ) return; - if (payload_app_id != id) + if ( payload_app_id != id ) { - if (payload_app_id) + if ( payload_app_id ) { unsigned prev_priority = app_info_mgr->get_app_info_priority(payload_app_id); unsigned curr_priority = app_info_mgr->get_app_info_priority(id); @@ -583,27 +598,20 @@ void AppIdSession::set_payload_app_id_data(ApplicationId id, char** version) payload_app_id = id; - if (payload_version) + if ( payload_version ) snort_free(payload_version); - - if (version && *version) - { - payload_version = *version; - *version = nullptr; - } - else - payload_version = nullptr; + if (version) + payload_version = snort_strdup(version); } - else if (version && *version) + else if ( version ) { - if (payload_version) + if ( payload_version ) snort_free(payload_version); - payload_version = *version; - *version = nullptr; + payload_version = snort_strdup(version); } } -void AppIdSession::set_service_appid_data(AppId id, char* vendor, char** version) +void AppIdSession::set_service_appid_data(AppId id, char* vendor, char* version) { if (id <= APP_ID_NONE) return; @@ -616,161 +624,30 @@ void AppIdSession::set_service_appid_data(AppId id, char* vendor, char** version return; } - if (serviceAppId != id) - { - serviceAppId = id; - - if (serviceVendor) - { - snort_free(serviceVendor); - serviceVendor = nullptr; - } - if (serviceVersion) - { - snort_free(serviceVersion); - serviceVersion = nullptr; - } - - if (vendor) - serviceVendor = vendor; - - if (version && *version) - { - serviceVersion = *version; - *version = nullptr; - } - } - else + if (service_app_id != id) { - if (vendor || version) - { - if (serviceVendor) - snort_free(serviceVendor); - if (serviceVersion) - snort_free(serviceVersion); - - if (vendor) - serviceVendor = vendor; - else - serviceVendor = nullptr; - - if (version && *version) - { - serviceVersion = *version; - *version = nullptr; - } - else - serviceVersion = nullptr; - } - } -} + service_app_id = id; -void AppIdSession::clear_http_field() -{ - if (hsession == nullptr) - return; + if (service_vendor) + snort_free(service_vendor); + service_vendor = vendor; - if (hsession->x_working_with) - { - snort_free(hsession->x_working_with); - hsession->x_working_with = nullptr; - } - if (hsession->referer) - { - snort_free(hsession->referer); - hsession->referer = nullptr; - } - if (hsession->cookie) - { - snort_free(hsession->cookie); - hsession->cookie = nullptr; - } - if (hsession->url) - { - snort_free(hsession->url); - hsession->url = nullptr; + if (service_version) + snort_free(service_version); + if (version) + service_version = snort_strdup(version); } - if (hsession->useragent) + else if (vendor || version) { - snort_free(hsession->useragent); - hsession->useragent = nullptr; - } - if (hsession->host) - { - snort_free(hsession->host); - hsession->host = nullptr; - } - if (hsession->uri) - { - snort_free(hsession->uri); - hsession->uri = nullptr; - } - if (hsession->content_type) - { - snort_free(hsession->content_type); - hsession->content_type = nullptr; - } - if (hsession->location) - { - snort_free(hsession->location); - hsession->location = nullptr; - } - if (hsession->body) - { - snort_free(hsession->body); - hsession->body = nullptr; - } - if (hsession->req_body) - { - snort_free(hsession->req_body); - hsession->req_body = nullptr; - } - if (hsession->xffAddr) - { - delete hsession->xffAddr; - hsession->xffAddr = nullptr; - } -} + if (service_vendor) + snort_free(service_vendor); + service_vendor = vendor; -void AppIdSession::free_http_session_data() -{ - if (hsession == nullptr) - return; - - clear_http_field(); - - if (hsession->new_field_contents) - for ( unsigned i = 0; i < NUMBER_OF_PTYPES; i++) - { - if (nullptr != hsession->new_field[i]) - { - snort_free(hsession->new_field[i]); - hsession->new_field[i] = nullptr; - } - } - if (hsession->via) - { - snort_free(hsession->via); - hsession->via = nullptr; - } - if (hsession->content_type) - { - snort_free(hsession->content_type); - hsession->content_type = nullptr; - } - if (hsession->response_code) - { - snort_free(hsession->response_code); - hsession->response_code = nullptr; - } - if (hsession->server) - { - snort_free(hsession->server); - hsession->server = nullptr; + if (service_version) + snort_free(service_version); + if (version) + service_version = snort_strdup(version); } - - snort_free(hsession); - hsession = nullptr; } void AppIdSession::free_dns_session_data() @@ -806,9 +683,9 @@ void AppIdSession::free_flow_data() { AppIdFlowData* tmp_fd; - while ((tmp_fd = flowData)) + while ((tmp_fd = flow_data)) { - flowData = tmp_fd->next; + flow_data = tmp_fd->next; if (tmp_fd->fd_data && tmp_fd->fd_free) tmp_fd->fd_free(tmp_fd->fd_data); @@ -816,20 +693,17 @@ void AppIdSession::free_flow_data() } } -void AppIdSession::delete_shared_data() +void AppIdSession::delete_session_data() { - if (thirdparty_appid_module) - { - thirdparty_appid_module->session_delete(tpsession, 0); - tpsession = nullptr; - } - snort_free(client_version); - snort_free(serviceVendor); - snort_free(serviceVersion); + snort_free(payload_version); + snort_free(service_vendor); + snort_free(service_version); snort_free(netbios_name); + snort_free(username); + snort_free(netbios_domain); - RNAServiceSubtype* rna_ss = subtype; + AppIdServiceSubtype* rna_ss = subtype; while ( rna_ss ) { subtype = rna_ss->next; @@ -840,17 +714,9 @@ void AppIdSession::delete_shared_data() rna_ss = subtype; } - service_candidates.clear(); - client_candidates.clear(); - snort_free(username); - snort_free(netbios_domain); - snort_free(payload_version); - free_http_session_data(); + delete hsession; free_tls_session_data(); free_dns_session_data(); - - snort_free(firewallEarlyData); - firewallEarlyData = nullptr; } void AppIdSession::release_free_list_flow_data() @@ -868,7 +734,7 @@ void* AppIdSession::get_flow_data(unsigned id) { AppIdFlowData* tmp_fd; - for (tmp_fd = flowData; tmp_fd && tmp_fd->fd_id != id; tmp_fd = tmp_fd->next) + for (tmp_fd = flow_data; tmp_fd && tmp_fd->fd_id != id; tmp_fd = tmp_fd->next) ; return tmp_fd ? tmp_fd->fd_data : nullptr; } @@ -878,7 +744,7 @@ void* AppIdSession::remove_flow_data(unsigned id) AppIdFlowData** pfd; AppIdFlowData* fd; - for (pfd = &flowData; *pfd && (*pfd)->fd_id != id; pfd = &(*pfd)->next) + for (pfd = &flow_data; *pfd && (*pfd)->fd_id != id; pfd = &(*pfd)->next) ; if ((fd = *pfd)) { @@ -895,7 +761,7 @@ void AppIdSession::free_flow_data_by_id(unsigned id) AppIdFlowData** pfd; AppIdFlowData* fd; - for (pfd = &flowData; *pfd && (*pfd)->fd_id != id; pfd = &(*pfd)->next) + for (pfd = &flow_data; *pfd && (*pfd)->fd_id != id; pfd = &(*pfd)->next) ; if ((fd = *pfd)) @@ -910,7 +776,7 @@ void AppIdSession::free_flow_data_by_id(unsigned id) void AppIdSession::free_flow_data_by_mask(unsigned mask) { - AppIdFlowData** pfd = &flowData; + AppIdFlowData** pfd = &flow_data; while (*pfd) { if ((*pfd)->fd_id & mask) @@ -944,8 +810,8 @@ int AppIdSession::add_flow_data(void* data, unsigned id, AppIdFreeFCN fcn) tmp_fd->fd_id = id; tmp_fd->fd_data = data; tmp_fd->fd_free = fcn; - tmp_fd->next = flowData; - flowData = tmp_fd; + tmp_fd->next = flow_data; + flow_data = tmp_fd; return 0; } @@ -976,11 +842,6 @@ void AppIdSession::stop_rna_service_inspection(Packet* p, int direction) clear_session_flags(APPID_SESSION_CONTINUE); } -AppId AppIdSession::is_appid_detection_done() -{ - return get_session_flags(APPID_SESSION_SERVICE_DETECTED); -} - AppId AppIdSession::pick_service_app_id() { AppId rval; @@ -988,19 +849,19 @@ AppId AppIdSession::pick_service_app_id() if ( common.flow_type != APPID_FLOW_TYPE_NORMAL ) return APP_ID_NONE; - if (get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if ( is_service_detected() ) { - bool deferred = app_info_mgr->get_app_info_flags(serviceAppId, APPINFO_FLAG_DEFER) + bool deferred = app_info_mgr->get_app_info_flags(service_app_id, APPINFO_FLAG_DEFER) || app_info_mgr->get_app_info_flags(tp_app_id, APPINFO_FLAG_DEFER); - if (serviceAppId > APP_ID_NONE && !deferred) - return serviceAppId; + if (service_app_id > APP_ID_NONE && !deferred) + return service_app_id; if (is_third_party_appid_available(tpsession)) { if (tp_app_id > APP_ID_NONE) return tp_app_id; else if (deferred) - return serviceAppId; + return service_app_id; else rval = APP_ID_UNKNOWN_UI; } @@ -1015,8 +876,8 @@ AppId AppIdSession::pick_service_app_id() if (client_service_app_id > APP_ID_NONE) return client_service_app_id; - if (portServiceAppId > APP_ID_NONE) - return portServiceAppId; + if (port_service_id > APP_ID_NONE) + return port_service_id; return rval; } @@ -1026,18 +887,18 @@ AppId AppIdSession::pick_only_service_app_id() if ( common.flow_type != APPID_FLOW_TYPE_NORMAL ) return APP_ID_NONE; - bool deferred = app_info_mgr->get_app_info_flags(serviceAppId, APPINFO_FLAG_DEFER) + bool deferred = app_info_mgr->get_app_info_flags(service_app_id, APPINFO_FLAG_DEFER) || app_info_mgr->get_app_info_flags(tp_app_id, APPINFO_FLAG_DEFER); - if (serviceAppId > APP_ID_NONE && !deferred) - return serviceAppId; + if (service_app_id > APP_ID_NONE && !deferred) + return service_app_id; if (is_third_party_appid_available(tpsession) && tp_app_id > APP_ID_NONE) return tp_app_id; else if (deferred) - return serviceAppId; + return service_app_id; - if (serviceAppId < APP_ID_NONE) + if (service_app_id < APP_ID_NONE) return APP_ID_UNKNOWN_UI; return APP_ID_NONE; @@ -1091,7 +952,7 @@ AppId AppIdSession::pick_fw_service_app_id() { AppId appId = pick_service_app_id(); if (appId == APP_ID_NONE || appId== APP_ID_UNKNOWN_UI) - appId = encrypted.serviceAppId; + appId = encrypted.service_app_id; return appId; } @@ -1099,7 +960,7 @@ AppId AppIdSession::pick_fw_misc_app_id() { AppId appId = pick_misc_app_id(); if (appId == APP_ID_NONE) - appId = encrypted.miscAppId; + appId = encrypted.misc_app_id; return appId; } @@ -1113,7 +974,7 @@ AppId AppIdSession::pick_fw_payload_app_id() { AppId appId = pick_payload_app_id(); if (appId == APP_ID_NONE) - appId = encrypted.payloadAppId; + appId = encrypted.payload_app_id; return appId; } @@ -1121,7 +982,7 @@ AppId AppIdSession::pick_fw_referred_payload_app_id() { AppId appId = pick_referred_payload_app_id(); if (appId == APP_ID_NONE) - appId = encrypted.referredAppId; + appId = encrypted.referred_app_id; return appId; } @@ -1130,155 +991,27 @@ bool AppIdSession::is_ssl_session_decrypted() return get_session_flags(APPID_SESSION_DECRYPTED); } -static const char* httpFieldName[ NUMBER_OF_PTYPES ] = // for use in debug messages -{ - "useragent", - "host", - "referer", - "uri", - "cookie", - "req_body", - "content_type", - "location", - "body", -}; - -void AppIdSession::clear_app_id_data() +void AppIdSession::reset_session_data() { + delete_session_data(); + client_version = nullptr; + payload_version = nullptr; + service_vendor = nullptr; + service_version = nullptr; + netbios_name = nullptr; + netbios_domain = nullptr; + username = nullptr; + hsession = nullptr; + payload_app_id = APP_ID_UNKNOWN; - serviceAppId = APP_ID_UNKNOWN; + service_app_id = APP_ID_UNKNOWN; tp_payload_app_id = APP_ID_UNKNOWN; tp_app_id = APP_ID_UNKNOWN; - if (payload_version) - { - snort_free(payload_version); - payload_version = nullptr; - } - - if (serviceVendor) - { - snort_free(serviceVendor); - serviceVendor = nullptr; - } - - if (serviceVersion) - { - snort_free(serviceVersion); - serviceVersion = nullptr; - } - - if (tsession) - free_tls_session_data(); - - if (hsession) - free_http_session_data(); - - if (dsession) - free_dns_session_data(); - if (thirdparty_appid_module) thirdparty_appid_module->session_delete(tpsession, 1); } -static void free_chp_matches( HttpPatternMatchers* http_matchers, MatchedCHPAction** ppmatches, unsigned max_matches ) -{ - for (unsigned i = 0; i <= max_matches; i++) - { - if (ppmatches[i]) - { - http_matchers->free_matched_chp_actions(ppmatches[i]); - ppmatches[i] = nullptr; - } - } -} - -int AppIdSession::initial_chp_sweep(char** chp_buffers, uint16_t* chp_buffer_lengths, - MatchedCHPAction** ppmatches) -{ - CHPApp* cah = nullptr; - CHPTallyAndActions chp; - chp.matches = *ppmatches; - - for (unsigned i = 0; i <= MAX_KEY_PATTERN; i++) - { - ppmatches[i] = nullptr; - if (chp_buffers[i] && chp_buffer_lengths[i]) - http_matchers->scan_key_chp((PatternType)i, chp_buffers[i], chp_buffer_lengths[i], - chp); - } - - if (chp.match_tally.empty()) - { - free_chp_matches( http_matchers, ppmatches, MAX_KEY_PATTERN ); - return 0; - } - - int longest = 0; - for (auto& item: chp.match_tally) - { - // Only those items with key_pattern_countdown field reduced to zero are a full match - if (item.key_pattern_countdown) - continue; - if (longest < item.key_pattern_length_sum) - { - // We've found a new longest pattern set - longest = item.key_pattern_length_sum; - cah = item.chpapp; - } - } - - if ( !cah ) - { - free_chp_matches( http_matchers, ppmatches, MAX_KEY_PATTERN ); - return 0; - } - - /*************************************************************** - candidate has been chosen and it is pointed to by cah - we will preserve any match sets until the calls to scanCHP() - ***************************************************************/ - for (unsigned i = 0; i < NUMBER_OF_PTYPES; i++) - { - hsession->ptype_scan_counts[i] = cah->ptype_scan_counts[i]; - hsession->ptype_req_counts[i] = cah->ptype_req_counts[i] + - cah->ptype_rewrite_insert_used[i]; - if (i > 3 && !cah->ptype_scan_counts[i] - && !get_session_flags(APPID_SESSION_SPDY_SESSION)) - { - clear_session_flags(APPID_SESSION_CHP_INSPECTING); - if (thirdparty_appid_module) - thirdparty_appid_module->session_attr_clear(tpsession, - TP_ATTR_CONTINUE_MONITORING); - } - } - hsession->chp_candidate = cah->appIdInstance; - hsession->app_type_flags = cah->app_type_flags; - hsession->num_matches = cah->num_matches; - hsession->num_scans = cah->num_scans; - - if (thirdparty_appid_module) - { - if ((hsession->ptype_scan_counts[CONTENT_TYPE_PT])) - thirdparty_appid_module->session_attr_set(tpsession, TP_ATTR_COPY_RESPONSE_CONTENT); - else - thirdparty_appid_module->session_attr_clear(tpsession, TP_ATTR_COPY_RESPONSE_CONTENT); - - if ((hsession->ptype_scan_counts[LOCATION_PT])) - thirdparty_appid_module->session_attr_set(tpsession, TP_ATTR_COPY_RESPONSE_LOCATION); - else - thirdparty_appid_module->session_attr_clear(tpsession, TP_ATTR_COPY_RESPONSE_LOCATION); - - - if ((hsession->ptype_scan_counts[BODY_PT])) - thirdparty_appid_module->session_attr_set(tpsession, TP_ATTR_COPY_RESPONSE_BODY); - else - thirdparty_appid_module->session_attr_clear(tpsession, TP_ATTR_COPY_RESPONSE_BODY); - } - - return 1; -} - bool AppIdSession::is_payload_appid_set() { return ( payload_app_id || tp_payload_app_id ); @@ -1295,520 +1028,3 @@ void AppIdSession::clear_http_flags() } } -void AppIdSession::process_chp_buffers(char** version, Packet* p) -{ - char* chp_buffers[NUMBER_OF_PTYPES] = - { - hsession->useragent, - hsession->host, - hsession->referer, - hsession->uri, - hsession->cookie, - hsession->req_body, - hsession->content_type, - hsession->location, - hsession->body, - }; - - uint16_t chp_buffer_lengths[NUMBER_OF_PTYPES] = - { - hsession->useragent_buflen, - hsession->host_buflen, - hsession->referer_buflen, - hsession->uri_buflen, - hsession->cookie_buflen, - hsession->req_body_buflen, - hsession->content_type_buflen, - hsession->location_buflen, - hsession->body_buflen, - }; - - char* chp_rewritten[NUMBER_OF_PTYPES] = - { - nullptr,nullptr,nullptr, - nullptr,nullptr,nullptr, - nullptr,nullptr,nullptr - }; - - MatchedCHPAction* chp_matches[NUMBER_OF_PTYPES] = - { - nullptr,nullptr,nullptr, - nullptr,nullptr,nullptr, - nullptr,nullptr,nullptr - }; - - if ( hsession->chp_hold_flow ) - hsession->chp_finished = 0; - - if ( !hsession->chp_candidate ) - { - // remove artifacts from previous matches before we start again. - for (unsigned i = 0; i < NUMBER_OF_PTYPES; i++) - if (hsession->new_field[i]) - { - snort_free(hsession->new_field[i]); - hsession->new_field[i] = nullptr; - } - - if ( !initial_chp_sweep(chp_buffers, chp_buffer_lengths, chp_matches) ) - hsession->chp_finished = 1; // this is a failure case. - } - - if ( !hsession->chp_finished && hsession->chp_candidate ) - { - char* user = nullptr; - - for (unsigned i = 0; i < NUMBER_OF_PTYPES; i++) - { - if ( !hsession->ptype_scan_counts[i] ) - continue; - - if ( chp_buffers[i] && chp_buffer_lengths[i] ) - { - int found_in_buffer = 0; - AppId ret = http_matchers->scan_chp((PatternType)i, chp_buffers[i], - chp_buffer_lengths[i], chp_matches[i], version, &user, - &chp_rewritten[i], &found_in_buffer, hsession, p, config->mod_config); - chp_matches[i] = nullptr; // freed by scanCHP() - hsession->total_found += found_in_buffer; - if (!ret || found_in_buffer < hsession->ptype_req_counts[i]) - { - // No match at all or the required matches for the field was NOT made - if (!hsession->num_matches) - { - // num_matches == 0 means: all must succeed - // give up early - hsession->chp_candidate = 0; - break; - } - } - } - else if ( !hsession->num_matches ) - { - // num_matches == 0 means: all must succeed give up early - hsession->chp_candidate = 0; - break; - } - - // Decrement the expected scan count toward 0. - hsession->ptype_scan_counts[i] = 0; - hsession->num_scans--; - // if we have reached the end of the list of scans (which have something to do), then - // num_scans == 0 - if (hsession->num_scans == 0) - { - // we finished the last scan - // either the num_matches value was zero and we failed early-on or we need to check - // for the min. - if (hsession->num_matches && - hsession->total_found < hsession->num_matches) - { - // There was a minimum scans match count (num_matches != 0) - // And we did not reach that minimum - hsession->chp_candidate = 0; - break; - } - // All required matches were met. - hsession->chp_finished = 1; - break; - } - } - - free_chp_matches( http_matchers, chp_matches, NUMBER_OF_PTYPES ); - - if ( !hsession->chp_candidate ) - { - hsession->chp_finished = 1; - if ( *version ) - { - snort_free(*version); - *version = nullptr; - } - - if ( user ) - { - snort_free(user); - user = nullptr; - } - - for (unsigned i = 0; i < NUMBER_OF_PTYPES; i++) - { - if (nullptr != chp_rewritten[i]) - { - snort_free(chp_rewritten[i]); - chp_rewritten[i] = nullptr; - } - } - memset(hsession->ptype_scan_counts, 0, NUMBER_OF_PTYPES * sizeof(int)); - - // Make it possible for other detectors to run. - hsession->skip_simple_detect = false; - return; - } - - if (hsession->chp_candidate && hsession->chp_finished) - { - AppId chp_final = hsession->chp_alt_candidate ? hsession->chp_alt_candidate - : CHP_APPIDINSTANCE_TO_ID(hsession->chp_candidate); - - if (hsession->app_type_flags & APP_TYPE_SERVICE) - set_service_appid_data(chp_final, nullptr, version); - - if (hsession->app_type_flags & APP_TYPE_CLIENT) - set_client_app_id_data(chp_final, version); - - if ( hsession->app_type_flags & APP_TYPE_PAYLOAD ) - set_payload_app_id_data((ApplicationId)chp_final, version); - - if ( *version ) - *version = nullptr; - - if ( user ) - { - username = user; - user = nullptr; - if (hsession->app_type_flags & APP_TYPE_SERVICE) - username_service = chp_final; - else - username_service = serviceAppId; - set_session_flags(APPID_SESSION_LOGIN_SUCCEEDED); - } - - for (unsigned i = 0; i < NUMBER_OF_PTYPES; i++) - if ( chp_rewritten[i] ) - { - if (session_logging_enabled) - LogMessage("AppIdDbg %s rewritten %s: %s\n", session_logging_id, - httpFieldName[i], chp_rewritten[i]); - if (hsession->new_field[i]) - snort_free(hsession->new_field[i]); - hsession->new_field[i] = chp_rewritten[i]; - hsession->new_field_contents = true; - chp_rewritten[i] = nullptr; - } - - hsession->chp_candidate = 0; - //if we're doing safesearch rewrites, we want to continue to hold the flow - if (!hsession->get_offsets_from_rebuilt) - hsession->chp_hold_flow = 0; - scan_flags &= ~SCAN_HTTP_VIA_FLAG; - scan_flags &= ~SCAN_HTTP_USER_AGENT_FLAG; - scan_flags &= ~SCAN_HTTP_HOST_URL_FLAG; - memset(hsession->ptype_scan_counts, 0, - NUMBER_OF_PTYPES * sizeof(hsession->ptype_scan_counts[0])); - } - else /* if we have a candidate, but we're not finished */ - { - if ( user ) - { - snort_free(user); - user = nullptr; - } - - for (unsigned i = 0; i < NUMBER_OF_PTYPES; i++) - if (nullptr != chp_rewritten[i]) - { - snort_free(chp_rewritten[i]); - chp_rewritten[i] = nullptr; - } - } - } -} - -int AppIdSession::process_http_packet(int direction) -{ - Profile http_profile_context(httpPerfStats); - constexpr auto RESPONSE_CODE_LENGTH = 3; - int size; - char* version = nullptr; - char* vendorVersion = nullptr; - char* vendor = nullptr; - AppId service_id = 0; - AppId client_id = 0; - AppId payload_id = 0; - - if (!hsession) - { - clear_app_id_data(); - if (session_logging_enabled) - LogMessage("AppIdDbg %s attempt to process HTTP packet with no HTTP data\n", - session_logging_id); - - return 0; - } - - // For fragmented HTTP headers, do not process if none of the fields are set. - // These fields will get set when the HTTP header is reassembled. - if ((!hsession->useragent) && (!hsession->host) && (!hsession->referer) && - (!hsession->uri)) - { - if (!hsession->skip_simple_detect) - clear_http_flags(); - - return 0; - } - - if (direction == APP_ID_FROM_RESPONDER && !get_session_flags( - APPID_SESSION_RESPONSE_CODE_CHECKED)) - { - if (hsession->response_code) - { - set_session_flags(APPID_SESSION_RESPONSE_CODE_CHECKED); - if (hsession->response_code_buflen != RESPONSE_CODE_LENGTH) - { - /* received bad response code. Stop processing this session */ - clear_app_id_data(); - if (session_logging_enabled) - LogMessage("AppIdDbg %s bad http response code\n", session_logging_id); - - return 0; - } - } -#if RESPONSE_CODE_PACKET_THRESHHOLD - else if (++(hsession->response_code_packets) == RESPONSE_CODE_PACKET_THRESHHOLD) - { - set_session_flags(APPID_SESSION_RESPONSE_CODE_CHECKED); - /* didn't receive response code in first X packets. Stop processing this asd */ - clear_app_id_data(asd); - if (session_logging_enabled) - LogMessage("AppIdDbg %s no response code received\n", session_logging_id); - PREPROC_PROFILE_END(httpPerfStats); - return 0; - } -#endif - } - char* host = hsession->host; - char* url = hsession->url; - char* via = hsession->via; - char* useragent = hsession->useragent; - char* referer = hsession->referer; - - if (serviceAppId == APP_ID_NONE) - serviceAppId = APP_ID_HTTP; - - if (session_logging_enabled) - LogMessage("AppIdDbg %s chp_finished %d chp_hold_flow %d\n", session_logging_id, - hsession->chp_finished, hsession->chp_hold_flow); - - if (!hsession->chp_finished || hsession->chp_hold_flow) - process_chp_buffers(&version, nullptr); - - if (!hsession->skip_simple_detect) // true if processCHP found match - { - if (!get_session_flags(APPID_SESSION_APP_REINSPECT)) - { - // Scan Server Header for Vendor & Version - // FIXIT-M: Should we be checking the scan_flags even when - // thirdparty_appid_module is off? - if ((thirdparty_appid_module && (scan_flags & SCAN_HTTP_VENDOR_FLAG) && - hsession->server) || - (!thirdparty_appid_module && hsession->server)) - { - if (serviceAppId == APP_ID_NONE || serviceAppId == APP_ID_HTTP) - { - RNAServiceSubtype* local_subtype = nullptr; - RNAServiceSubtype** tmpSubtype; - - http_matchers->get_server_vendor_version((uint8_t*)hsession->server, - strlen(hsession->server), &vendorVersion, &vendor, &subtype); - if (vendor || vendorVersion) - { - if (serviceVendor) - { - snort_free(serviceVendor); - serviceVendor = nullptr; - } - if (serviceVersion) - { - snort_free(serviceVersion); - serviceVersion = nullptr; - } - if (vendor) - serviceVendor = vendor; - if (vendorVersion) - serviceVersion = vendorVersion; - scan_flags &= ~SCAN_HTTP_VENDOR_FLAG; - } - if (local_subtype) - { - for (tmpSubtype = &subtype; *tmpSubtype; tmpSubtype = &(*tmpSubtype)->next) - ; - - *tmpSubtype = local_subtype; - } - } - } - - if (hsession->is_webdav) - { - if (session_logging_enabled and payload_app_id != APP_ID_WEBDAV) - LogMessage("AppIdDbg %s data is webdav\n", session_logging_id); - set_payload_app_id_data(APP_ID_WEBDAV, nullptr); - } - - // Scan User-Agent for Browser types or Skype - if ((scan_flags & SCAN_HTTP_USER_AGENT_FLAG) && client_app_id <= APP_ID_NONE - && useragent && hsession->useragent_buflen) - { - if (version) - { - snort_free(version); - version = nullptr; - } - http_matchers->identify_user_agent((uint8_t*)useragent, hsession->useragent_buflen, - &service_id, &client_id, &version); - if (session_logging_enabled && service_id > APP_ID_NONE && - service_id != APP_ID_HTTP && serviceAppId != service_id) - LogMessage("AppIdDbg %s User Agent is service %d\n", session_logging_id, - service_id); - set_service_appid_data(service_id, nullptr, nullptr); - if (session_logging_enabled && client_id > APP_ID_NONE && - client_id != APP_ID_HTTP && client_app_id != client_id) - LogMessage("AppIdDbg %s User Agent is client %d\n", session_logging_id, - client_id); - set_client_app_id_data(client_id, &version); - scan_flags &= ~SCAN_HTTP_USER_AGENT_FLAG; - } - - /* Scan Via Header for squid */ - if (!is_payload_appid_set() && (scan_flags & SCAN_HTTP_VIA_FLAG) && via && - (size = strlen(via)) > 0) - { - if (version) - { - snort_free(version); - version = nullptr; - } - payload_id = http_matchers->get_appid_by_pattern((uint8_t*)via, size, &version); - if (session_logging_enabled && payload_id > APP_ID_NONE && - payload_app_id != payload_id) - LogMessage("AppIdDbg %s VIA is data %d\n", session_logging_id, - payload_id); - set_payload_app_id_data((ApplicationId)payload_id, nullptr); - scan_flags &= ~SCAN_HTTP_VIA_FLAG; - } - } - - /* Scan X-Working-With HTTP header */ - // FIXIT-M: Should we be checking the scan_flags even when - // thirdparty_appid_module is off? - if ((thirdparty_appid_module && (scan_flags & SCAN_HTTP_XWORKINGWITH_FLAG) && - hsession->x_working_with) || - (!thirdparty_appid_module && hsession->x_working_with)) - { - AppId appId; - - appId = http_matchers->scan_header_x_working_with((uint8_t*)hsession->x_working_with, - strlen(hsession->x_working_with), &version); - if (appId) - { - if (direction == APP_ID_FROM_INITIATOR) - { - if (session_logging_enabled && client_id > APP_ID_NONE && client_id != - APP_ID_HTTP && client_app_id != client_id) - LogMessage("AppIdDbg %s X is client %d\n", session_logging_id, appId); - set_client_app_id_data(appId, &version); - } - else - { - if (session_logging_enabled && service_id > APP_ID_NONE && service_id != - APP_ID_HTTP && serviceAppId != service_id) - LogMessage("AppIdDbg %s X is service %d\n", session_logging_id, appId); - set_service_appid_data(appId, nullptr, &version); - } - scan_flags &= ~SCAN_HTTP_XWORKINGWITH_FLAG; - } - } - - // Scan Content-Type Header for multimedia types and scan contents - // FIXIT-M: Should we be checking the scan_flags even when - // thirdparty_appid_module is off? - if ((thirdparty_appid_module && (scan_flags & SCAN_HTTP_CONTENT_TYPE_FLAG) - && hsession->content_type && !is_payload_appid_set()) || - (!thirdparty_appid_module && !is_payload_appid_set() && - hsession->content_type)) - { - payload_id = http_matchers->get_appid_by_content_type((uint8_t*)hsession->content_type, - strlen(hsession->content_type)); - if (session_logging_enabled && payload_id > APP_ID_NONE - && payload_app_id != payload_id) - LogMessage("AppIdDbg %s Content-Type is data %d\n", session_logging_id, - payload_id); - set_payload_app_id_data((ApplicationId)payload_id, nullptr); - scan_flags &= ~SCAN_HTTP_CONTENT_TYPE_FLAG; - } - - if (scan_flags & SCAN_HTTP_HOST_URL_FLAG) - { - AppId referredPayloadAppId = 0; - - if (version) - { - snort_free(version); - version = nullptr; - } - - if (http_matchers->get_appid_from_url(host, url, &version, referer, &client_id, - &service_id, - &payload_id, &referredPayloadAppId, 0) == 1) - { - // do not overwrite a previously-set client or service - if (client_app_id <= APP_ID_NONE) - { - if (session_logging_enabled && client_id > APP_ID_NONE && client_id != - APP_ID_HTTP && client_app_id != client_id) - LogMessage("AppIdDbg %s URL is client %d\n", session_logging_id, - client_id); - set_client_app_id_data(client_id, nullptr); - } - if (serviceAppId <= APP_ID_NONE) - { - if (session_logging_enabled && service_id > APP_ID_NONE && service_id != - APP_ID_HTTP && serviceAppId != service_id) - LogMessage("AppIdDbg %s URL is service %d\n", session_logging_id, - service_id); - set_service_appid_data(service_id, nullptr, nullptr); - } - // DO overwrite a previously-set data - if (session_logging_enabled && payload_id > APP_ID_NONE && - payload_app_id != payload_id) - LogMessage("AppIdDbg %s URL is data %d\n", session_logging_id, payload_id); - set_payload_app_id_data((ApplicationId)payload_app_id, &version); - set_referred_payload_app_id_data(referredPayloadAppId); - } - scan_flags &= ~SCAN_HTTP_HOST_URL_FLAG; - } - - if (client_app_id == APP_ID_APPLE_CORE_MEDIA) - { - AppInfoTableEntry* entry; - - if (tp_payload_app_id > APP_ID_NONE) - { - entry = app_info_mgr->get_app_info_entry(tp_payload_app_id); - // only move tpPayloadAppId to client if its got a client_app_id - if (entry && entry->clientId > APP_ID_NONE) - { - misc_app_id = client_app_id; - client_app_id = tp_payload_app_id; - } - } - else if (payload_app_id > APP_ID_NONE) - { - entry = app_info_mgr->get_app_info_entry(payload_app_id); - // only move payload_app_id to client if it has a ClientAppid - if (entry && entry->clientId > APP_ID_NONE) - { - misc_app_id = client_app_id; - client_app_id = payload_app_id; - } - } - } - - clear_http_flags(); - } // end DON'T skip_simple_detect - - snort_free(version); - return 0; -} - diff --git a/src/network_inspectors/appid/appid_session.h b/src/network_inspectors/appid/appid_session.h index 9c38142c3..345e15335 100644 --- a/src/network_inspectors/appid/appid_session.h +++ b/src/network_inspectors/appid/appid_session.h @@ -31,13 +31,17 @@ #include "service_state.h" #include "detector_plugins/http_url_patterns.h" -struct RNAServiceSubtype; +struct AppIdServiceSubtype; class ClientDetector; class ServiceDetector; class AppInfoManager; +class AppIdHttpSession; using AppIdFreeFCN = void (*)(void*); +const uint8_t* service_strstr(const uint8_t* haystack, unsigned haystack_len, + const uint8_t* needle, unsigned needle_len); + #define MAX_ATTR_LEN 1024 #define HTTP_PREFIX "http://" @@ -116,75 +120,6 @@ struct CommonAppIdData uint16_t initiator_port = 0; }; -#define SCAN_HTTP_VIA_FLAG (1<<0) -#define SCAN_HTTP_USER_AGENT_FLAG (1<<1) -#define SCAN_HTTP_HOST_URL_FLAG (1<<2) -#define SCAN_SSL_HOST_FLAG (1<<4) -#define SCAN_HOST_PORT_FLAG (1<<5) -#define SCAN_HTTP_VENDOR_FLAG (1<<6) -#define SCAN_HTTP_XWORKINGWITH_FLAG (1<<7) -#define SCAN_HTTP_CONTENT_TYPE_FLAG (1<<8) - -#define RESPONSE_CODE_PACKET_THRESHHOLD 0 - -// These values are used in Lua code as raw numbers. Do NOT reassign new values. -#define APP_TYPE_SERVICE 0x1 -#define APP_TYPE_CLIENT 0x2 -#define APP_TYPE_PAYLOAD 0x4 - -struct HttpSession -{ - char* host = nullptr; - uint16_t host_buflen = 0; - char* url = nullptr; - char* uri = nullptr; - uint16_t uri_buflen = 0; - char* via = nullptr; - char* useragent = nullptr; - uint16_t useragent_buflen = 0; - char* response_code = nullptr; - uint16_t response_code_buflen = 0; - char* referer = nullptr; - uint16_t referer_buflen = 0; - char* cookie = nullptr; - uint16_t cookie_buflen = 0; - char* content_type = nullptr; - uint16_t content_type_buflen = 0; - char* location = nullptr; - uint16_t location_buflen = 0; - char* body = nullptr; - uint16_t body_buflen = 0; - char* req_body = nullptr; - uint16_t req_body_buflen = 0; - char* server = nullptr; - char* x_working_with = nullptr; - char* new_field[HTTP_FIELD_MAX + 1] = { nullptr }; - uint16_t new_field_len[HTTP_FIELD_MAX + 1] = { 0 }; - uint16_t fieldOffset[HTTP_FIELD_MAX + 1] = { 0 }; - uint16_t fieldEndOffset[HTTP_FIELD_MAX + 1] = { 0 }; - bool new_field_contents = false; - bool is_webdav = false; - int chp_finished = 0; - AppId chp_candidate = APP_ID_NONE; - AppId chp_alt_candidate = APP_ID_NONE; - int chp_hold_flow = 0; - int ptype_req_counts[NUMBER_OF_PTYPES] = { 0 }; - int total_found = 0; - unsigned app_type_flags = 0; - int num_matches = 0; - int num_scans = 0; - int get_offsets_from_rebuilt = 0; - bool skip_simple_detect = false; - SfIp* xffAddr = nullptr; - const char** xffPrecedence = nullptr; - int numXffFields = 0; - int ptype_scan_counts[NUMBER_OF_PTYPES] = { 0 }; - -#if RESPONSE_CODE_PACKET_THRESHHOLD - unsigned response_code_packets = 0; -#endif -}; - // For dnsSession.state: #define DNS_GOT_QUERY 0x01 #define DNS_GOT_RESPONSE 0x02 @@ -202,7 +137,7 @@ struct DnsSession // lookup) }; -struct _RNAServiceSubtype; +struct _AppIdServiceSubtype; struct TlsSession { @@ -227,9 +162,8 @@ public: AppIdConfig* config = nullptr; CommonAppIdData common; Flow* flow = nullptr; - AppIdFlowData* flowData = nullptr; + AppIdFlowData* flow_data = nullptr; AppInfoManager* app_info_mgr = nullptr; - HttpPatternMatchers* http_matchers; SfIp service_ip; uint16_t service_port = 0; @@ -238,13 +172,13 @@ public: // AppId matching service side APPID_DISCOVERY_STATE service_disco_state = APPID_DISCO_STATE_NONE; - SESSION_SERVICE_ID_STATE service_search_state = START; - AppId serviceAppId = APP_ID_NONE; - AppId portServiceAppId = APP_ID_NONE; + SESSION_SERVICE_SEARCH_STATE service_search_state = SESSION_SERVICE_SEARCH_STATE::START; + AppId service_app_id = APP_ID_NONE; + AppId port_service_id = APP_ID_NONE; ServiceDetector* service_detector = nullptr; - char* serviceVendor = nullptr; - char* serviceVersion = nullptr; - RNAServiceSubtype* subtype = nullptr; + char* service_vendor = nullptr; + char* service_version = nullptr; + AppIdServiceSubtype* subtype = nullptr; char* netbios_name = nullptr; std::vector service_candidates; bool got_incompatible_services = false; @@ -271,10 +205,10 @@ public: AppId username_service = APP_ID_NONE; char* netbios_domain = nullptr; uint32_t session_id = 0; - HttpSession* hsession = nullptr; + AppIdHttpSession* hsession = nullptr; TlsSession* tsession = nullptr; unsigned scan_flags = 0; - AppId referredAppId = APP_ID_NONE; + AppId referred_app_id = APP_ID_NONE; AppId temp_app_id = APP_ID_NONE; void* tpsession = nullptr; uint16_t init_tpPackets = 0; @@ -289,10 +223,10 @@ public: struct { - uint32_t firstPktsecond; - uint32_t lastPktsecond; - uint64_t initiatorBytes; - uint64_t responderBytes; + uint32_t first_packet_second; + uint32_t last_packet_second; + uint64_t initiator_bytes; + uint64_t responder_bytes; } stats = { 0, 0, 0, 0 }; // Policy and rule ID for related flows (e.g. ftp-data) @@ -301,19 +235,19 @@ public: //appIds picked from encrypted session. struct { - AppId serviceAppId; - AppId ClientAppId; - AppId payloadAppId; - AppId miscAppId; - AppId referredAppId; + AppId service_app_id; + AppId client_app_id; + AppId payload_app_id; + AppId misc_app_id; + AppId referred_app_id; } encrypted = { APP_ID_NONE, APP_ID_NONE, APP_ID_NONE, APP_ID_NONE, APP_ID_NONE }; // New fields introduced for DNS Blacklisting DnsSession* dsession = nullptr; - void* firewallEarlyData = nullptr; - AppId pastIndicator = APP_ID_NONE; - AppId pastForecast = APP_ID_NONE; + void* firewall_early_data = nullptr; + AppId past_indicator = APP_ID_NONE; + AppId past_forecast = APP_ID_NONE; bool is_http2 = false; SEARCH_SUPPORT_TYPE search_support_type = UNKNOWN_SEARCH_ENGINE; @@ -336,10 +270,31 @@ public: return (common.flags & flags); } + void set_service_detected() + { + common.flags |= APPID_SESSION_SERVICE_DETECTED; + } + + bool is_service_detected() + { + return common.flags & APPID_SESSION_SERVICE_DETECTED; + } + + void set_client_detected() + { + common.flags |= APPID_SESSION_CLIENT_DETECTED; + } + + bool is_client_detected() + { + return common.flags & APPID_SESSION_CLIENT_DETECTED; + } + bool is_decrypted() { - return get_session_flags(APPID_SESSION_DECRYPTED) == APPID_SESSION_DECRYPTED; + return common.flags & APPID_SESSION_DECRYPTED; } + char session_logging_id[MAX_SESSION_LOGGING_ID_LEN]; bool session_logging_enabled = false; @@ -350,15 +305,10 @@ public: void* remove_flow_data(unsigned id); void free_flow_data_by_id(unsigned id); void free_flow_data_by_mask(unsigned mask); - - void clear_http_field(); - void free_http_session_data(); void free_dns_session_data(); void free_tls_session_data(); void free_flow_data(); - void delete_shared_data(); - AppId is_appid_detection_done(); AppId pick_service_app_id(); AppId pick_only_service_app_id(); AppId pick_misc_app_id(); @@ -371,29 +321,28 @@ public: AppId pick_fw_payload_app_id(); AppId pick_fw_referred_payload_app_id(); bool is_ssl_session_decrypted(); - int process_http_packet(int); void examine_ssl_metadata(Packet*); - void set_client_app_id_data(AppId clientAppId, char** version); - void set_service_appid_data(AppId, char*, char**); + void set_client_app_id_data(AppId, char*); + void set_service_appid_data(AppId, char*, char*); void set_referred_payload_app_id_data(AppId); - void set_payload_app_id_data(ApplicationId, char**); + void set_payload_app_id_data(ApplicationId, char*); void check_app_detection_restart(); void update_encrypted_app_id(AppId); void examine_rtmp_metadata(); void sync_with_snort_id(AppId, Packet*); void stop_rna_service_inspection(Packet*, int); -private: bool is_payload_appid_set(); - void reinit_shared_data(); + void clear_http_flags(); + void reset_session_data(); + +private: + void reinit_session_data(); + void delete_session_data(); bool is_ssl_decryption_enabled(); void set_session_logging_state(const Packet*, int direction); - void clear_app_id_data(); - int initial_chp_sweep(char**, uint16_t*, MatchedCHPAction**); - void clear_http_flags(); - void process_chp_buffers(char**, Packet*); void create_session_logging_id(int direction, Packet*); static THREAD_LOCAL uint32_t appid_flow_data_id; diff --git a/src/network_inspectors/appid/appid_stats.cc b/src/network_inspectors/appid/appid_stats.cc index b8a0dca94..1bdd27bd9 100644 --- a/src/network_inspectors/appid/appid_stats.cc +++ b/src/network_inspectors/appid/appid_stats.cc @@ -157,21 +157,19 @@ FILE* AppIdStatistics::open_stats_log_file(const char* const filename, time_t ts void AppIdStatistics::dump_statistics() { struct StatsBucket* bucket = nullptr; - uint8_t* buffer; uint32_t* buffPtr; - struct FwAvlNode* node; - struct AppIdStatRecord* record; - Serial_Unified2_Header header; - - size_t buffSize; time_t currTime = time(nullptr); - if (logBuckets == nullptr) + if ( !logBuckets ) return; while ((bucket = (struct StatsBucket*)sflist_remove_head(logBuckets)) != nullptr) { - if (bucket->appRecordCnt) + uint8_t* buffer; + size_t buffSize; + Serial_Unified2_Header header; + + if ( bucket->appRecordCnt ) { buffSize = ( bucket->appRecordCnt * sizeof(struct AppIdStatOutputRecord) ) + ( 4 * sizeof(uint32_t) ); @@ -186,7 +184,7 @@ void AppIdStatistics::dump_statistics() else buffer = nullptr; - if (buffer) + if ( buffer ) { buffPtr = (uint32_t*)buffer; *buffPtr++ = htonl(header.type); @@ -194,6 +192,7 @@ void AppIdStatistics::dump_statistics() *buffPtr++ = htonl(bucket->startTime); *buffPtr++ = htonl(bucket->appRecordCnt); + struct FwAvlNode* node; for (node = fwAvlFirst(bucket->appsTree); node != nullptr; node = fwAvlNext(node)) { struct AppIdStatOutputRecord* recBuffPtr; @@ -201,13 +200,14 @@ void AppIdStatistics::dump_statistics() bool cooked_client = false; AppId app_id; char tmpBuff[MAX_EVENT_APPNAME_LEN]; + struct AppIdStatRecord* record; record = (struct AppIdStatRecord*)node->data; app_id = record->app_id; recBuffPtr = (struct AppIdStatOutputRecord*)buffPtr; - if (app_id >= 2000000000) + if ( app_id >= 2000000000 ) { cooked_client = true; app_id -= 2000000000; @@ -215,7 +215,7 @@ void AppIdStatistics::dump_statistics() AppInfoTableEntry* entry = AppInfoManager::get_instance().get_app_info_entry( app_id); - if (entry) + if ( entry ) { app_name = entry->app_name; if (cooked_client) @@ -225,9 +225,9 @@ void AppIdStatistics::dump_statistics() app_name = tmpBuff; } } - else if (app_id == APP_ID_UNKNOWN || app_id == APP_ID_UNKNOWN_UI) + else if ( app_id == APP_ID_UNKNOWN || app_id == APP_ID_UNKNOWN_UI ) app_name = "__unknown"; - else if (app_id == APP_ID_NONE) + else if ( app_id == APP_ID_NONE ) app_name = "__none"; else { @@ -248,32 +248,31 @@ void AppIdStatistics::dump_statistics() buffPtr += sizeof(*recBuffPtr)/sizeof(*buffPtr); } - if (appid_stats_filename) + if ( appid_stats_filename ) { - if (!appfp) + if ( !appfp ) { appfp = open_stats_log_file(appid_stats_filename, currTime); appTime = currTime; appSize = 0; } - else if (((currTime - appTime) > rollPeriod) || - ((appSize + buffSize) > rollSize)) + else if ( ( ( currTime - appTime ) > rollPeriod ) || + ( ( appSize + buffSize) > rollSize ) ) { fclose(appfp); appfp = open_stats_log_file(appid_stats_filename, currTime); appTime = currTime; appSize = 0; } - if (appfp) + if ( appfp ) { - if ((fwrite(buffer, buffSize, 1, appfp) == 1) && (fflush(appfp) == 0)) + if ( ( fwrite(buffer, buffSize, 1, appfp) == 1 ) && ( fflush(appfp) == 0 ) ) { appSize += buffSize; } else { - ErrorMessage( - "AppID ailed to write to statistics file (%s): %s\n", + ErrorMessage("AppID ailed to write to statistics file (%s): %s\n", appid_stats_filename, strerror(errno)); fclose(appfp); appfp = nullptr; @@ -312,17 +311,18 @@ AppIdStatistics::~AppIdStatistics() /*flush the last stats period. */ end_stats_period(); dump_statistics(); - if (appfp) + + if ( appfp ) { fclose(appfp); appfp = nullptr; } snort_free((void*)appid_stats_filename); - if (logBuckets) + if ( logBuckets ) snort_free(logBuckets); - if (currBuckets) + if ( currBuckets ) { while (auto bucket = (StatsBucket*)sflist_remove_head(currBuckets)) { @@ -339,6 +339,32 @@ AppIdStatistics* AppIdStatistics::initialize_manager(const AppIdModuleConfig& co return new AppIdStatistics(config); } +static void update_stats(AppIdSession* asd, AppId app_id, StatsBucket* bucket) +{ + AppIdStatRecord* record = (AppIdStatRecord*)(fwAvlLookup(app_id, bucket->appsTree)); + if ( !record ) + { + record = (AppIdStatRecord*)(snort_calloc(sizeof(struct AppIdStatRecord))); + if (fwAvlInsert(app_id, record, bucket->appsTree) == 0) + { + record->app_id = app_id; + bucket->appRecordCnt += 1; + } + else + { + WarningMessage("Error saving statistics record for app id: %u", app_id); + snort_free(record); + record = nullptr; + } + } + + if ( record ) + { + record->initiatorBytes += asd->stats.initiator_bytes; + record->responderBytes += asd->stats.responder_bytes; + } +} + void AppIdStatistics::update(AppIdSession* asd) { if ( !enabled ) @@ -346,122 +372,35 @@ void AppIdStatistics::update(AppIdSession* asd) time_t now = get_time(); - if (now >= bucketEnd) + if ( now >= bucketEnd ) { end_stats_period(); dump_statistics(); start_stats_period(now); } - time_t bucketTime = asd->stats.firstPktsecond - - (asd->stats.firstPktsecond % bucketInterval); + time_t bucketTime = asd->stats.first_packet_second - + (asd->stats.first_packet_second % bucketInterval); StatsBucket* bucket = get_stats_bucket(bucketTime); if ( !bucket ) return; - bucket->totalStats.txByteCnt += asd->stats.initiatorBytes; - bucket->totalStats.rxByteCnt += asd->stats.responderBytes; + bucket->totalStats.txByteCnt += asd->stats.initiator_bytes; + bucket->totalStats.rxByteCnt += asd->stats.responder_bytes; - const uint32_t web_app_id = asd->pick_payload_app_id(); - if (web_app_id > APP_ID_NONE) - { - const uint32_t app_id = web_app_id; - AppIdStatRecord* record = (AppIdStatRecord*)fwAvlLookup(app_id, bucket->appsTree); - if ( !record ) - { - record = (AppIdStatRecord*)snort_calloc(sizeof(struct AppIdStatRecord)); - if (fwAvlInsert(app_id, record, bucket->appsTree) == 0) - { - record->app_id = app_id; - bucket->appRecordCnt += 1; -#ifdef DEBUG_STATS - fprintf(SF_DEBUG_FILE, "New App: %u Count %u\n", record->app_id, - bucket->appRecordCnt); -#endif - } - else - { - WarningMessage("Error saving statistics record for app id: %u", app_id); - snort_free(record); - record = nullptr; - } - } + AppId web_app_id = asd->pick_payload_app_id(); + if ( web_app_id > APP_ID_NONE ) + update_stats(asd, web_app_id, bucket); - if (record) - { - record->initiatorBytes += asd->stats.initiatorBytes; - record->responderBytes += asd->stats.responderBytes; - } - } + AppId service_app_id = asd->pick_service_app_id(); + if ( service_app_id && ( service_app_id != web_app_id ) ) + update_stats(asd, service_app_id, bucket); - const uint32_t service_app_id = asd->pick_service_app_id(); - if ((service_app_id) && - (service_app_id != web_app_id)) - { - const uint32_t app_id = service_app_id; - AppIdStatRecord* record = (AppIdStatRecord*)fwAvlLookup(app_id, bucket->appsTree); - if ( !record ) - { - record = (AppIdStatRecord*)snort_calloc(sizeof(struct AppIdStatRecord)); - if (fwAvlInsert(app_id, record, bucket->appsTree) == 0) - { - record->app_id = app_id; - bucket->appRecordCnt += 1; -#ifdef DEBUG_STATS - fprintf(SF_DEBUG_FILE, "New App: %u Count %u\n", record->app_id, - bucket->appRecordCnt); -#endif - } - else - { - WarningMessage("Error saving statistics record for app id: %u", app_id); - snort_free(record); - record = nullptr; - } - } - - if (record) - { - record->initiatorBytes += asd->stats.initiatorBytes; - record->responderBytes += asd->stats.responderBytes; - } - } - - const uint32_t client_app_id = asd->pick_client_app_id(); - if (client_app_id > APP_ID_NONE - && client_app_id != service_app_id - && client_app_id != web_app_id) - { - const uint32_t app_id = client_app_id; - - AppIdStatRecord* record = (AppIdStatRecord*)fwAvlLookup(app_id, bucket->appsTree); - if ( !record ) - { - record = (AppIdStatRecord*)snort_calloc(sizeof(struct AppIdStatRecord)); - if (fwAvlInsert(app_id, record, bucket->appsTree) == 0) - { - record->app_id = app_id; - bucket->appRecordCnt += 1; -#ifdef DEBUG_STATS - fprintf(SF_DEBUG_FILE, "New App: %u Count %u\n", record->app_id, - bucket->appRecordCnt); -#endif - } - else - { - WarningMessage("Error saving statistics record for app id: %u", app_id); - snort_free(record); - record = nullptr; - } - } - - if (record) - { - record->initiatorBytes += asd->stats.initiatorBytes; - record->responderBytes += asd->stats.responderBytes; - } - } + AppId client_app_id = asd->pick_client_app_id(); + if ( client_app_id > APP_ID_NONE && client_app_id != service_app_id + && client_app_id != web_app_id ) + update_stats(asd, client_app_id, bucket); } void AppIdStatistics::flush() diff --git a/src/network_inspectors/appid/appid_utils/appid_utils.cc b/src/network_inspectors/appid/appid_utils/appid_utils.cc deleted file mode 100644 index d1bfcb639..000000000 --- a/src/network_inspectors/appid/appid_utils/appid_utils.cc +++ /dev/null @@ -1,202 +0,0 @@ -//-------------------------------------------------------------------------- -// Copyright (C) 2014-2017 Cisco and/or its affiliates. All rights reserved. -// Copyright (C) 2005-2013 Sourcefire, Inc. -// -// This program is free software; you can redistribute it and/or modify it -// under the terms of the GNU General Public License Version 2 as published -// by the Free Software Foundation. You may not use, modify or distribute -// this program under any other version of the GNU General Public License. -// -// This program is distributed in the hope that it will be useful, but -// WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU -// General Public License for more details. -// -// You should have received a copy of the GNU General Public License along -// with this program; if not, write to the Free Software Foundation, Inc., -// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. -//-------------------------------------------------------------------------- - -// sfutil.cc author Sourcefire Inc. - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include "appid_utils.h" - -#include -#include - -int AppIdUtils::split(char* data, char** toklist, int max_toks, const char* separator) -{ - char** ap; - int argcount = 0; - - memset(toklist, 0, max_toks * sizeof(*toklist)); - for (ap = (char**)toklist; - ap < &toklist[max_toks] && (*ap = strsep(&data, separator)) != nullptr; ) - { - if (**ap != '\0') - { - ap++; - argcount++; - } - } - - return argcount; -} - -void AppIdUtils::init_netmasks(uint32_t netmasks[]) -{ - netmasks[0] = 0x0; - netmasks[1] = 0x80000000; - netmasks[2] = 0xC0000000; - netmasks[3] = 0xE0000000; - netmasks[4] = 0xF0000000; - netmasks[5] = 0xF8000000; - netmasks[6] = 0xFC000000; - netmasks[7] = 0xFE000000; - netmasks[8] = 0xFF000000; - netmasks[9] = 0xFF800000; - netmasks[10] = 0xFFC00000; - netmasks[11] = 0xFFE00000; - netmasks[12] = 0xFFF00000; - netmasks[13] = 0xFFF80000; - netmasks[14] = 0xFFFC0000; - netmasks[15] = 0xFFFE0000; - netmasks[16] = 0xFFFF0000; - netmasks[17] = 0xFFFF8000; - netmasks[18] = 0xFFFFC000; - netmasks[19] = 0xFFFFE000; - netmasks[20] = 0xFFFFF000; - netmasks[21] = 0xFFFFF800; - netmasks[22] = 0xFFFFFC00; - netmasks[23] = 0xFFFFFE00; - netmasks[24] = 0xFFFFFF00; - netmasks[25] = 0xFFFFFF80; - netmasks[26] = 0xFFFFFFC0; - netmasks[27] = 0xFFFFFFE0; - netmasks[28] = 0xFFFFFFF0; - netmasks[29] = 0xFFFFFFF8; - netmasks[30] = 0xFFFFFFFC; - netmasks[31] = 0xFFFFFFFE; - netmasks[32] = 0xFFFFFFFF; -} - -int AppIdUtils::strip(char* data) -{ - int size; - char* idx; - - idx = data; - size = 0; - - while (*idx) - { - if ((*idx == '\n') || (*idx == '\r')) - { - *idx = 0; - break; - } - if (*idx == '\t') - { - *idx = ' '; - } - size++; - idx++; - } - - return size; -} - -int AppIdUtils::tokenize(char* data, char* toklist[]) -{ - char** ap; - int argcount = 0; - int i = 0; - char* tok; - int drop_further = 0; - - for (ap = (char**)toklist; ap < &toklist[MAX_TOKS] && (*ap = strsep(&data, " ")) != nullptr; ) - { - if (**ap != '\0') - { - ap++; - argcount++; - } - } - - *ap = nullptr; - - /* scan for comments */ - while (i < argcount) - { - tok = toklist[i]; - - if (tok[0] == '#' && !drop_further) - { - argcount = i; - drop_further = 1; - } - - if (drop_further) - { - toklist[i] = nullptr; - } - - i++; - } - - return argcount; -} - -// FIXIT-L - refactor this to be a general snort utility...also look at LogBuffer() in u2spewfoo.cc -void AppIdUtils::dump_hex(FILE* fp, const uint8_t* data, unsigned len) -{ - char str[18]; - unsigned i; - unsigned pos; - char c; - - for (i=0, pos=0; i #include "log/messages.h" #include "utils/util.h" -#include "appid_utils.h" + +// FIXIT-L - These utility functions should probably go in the shared src/utils/ instead of just +// appid if they are truly generic. + +// convert tabs to space, convert new line or carriage return to null +// and stop returning the length of the converted string +static int strip(char* data) +{ + int size; + char* idx; + + idx = data; + size = 0; + + while (*idx) + { + if ((*idx == '\n') || (*idx == '\r')) + { + *idx = 0; + break; + } + if (*idx == '\t') + { + *idx = ' '; + } + size++; + idx++; + } + + return size; +} + +// split string pointed to by 'data' into tokens based on the set of delimiters +// defined by the 'separator string, return number of tokens +static int split(char* data, char** toklist, int max_toks, const char* separator) +{ + char** ap; + int argcount = 0; + + memset(toklist, 0, max_toks * sizeof(*toklist)); + for (ap = (char**)toklist; + ap < &toklist[max_toks] && (*ap = strsep(&data, separator)) != nullptr; ) + { + if (**ap != '\0') + { + ap++; + argcount++; + } + } + + return argcount; +} RNAIpAddrSet* ParseIpCidr(char* ipstring, uint32_t* netmasks) { @@ -44,7 +95,7 @@ RNAIpAddrSet* ParseIpCidr(char* ipstring, uint32_t* netmasks) return nullptr; ias = (RNAIpAddrSet*)snort_calloc(sizeof(RNAIpAddrSet)); - AppIdUtils::strip(ipstring); + strip(ipstring); cp = ipstring; if (*cp == 'h') { @@ -70,7 +121,7 @@ RNAIpAddrSet* ParseIpCidr(char* ipstring, uint32_t* netmasks) return ias; } - num_toks = AppIdUtils::split(cp, toks, 2, "/"); + num_toks = split(cp, toks, 2, "/"); if (inet_pton(AF_INET, toks[0], &ia) <= 0) { @@ -122,7 +173,7 @@ RNAIpv6AddrSet* ParseIpv6Cidr(char* ipstring) return nullptr; ias = (RNAIpv6AddrSet*)snort_calloc(sizeof(*ias)); - AppIdUtils::strip(ipstring); + strip(ipstring); cp = ipstring; if (*cp == 'h') { @@ -149,7 +200,7 @@ RNAIpv6AddrSet* ParseIpv6Cidr(char* ipstring) return ias; } - num_toks = AppIdUtils::split(cp, toks, 2, "/"); + num_toks = split(cp, toks, 2, "/"); if (inet_pton(AF_INET6, toks[0], &ia) <= 0) { diff --git a/src/network_inspectors/appid/application_ids.h b/src/network_inspectors/appid/application_ids.h index 8fa9b1522..e894eac98 100644 --- a/src/network_inspectors/appid/application_ids.h +++ b/src/network_inspectors/appid/application_ids.h @@ -1002,6 +1002,11 @@ enum ApplicationId : int32_t APP_ID_HTTP_SSL_TUNNEL = 3860, APP_ID_FTP_ACTIVE = 4002, APP_ID_FTP_PASSIVE = 4003, +#ifdef REG_TEST + APP_ID_REGTEST = 10000, + APP_ID_REGTEST1 = 10001, + APP_ID_REGTEST2 = 10002, +#endif APP_ID_UNKNOWN_UI = 65535 // UI renders this value as 'Unknown' }; diff --git a/src/network_inspectors/appid/client_plugins/client_app_aim.cc b/src/network_inspectors/appid/client_plugins/client_app_aim.cc index 373d00c6f..f4f2cb7f0 100644 --- a/src/network_inspectors/appid/client_plugins/client_app_aim.cc +++ b/src/network_inspectors/appid/client_plugins/client_app_aim.cc @@ -201,7 +201,7 @@ int AimClientDetector::validate(AppIdDiscoveryArgs& args) char username[USERNAME_LEN]; if ( check_username(cur, tlv, username, username + USERNAME_LEN) ) - add_user(args.asd, username, APP_ID_AOL_INSTANT_MESSENGER, 1); + add_user(args.asd, username, APP_ID_AOL_INSTANT_MESSENGER, true); } break; case 0x0003: @@ -241,7 +241,7 @@ int AimClientDetector::validate(AppIdDiscoveryArgs& args) return APPID_INPROCESS; bail: - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); return APPID_SUCCESS; } diff --git a/src/network_inspectors/appid/client_plugins/client_app_bit.cc b/src/network_inspectors/appid/client_plugins/client_app_bit.cc index 62d4ef04c..1f0356d58 100644 --- a/src/network_inspectors/appid/client_plugins/client_app_bit.cc +++ b/src/network_inspectors/appid/client_plugins/client_app_bit.cc @@ -159,7 +159,7 @@ inprocess: done: add_app(args.asd, APP_ID_BITTORRENT, APP_ID_BITTORRENT, nullptr); - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); appid_stats.bit_clients++; return APPID_SUCCESS; } diff --git a/src/network_inspectors/appid/client_plugins/client_app_bit_tracker.cc b/src/network_inspectors/appid/client_plugins/client_app_bit_tracker.cc index eb9f39864..f9dca6cff 100644 --- a/src/network_inspectors/appid/client_plugins/client_app_bit_tracker.cc +++ b/src/network_inspectors/appid/client_plugins/client_app_bit_tracker.cc @@ -206,7 +206,7 @@ inprocess: done: add_app(args.asd, APP_ID_BITTORRENT, APP_ID_BITTRACKER_CLIENT, nullptr); - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); appid_stats.bittracker_clients++; return APPID_SUCCESS; } diff --git a/src/network_inspectors/appid/client_plugins/client_app_msn.cc b/src/network_inspectors/appid/client_plugins/client_app_msn.cc index 57eea682e..db3d90c59 100644 --- a/src/network_inspectors/appid/client_plugins/client_app_msn.cc +++ b/src/network_inspectors/appid/client_plugins/client_app_msn.cc @@ -110,17 +110,16 @@ int MsnClientDetector::validate(AppIdDiscoveryArgs& args) args.data++; /* skip the space */ } - else if ( end - args.data >= (int)sizeof(MACMSGS) && memcmp(args.data, MACMSGS, - sizeof(MACMSGS)-1) == - 0 ) + else if ( end - args.data >= (int)sizeof(MACMSGS) && + memcmp(args.data, MACMSGS, sizeof(MACMSGS)-1) == 0 ) { product_id = APP_ID_MSN_MESSENGER; args.data += sizeof(MACMSGS) - 1; args.data++; /* skip the space */ } - else if ( end - args.data >= (int)sizeof(MSMSGS) && memcmp(args.data, MSMSGS, - sizeof(MSMSGS)-1) == 0 ) + else if ( end - args.data >= (int)sizeof(MSMSGS) && + memcmp(args.data, MSMSGS, sizeof(MSMSGS)-1) == 0 ) { product_id = APP_ID_MICROSOFT_WINDOWS_MESSENGER; args.data += sizeof(MSMSGS) - 1; @@ -154,7 +153,7 @@ int MsnClientDetector::validate(AppIdDiscoveryArgs& args) done: add_app(args.asd, APP_ID_MSN_MESSENGER, product_id, (char*)version); - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); appid_stats.msn_clients++; return APPID_SUCCESS; } diff --git a/src/network_inspectors/appid/client_plugins/client_app_rtp.cc b/src/network_inspectors/appid/client_plugins/client_app_rtp.cc index d9fa9bbe8..e6430f24b 100644 --- a/src/network_inspectors/appid/client_plugins/client_app_rtp.cc +++ b/src/network_inspectors/appid/client_plugins/client_app_rtp.cc @@ -291,7 +291,7 @@ int RtpClientDetector::validate(AppIdDiscoveryArgs& args) } add_app(args.asd, APP_ID_RTP, APP_ID_RTP, nullptr); - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); appid_stats.rtp_clients++; return APPID_SUCCESS; } diff --git a/src/network_inspectors/appid/client_plugins/client_app_ssh.cc b/src/network_inspectors/appid/client_plugins/client_app_ssh.cc index 94320e94f..6f242d73c 100644 --- a/src/network_inspectors/appid/client_plugins/client_app_ssh.cc +++ b/src/network_inspectors/appid/client_plugins/client_app_ssh.cc @@ -574,7 +574,7 @@ int SshClientDetector::validate(AppIdDiscoveryArgs& args) return sm_ret; add_app(args.asd, APP_ID_SSH, fd->client_id, (const char*)fd->version); - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); appid_stats.ssh_clients++; return APPID_SUCCESS; } diff --git a/src/network_inspectors/appid/client_plugins/client_app_timbuktu.cc b/src/network_inspectors/appid/client_plugins/client_app_timbuktu.cc index 84f3594cd..0d359e7e9 100644 --- a/src/network_inspectors/appid/client_plugins/client_app_timbuktu.cc +++ b/src/network_inspectors/appid/client_plugins/client_app_timbuktu.cc @@ -176,7 +176,7 @@ inprocess: done: add_app(args.asd, APP_ID_TIMBUKTU, APP_ID_TIMBUKTU, nullptr); appid_stats.timbuktu_clients++; - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); return APPID_SUCCESS; } diff --git a/src/network_inspectors/appid/client_plugins/client_app_tns.cc b/src/network_inspectors/appid/client_plugins/client_app_tns.cc index ce846e51c..458cc63b8 100644 --- a/src/network_inspectors/appid/client_plugins/client_app_tns.cc +++ b/src/network_inspectors/appid/client_plugins/client_app_tns.cc @@ -363,9 +363,9 @@ done: user_size = TNS_MAX_INFO_SIZE; memcpy(username, &args.data[user_start], user_size); username[user_size] = 0; - add_user(args.asd, username, APP_ID_ORACLE_DATABASE, 1); + add_user(args.asd, username, APP_ID_ORACLE_DATABASE, true); } - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); appid_stats.tns_clients++; return APPID_SUCCESS; } diff --git a/src/network_inspectors/appid/client_plugins/client_app_vnc.cc b/src/network_inspectors/appid/client_plugins/client_app_vnc.cc index f5b50347a..b231a5343 100644 --- a/src/network_inspectors/appid/client_plugins/client_app_vnc.cc +++ b/src/network_inspectors/appid/client_plugins/client_app_vnc.cc @@ -132,7 +132,7 @@ inprocess: done: add_app(args.asd, APP_ID_VNC_RFB, APP_ID_VNC, (const char*)fd->version); - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); appid_stats.vnc_clients++; return APPID_SUCCESS; } diff --git a/src/network_inspectors/appid/client_plugins/client_app_ym.cc b/src/network_inspectors/appid/client_plugins/client_app_ym.cc index babbff486..fb11250e7 100644 --- a/src/network_inspectors/appid/client_plugins/client_app_ym.cc +++ b/src/network_inspectors/appid/client_plugins/client_app_ym.cc @@ -155,7 +155,7 @@ int YmDetector::validate(AppIdDiscoveryArgs& args) done: add_app(args.asd, APP_ID_YAHOO, product_id, (char*)version); - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); appid_stats.yahoo_messenger_clients++; return APPID_SUCCESS; } diff --git a/src/network_inspectors/appid/client_plugins/client_detector.cc b/src/network_inspectors/appid/client_plugins/client_detector.cc index fc0c31078..b47a61c5c 100644 --- a/src/network_inspectors/appid/client_plugins/client_detector.cc +++ b/src/network_inspectors/appid/client_plugins/client_detector.cc @@ -40,11 +40,6 @@ ClientDetector::ClientDetector() flow_data_index = client_module_index++ | APPID_SESSION_DATA_CLIENT_MODSTATE_BIT; } -int ClientDetector::validate(AppIdDiscoveryArgs&) -{ - return APPID_SUCCESS; -} - void ClientDetector::register_appid(AppId appId, unsigned extractsInfo) { AppInfoTableEntry* pEntry = AppInfoManager::get_instance().get_app_info_entry(appId); diff --git a/src/network_inspectors/appid/client_plugins/client_detector.h b/src/network_inspectors/appid/client_plugins/client_detector.h index 2c2828bff..d317b853b 100644 --- a/src/network_inspectors/appid/client_plugins/client_detector.h +++ b/src/network_inspectors/appid/client_plugins/client_detector.h @@ -34,7 +34,6 @@ public: virtual ~ClientDetector() { } virtual void do_custom_init() override { } - virtual int validate(AppIdDiscoveryArgs&) override; virtual void register_appid(AppId, unsigned extractsInfo) override; }; #endif diff --git a/src/network_inspectors/appid/client_plugins/client_discovery.cc b/src/network_inspectors/appid/client_plugins/client_discovery.cc index d4b8c1545..cce498342 100644 --- a/src/network_inspectors/appid/client_plugins/client_discovery.cc +++ b/src/network_inspectors/appid/client_plugins/client_discovery.cc @@ -162,23 +162,6 @@ static int pattern_match(void* id, void* /*unused_tree*/, int match_end_pos, voi return 0; } -static ClientAppMatch* find_detector_candidates(const Packet* pkt, IpProtocol protocol) -{ - ClientAppMatch* match_list = nullptr; - SearchTool* patterns; - - if (protocol == IpProtocol::TCP) - patterns = ClientDiscovery::get_instance().tcp_patterns; - else - patterns = ClientDiscovery::get_instance().udp_patterns; - - if (!patterns) - return nullptr; - - patterns->find_all((char*)pkt->data, pkt->dsize, &pattern_match, false, (void*)&match_list); - return match_list; -} - static const ClientDetector* get_next_detector(ClientAppMatch** match_list) { ClientAppMatch* curr = nullptr; @@ -193,12 +176,12 @@ static const ClientDetector* get_next_detector(ClientAppMatch** match_list) max_precedence = 0; while (curr) { - if (curr->count >= curr->detector->minimum_matches + if (curr->count >= curr->detector->get_minimum_matches() && ((curr->count > max_count) - || (curr->count == max_count && curr->detector->precedence > max_precedence))) + || (curr->count == max_count && curr->detector->get_precedence() > max_precedence))) { max_count = curr->count; - max_precedence = curr->detector->precedence; + max_precedence = curr->detector->get_precedence(); max_curr = curr; max_prev = prev; } @@ -238,43 +221,55 @@ static void free_matched_list(ClientAppMatch** match_list) *match_list = nullptr; } -/** - * The process to determine the running client app given the packet data. - * - * @param p packet to process - */ -static void create_detector_candidates_list(Packet* p, const int /*direction*/, AppIdSession* asd) +ClientAppMatch* ClientDiscovery::find_detector_candidates(const Packet* pkt, IpProtocol protocol) +{ + ClientAppMatch* match_list = nullptr; + SearchTool* patterns; + + if (protocol == IpProtocol::TCP) + patterns = ClientDiscovery::get_instance().tcp_patterns; + else + patterns = ClientDiscovery::get_instance().udp_patterns; + + if (!patterns) + return nullptr; + + patterns->find_all((char*)pkt->data, pkt->dsize, &pattern_match, false, (void*)&match_list); + return match_list; +} + +void ClientDiscovery::create_detector_candidates_list(AppIdSession& asd, Packet* p) { ClientAppMatch* match_list; - if ( !p->dsize || asd->client_detector != nullptr || asd->client_candidates.size() ) + if ( !p->dsize || asd.client_detector != nullptr || asd.client_candidates.size() ) return; - match_list = find_detector_candidates(p, asd->protocol); - while (asd->client_candidates.size() < MAX_CANDIDATE_CLIENTS) + match_list = find_detector_candidates(p, asd.protocol); + while ( asd.client_candidates.size() < MAX_CANDIDATE_CLIENTS ) { ClientDetector* cd = const_cast(get_next_detector(&match_list)); if (!cd) break; - if ( asd->client_candidates.find(cd->name) == asd->client_candidates.end() ) - asd->client_candidates[cd->name] = cd; + if ( asd.client_candidates.find(cd->get_name()) == asd.client_candidates.end() ) + asd.client_candidates[cd->get_name()] = cd; } free_matched_list(&match_list); } -int get_detector_candidates_list(Packet* p, int direction, AppIdSession* asd) +int ClientDiscovery::get_detector_candidates_list(AppIdSession& asd, Packet* p, int direction) { if (direction == APP_ID_FROM_INITIATOR) { /* get out if we've already tried to validate a client app */ - if (!asd->get_session_flags(APPID_SESSION_CLIENT_DETECTED)) - create_detector_candidates_list(p, direction, asd); + if ( !asd.is_client_detected() ) + create_detector_candidates_list(asd, p); } - else if ( asd->service_disco_state != APPID_DISCO_STATE_STATEFUL - && asd->get_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS)) - create_detector_candidates_list(p, direction, asd); + else if ( asd.service_disco_state != APPID_DISCO_STATE_STATEFUL + && asd.get_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS) ) + create_detector_candidates_list(asd, p); return APPID_SESSION_SUCCESS; } @@ -289,7 +284,7 @@ int ClientDiscovery::exec_client_detectors(AppIdSession& asd, Packet* p, int dir ret = asd.client_detector->validate(disco_args); if (asd.session_logging_enabled) LogMessage("AppIdDbg %s %s client detector returned %d\n", - asd.session_logging_id, asd.client_detector->name.c_str(), ret); + asd.session_logging_id, asd.client_detector->get_name().c_str(), ret); } else { @@ -299,7 +294,7 @@ int ClientDiscovery::exec_client_detectors(AppIdSession& asd, Packet* p, int dir int result = kv->second->validate(disco_args); if (asd.session_logging_enabled) LogMessage("AppIdDbg %s %s client detector returned %d\n", - asd.session_logging_id, kv->second->name.c_str(), result); + asd.session_logging_id, kv->second->get_name().c_str(), result); if (result == APPID_SUCCESS) { @@ -318,130 +313,125 @@ int ClientDiscovery::exec_client_detectors(AppIdSession& asd, Packet* p, int dir return ret; } -bool ClientDiscovery::do_client_discovery(AppIdSession& asd, int direction, Packet* p) +bool ClientDiscovery::do_client_discovery(AppIdSession& asd, Packet* p, int direction) { bool isTpAppidDiscoveryDone = false; AppInfoTableEntry* entry; - if (asd.client_disco_state != APPID_DISCO_STATE_FINISHED) + Profile clientMatchPerfStats_profile_context(clientMatchPerfStats); + uint32_t prevRnaClientState = asd.client_disco_state; + bool was_http2 = asd.is_http2; + bool was_service = asd.is_service_detected(); + + if ( asd.client_disco_state == APPID_DISCO_STATE_NONE + && p->dsize && direction == APP_ID_FROM_INITIATOR ) { - Profile clientMatchPerfStats_profile_context(clientMatchPerfStats); - uint32_t prevRnaClientState = asd.client_disco_state; - bool was_http2 = asd.is_http2; - bool was_service = asd.get_session_flags(APPID_SESSION_SERVICE_DETECTED) ? true : false; - //decision to directly call validator or go through elaborate service_state tracking - //is made once at the beginning of sesssion. - if (asd.client_disco_state == APPID_DISCO_STATE_NONE && p->dsize && direction == - APP_ID_FROM_INITIATOR) + if ( p->flow->get_session_flags() & SSNFLAG_MIDSTREAM ) + asd.client_disco_state = APPID_DISCO_STATE_FINISHED; + else if ( is_third_party_appid_available(asd.tpsession) + && ( asd.tp_app_id > APP_ID_NONE && asd.tp_app_id < SF_APPID_MAX ) ) { - if (p->flow->get_session_flags() & SSNFLAG_MIDSTREAM) - asd.client_disco_state = APPID_DISCO_STATE_FINISHED; - else if (is_third_party_appid_available(asd.tpsession) && ( asd.tp_app_id > - APP_ID_NONE ) - && ( asd.tp_app_id < SF_APPID_MAX ) ) + //tp has positively identified appId, Dig deeper only if sourcefire + // detector identifies additional information + entry = asd.app_info_mgr->get_app_info_entry(asd.tp_app_id); + if ( entry && entry->client_detector + && ( ( entry->flags & ( APPINFO_FLAG_CLIENT_ADDITIONAL | + APPINFO_FLAG_CLIENT_USER ) ) + && asd.get_session_flags(APPID_SESSION_DISCOVER_USER) ) ) { - entry = asd.app_info_mgr->get_app_info_entry(asd.tp_app_id); - if ( entry && entry->client_detector - && ( ( entry->flags & APPINFO_FLAG_CLIENT_ADDITIONAL ) - || ( ( entry->flags & APPINFO_FLAG_CLIENT_USER) - && asd.get_session_flags(APPID_SESSION_DISCOVER_USER) ) ) ) - { - //tp has positively identified appId, Dig deeper only if sourcefire - // detector identifies additional information - asd.client_detector = entry->client_detector; - asd.client_disco_state = APPID_DISCO_STATE_DIRECT; - } - else - { - asd.set_session_flags(APPID_SESSION_CLIENT_DETECTED); - asd.client_disco_state = APPID_DISCO_STATE_FINISHED; - } + asd.client_detector = entry->client_detector; + asd.client_disco_state = APPID_DISCO_STATE_DIRECT; } - else if (asd.get_session_flags(APPID_SESSION_HTTP_SESSION)) - asd.client_disco_state = APPID_DISCO_STATE_FINISHED; else - asd.client_disco_state = APPID_DISCO_STATE_STATEFUL; - } - //stop rna inspection as soon as tp has classified a valid AppId later in the session - if ( (asd.client_disco_state == APPID_DISCO_STATE_STATEFUL || - asd.client_disco_state == APPID_DISCO_STATE_DIRECT) && - asd.client_disco_state == prevRnaClientState && - !asd.get_session_flags( APPID_SESSION_NO_TPI) && - is_third_party_appid_available(asd.tpsession) && - asd.tp_app_id > APP_ID_NONE && asd.tp_app_id < SF_APPID_MAX) - { - entry = asd.app_info_mgr->get_app_info_entry(asd.tp_app_id); - if (!(entry && entry->client_detector && entry->client_detector == asd.client_detector - && (entry->flags & (APPINFO_FLAG_CLIENT_ADDITIONAL | APPINFO_FLAG_CLIENT_USER)))) { + asd.set_client_detected(); asd.client_disco_state = APPID_DISCO_STATE_FINISHED; - asd.set_session_flags(APPID_SESSION_CLIENT_DETECTED); } } + else if ( asd.get_session_flags(APPID_SESSION_HTTP_SESSION) ) + asd.client_disco_state = APPID_DISCO_STATE_FINISHED; + else + asd.client_disco_state = APPID_DISCO_STATE_STATEFUL; + } + + //stop rna inspection as soon as tp has classified a valid AppId + if ( ( asd.client_disco_state == APPID_DISCO_STATE_STATEFUL || + asd.client_disco_state == APPID_DISCO_STATE_DIRECT) && + asd.client_disco_state == prevRnaClientState && + !asd.get_session_flags(APPID_SESSION_NO_TPI) && + is_third_party_appid_available(asd.tpsession) && + asd.tp_app_id > APP_ID_NONE && asd.tp_app_id < SF_APPID_MAX) + { + entry = asd.app_info_mgr->get_app_info_entry(asd.tp_app_id); + if ( !( entry && entry->client_detector + && entry->client_detector == asd.client_detector + && (entry->flags & (APPINFO_FLAG_CLIENT_ADDITIONAL | APPINFO_FLAG_CLIENT_USER) ) ) ) + { + asd.client_disco_state = APPID_DISCO_STATE_FINISHED; + asd.set_client_detected(); + } + } - if (asd.client_disco_state == APPID_DISCO_STATE_DIRECT) + if ( asd.client_disco_state == APPID_DISCO_STATE_DIRECT ) + { + int ret = APPID_INPROCESS; + if ( direction == APP_ID_FROM_INITIATOR ) + { + /* get out if we've already tried to validate a client app */ + if (!asd.is_client_detected() ) + ret = exec_client_detectors(asd, p, direction); + } + else if ( asd.service_disco_state != APPID_DISCO_STATE_STATEFUL + && asd.get_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS) ) + { + ret = exec_client_detectors(asd, p, direction); + } + + switch (ret) + { + case APPID_INPROCESS: + break; + default: + asd.client_disco_state = APPID_DISCO_STATE_FINISHED; + break; + } + } + else if ( asd.client_disco_state == APPID_DISCO_STATE_STATEFUL ) + { + get_detector_candidates_list(asd, p, direction); + isTpAppidDiscoveryDone = true; + if ( asd.client_candidates.size() ) { - int ret = APPID_INPROCESS; - if (direction == APP_ID_FROM_INITIATOR) + int ret = 0; + if ( direction == APP_ID_FROM_INITIATOR ) { /* get out if we've already tried to validate a client app */ - if (!asd.get_session_flags(APPID_SESSION_CLIENT_DETECTED)) - { + if (!asd.is_client_detected()) ret = exec_client_detectors(asd, p, direction); - } } - else if (asd.service_disco_state != APPID_DISCO_STATE_STATEFUL - && asd.get_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS)) - { + else if ( asd.service_disco_state != APPID_DISCO_STATE_STATEFUL + && asd.get_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS) ) ret = exec_client_detectors(asd, p, direction); - } - switch (ret) + if ( ret < 0 ) { - case APPID_INPROCESS: - break; - default: + asd.set_client_detected(); asd.client_disco_state = APPID_DISCO_STATE_FINISHED; - break; } } - else if (asd.client_disco_state == APPID_DISCO_STATE_STATEFUL) + else { - get_detector_candidates_list(p, direction, &asd); - isTpAppidDiscoveryDone = true; - if ( asd.client_candidates.size() ) - { - int ret = 0; - if (direction == APP_ID_FROM_INITIATOR) - { - /* get out if we've already tried to validate a client app */ - if (!asd.get_session_flags(APPID_SESSION_CLIENT_DETECTED)) - ret = exec_client_detectors(asd, p, direction); - } - else if (asd.service_disco_state != APPID_DISCO_STATE_STATEFUL - && asd.get_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS)) - ret = exec_client_detectors(asd, p, direction); - - if (ret < 0) - { - asd.set_session_flags(APPID_SESSION_CLIENT_DETECTED); - asd.client_disco_state = APPID_DISCO_STATE_FINISHED; - } - } - else - { - asd.set_session_flags(APPID_SESSION_CLIENT_DETECTED); - asd.client_disco_state = APPID_DISCO_STATE_FINISHED; - } + asd.set_client_detected(); + asd.client_disco_state = APPID_DISCO_STATE_FINISHED; } + } - if (asd.session_logging_enabled) - if (!was_http2 && asd.is_http2) - LogMessage("AppIdDbg %s Got a preface for HTTP/2\n", asd.session_logging_id); + if ( asd.session_logging_enabled ) + if ( !was_http2 && asd.is_http2 ) + LogMessage("AppIdDbg %s Got a preface for HTTP/2\n", asd.session_logging_id); - if (!was_service && asd.get_session_flags(APPID_SESSION_SERVICE_DETECTED)) - asd.sync_with_snort_id(asd.serviceAppId, p); - } + if ( !was_service && asd.is_service_detected() ) + asd.sync_with_snort_id(asd.service_app_id, p); return isTpAppidDiscoveryDone; } diff --git a/src/network_inspectors/appid/client_plugins/client_discovery.h b/src/network_inspectors/appid/client_plugins/client_discovery.h index f2d94fd3c..0e31f1e13 100644 --- a/src/network_inspectors/appid/client_plugins/client_discovery.h +++ b/src/network_inspectors/appid/client_plugins/client_discovery.h @@ -46,15 +46,16 @@ public: static ClientDiscovery& get_instance(); void finalize_client_plugins(); - bool do_client_discovery(AppIdSession&, int direction, Packet*); + bool do_client_discovery(AppIdSession&, Packet*, int direction); private: ClientDiscovery(); void initialize() override; int exec_client_detectors(AppIdSession&, Packet*, int direction); + ClientAppMatch* find_detector_candidates(const Packet* pkt, IpProtocol); + void create_detector_candidates_list(AppIdSession&, Packet*); + int get_detector_candidates_list(AppIdSession&, Packet*, int direction); }; -int get_detector_candidates_list(Packet*, int direction, AppIdSession*); - #endif diff --git a/src/network_inspectors/appid/detector_plugins/detector_dns.cc b/src/network_inspectors/appid/detector_plugins/detector_dns.cc index 6c234d3b5..4bba2e279 100644 --- a/src/network_inspectors/appid/detector_plugins/detector_dns.cc +++ b/src/network_inspectors/appid/detector_plugins/detector_dns.cc @@ -260,8 +260,7 @@ DnsUdpServiceDetector::~DnsUdpServiceDetector() } void DnsValidator::add_dns_query_info(AppIdSession* asd, uint16_t id, const uint8_t* host, uint8_t - host_len, - uint16_t host_offset, uint16_t record_type) + host_len, uint16_t host_offset, uint16_t record_type) { if ( asd->dsession ) { @@ -392,7 +391,7 @@ int DnsValidator::dns_validate_label(const uint8_t* data, uint16_t* offset, uint } int DnsValidator::dns_validate_query(const uint8_t* data, uint16_t* offset, uint16_t size, - uint16_t id, unsigned host_reporting, AppIdSession* asd) + uint16_t id, bool host_reporting, AppIdSession* asd) { int ret; const uint8_t* host; @@ -442,7 +441,7 @@ int DnsValidator::dns_validate_query(const uint8_t* data, uint16_t* offset, uint } int DnsValidator::dns_validate_answer(const uint8_t* data, uint16_t* offset, uint16_t size, - uint16_t id, uint8_t rcode, unsigned host_reporting, AppIdSession* asd) + uint16_t id, uint8_t rcode, bool host_reporting, AppIdSession* asd) { int ret; const uint8_t* host; @@ -501,7 +500,7 @@ int DnsValidator::dns_validate_answer(const uint8_t* data, uint16_t* offset, uin } int DnsValidator::dns_validate_header(const int dir, DNSHeader* hdr, - unsigned host_reporting, AppIdSession* asd) + bool host_reporting, AppIdSession* asd) { if (hdr->Opcode > MAX_OPCODE || hdr->Opcode == INVALID_OPCODE) { @@ -528,7 +527,7 @@ int DnsValidator::dns_validate_header(const int dir, DNSHeader* hdr, } int DnsValidator::validate_packet(const uint8_t* data, uint16_t size, const int, - unsigned host_reporting, AppIdSession* asd) + bool host_reporting, AppIdSession* asd) { uint16_t i; uint16_t count; @@ -830,7 +829,7 @@ int dns_host_scan_hostname(const uint8_t* pattern, size_t size, AppId* ClientApp AppId* payloadId) { return dns_host_scan_patterns(serviceDnsConfig.dns_host_host_matcher, pattern, size, - +ClientAppId, payloadId); + ClientAppId, payloadId); } void service_dns_host_clean() diff --git a/src/network_inspectors/appid/detector_plugins/detector_dns.h b/src/network_inspectors/appid/detector_plugins/detector_dns.h index 046ae1d4c..8fe3eb08c 100644 --- a/src/network_inspectors/appid/detector_plugins/detector_dns.h +++ b/src/network_inspectors/appid/detector_plugins/detector_dns.h @@ -44,12 +44,12 @@ public: int dns_validate_label(const uint8_t* data, uint16_t* offset, uint16_t size, uint8_t* len, unsigned* len_valid); int dns_validate_query(const uint8_t* data, uint16_t* offset, uint16_t size, - uint16_t id, unsigned host_reporting, AppIdSession*); + uint16_t id, bool host_reporting, AppIdSession*); int dns_validate_answer(const uint8_t* data, uint16_t* offset, uint16_t size, - uint16_t id, uint8_t rcode, unsigned host_reporting, AppIdSession*); - int dns_validate_header(const int dir, DNSHeader*, unsigned host_reporting, AppIdSession*); + uint16_t id, uint8_t rcode, bool host_reporting, AppIdSession*); + int dns_validate_header(const int dir, DNSHeader*, bool host_reporting, AppIdSession*); int validate_packet(const uint8_t* data, uint16_t size, const int, - unsigned host_reporting, AppIdSession*); + bool host_reporting, AppIdSession*); }; class DnsTcpServiceDetector : public ServiceDetector, public DnsValidator diff --git a/src/network_inspectors/appid/detector_plugins/detector_imap.cc b/src/network_inspectors/appid/detector_plugins/detector_imap.cc index 986afbfa0..e942d8962 100644 --- a/src/network_inspectors/appid/detector_plugins/detector_imap.cc +++ b/src/network_inspectors/appid/detector_plugins/detector_imap.cc @@ -124,19 +124,18 @@ enum Client_App_Pattern_Index PATTERN_IMAP_OTHER // always last }; -struct ClientAppData +struct ImapClientData { IMAPClientState state; unsigned count; int detected; int got_user; int auth; - int set_flags; char username[IMAP_USER_NAME_MAX_LEN+1]; char imapCmdTag[IMAP_TAG_MAX_LEN+1]; }; -struct ServiceIMAPData +struct ImapServiceData { IMAPState state; unsigned pos; @@ -146,13 +145,15 @@ struct ServiceIMAPData char tagValue[IMAP_TAG_MAX_LEN+1]; }; -struct DetectorData +struct ImapDetectorData { - ClientAppData client; - ServiceIMAPData server; + ImapClientData client; + ImapServiceData server; int need_continue; }; +static THREAD_LOCAL ImapClientDetector* imap_client_detector = nullptr; + static int isImapTagChar(uint8_t tag) { /* Per RFC 3501 @@ -175,11 +176,11 @@ static int isImapTagChar(uint8_t tag) return 0; } -static int imap_server_validate(DetectorData* dd, const uint8_t* data, uint16_t size, +static int imap_server_validate(ImapDetectorData* dd, const uint8_t* data, uint16_t size, AppIdSession* asd, AppIdDetector* detector) { const uint8_t* end = data + size; - ServiceIMAPData* id = &dd->server; + ImapServiceData* id = &dd->server; id->flags &= ~IMAP_FLAG_RESULT_ALL; // flags will tell us OK vs. NO vs. BAD @@ -346,7 +347,7 @@ static int imap_server_validate(DetectorData* dd, const uint8_t* data, uint16_t case IMAP_STATE_MID_OK_LOGIN: // add user successful - note: use of LOGIN cmd implies no IMAPS if ((id->flags & IMAP_FLAG_RESULT_OK) && dd->client.username[0]) - detector->add_user(asd, dd->client.username, APP_ID_IMAP, 1); + detector->add_user(asd, dd->client.username, APP_ID_IMAP, true); id->state = IMAP_STATE_MID_LINE; break; @@ -377,7 +378,7 @@ static int imap_server_validate(DetectorData* dd, const uint8_t* data, uint16_t id->state = IMAP_STATE_ALNUM_CODE_TERM; // add user login failed - note: use of LOGIN cmd implies no IMAPS if ((id->flags & IMAP_FLAG_RESULT_NO) && dd->client.username[0]) - detector->add_user(asd, dd->client.username, APP_ID_IMAP, 0); + detector->add_user(asd, dd->client.username, APP_ID_IMAP, false); } } else @@ -488,6 +489,7 @@ static std::array eoc = ImapClientDetector::ImapClientDetector(ClientDiscovery* cdm) { + imap_client_detector = this; handler = cdm; name = "IMAP"; proto = IpProtocol::TCP; @@ -513,13 +515,13 @@ ImapClientDetector::~ImapClientDetector() void ImapClientDetector::do_custom_init() { - unsigned cooked_idx = 1; + unsigned index = 0; cmd_matcher = new SearchTool("ac_full"); if ( tcp_patterns.size() ) for (auto& pat : tcp_patterns) { - cmd_matcher->add(pat.pattern, pat.length, cooked_idx++); + cmd_matcher->add(pat.pattern, pat.length, index++); if (pat.length > longest_pattern) longest_pattern = pat.length; } @@ -529,7 +531,7 @@ void ImapClientDetector::do_custom_init() static int pattern_match(void* id, void*, int match_end_pos, void* data, void*) { unsigned long idx = (unsigned long)id; - if ( (int)imap_client_patterns[ idx - 1].length != match_end_pos ) + if ( (int)imap_client_patterns[idx].length != match_end_pos ) return 0; unsigned long* pat_idx = (unsigned long*)data; @@ -537,13 +539,28 @@ static int pattern_match(void* id, void*, int match_end_pos, void* data, void*) return 1; } +ImapDetectorData* ImapClientDetector::get_common_data(AppIdSession* asd) +{ + ImapDetectorData* dd = (ImapDetectorData*)data_get(asd); + if (!dd) + { + dd = (ImapDetectorData*)snort_calloc(sizeof(ImapDetectorData)); + data_add(asd, dd, &snort_free); + dd->server.state = IMAP_STATE_BEGIN; + dd->server.flags = IMAP_FLAG_FIRST_PACKET; + dd->need_continue = 1; + asd->set_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); + } + + return dd; +} + int ImapClientDetector::validate(AppIdDiscoveryArgs& args) { const uint8_t* s = args.data; const uint8_t* end = (args.data + args.size); unsigned length; AppIdFlowContentPattern* cmd = nullptr; - ClientAppData* fd; char tag[IMAP_TAG_MAX_LEN + 1] = { 0 }; #ifdef APP_ID_USES_REASSEMBLED @@ -553,23 +570,8 @@ int ImapClientDetector::validate(AppIdDiscoveryArgs& args) if (!args.size) return APPID_INPROCESS; - DetectorData* dd = (DetectorData*)data_get(args.asd); - if (!dd) - { - dd = (DetectorData*)snort_calloc(sizeof(DetectorData)); - data_add(args.asd, dd, &snort_free); - dd->server.flags = IMAP_FLAG_FIRST_PACKET; - fd = &dd->client; - } - else - fd = &dd->client; - - if (!fd->set_flags) - { - dd->need_continue = 1; - fd->set_flags = 1; - args.asd->set_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); - } + ImapDetectorData* dd = get_common_data(args.asd); + ImapClientData* fd = &dd->client; if (args.dir == APP_ID_FROM_RESPONDER) { @@ -611,7 +613,7 @@ int ImapClientDetector::validate(AppIdDiscoveryArgs& args) if (end == s || !isblank(*s)) { dd->need_continue = 0; - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); args.asd->clear_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); return APPID_SUCCESS; } @@ -622,17 +624,17 @@ int ImapClientDetector::validate(AppIdDiscoveryArgs& args) if ((length = (end - s)) <= 0) { dd->need_continue = 0; - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); args.asd->clear_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); return APPID_SUCCESS; } cmd = nullptr; - pattern_index = 0; + pattern_index = num_imap_client_patterns; cmd_matcher->find_all((char*)s, (length > longest_pattern ? longest_pattern : length), &pattern_match, false, (void*)&pattern_index); - if (pattern_index > 0) - cmd = &tcp_patterns[ pattern_index - 1]; + if (pattern_index < num_imap_client_patterns) + cmd = &tcp_patterns[pattern_index]; if (!cmd) { if ( (s[0] >= 'A' && s[0] <= 'Z') || (s[0] >= 'a' && s[0] <= 'z') ) @@ -646,6 +648,7 @@ int ImapClientDetector::validate(AppIdDiscoveryArgs& args) return APPID_ENULL; // anything but CLIENT_APP_SUCCESS or CLIENT_APP_INPROCESS } } + s += cmd->length; switch (fd->state) { @@ -680,7 +683,7 @@ int ImapClientDetector::validate(AppIdDiscoveryArgs& args) fd->detected = 1; if (fd->got_user) { - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); args.asd->clear_session_flags( APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); } @@ -723,7 +726,7 @@ int ImapClientDetector::validate(AppIdDiscoveryArgs& args) fd->detected = 1; if (fd->got_user) { - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); args.asd->clear_session_flags( APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); } @@ -772,7 +775,7 @@ int ImapClientDetector::validate(AppIdDiscoveryArgs& args) fd->detected = 1; if (fd->got_user) { - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); args.asd->clear_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); } } @@ -794,7 +797,7 @@ int ImapClientDetector::validate(AppIdDiscoveryArgs& args) fd->detected = 1; if (fd->got_user) { - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); args.asd->clear_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); } } @@ -845,8 +848,8 @@ ImapServiceDetector::~ImapServiceDetector() int ImapServiceDetector::validate(AppIdDiscoveryArgs& args) { - DetectorData* dd; - ServiceIMAPData* id; + ImapDetectorData* dd; + ImapServiceData* id; if (args.dir != APP_ID_FROM_RESPONDER) goto inprocess; @@ -858,17 +861,8 @@ int ImapServiceDetector::validate(AppIdDiscoveryArgs& args) if (!args.size) goto inprocess; - dd = (DetectorData*)data_get(args.asd); - if (!dd) - { - dd = (DetectorData*)snort_calloc(sizeof(DetectorData)); - data_add(args.asd, dd, &snort_free); - id = &dd->server; - id->state = IMAP_STATE_BEGIN; - id->flags = IMAP_FLAG_FIRST_PACKET; - } - else - id = &dd->server; + dd = imap_client_detector->get_common_data(args.asd); + id = &dd->server; // server side is seeing packets so no need for client side to process them args.asd->clear_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); @@ -878,7 +872,7 @@ int ImapServiceDetector::validate(AppIdDiscoveryArgs& args) else { args.asd->clear_session_flags(APPID_SESSION_CONTINUE); - if (args.asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (args.asd->is_service_detected()) { appid_stats.imap_flows++; return APPID_SUCCESS; @@ -897,14 +891,14 @@ int ImapServiceDetector::validate(AppIdDiscoveryArgs& args) } if (id->count >= IMAP_COUNT_THRESHOLD && - !args.asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + !args.asd->is_service_detected()) { add_service(args.asd, args.pkt, args.dir, APP_ID_IMAP, nullptr, nullptr, nullptr); appid_stats.imap_flows++; return APPID_SUCCESS; } } - else if (!args.asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + else if (!args.asd->is_service_detected()) { fail_service(args.asd, args.pkt, args.dir); return APPID_NOMATCH; diff --git a/src/network_inspectors/appid/detector_plugins/detector_imap.h b/src/network_inspectors/appid/detector_plugins/detector_imap.h index b689560e7..fbe605eae 100644 --- a/src/network_inspectors/appid/detector_plugins/detector_imap.h +++ b/src/network_inspectors/appid/detector_plugins/detector_imap.h @@ -26,6 +26,7 @@ #include "service_plugins/service_detector.h" class AppIdSession; +struct ImapDetectorData; class ImapClientDetector : public ClientDetector { @@ -35,6 +36,7 @@ public: void do_custom_init() override; int validate(AppIdDiscoveryArgs&) override; + ImapDetectorData* get_common_data(AppIdSession*); private: SearchTool* cmd_matcher = nullptr; diff --git a/src/network_inspectors/appid/detector_plugins/detector_kerberos.cc b/src/network_inspectors/appid/detector_plugins/detector_kerberos.cc index e4d0d3450..e3f1120f3 100644 --- a/src/network_inspectors/appid/detector_plugins/detector_kerberos.cc +++ b/src/network_inspectors/appid/detector_plugins/detector_kerberos.cc @@ -94,11 +94,10 @@ struct KRBState unsigned flags; }; -struct DetectorData +struct KerberosDetectorData { KRBState clnt_state; KRBState svr_state; - int set_flags; int need_continue; }; @@ -413,11 +412,11 @@ static int krb_walk_server_packet(KRBState* krbs, const uint8_t* s, const uint8_ DebugFormat(DEBUG_APPID,"%p Valid\n", (void*)asd); if (krbs->flags & KRB_FLAG_SERVICE_DETECTED) { - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED) && pkt) + if (!asd->is_service_detected() && pkt) { krb_service_detector->add_service(asd, pkt, dir, APP_ID_KERBEROS, nullptr, krbs->ver, nullptr); - asd->set_session_flags(APPID_SESSION_SERVICE_DETECTED); + asd->set_service_detected(); } } @@ -428,13 +427,13 @@ static int krb_walk_server_packet(KRBState* krbs, const uint8_t* s, const uint8_ { krb_service_detector->add_user(asd, (krbs->flags & KRB_FLAG_USER_DETECTED) ? krbs->cname : reqCname, - APP_ID_LDAP, 0); + APP_ID_LDAP, false); appid_stats.kerberos_users++; } } else if (krbs->flags & KRB_FLAG_USER_DETECTED) { - krb_service_detector->add_user(asd, krbs->cname, APP_ID_LDAP, 1); + krb_service_detector->add_user(asd, krbs->cname, APP_ID_LDAP, true); appid_stats.kerberos_users++; } @@ -488,72 +487,48 @@ KerberosServiceDetector::~KerberosServiceDetector() int KerberosServiceDetector::validate(AppIdDiscoveryArgs& args) { - DetectorData* fd; - AppIdSession* asd = args.asd; - const uint8_t* data = args.data; - Packet* pkt = args.pkt; - const int dir = args.dir; - uint16_t size = args.size; - const uint8_t* s = data; - const uint8_t* end = (data + size); - - DebugFormat(DEBUG_APPID, "%p Processing %u %hu->%hu %hu %d", - (void*)asd, (unsigned int)asd->protocol, pkt->ptrs.sp, pkt->ptrs.dp, size, dir); - - if (dir != APP_ID_FROM_RESPONDER) + KerberosDetectorData* fd; + const uint8_t* s = args.data; + const uint8_t* end = (args.data + args.size); + + if (args.dir != APP_ID_FROM_RESPONDER) goto inprocess; #ifdef APP_ID_USES_REASSEMBLED Stream::flush_response_flush(pkt); #endif - if (!size) + if (!args.size) goto inprocess; // server side is seeing packets so no need for client side to process them - asd->clear_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); - - fd = (DetectorData*)data_get(asd); - if (!fd) - { - fd = (DetectorData*)snort_calloc(sizeof(DetectorData)); - data_add(asd, fd, &snort_free); - if (asd->protocol == IpProtocol::TCP) - { - fd->clnt_state.state = KRB_STATE_TCP_LENGTH; - fd->svr_state.state = KRB_STATE_TCP_LENGTH; - } - else - { - fd->clnt_state.state = KRB_STATE_APP; - fd->svr_state.state = KRB_STATE_APP; - } - } + args.asd->clear_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); + fd = krb_client_detector->get_common_data(args.asd, false); if (fd->need_continue) - asd->set_session_flags(APPID_SESSION_CONTINUE); + args.asd->set_session_flags(APPID_SESSION_CONTINUE); else { - asd->clear_session_flags(APPID_SESSION_CONTINUE); - if (asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + args.asd->clear_session_flags(APPID_SESSION_CONTINUE); + if (args.asd->is_service_detected()) return APPID_SUCCESS; } - if (krb_walk_server_packet(&fd->svr_state, s, end, asd, pkt, dir, fd->clnt_state.cname) == + if (krb_walk_server_packet(&fd->svr_state, s, end, args.asd, args.pkt, args.dir, fd->clnt_state.cname) == KRB_FAILED) { - DebugFormat(DEBUG_APPID,"%p Failed\n", (void*)asd); - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + DebugFormat(DEBUG_APPID,"%p Failed\n", (void*)args.asd); + if (!args.asd->is_service_detected()) { - fail_service(asd, pkt, dir); + fail_service(args.asd, args.pkt, args.dir); return APPID_NOMATCH; } - asd->clear_session_flags(APPID_SESSION_CONTINUE); + args.asd->clear_session_flags(APPID_SESSION_CONTINUE); return APPID_SUCCESS; } inprocess: - service_inprocess(asd, pkt, dir); + service_inprocess(args.asd, args.pkt, args.dir); return APPID_INPROCESS; } @@ -593,9 +568,8 @@ KerberosClientDetector::~KerberosClientDetector() { } -int KerberosClientDetector::krb_walk_client_packet(KRBState* krbs, const uint8_t* s, const - uint8_t* end, - AppIdSession* asd) +int KerberosClientDetector::krb_walk_client_packet(KRBState* krbs, const uint8_t* s, + const uint8_t* end, AppIdSession* asd) { static const uint8_t KRB_CLIENT_VERSION[] = "\x0a1\x003\x002\x001"; static const uint8_t KRB_CLIENT_TYPE[] = "\x0a2\x003\x002\x001"; @@ -909,11 +883,39 @@ int KerberosClientDetector::krb_walk_client_packet(KRBState* krbs, const uint8_t return KRB_INPROCESS; } +KerberosDetectorData* KerberosClientDetector::get_common_data(AppIdSession* asd, bool client) +{ + KerberosDetectorData* dd = (KerberosDetectorData*)data_get(asd); + if (!dd) + { + dd = (KerberosDetectorData*)snort_calloc(sizeof(KerberosDetectorData)); + data_add(asd, dd, &snort_free); + if (asd->protocol == IpProtocol::TCP) + { + dd->clnt_state.state = KRB_STATE_TCP_LENGTH; + dd->svr_state.state = KRB_STATE_TCP_LENGTH; + } + else + { + dd->clnt_state.state = KRB_STATE_APP; + dd->svr_state.state = KRB_STATE_APP; + } + + dd->need_continue = 1; + asd->set_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); + + // FIXIT-M - why is this state increment here? + if( client ) + appid_stats.kerberos_flows++; + } + + return dd; +} + int KerberosClientDetector::validate(AppIdDiscoveryArgs& args) { const uint8_t* s = args.data; const uint8_t* end = (args.data + args.size); - DetectorData* fd; #ifdef APP_ID_USES_REASSEMBLED Stream::flush_response_flush(pkt); @@ -924,37 +926,14 @@ int KerberosClientDetector::validate(AppIdDiscoveryArgs& args) if (!args.size) return APPID_INPROCESS; - fd = (DetectorData*)data_get(args.asd); - if (!fd) - { - fd = (DetectorData*)snort_calloc(sizeof(DetectorData)); - data_add(args.asd, fd, &snort_free); - if (args.asd->protocol == IpProtocol::TCP) - { - fd->clnt_state.state = KRB_STATE_TCP_LENGTH; - fd->svr_state.state = KRB_STATE_TCP_LENGTH; - } - else - { - fd->clnt_state.state = KRB_STATE_APP; - fd->svr_state.state = KRB_STATE_APP; - } - appid_stats.kerberos_flows++; - } - - if (!fd->set_flags) - { - fd->need_continue = 1; - fd->set_flags = 1; - args.asd->set_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); - } + KerberosDetectorData* fd = get_common_data(args.asd, true); if (args.dir == APP_ID_FROM_INITIATOR) { if (krb_walk_client_packet(&fd->clnt_state, s, end, args.asd) == KRB_FAILED) { DebugFormat(DEBUG_APPID,"%p Failed\n", (void*)args.asd); - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); args.asd->clear_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); return APPID_SUCCESS; } diff --git a/src/network_inspectors/appid/detector_plugins/detector_kerberos.h b/src/network_inspectors/appid/detector_plugins/detector_kerberos.h index 05f280697..5a5b2656e 100644 --- a/src/network_inspectors/appid/detector_plugins/detector_kerberos.h +++ b/src/network_inspectors/appid/detector_plugins/detector_kerberos.h @@ -26,6 +26,7 @@ #include "service_plugins/service_detector.h" struct KRBState; +struct KerberosDetectorData; class KerberosClientDetector : public ClientDetector { @@ -34,6 +35,7 @@ public: ~KerberosClientDetector(); int validate(AppIdDiscoveryArgs&) override; + KerberosDetectorData* get_common_data(AppIdSession*, bool client); bool failed_login = false; diff --git a/src/network_inspectors/appid/detector_plugins/detector_pattern.cc b/src/network_inspectors/appid/detector_plugins/detector_pattern.cc index 85dec27a7..180086e0c 100644 --- a/src/network_inspectors/appid/detector_plugins/detector_pattern.cc +++ b/src/network_inspectors/appid/detector_plugins/detector_pattern.cc @@ -34,8 +34,6 @@ static THREAD_LOCAL PatternServiceDetector* service_pattern_detector; static THREAD_LOCAL PatternClientDetector* client_pattern_detector; -static int csdPatternTreeSearch(const uint8_t* data, uint16_t size, SearchTool* patternTree); - static void dumpPatterns(const char* name, PatternService* pList) { UNUSED(name); @@ -49,17 +47,7 @@ static void dumpPatterns(const char* name, PatternService* pList) } } -static void FreePattern(Pattern* pattern) -{ - if (pattern) - { - if (pattern->data) - snort_free(pattern->data); - snort_free(pattern); - } -} - -static void FreePatternService(PatternService* ps) +static void free_pattern_service(PatternService* ps) { if (ps) { @@ -69,7 +57,9 @@ static void FreePatternService(PatternService* ps) while ((pattern = ps->pattern)) { ps->pattern = pattern->next; - FreePattern(pattern); + if (pattern->data) + snort_free(pattern->data); + snort_free(pattern); } while ((port = ps->port)) @@ -128,7 +118,7 @@ static void read_patterns(PortPatternNode* portPatternList, PatternService** ser } } -static void RegisterPattern(SearchTool** patterns, Pattern* pattern) +static void register_pattern(SearchTool** patterns, Pattern* pattern) { if (!*patterns) { @@ -209,7 +199,7 @@ static int pattern_match(void* id, void*, int match_end_pos, void* data, void*) return 0; } -static int csdPatternTreeSearch(const uint8_t* data, uint16_t size, SearchTool* patternTree) +static int csd_pattern_tree_search(const uint8_t* data, uint16_t size, SearchTool* patternTree) { PServiceMatch* matches = nullptr; @@ -280,16 +270,16 @@ static int csdPatternTreeSearch(const uint8_t* data, uint16_t size, SearchTool* } // Creates unique subset of services registered on ports, and then creates pattern trees. -void PatternServiceDetector::createServicePatternTrees() +void PatternServiceDetector::create_service_pattern_trees() { for (PatternService* ps = servicePortPattern; ps; ps = ps->next) for (PortNode* port = ps->port; port; port = port->next) for (Pattern* pattern = ps->pattern; pattern; pattern = pattern->next) if (ps->proto == IpProtocol::TCP) - RegisterPattern(&tcpPortPatternTree[port->port], + register_pattern(&tcpPortPatternTree[port->port], pattern); else - RegisterPattern(&udpPortPatternTree[port->port], + register_pattern(&udpPortPatternTree[port->port], pattern); for (unsigned i = 0; i < 65536; i++) @@ -302,7 +292,7 @@ void PatternServiceDetector::createServicePatternTrees() continue; for (Pattern* pattern = ps->pattern; pattern; pattern = pattern->next) - RegisterPattern(&tcpPortPatternTree[i], pattern); + register_pattern(&tcpPortPatternTree[i], pattern); } tcpPortPatternTree[i]->prep(); @@ -316,7 +306,7 @@ void PatternServiceDetector::createServicePatternTrees() continue; for (Pattern* pattern = ps->pattern; pattern; pattern = pattern->next) - RegisterPattern(&udpPortPatternTree[i], pattern); + register_pattern(&udpPortPatternTree[i], pattern); } udpPortPatternTree[i]->prep(); @@ -324,7 +314,7 @@ void PatternServiceDetector::createServicePatternTrees() } } -void PatternServiceDetector::registerServicePatterns() +void PatternServiceDetector::register_service_patterns() { /**Register patterns with no associated ports, to RNA and local * pattern tree. Register patterns with ports with local pattern @@ -343,14 +333,14 @@ void PatternServiceDetector::registerServicePatterns() DebugFormat(DEBUG_LOG,"Adding pattern with length %u\n",pattern->length); handler->register_tcp_pattern(this, pattern->data, pattern->length, pattern->offset, 0); - RegisterPattern(&tcp_patterns, pattern); + register_pattern(&tcp_patterns, pattern); } else { DebugFormat(DEBUG_LOG,"Adding pattern with length %u\n",pattern->length); handler->register_udp_pattern(this, pattern->data, pattern->length, pattern->offset, 0); - RegisterPattern(&udp_patterns, pattern); + register_pattern(&udp_patterns, pattern); } } } @@ -419,8 +409,8 @@ void PatternServiceDetector::finalize_service_port_patterns() read_patterns(service_pattern_detector->luaInjectedPatterns, &service_pattern_detector->servicePortPattern); service_pattern_detector->install_ports(service_pattern_detector->servicePortPattern); - service_pattern_detector->createServicePatternTrees(); - service_pattern_detector->registerServicePatterns(); + service_pattern_detector->create_service_pattern_trees(); + service_pattern_detector->register_service_patterns(); dumpPatterns("Server", service_pattern_detector->servicePortPattern); } @@ -437,45 +427,29 @@ PatternServiceDetector::PatternServiceDetector(ServiceDiscovery* sd) PatternServiceDetector::~PatternServiceDetector() { - PatternService* ps; - if ( servicePortPattern ) { - unsigned i; + delete tcp_patterns; + delete udp_patterns; - if (tcp_patterns) - { - delete tcp_patterns; - tcp_patterns = nullptr; - } - if (udp_patterns) - { - delete udp_patterns; - udp_patterns = nullptr; - } - for (i = 0; i < 65536; i++) + for (unsigned i = 0; i < 65536; i++) { if (tcpPortPatternTree[i]) - { delete tcpPortPatternTree[i]; - tcpPortPatternTree[i] = nullptr; - } if (udpPortPatternTree[i]) - { delete udpPortPatternTree[i]; - udpPortPatternTree[i] = nullptr; - } } + + PatternService* ps; while (servicePortPattern) { ps = servicePortPattern; servicePortPattern = ps->next; - FreePatternService(ps); + free_pattern_service(ps); } } PortPatternNode* tmp; - while ((tmp = luaInjectedPatterns)) { luaInjectedPatterns = tmp->next; @@ -510,7 +484,7 @@ int PatternServiceDetector::validate(AppIdDiscoveryArgs& args) patternTree = tcp_patterns; } - uint32_t id = csdPatternTreeSearch(args.data, args.size, patternTree); + uint32_t id = csd_pattern_tree_search(args.data, args.size, patternTree); if (!id) { fail_service(args.asd, args.pkt, args.dir); @@ -533,17 +507,6 @@ PatternClientDetector::PatternClientDetector(ClientDiscovery* cdm) PatternClientDetector::~PatternClientDetector() { - PortPatternNode* tmp; - - while ((tmp = luaInjectedPatterns)) - { - luaInjectedPatterns = tmp->next; - snort_free(tmp->pattern); - snort_free(tmp->detectorName); - snort_free(tmp); - } - - // FIXIT-H - need to clean servicePortPattern?? if (servicePortPattern) { if (tcp_patterns) @@ -557,6 +520,22 @@ PatternClientDetector::~PatternClientDetector() delete udp_patterns; udp_patterns = nullptr; } + + PatternService* ps; + while (servicePortPattern) + { + ps = servicePortPattern; + servicePortPattern = ps->next; + free_pattern_service(ps); + } + } + PortPatternNode* tmp; + while ((tmp = luaInjectedPatterns)) + { + luaInjectedPatterns = tmp->next; + snort_free(tmp->pattern); + snort_free(tmp->detectorName); + snort_free(tmp); } } @@ -567,7 +546,7 @@ int PatternClientDetector::validate(AppIdDiscoveryArgs& args) SearchTool* patternTree = (args.asd->protocol == IpProtocol::UDP) ? udp_patterns : tcp_patterns; - AppId id = csdPatternTreeSearch(args.data, args.size, patternTree); + AppId id = csd_pattern_tree_search(args.data, args.size, patternTree); if (!id) return APPID_EINVALID; @@ -575,21 +554,21 @@ int PatternClientDetector::validate(AppIdDiscoveryArgs& args) return APPID_SUCCESS; } -void PatternClientDetector::createClientPatternTrees() +void PatternClientDetector::create_client_pattern_trees() { for (PatternService* ps = servicePortPattern; ps; ps = ps->next) { for ( Pattern* pattern = ps->pattern; pattern; pattern = pattern->next) { if (ps->proto == IpProtocol::TCP) - RegisterPattern(&tcp_patterns, pattern); + register_pattern(&tcp_patterns, pattern); else - RegisterPattern(&udp_patterns, pattern); + register_pattern(&udp_patterns, pattern); } } } -void PatternClientDetector::insert_client_port_pattern(PortPatternNode* pPattern) +void PatternClientDetector::insert_client_port_pattern(PortPatternNode* port_pattern) { //insert ports in order. PortPatternNode** prev = nullptr; @@ -597,27 +576,27 @@ void PatternClientDetector::insert_client_port_pattern(PortPatternNode* pPattern for (curr = &client_pattern_detector->luaInjectedPatterns; *curr; prev = curr, curr = &((*curr)->next)) { - if (strcmp(pPattern->detectorName, (*curr)->detectorName) || pPattern->protocol < - (*curr)->protocol - || pPattern->port < (*curr)->port) + if (strcmp(port_pattern->detectorName, (*curr)->detectorName) + || port_pattern->protocol < (*curr)->protocol + || port_pattern->port < (*curr)->port) break; } if (prev) { - pPattern->next = (*prev)->next; - (*prev)->next = pPattern; + port_pattern->next = (*prev)->next; + (*prev)->next = port_pattern; } else { - pPattern->next = *curr; - *curr = pPattern; + port_pattern->next = *curr; + *curr = port_pattern; } } // Register patterns with no associated ports, to RNA and local pattern tree. Register // patterns with ports with local pattern tree only. -void PatternClientDetector::registerClientPatterns() +void PatternClientDetector::register_client_patterns() { for (PatternService* ps = servicePortPattern; ps; ps = ps->next) for (Pattern* pattern = ps->pattern; pattern; pattern = pattern->next) @@ -629,14 +608,14 @@ void PatternClientDetector::registerClientPatterns() DebugFormat(DEBUG_LOG,"Adding pattern with length %u\n",pattern->length); handler->register_tcp_pattern(this, pattern->data, pattern->length, pattern->offset, 0); - RegisterPattern(&tcp_patterns, pattern); + register_pattern(&tcp_patterns, pattern); } else { DebugFormat(DEBUG_LOG,"Adding pattern with length %u\n",pattern->length); handler->register_udp_pattern(this, pattern->data, pattern->length, pattern->offset, 0); - RegisterPattern(&udp_patterns, pattern); + register_pattern(&udp_patterns, pattern); } } ps->count++; @@ -653,8 +632,8 @@ void PatternClientDetector::finalize_client_port_patterns() { read_patterns(client_pattern_detector->luaInjectedPatterns, &client_pattern_detector->servicePortPattern); - client_pattern_detector->createClientPatternTrees(); - client_pattern_detector->registerClientPatterns(); + client_pattern_detector->create_client_pattern_trees(); + client_pattern_detector->register_client_patterns(); dumpPatterns("Client", client_pattern_detector->servicePortPattern); } diff --git a/src/network_inspectors/appid/detector_plugins/detector_pattern.h b/src/network_inspectors/appid/detector_plugins/detector_pattern.h index a325cec45..6a1eb7045 100644 --- a/src/network_inspectors/appid/detector_plugins/detector_pattern.h +++ b/src/network_inspectors/appid/detector_plugins/detector_pattern.h @@ -82,8 +82,8 @@ public: int validate(AppIdDiscoveryArgs&) override; private: - void createClientPatternTrees(); - void registerClientPatterns(); + void create_client_pattern_trees(); + void register_client_patterns(); PortPatternNode* luaInjectedPatterns = nullptr; PatternService* servicePortPattern = nullptr; @@ -103,8 +103,8 @@ public: int validate(AppIdDiscoveryArgs&) override; private: - void createServicePatternTrees(); - void registerServicePatterns(); + void create_service_pattern_trees(); + void register_service_patterns(); void install_ports(PatternService*); PortPatternNode* luaInjectedPatterns = nullptr; diff --git a/src/network_inspectors/appid/detector_plugins/detector_pop3.cc b/src/network_inspectors/appid/detector_plugins/detector_pop3.cc index ae0262e91..39f5619e6 100644 --- a/src/network_inspectors/appid/detector_plugins/detector_pop3.cc +++ b/src/network_inspectors/appid/detector_plugins/detector_pop3.cc @@ -27,9 +27,6 @@ #include "appid_module.h" #include "app_info_table.h" -#include "service_plugins/service_util.h" - -/*#define DEBUG_POP3 1 */ enum POP3ClientState { @@ -43,7 +40,6 @@ struct ClientPOP3Data int auth; char* username; POP3ClientState state; - int set_flags; int detected; int got_user; }; @@ -115,7 +111,7 @@ struct ServicePOP3Data unsigned count; const char* vendor; char version[MAX_VERSION_SIZE]; - RNAServiceSubtype* subtype; + AppIdServiceSubtype* subtype; int error; }; @@ -174,6 +170,16 @@ static std::array eoc = false, false, true, true, true, true } }; +static const char ven_cppop[] = "cppop"; +static const char ven_cc[] = "Cubic Circle"; +static const char ven_im[] = "InterMail"; +static const char ver_cc[] = "'s v"; +static const char ven_po[] = "Post.Office"; +static const char ver_po[] = " v"; +static const char ver_po2[] = " release "; +static const char sub_po[] = " with "; +static const char subver_po[] = " version "; + Pop3ClientDetector::Pop3ClientDetector(ClientDiscovery* cdm) { handler = cdm; @@ -202,13 +208,13 @@ Pop3ClientDetector::~Pop3ClientDetector() void Pop3ClientDetector::do_custom_init() { - unsigned cooked_idx = 1; + unsigned index = 0; cmd_matcher = new SearchTool("ac_full"); if ( tcp_patterns.size() ) for (auto& pat : tcp_patterns) { - cmd_matcher->add(pat.pattern, pat.length, cooked_idx++); + cmd_matcher->add(pat.pattern, pat.length, index++); if (pat.length > longest_pattern) longest_pattern = pat.length; } @@ -218,7 +224,7 @@ void Pop3ClientDetector::do_custom_init() static int pop3_pattern_match(void* id, void*, int match_end_pos, void* data, void*) { unsigned long idx = (unsigned long)id; - if ( (int)pop3_client_patterns[ idx - 1].length != match_end_pos ) + if ( (int)pop3_client_patterns[idx].length != match_end_pos ) return 0; unsigned long* pat_idx = (unsigned long*)data; @@ -229,16 +235,12 @@ static int pop3_pattern_match(void* id, void*, int match_end_pos, void* data, vo static void pop3_free_state(void* data) { POP3DetectorData* dd = (POP3DetectorData*)data; - ClientPOP3Data* cd; - ServicePOP3Data* sd; - RNAServiceSubtype* sub; - if (dd) { - sd = &dd->server; + ServicePOP3Data* sd = &dd->server; while (sd->subtype) { - sub = sd->subtype; + AppIdServiceSubtype* sub = sd->subtype; sd->subtype = sub->next; if (sub->service) snort_free((void*)sub->service); @@ -246,7 +248,7 @@ static void pop3_free_state(void* data) snort_free((void*)sub->version); snort_free(sub); } - cd = &dd->client; + ClientPOP3Data* cd = &dd->client; if (cd->username) snort_free(cd->username); snort_free(dd); @@ -277,31 +279,11 @@ static int pop3_check_line(const uint8_t** data, const uint8_t* end) static int pop3_server_validate(POP3DetectorData* dd, const uint8_t* data, uint16_t size, AppIdSession* asd, int server) { - static const char ven_cppop[] = "cppop"; - static const char ven_cc[] = "Cubic Circle"; - static const char ven_im[] = "InterMail"; - static const char ver_cc[] = "'s v"; - static const char ven_po[] = "Post.Office"; - static const char ver_po[] = " v"; - static const char ver_po2[] = " release "; - static const char sub_po[] = " with "; - static const char subver_po[] = " version "; ServicePOP3Data* pd = &dd->server; const uint8_t* begin = nullptr; - const uint8_t* end; - const uint8_t* line_end; - const uint8_t* p; - const uint8_t* p2; - const uint8_t* ver; - const uint8_t* rel; - const uint8_t* s; - unsigned len; - char* v; - char* v_end; - - end = data + size; - v_end = pd->version; - v_end += MAX_VERSION_SIZE - 1; + + const uint8_t* end = data + size; + char* v_end = pd->version + MAX_VERSION_SIZE - 1; switch (pd->state) { case POP3_STATE_CONNECT: @@ -345,39 +327,39 @@ static int pop3_server_validate(POP3DetectorData* dd, const uint8_t* data, uint1 else { // we are potentially overriding the APP_ID_POP3 assessment that was made earlier. - // sets APPID_SESSION_CLIENT_DETECTED asd->set_session_flags(APPID_SESSION_ENCRYPTED); asd->clear_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); pop3_client_detector->add_app(asd, APP_ID_POP3S, APP_ID_POP3S, nullptr); appid_stats.pop3s_clients++; } } - else if (dd->client.username) // possible only with non-TLS authentication therefore - // APP_ID_POP3 + else if (dd->client.username) // possible only with non-TLS auth, therefore APP_ID_POP3 { if (pd->error) { - pop3_service_detector->add_user(asd, dd->client.username, APP_ID_POP3, 0); + pop3_service_detector->add_user(asd, dd->client.username, APP_ID_POP3, false); snort_free(dd->client.username); dd->client.username = nullptr; } else { - pop3_service_detector->add_user(asd, dd->client.username, APP_ID_POP3, 1); + pop3_service_detector->add_user(asd, dd->client.username, APP_ID_POP3, true); snort_free(dd->client.username); dd->client.username = nullptr; dd->need_continue = 0; asd->clear_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); dd->client.got_user = 1; if (dd->client.detected) - asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + asd->set_client_detected(); } } if (server && begin) { - line_end = &data[-1]; - len = line_end - begin; - if ((p=service_strstr(begin, len, (unsigned char*)ven_cppop, sizeof(ven_cppop)-1))) + const uint8_t* p; + char* v; + const uint8_t* line_end = &data[-1]; + unsigned len = line_end - begin; + if (( p = service_strstr(begin, len, (unsigned char*)ven_cppop, sizeof(ven_cppop)-1)) ) { pd->vendor = ven_cppop; p += (sizeof(ven_cppop) - 1); @@ -426,14 +408,14 @@ static int pop3_server_validate(POP3DetectorData* dd, const uint8_t* data, uint1 pd->vendor = ven_im; else if ((p=service_strstr(begin, len, (unsigned char*)ven_po, sizeof(ven_po)-1))) { - RNAServiceSubtype* sub; + AppIdServiceSubtype* sub; pd->vendor = ven_po; p += (sizeof(ven_po) - 1); if (line_end-p < (int)sizeof(ver_po)-1 || memcmp(p, ver_po, sizeof(ver_po)-1) != 0) goto ven_ver_done; p += sizeof(ver_po) - 1; - ver = p; + const uint8_t* ver = p; for (; p < line_end && *p && *p != ' '; p++) ; if (p == ver || p >= line_end || !(*p)) @@ -457,8 +439,8 @@ static int pop3_server_validate(POP3DetectorData* dd, const uint8_t* data, uint1 goto ven_ver_done; } /* Move past release and look for number followed by a space */ - p2 = p + sizeof(ver_po2) - 1; - rel = p2; + const uint8_t* p2 = p + sizeof(ver_po2) - 1; + const uint8_t* rel = p2; for (; p2 < line_end && *p2 && *p2 != ' '; p2++) ; if (p2 >= line_end || p2 == rel || !(*p2)) @@ -492,12 +474,12 @@ static int pop3_server_validate(POP3DetectorData* dd, const uint8_t* data, uint1 if (line_end-p2 < (int)sizeof(sub_po)-1 || memcmp(p2, sub_po, sizeof(sub_po)-1) != 0) goto ven_ver_done; - s = p2 + (sizeof(sub_po) - 1); + const uint8_t* s = p2 + (sizeof(sub_po) - 1); for (p=s; p < line_end && *p && *p != ' '; p++) ; if (p == s || p >= line_end || !(*p)) goto ven_ver_done; - sub = (RNAServiceSubtype*)snort_calloc(sizeof(RNAServiceSubtype)); + sub = (AppIdServiceSubtype*)snort_calloc(sizeof(AppIdServiceSubtype)); unsigned sub_len; sub_len = p - s; @@ -549,13 +531,27 @@ ven_ver_done:; return 0; } +POP3DetectorData* Pop3ClientDetector::get_common_data(AppIdSession* asd) +{ + POP3DetectorData* dd = (POP3DetectorData*)data_get(asd); + if (!dd) + { + dd = (POP3DetectorData*)snort_calloc(sizeof(POP3DetectorData)); + data_add(asd, dd, &pop3_free_state); + dd->server.state = POP3_STATE_CONNECT; + dd->client.state = POP3_CLIENT_STATE_AUTH; + dd->need_continue = 1; + asd->set_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); + } + + return dd; +} + int Pop3ClientDetector::validate(AppIdDiscoveryArgs& args) { const uint8_t* s = args.data; const uint8_t* end = (args.data + args.size); unsigned length; - POP3DetectorData* dd; - ClientPOP3Data* fd; if (!args.size) return APPID_INPROCESS; @@ -564,57 +560,31 @@ int Pop3ClientDetector::validate(AppIdDiscoveryArgs& args) Stream::flush_response_flush(pkt); #endif - dd = (POP3DetectorData*)data_get(args.asd); - if (!dd) - { - dd = (POP3DetectorData*)snort_calloc(sizeof(POP3DetectorData)); - data_add(args.asd, dd, &pop3_free_state); - dd->server.state = POP3_STATE_CONNECT; - fd = &dd->client; - fd->state = POP3_CLIENT_STATE_AUTH; - } - else - fd = &dd->client; - - if (!fd->set_flags) - { - dd->need_continue = 1; - fd->set_flags = 1; - args.asd->set_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); - } + POP3DetectorData* dd = get_common_data(args.asd); + ClientPOP3Data* fd = &dd->client; if (args.dir == APP_ID_FROM_RESPONDER) { -#ifdef DEBUG_POP3 - DebugFormat(DEBUG_APPID,"%p Calling server\n",asd); - AppIdUtils::DumpHex(SF_DEBUG_FILE, data, size); -#endif - if (pop3_server_validate(dd, args.data, args.size, args.asd, 0)) args.asd->clear_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); return APPID_INPROCESS; } -#ifdef DEBUG_POP3 - DebugFormat(DEBUG_APPID,"%p Client\n",asd); - AppIdUtils::DumpHex(SF_DEBUG_FILE, data, size); -#endif - while ((length = (end - s))) { unsigned long pattern_index; AppIdFlowContentPattern* cmd = nullptr; - pattern_index = 0; + pattern_index = num_pop3_client_patterns; cmd_matcher->find_all((char*)s, (length > longest_pattern ? longest_pattern : length), &pop3_pattern_match, false, (void*)&pattern_index); - if (pattern_index > 0) - cmd = &tcp_patterns[ pattern_index - 1]; + if (pattern_index < num_pop3_client_patterns) + cmd = &tcp_patterns[pattern_index]; if (!cmd) { dd->need_continue = 0; - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); return APPID_SUCCESS; } s += cmd->length; @@ -730,7 +700,6 @@ int Pop3ClientDetector::validate(AppIdDiscoveryArgs& args) if (pattern_index >= PATTERN_POP3_OTHER) { // Still in non-secure mode and received a TRANSACTION-state command: POP3 found - // sets APPID_SESSION_CLIENT_DETECTED add_app(args.asd, APP_ID_POP3, APP_ID_POP3, nullptr); appid_stats.pop3_clients++; fd->detected = 1; @@ -787,60 +756,41 @@ int Pop3ServiceDetector::validate(AppIdDiscoveryArgs& args) { POP3DetectorData* dd; ServicePOP3Data* pd; - AppIdSession* asd = args.asd; - const uint8_t* data = args.data; - Packet* pkt = args.pkt; - const int dir = args.dir; - uint16_t size = args.size; - if (!size) + if (!args.size) goto inprocess; #ifdef APP_ID_USES_REASSEMBLED Stream::flush_response_flush(pkt); #endif - if (dir != APP_ID_FROM_RESPONDER) + if (args.dir != APP_ID_FROM_RESPONDER) goto inprocess; -#ifdef DEBUG_POP3 - DebugFormat(DEBUG_APPID,"%p Dir %d\n",asd, dir); - AppIdUtils::DumpHex(SF_DEBUG_FILE, data, size); -#endif - - dd = (POP3DetectorData*)data_get(asd); - if (!dd) - { - dd = (POP3DetectorData*)snort_calloc(sizeof(POP3DetectorData)); - data_add(asd, dd, &pop3_free_state); - dd->client.state = POP3_CLIENT_STATE_AUTH; - pd = &dd->server; - pd->state = POP3_STATE_CONNECT; - } - else - pd = &dd->server; + dd = pop3_client_detector->get_common_data(args.asd); + pd = &dd->server; // server side is seeing packets so no need for client side to process them - asd->clear_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); + args.asd->clear_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); if (dd->need_continue) - asd->set_session_flags(APPID_SESSION_CONTINUE); + args.asd->set_session_flags(APPID_SESSION_CONTINUE); else { - asd->clear_session_flags(APPID_SESSION_CONTINUE); - if (asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + args.asd->clear_session_flags(APPID_SESSION_CONTINUE); + if (args.asd->is_service_detected()) { appid_stats.pop_flows++; return APPID_SUCCESS; } } - if (!pop3_server_validate(dd, data, size, asd, 1)) + if (!pop3_server_validate(dd, args.data, args.size, args.asd, 1)) { if (pd->count >= POP3_COUNT_THRESHOLD - && !asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + && !args.asd->is_service_detected()) { - add_service_consume_subtype(asd, pkt, dir, + add_service_consume_subtype(args.asd, args.pkt, args.dir, dd->client.state == POP3_CLIENT_STATE_STLS_CMD ? APP_ID_POP3S : APP_ID_POP3, pd->vendor, pd->version[0] ? pd->version : nullptr, pd->subtype); pd->subtype = nullptr; @@ -848,20 +798,20 @@ int Pop3ServiceDetector::validate(AppIdDiscoveryArgs& args) return APPID_SUCCESS; } } - else if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + else if (!args.asd->is_service_detected()) { - fail_service(asd, pkt, dir); + fail_service(args.asd, args.pkt, args.dir); return APPID_NOMATCH; } else { - asd->clear_session_flags(APPID_SESSION_CONTINUE); + args.asd->clear_session_flags(APPID_SESSION_CONTINUE); appid_stats.pop_flows++; return APPID_SUCCESS; } inprocess: - service_inprocess(asd, pkt, dir); + service_inprocess(args.asd, args.pkt, args.dir); return APPID_INPROCESS; } diff --git a/src/network_inspectors/appid/detector_plugins/detector_pop3.h b/src/network_inspectors/appid/detector_plugins/detector_pop3.h index e1fc04f51..1b99ed013 100644 --- a/src/network_inspectors/appid/detector_plugins/detector_pop3.h +++ b/src/network_inspectors/appid/detector_plugins/detector_pop3.h @@ -25,6 +25,8 @@ #include "client_plugins/client_detector.h" #include "service_plugins/service_detector.h" +struct POP3DetectorData; + class Pop3ClientDetector : public ClientDetector { public: @@ -33,6 +35,7 @@ public: void do_custom_init() override; int validate(AppIdDiscoveryArgs&) override; + POP3DetectorData* get_common_data(AppIdSession*); private: SearchTool* cmd_matcher = nullptr; diff --git a/src/network_inspectors/appid/detector_plugins/detector_sip.cc b/src/network_inspectors/appid/detector_plugins/detector_sip.cc index 47614916c..0c332984e 100644 --- a/src/network_inspectors/appid/detector_plugins/detector_sip.cc +++ b/src/network_inspectors/appid/detector_plugins/detector_sip.cc @@ -345,7 +345,7 @@ void SipServiceDetector::createRtpFlow(AppIdSession* asd, const Packet* pkt, con { fp->client_app_id = asd->client_app_id; fp->payload_app_id = asd->payload_app_id; - fp->serviceAppId = APP_ID_RTP; + fp->service_app_id = APP_ID_RTP; initialize_expected_session(asd, fp, APPID_SESSION_IGNORE_ID_FLAGS); } @@ -357,7 +357,7 @@ void SipServiceDetector::createRtpFlow(AppIdSession* asd, const Packet* pkt, con { fp2->client_app_id = asd->client_app_id; fp2->payload_app_id = asd->payload_app_id; - fp2->serviceAppId = APP_ID_RTCP; + fp2->service_app_id = APP_ID_RTCP; initialize_expected_session(asd, fp2, APPID_SESSION_IGNORE_ID_FLAGS); } } @@ -456,7 +456,7 @@ int SipServiceDetector::validate(AppIdDiscoveryArgs& args) if (ss->serverPkt > 10) { - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { fail_service(asd, args.pkt, args.dir); } @@ -464,7 +464,7 @@ int SipServiceDetector::validate(AppIdDiscoveryArgs& args) return APPID_NOMATCH; } - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) service_inprocess(asd, args.pkt, args.dir); return APPID_INPROCESS; @@ -557,9 +557,9 @@ success: appid_stats.sip_clients++; if ( fd->user_name.size() ) - client->add_user(asd, fd->user_name.c_str(), APP_ID_SIP, 1); + client->add_user(asd, fd->user_name.c_str(), APP_ID_SIP, true); - asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + asd->set_client_detected(); } void SipEventHandler::service_handler(SipEvent& sip_event, AppIdSession* asd) @@ -599,7 +599,7 @@ void SipEventHandler::service_handler(SipEvent& sip_event, AppIdSession* asd) if ( sip_event.is_dialog_established() ) { - if ( !asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED) ) + if ( !asd->is_service_detected() ) { asd->set_session_flags(APPID_SESSION_CONTINUE); service->add_service(asd, sip_event.get_packet(), direction, APP_ID_SIP, diff --git a/src/network_inspectors/appid/detector_plugins/detector_smtp.cc b/src/network_inspectors/appid/detector_plugins/detector_smtp.cc index 668f83077..2af382be9 100644 --- a/src/network_inspectors/appid/detector_plugins/detector_smtp.cc +++ b/src/network_inspectors/appid/detector_plugins/detector_smtp.cc @@ -23,11 +23,10 @@ #include "detector_smtp.h" -#include "protocols/packet.h" #include "appid_module.h" #include "application_ids.h" #include "app_info_table.h" -#include "service_plugins/service_util.h" +#include "protocols/packet.h" enum SMTPClientState { @@ -87,7 +86,6 @@ struct ServiceSMTPData SMTPServiceState state; int code; int multiline; - int set_flags; bool detected; }; @@ -207,11 +205,10 @@ int SmtpClientDetector::extract_version_and_add_client_app(ApplicationId clientI const uint8_t* p = product + prefix_len - 1; if (p >= product_end || isspace(*p)) return 1; - - for (uint8_t* v = client_data->version; v < v_end && p < product_end; v++,p++) - { + uint8_t* v; + for (v = client_data->version; v < v_end && p < product_end; v++,p++) *v = *p; - } + *v = 0; add_app(asd, appId, clientId, (char*)client_data->version); (*stat_counter)++; return 0; @@ -286,10 +283,12 @@ int SmtpClientDetector::identify_client_version(ClientSMTPData* const fd, const if (p >= data_end || *(data_end - 1) != ')' || *p == ')' || isspace(*p)) return 1; - for (uint8_t* v = fd->version; v < v_end && p < data_end - 1; v++,p++) + uint8_t* v; + for (v = fd->version; v < v_end && p < data_end - 1; v++,p++) { *v = *p; } + *v = 0; add_app(asd, appId, APP_ID_APPLE_EMAIL, (char*)fd->version); appid_stats.smtp_applemail_clients++; @@ -379,30 +378,26 @@ static void smtp_free_state(void* data) } } -SMTPDetectorData* SmtpClientDetector::get_smtp_detector_data(AppIdSession* asd) +SMTPDetectorData* SmtpClientDetector::get_common_data(AppIdSession* asd) { SMTPDetectorData* dd = (SMTPDetectorData*)data_get(asd); - if (dd) - return dd; - - dd = (SMTPDetectorData*)snort_calloc(1, sizeof(*dd)); - if (data_add(asd, dd, &smtp_free_state)) + if (!dd) { - snort_free(dd); - return nullptr; + dd = (SMTPDetectorData*)snort_calloc(1, sizeof(*dd)); + data_add(asd, dd, &smtp_free_state); + dd->server.state = SMTP_SERVICE_STATE_CONNECTION; + dd->server.detected = false; + dd->client.state = SMTP_CLIENT_STATE_HELO; + dd->need_continue = 1; + asd->set_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); } - dd->server.state = SMTP_SERVICE_STATE_CONNECTION; - dd->server.detected = false; - dd->client.state = SMTP_CLIENT_STATE_HELO; - dd->need_continue = 1; - asd->set_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); return dd; } int SmtpClientDetector::validate(AppIdDiscoveryArgs& args) { - SMTPDetectorData* dd = get_smtp_detector_data(args.asd); + SMTPDetectorData* dd = get_common_data(args.asd); if ( !dd ) return APPID_ENOMEM; @@ -467,13 +462,13 @@ int SmtpClientDetector::validate(AppIdDiscoveryArgs& args) fd->nextstate = fd->state; fd->state = SMTP_CLIENT_STATE_SKIP_LINE; } - else if (len >= (sizeof(AUTH_PLAIN)-1) && strncasecmp((const char *)args.data, AUTH_PLAIN, sizeof(AUTH_PLAIN)-1) == 0) + else if (len >= (sizeof(AUTH_PLAIN)-1) && strncasecmp((const char*)args.data, AUTH_PLAIN, sizeof(AUTH_PLAIN)-1) == 0) { args.data += (sizeof(AUTH_PLAIN)-1)-1; fd->nextstate = fd->state; fd->state = SMTP_CLIENT_STATE_SKIP_LINE; } - else if (len >= (sizeof(AUTH_LOGIN)-1) && strncasecmp((const char *)args.data, AUTH_LOGIN, sizeof(AUTH_LOGIN)-1) == 0) + else if (len >= (sizeof(AUTH_LOGIN)-1) && strncasecmp((const char*)args.data, AUTH_LOGIN, sizeof(AUTH_LOGIN)-1) == 0) { args.data += (sizeof(AUTH_LOGIN)-1)-1; fd->nextstate = SMTP_CLIENT_STATE_LOGIN_USER; @@ -487,37 +482,39 @@ int SmtpClientDetector::validate(AppIdDiscoveryArgs& args) fd->state = SMTP_CLIENT_STATE_SKIP_LINE; } /* check for state reversion */ - else if (len >= (sizeof(HELO)-1) && strncasecmp((const char *)args.data, HELO, sizeof(HELO)-1) == 0) + else if (len >= (sizeof(HELO)-1) && strncasecmp((const char*)args.data, HELO, sizeof(HELO)-1) == 0) { args.data += (sizeof(HELO)-1)-1; fd->nextstate = fd->state; fd->state = SMTP_CLIENT_STATE_SKIP_LINE; - dd->server.state = SMTP_SERVICE_STATE_HELO; // make sure that service side expects the 250 + dd->server.state = SMTP_SERVICE_STATE_HELO; // make sure that service side expects + // the 250 } - else if (len >= (sizeof(EHLO)-1) && strncasecmp((const char *)args.data, EHLO, sizeof(EHLO)-1) == 0) + else if (len >= (sizeof(EHLO)-1) && strncasecmp((const char*)args.data, EHLO, sizeof(EHLO)-1) == 0) { args.data += (sizeof(EHLO)-1)-1; fd->nextstate = fd->state; fd->state = SMTP_CLIENT_STATE_SKIP_LINE; - dd->server.state = SMTP_SERVICE_STATE_HELO; // make sure that service side expects the 250 + dd->server.state = SMTP_SERVICE_STATE_HELO; // make sure that service side expects + // the 250 } else goto done; break; case SMTP_CLIENT_STATE_LOGIN_USER: - { - fd->nextstate = SMTP_CLIENT_STATE_LOGIN_PASSWORD; - fd->state = SMTP_CLIENT_STATE_SKIP_LINE; - } - break; + { + fd->nextstate = SMTP_CLIENT_STATE_LOGIN_PASSWORD; + fd->state = SMTP_CLIENT_STATE_SKIP_LINE; + } + break; case SMTP_CLIENT_STATE_LOGIN_PASSWORD: - { - fd->nextstate = SMTP_CLIENT_STATE_MAIL_FROM; - fd->state = SMTP_CLIENT_STATE_SKIP_LINE; - } - break; + { + fd->nextstate = SMTP_CLIENT_STATE_MAIL_FROM; + fd->state = SMTP_CLIENT_STATE_SKIP_LINE; + } + break; case SMTP_CLIENT_STATE_RCPT_TO: if (len >= (sizeof(RCPTTO)-1) && strncasecmp((const char*)args.data, RCPTTO, sizeof(RCPTTO)-1) == 0) @@ -622,7 +619,7 @@ int SmtpClientDetector::validate(AppIdDiscoveryArgs& args) done: dd->need_continue = 0; - args.asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + args.asd->set_client_detected(); return APPID_SUCCESS; } @@ -785,8 +782,7 @@ static inline int smtp_validate_reply(const uint8_t* data, uint16_t* offset, uin int SmtpServiceDetector::validate(AppIdDiscoveryArgs& args) { - - SMTPDetectorData* dd = smtp_client_detector->get_smtp_detector_data(args.asd); + SMTPDetectorData* dd = smtp_client_detector->get_common_data(args.asd); if ( !dd ) return APPID_ENOMEM; @@ -810,7 +806,7 @@ int SmtpServiceDetector::validate(AppIdDiscoveryArgs& args) add_service(args.asd, args.pkt, args.dir, APP_ID_SMTPS, nullptr, nullptr, nullptr); return APPID_SUCCESS; } - else if (args.asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + else if (args.asd->is_service_detected()) { // Client made it's decision so we are totally done. return APPID_SUCCESS; diff --git a/src/network_inspectors/appid/detector_plugins/detector_smtp.h b/src/network_inspectors/appid/detector_plugins/detector_smtp.h index 775260311..fa5868a93 100644 --- a/src/network_inspectors/appid/detector_plugins/detector_smtp.h +++ b/src/network_inspectors/appid/detector_plugins/detector_smtp.h @@ -36,7 +36,7 @@ public: ~SmtpClientDetector(); int validate(AppIdDiscoveryArgs&) override; - SMTPDetectorData* get_smtp_detector_data(AppIdSession*); + SMTPDetectorData* get_common_data(AppIdSession*); private: int extract_version_and_add_client_app(ApplicationId, const int prefix_len, diff --git a/src/network_inspectors/appid/detector_plugins/http_url_patterns.cc b/src/network_inspectors/appid/detector_plugins/http_url_patterns.cc index 47c3d4a4a..f6e96595e 100644 --- a/src/network_inspectors/appid/detector_plugins/http_url_patterns.cc +++ b/src/network_inspectors/appid/detector_plugins/http_url_patterns.cc @@ -25,12 +25,12 @@ #include "http_url_patterns.h" +#include "appid_http_session.h" #include "appid_module.h" #include "app_info_table.h" #include "application_ids.h" #include "appid_session.h" #include "appid_utils/sf_mlmp.h" -#include "service_plugins/service_util.h" #include "search_engines/search_tool.h" #include "log/messages.h" #include "protocols/packet.h" @@ -308,60 +308,6 @@ static void destroy_host_url_patterns(HostUrlPatterns** pattern_list) *pattern_list = nullptr; } -int HttpPatternMatchers::add_mlmp_pattern(void* matcher, - const uint8_t* host_pattern, int host_pattern_size, const uint8_t* path_pattern, - int path_pattern_size, const uint8_t* query_pattern, int query_pattern_size, - AppId appId, uint32_t payload_id, uint32_t service_id, uint32_t client_id, DHPSequence seq) -{ - tMlmpPattern patterns[PATTERN_PART_MAX]; - int num_patterns; - - if (!host_pattern) - return -1; - - HostUrlDetectorPattern* detector = - (HostUrlDetectorPattern*)snort_calloc(sizeof(HostUrlDetectorPattern)); - detector->host.pattern = (uint8_t*)snort_strdup((char*)host_pattern); - - if (path_pattern) - detector->path.pattern = (uint8_t*)snort_strdup((char*)path_pattern); - else - detector->path.pattern = nullptr; - - if (query_pattern) - detector->query.pattern = (uint8_t*)snort_strdup((char*)query_pattern); - else - detector->query.pattern = nullptr; - - detector->host.patternSize = host_pattern_size; - detector->path.patternSize = path_pattern_size; - detector->query.patternSize = query_pattern_size; - detector->payload_id = payload_id; - detector->service_id = service_id; - detector->client_id = client_id; - detector->seq = seq; - detector->next = nullptr; - if (appId > APP_ID_NONE) - detector->appId = appId; - else if (payload_id > APP_ID_NONE) - detector->appId = payload_id; - else if (client_id > APP_ID_NONE) - detector->appId = client_id; - else - detector->appId = service_id; - - num_patterns = parse_multiple_http_patterns((const char*)host_pattern, patterns, - PATTERN_PART_MAX, 0); - if (path_pattern) - num_patterns += parse_multiple_http_patterns((const char*)path_pattern, patterns + - num_patterns, - PATTERN_PART_MAX - num_patterns, 1); - - patterns[num_patterns].pattern = nullptr; - add_host_url_pattern(detector, &host_url_patterns); - return mlmpAddPattern((tMlmpTree*)matcher, patterns, detector); -} - static void destroy_host_url_matcher(tMlmpTree** host_url_matcher) { if (host_url_matcher && *host_url_matcher) @@ -371,12 +317,8 @@ static void destroy_host_url_matcher(tMlmpTree** host_url_matcher) } } -static int match_query_elements( - tMlpPattern* packetData, - tMlpPattern* userPattern, - char* appVersion, - size_t appVersionSize - ) +static int match_query_elements(tMlpPattern* packetData, tMlpPattern* userPattern, + char* appVersion, size_t appVersionSize) { const uint8_t* index; const uint8_t* endKey; @@ -474,8 +416,8 @@ void HttpPatternMatchers::free_http_elements(HTTPListElement* list) while ( (element = list) ) { list = element->next; - if (element->detectorHTTPPattern.pattern) - snort_free(element->detectorHTTPPattern.pattern); + if (element->detector_http_pattern.pattern) + snort_free(element->detector_http_pattern.pattern); snort_free(element); } } @@ -595,15 +537,69 @@ void HttpPatternMatchers::insert_app_url_pattern(DetectorAppUrlPattern* pattern) HttpPatternMatchers::insert_url_pattern(pattern); } +int HttpPatternMatchers::add_mlmp_pattern(void* matcher, const uint8_t* host_pattern, + int host_pattern_size, const uint8_t* path_pattern, int path_pattern_size, + const uint8_t* query_pattern, int query_pattern_size, AppId appId, uint32_t payload_id, + uint32_t service_id, uint32_t client_id, DHPSequence seq) +{ + tMlmpPattern patterns[PATTERN_PART_MAX]; + int num_patterns; + + if (!host_pattern) + return -1; + + HostUrlDetectorPattern* detector = + (HostUrlDetectorPattern*)snort_calloc(sizeof(HostUrlDetectorPattern)); + detector->host.pattern = (uint8_t*)snort_strdup((char*)host_pattern); + + if (path_pattern) + detector->path.pattern = (uint8_t*)snort_strdup((char*)path_pattern); + else + detector->path.pattern = nullptr; + + if (query_pattern) + detector->query.pattern = (uint8_t*)snort_strdup((char*)query_pattern); + else + detector->query.pattern = nullptr; + + detector->host.patternSize = host_pattern_size; + detector->path.patternSize = path_pattern_size; + detector->query.patternSize = query_pattern_size; + detector->payload_id = payload_id; + detector->service_id = service_id; + detector->client_id = client_id; + detector->seq = seq; + detector->next = nullptr; + if (appId > APP_ID_NONE) + detector->appId = appId; + else if (payload_id > APP_ID_NONE) + detector->appId = payload_id; + else if (client_id > APP_ID_NONE) + detector->appId = client_id; + else + detector->appId = service_id; + + num_patterns = parse_multiple_http_patterns((const char*)host_pattern, patterns, + PATTERN_PART_MAX, 0); + if (path_pattern) + num_patterns += parse_multiple_http_patterns((const char*)path_pattern, patterns + + num_patterns, + PATTERN_PART_MAX - num_patterns, 1); + + patterns[num_patterns].pattern = nullptr; + add_host_url_pattern(detector, &host_url_patterns); + return mlmpAddPattern((tMlmpTree*)matcher, patterns, detector); +} + int HttpPatternMatchers::process_mlmp_patterns() { for (auto* element = hostPayloadPatternList; element != 0; element = element->next) { if ( add_mlmp_pattern(host_url_matcher, - element->detectorHTTPPattern.pattern, element->detectorHTTPPattern.pattern_size, - nullptr, 0, nullptr, 0, element->detectorHTTPPattern.appId, - element->detectorHTTPPattern.payload, element->detectorHTTPPattern.service_id, - element->detectorHTTPPattern.client_app, element->detectorHTTPPattern.seq) < 0 ) + element->detector_http_pattern.pattern, element->detector_http_pattern.pattern_size, + nullptr, 0, nullptr, 0, element->detector_http_pattern.appId, + element->detector_http_pattern.payload, element->detector_http_pattern.service_id, + element->detector_http_pattern.client_app, element->detector_http_pattern.seq) < 0 ) return -1; } @@ -782,8 +778,8 @@ static SearchTool* process_content_type_patterns(DetectorHTTPPattern* patternLis // Add patterns from Lua API for (HTTPListElement* element = luaPatternList; element; element = element->next) - patternMatcher->add(element->detectorHTTPPattern.pattern, - element->detectorHTTPPattern.pattern_size, &element->detectorHTTPPattern, false); + patternMatcher->add(element->detector_http_pattern.pattern, + element->detector_http_pattern.pattern_size, &element->detector_http_pattern, false); patternMatcher->prep(); @@ -844,7 +840,6 @@ static SearchTool* process_http_field_patterns(FieldPattern* patternList, size_t return patternMatcher; } -// FIXIT-M - should only create Searchtool if there are patterns to process... static SearchTool* process_patterns(DetectorHTTPPattern* patternList, size_t patternListCount, size_t*, HTTPListElement* luaPatternList) { @@ -854,10 +849,9 @@ static SearchTool* process_patterns(DetectorHTTPPattern* patternList, size_t pat patternMatcher->add(patternList[i].pattern, patternList[i].pattern_size, &patternList[i], false); - /* Add patterns from Lua API */ for (HTTPListElement* element = luaPatternList; element != nullptr; element = element->next) - patternMatcher->add(element->detectorHTTPPattern.pattern, - element->detectorHTTPPattern.pattern_size, &element->detectorHTTPPattern, false); + patternMatcher->add(element->detector_http_pattern.pattern, + element->detector_http_pattern.pattern_size, &element->detector_http_pattern, false); patternMatcher->prep(); return patternMatcher; @@ -871,14 +865,10 @@ int HttpPatternMatchers::finalize() size_t vpc = 0; uint32_t numPatterns; - /*create via pattern matcher */ numPatterns = sizeof(via_http_detector_patterns) / sizeof(*via_http_detector_patterns); via_matcher = process_patterns(via_http_detector_patterns, numPatterns, &vpc, nullptr); - - /*create url pattern matcher */ url_matcher = process_patterns(nullptr, 0, &upc, urlPatternList); - /*create client agent pattern matcher */ numPatterns = sizeof(client_agent_patterns) / sizeof(*client_agent_patterns); client_agent_matcher = process_patterns(client_agent_patterns, numPatterns, &apc, clientAgentPatternList); @@ -903,7 +893,7 @@ typedef struct fieldPatternData_t { const uint8_t* payload; unsigned length; - HttpSession* hsession; + AppIdHttpSession* hsession; } FieldPatternData; static int http_field_pattern_match(void* id, void*, int match_end_pos, void* data, void*) @@ -927,7 +917,7 @@ static int http_field_pattern_match(void* id, void*, int match_end_pos, void* da } // FIXIT-M: Is this still necessary now that we use inspection events? -void HttpPatternMatchers::get_http_offsets(Packet* pkt, HttpSession* hsession) +void HttpPatternMatchers::get_http_offsets(Packet* pkt, AppIdHttpSession* hsession) { constexpr auto MIN_HTTP_REQ_HEADER_SIZE = (sizeof("GET /\r\n\r\n") - 1); static const uint8_t crlfcrlf[] = "\r\n\r\n"; @@ -1113,6 +1103,18 @@ static void extract_chp(char* buf, int bs, int start, int psize, char* adata, c *outbuf = snort_strndup(begin, end-begin); } +void HttpPatternMatchers::free_matched_chp_actions(MatchedCHPAction* ma) +{ + MatchedCHPAction* tmp; + + while (ma) + { + tmp = ma; + ma = ma->next; + snort_free(tmp); + } +} + void HttpPatternMatchers::scan_key_chp(PatternType ptype, char* buf, int buf_size, CHPTallyAndActions& match_tally) { @@ -1122,7 +1124,7 @@ void HttpPatternMatchers::scan_key_chp(PatternType ptype, char* buf, int buf_siz AppId HttpPatternMatchers::scan_chp(PatternType ptype, char* buf, int buf_size, MatchedCHPAction* mp, char** version, char** user, char** new_field, - int* total_found, HttpSession* hsession, Packet*, AppIdModuleConfig* mod_config) + int* total_found, AppIdHttpSession* hsession, AppIdModuleConfig* mod_config) { MatchedCHPAction* second_sweep_for_inserts = nullptr; int do_not_further_modify_field = 0; @@ -1139,7 +1141,7 @@ AppId HttpPatternMatchers::scan_chp(PatternType ptype, char* buf, int buf_size, if (!mp) return APP_ID_NONE; - if (mod_config->disable_safe_search) + if (!mod_config->safe_search_enabled) new_field = nullptr; for (tmp = mp; tmp; tmp = tmp->next) @@ -1650,7 +1652,7 @@ int HttpPatternMatchers::get_appid_by_pattern(const uint8_t* data, unsigned size else i = 0; temp_ver[i] = 0; - replace_optional_string(version,temp_ver); + replace_optional_string(version, temp_ver); free_matched_patterns(mp); return APP_ID_SQUID; @@ -1686,7 +1688,7 @@ AppId HttpPatternMatchers::scan_header_x_working_with(const uint8_t* data, uint3 temp_ver[i++] = (char)*data; } temp_ver[i] = 0; - replace_optional_string(version,temp_ver); + replace_optional_string(version, temp_ver); return APP_ID_ASPROXY; } return APP_ID_NONE; @@ -1702,14 +1704,14 @@ AppId HttpPatternMatchers::get_appid_by_content_type(const uint8_t* data, int si return APP_ID_NONE; DetectorHTTPPattern* match = mp->mpattern; - AppId payloadId = match->appId; + AppId payload_id = match->appId; free_matched_patterns(mp); - return payloadId; + return payload_id; } -AppId HttpPatternMatchers::get_appid_from_url(char* host, char* url, char** version, +bool HttpPatternMatchers::get_appid_from_url(char* host, char* url, char** version, char* referer, AppId* ClientAppId, AppId* serviceAppId, AppId* payloadAppId, AppId* referredPayloadAppId, unsigned from_rtmp) { @@ -1725,7 +1727,7 @@ AppId HttpPatternMatchers::get_appid_from_url(char* host, char* url, char** vers tMlpPattern query; HostUrlDetectorPattern* data; char* q; - int payload_found = 0; + bool payload_found = false; int url_len; static tMlmpTree* matcher; @@ -1791,7 +1793,7 @@ AppId HttpPatternMatchers::get_appid_from_url(char* host, char* url, char** vers data = (HostUrlDetectorPattern*)mlmpMatchPatternUrl(matcher, patterns); if (data) { - payload_found = 1; + payload_found = true; if (url) { q = strchr(url, '?'); @@ -1805,7 +1807,7 @@ AppId HttpPatternMatchers::get_appid_from_url(char* host, char* url, char** vers match_query_elements(&query, &data->query, temp_ver, MAX_VERSION_SIZE); if (temp_ver[0] != 0) - replace_optional_string(version,temp_ver); + replace_optional_string(version, temp_ver); } } @@ -1858,24 +1860,25 @@ AppId HttpPatternMatchers::get_appid_from_url(char* host, char* url, char** vers if (payload_found) *referredPayloadAppId = *payloadAppId; else - payload_found = 1; + payload_found = true; *payloadAppId = data->payload_id; } } } + return payload_found; } void HttpPatternMatchers::get_server_vendor_version(const uint8_t* data, int len, char** version, char** vendor, - RNAServiceSubtype** subtype) + AppIdServiceSubtype** subtype) { int vendor_len = len; const uint8_t* ver = (const uint8_t*)memchr(data, '/', len); if (ver) { - RNAServiceSubtype* sub; + AppIdServiceSubtype* sub; int version_len = 0; int subver_len; const uint8_t* subname = nullptr; @@ -1910,7 +1913,7 @@ void HttpPatternMatchers::get_server_vendor_version(const uint8_t* data, int len { if (subname && subname_len > 0 && subver && *subname) { - sub = (RNAServiceSubtype*)snort_calloc(sizeof(RNAServiceSubtype)); + sub = (AppIdServiceSubtype*)snort_calloc(sizeof(AppIdServiceSubtype)); char* tmp = (char*)snort_calloc(subname_len + 1); memcpy(tmp, subname, subname_len); tmp[subname_len] = 0; @@ -1941,7 +1944,7 @@ void HttpPatternMatchers::get_server_vendor_version(const uint8_t* data, int len } if (subname && subname_len > 0 && subver && *subname) { - sub = (RNAServiceSubtype*)snort_calloc(sizeof(RNAServiceSubtype)); + sub = (AppIdServiceSubtype*)snort_calloc(sizeof(AppIdServiceSubtype)); char* tmp = (char*)snort_calloc(subname_len + 1); memcpy(tmp, subname, subname_len); tmp[subname_len] = 0; diff --git a/src/network_inspectors/appid/detector_plugins/http_url_patterns.h b/src/network_inspectors/appid/detector_plugins/http_url_patterns.h index 234632f20..c7548c6c1 100644 --- a/src/network_inspectors/appid/detector_plugins/http_url_patterns.h +++ b/src/network_inspectors/appid/detector_plugins/http_url_patterns.h @@ -30,8 +30,8 @@ #include "utils/util.h" struct Packet; -struct RNAServiceSubtype; -struct HttpSession; +struct AppIdServiceSubtype; +class AppIdHttpSession; class AppIdModuleConfig; class SearchTool; @@ -93,7 +93,7 @@ struct DetectorHTTPPattern struct HTTPListElement { - DetectorHTTPPattern detectorHTTPPattern; + DetectorHTTPPattern detector_http_pattern; HTTPListElement* next; }; @@ -233,6 +233,7 @@ class HttpPatternMatchers public: HttpPatternMatchers() { } ~HttpPatternMatchers(); + static HttpPatternMatchers* get_instance(); int finalize(); void insert_chp_pattern(CHPListElement*); @@ -246,30 +247,20 @@ public: int process_host_patterns(DetectorHTTPPattern*, size_t patternListCount); int process_mlmp_patterns(); + void free_matched_chp_actions(MatchedCHPAction* ma); void scan_key_chp(PatternType, char* buf, int buf_size, CHPTallyAndActions&); AppId scan_chp(PatternType, char*, int, MatchedCHPAction*, char**, char**, char**, - int*, HttpSession*, Packet*, AppIdModuleConfig*); + int*, AppIdHttpSession*, AppIdModuleConfig*); AppId scan_header_x_working_with(const uint8_t*, uint32_t, char**); int get_appid_by_pattern(const uint8_t*, unsigned, char**); - AppId get_appid_from_url(char*, char*, char**, char*, AppId*, AppId*, + bool get_appid_from_url(char*, char*, char**, char*, AppId*, AppId*, AppId*, AppId*, unsigned); AppId get_appid_by_content_type(const uint8_t*, int); - void get_server_vendor_version(const uint8_t*, int, char**, char**, RNAServiceSubtype**); + void get_server_vendor_version(const uint8_t*, int, char**, char**, AppIdServiceSubtype**); void identify_user_agent(const uint8_t*, int, AppId*, AppId*, char**); - void get_http_offsets(Packet*, HttpSession*); + void get_http_offsets(Packet*, AppIdHttpSession*); uint32_t parse_multiple_http_patterns(const char* pattern, tMlmpPattern*, uint32_t numPartLimit, int level); - void free_matched_chp_actions(MatchedCHPAction* ma) - { - MatchedCHPAction* tmp; - - while (ma) - { - tmp = ma; - ma = ma->next; - snort_free(tmp); - } - } private: HTTPListElement* hostPayloadPatternList = nullptr; diff --git a/src/network_inspectors/appid/detector_plugins/test/detector_smtp_test.cc b/src/network_inspectors/appid/detector_plugins/test/detector_smtp_test.cc index 297f4f506..16a229cac 100644 --- a/src/network_inspectors/appid/detector_plugins/test/detector_smtp_test.cc +++ b/src/network_inspectors/appid/detector_plugins/test/detector_smtp_test.cc @@ -247,7 +247,7 @@ TEST(client_app_smtp, identify_client_version_mozilla_thunderbird) #endif // FIXIT-M Add additional tests for other client types (Outlook, etc). -int main(int argc, char** argv) +int main(int, char**) { #if 0 int return_value = CommandLineTestRunner::RunAllTests(argc, argv); diff --git a/src/network_inspectors/appid/host_port_app_cache.cc b/src/network_inspectors/appid/host_port_app_cache.cc index e15c892f6..c27543afe 100644 --- a/src/network_inspectors/appid/host_port_app_cache.cc +++ b/src/network_inspectors/appid/host_port_app_cache.cc @@ -67,7 +67,7 @@ struct HostPortKey }; PADDING_GUARD_END -THREAD_LOCAL std::map* host_port_cache = nullptr; +static THREAD_LOCAL std::map* host_port_cache = nullptr; void HostPortCache::initialize() { diff --git a/src/network_inspectors/appid/lua_detector_api.cc b/src/network_inspectors/appid/lua_detector_api.cc index dedf64d72..5a988e46c 100644 --- a/src/network_inspectors/appid/lua_detector_api.cc +++ b/src/network_inspectors/appid/lua_detector_api.cc @@ -145,7 +145,7 @@ static int service_init(lua_State* L) else { ErrorMessage("%s: attempted setting validator/fini to non-function\n", - ud->name.c_str()); + ud->get_name().c_str()); lua_pop(L, 2); return 0; @@ -201,7 +201,7 @@ static int common_register_application_id(lua_State* L) auto& ud = *UserData::check(L, DETECTOR, index); AppId appId = lua_tonumber(L, ++index); - if ( ud->packageInfo.client_detector ) + if ( ud->package_info.client_detector ) { auto& cd = *UserData::check(L, DETECTOR, ++index); cd->register_appid(appId, APPINFO_FLAG_CLIENT_ADDITIONAL); @@ -242,7 +242,7 @@ static int detector_htonl(lua_State* L) // #2 - message - message to be logged. static int detector_log_message(lua_State* L) { - const auto& name = (*UserData::check(L, DETECTOR, 1))->name; + const auto& name = (*UserData::check(L, DETECTOR, 1))->get_name(); unsigned int level = lua_tonumber(L, 2); const char* message = lua_tostring(L, 3); @@ -283,28 +283,28 @@ static int detector_log_message(lua_State* L) static int service_analyze_payload(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.asd); - ud->validateParams.asd->payload_app_id = lua_tonumber(L, 2); + assert(ud->validate_params.asd); + ud->validate_params.asd->payload_app_id = lua_tonumber(L, 2); return 0; } // FIXIT-M - the comments and code below for service_get_service_id don't appear to be useful -// the ud->server.serviceId field is set to APP_ID_UNKNOWN at init time and never updated +// the ud->server.service_id field is set to APP_ID_UNKNOWN at init time and never updated // is this function ever used? -/**design: dont store serviceId in detector structure since a single detector - * can get serviceId for multiple protocols. For example SIP which gets Id for RTP and +/**design: dont store service_id in detector structure since a single detector + * can get service_id for multiple protocols. For example SIP which gets Id for RTP and * SIP services. */ // Get service id from database, given service name. Lua detectors call this function at init time // get get a service Id (an integer) from database. // @param serviceName/stack - Name of service -// @return serviceId/stack - serviceId if successful, -1 otherwise. +// @return service_id/stack - service_id if successful, -1 otherwise. static int service_get_service_id(lua_State* L) { auto ud = *UserData::check(L, DETECTOR, 1); - lua_pushnumber(L, ud->serviceId); + lua_pushnumber(L, ud->service_id); return 1; } @@ -328,7 +328,7 @@ static int service_add_ports(lua_State* L) return 1; } - if ( ud->handler->add_service_port(ud, pp) ) + if ( ud->get_handler().add_service_port(ud, pp) ) { lua_pushnumber(L, -1); return 1; @@ -373,7 +373,7 @@ static int service_get_service_name(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - lua_pushstring(L, ud->name.c_str()); + lua_pushstring(L, ud->get_name().c_str()); return 1; } @@ -388,7 +388,7 @@ static int service_get_service_name(lua_State* L) static int service_is_custom_detector(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - lua_pushnumber(L, ud->isCustom); + lua_pushnumber(L, ud->is_custom_detector()); return 1; } @@ -411,7 +411,7 @@ static int service_set_validator(lua_State* L) if (!lua_isfunction(L, -1)) { ErrorMessage("%s: attempted setting validator to non-function\n", - ud->name.c_str()); + ud->get_name().c_str()); lua_pop(L, 1); lua_pushnumber(L, -1); @@ -419,7 +419,7 @@ static int service_set_validator(lua_State* L) } lua_pop(L, 1); - ud->packageInfo.validateFunctionName = pValidator; + ud->package_info.validateFunctionName = pValidator; lua_pushnumber(L, 0); return 1; } @@ -435,9 +435,9 @@ static int service_set_validator(lua_State* L) static int service_add_data_id(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.asd); + assert(ud->validate_params.asd); uint16_t sport = lua_tonumber(L, 2); - ud->validateParams.asd->add_flow_data_id(sport, ud); + ud->validate_params.asd->add_flow_data_id(sport, ud); lua_pushnumber(L, 0); return 1; } @@ -446,7 +446,7 @@ static int service_add_data_id(lua_State* L) * * @param Lua_State* - Lua state variable. * @param detector/stack - detector object - * @param serviceId/stack - id of service postively identified on this flow. + * @param service_id/stack - id of service postively identified on this flow. * @param vendorName/stack - name of vendor of service. This is optional. * @param version/stack - version of service. This is optional. * @return int - Number of elements on stack, which is always 1. @@ -455,16 +455,16 @@ static int service_add_data_id(lua_State* L) static int service_add_service(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.pkt && ud->validateParams.asd); - AppId serviceId = lua_tonumber(L, 2); + assert(ud->validate_params.pkt && ud->validate_params.asd); + AppId service_id = lua_tonumber(L, 2); char* vendor = (char*)luaL_optstring(L, 3, nullptr); char* version = (char*)luaL_optstring(L, 4, nullptr); - /*Phase2 - discuss RNAServiceSubtype will be maintained on lua side therefore the last + /*Phase2 - discuss AppIdServiceSubtype will be maintained on lua side therefore the last parameter on the following call is nullptr. Subtype is not displayed on DC at present. */ - unsigned int retValue = ud->add_service(ud->validateParams.asd, - ud->validateParams.pkt, ud->validateParams.dir, - AppInfoManager::get_instance().get_appid_by_service_id(serviceId), + unsigned int retValue = ud->add_service(ud->validate_params.asd, + ud->validate_params.pkt, ud->validate_params.dir, + AppInfoManager::get_instance().get_appid_by_service_id(service_id), vendor, version, nullptr); lua_pushnumber(L, retValue); @@ -481,10 +481,10 @@ static int service_add_service(lua_State* L) static int service_fail_service(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.pkt && ud->validateParams.asd); - ServiceDiscovery* sdm = static_cast(ud->handler); - unsigned int retValue = sdm->fail_service(ud->validateParams.asd, ud->validateParams.pkt, - ud->validateParams.dir, nullptr); + assert(ud->validate_params.pkt && ud->validate_params.asd); + ServiceDiscovery& sdm = static_cast(ud->get_handler()); + unsigned int retValue = sdm.fail_service(ud->validate_params.asd, ud->validate_params.pkt, + ud->validate_params.dir, nullptr); lua_pushnumber(L, retValue); return 1; @@ -500,10 +500,10 @@ static int service_fail_service(lua_State* L) static int service_in_process_service(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.pkt && ud->validateParams.asd); + assert(ud->validate_params.pkt && ud->validate_params.asd); - unsigned int retValue = ud->service_inprocess(ud->validateParams.asd, - ud->validateParams.pkt, ud->validateParams.dir); + unsigned int retValue = ud->service_inprocess(ud->validate_params.asd, + ud->validate_params.pkt, ud->validate_params.dir); lua_pushnumber(L, retValue); return 1; @@ -519,10 +519,10 @@ static int service_in_process_service(lua_State* L) static int service_set_incompatible_data(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.pkt && ud->validateParams.asd); + assert(ud->validate_params.pkt && ud->validate_params.asd); - unsigned int retValue = ud->incompatible_data(ud->validateParams.asd, - ud->validateParams.pkt, ud->validateParams.dir); + unsigned int retValue = ud->incompatible_data(ud->validate_params.asd, + ud->validate_params.pkt, ud->validate_params.dir); lua_pushnumber(L, retValue); return 1; } @@ -540,7 +540,7 @@ static int detector_get_packet_size(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - lua_pushnumber(L, ud->validateParams.size); + lua_pushnumber(L, ud->validate_params.size); return 1; } @@ -556,7 +556,7 @@ static int detector_get_packet_direction(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - lua_pushnumber(L, ud->validateParams.dir); + lua_pushnumber(L, ud->validate_params.dir); return 1; } @@ -596,8 +596,8 @@ static int detector_get_pcre_groups(lua_State* L) /*pattern match against the subject string. */ int rc = pcre_exec(re, // compiled pattern nullptr, // no extra data - (char*)ud->validateParams.data, // subject string - ud->validateParams.size, // length of the subject + (char*)ud->validate_params.data, // subject string + ud->validate_params.size, // length of the subject offset, // offset 0 0, // default options ovector, // output vector for substring @@ -617,7 +617,7 @@ static int detector_get_pcre_groups(lua_State* L) lua_checkstack(L, rc); for (int i = 0; i < rc; i++) { - lua_pushlstring(L, (char*)ud->validateParams.data + ovector[2*i], ovector[2*i+1] - + lua_pushlstring(L, (char*)ud->validate_params.data + ovector[2*i], ovector[2*i+1] - ovector[2*i]); } } @@ -651,7 +651,7 @@ static int detector_memcmp(lua_State* L) char* pattern = (char*)lua_tostring(L, 2); unsigned int patternLen = lua_tonumber(L, 3); unsigned int offset = lua_tonumber(L, 4); /*offset can be zero, no check necessary. */ - int rc = memcmp((char*)ud->validateParams.data + offset, pattern, patternLen); + int rc = memcmp((char*)ud->validate_params.data + offset, pattern, patternLen); lua_checkstack (L, 1); lua_pushnumber(L, rc); return 1; @@ -666,9 +666,9 @@ static int detector_memcmp(lua_State* L) static int detector_get_protocol_type(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.pkt); + assert(ud->validate_params.pkt); - if ( !ud->validateParams.pkt->has_ip() ) + if ( !ud->validate_params.pkt->has_ip() ) { // FIXIT-M J why the inconsistent use of checkstack? lua_checkstack (L, 1); @@ -678,7 +678,7 @@ static int detector_get_protocol_type(lua_State* L) lua_checkstack (L, 1); // FIXIT-M is this conversion to double valid? - lua_pushnumber(L, (double)ud->validateParams.pkt->get_ip_proto_next() ); + lua_pushnumber(L, (double)ud->validate_params.pkt->get_ip_proto_next() ); return 1; } @@ -692,9 +692,9 @@ static int detector_get_protocol_type(lua_State* L) static int detector_get_packet_src_addr(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.pkt); + assert(ud->validate_params.pkt); - const SfIp* ipAddr = ud->validateParams.pkt->ptrs.ip_api.get_src(); + const SfIp* ipAddr = ud->validate_params.pkt->ptrs.ip_api.get_src(); lua_checkstack (L, 1); lua_pushnumber(L, ipAddr->get_ip4_value()); return 1; @@ -710,9 +710,9 @@ static int detector_get_packet_src_addr(lua_State* L) static int detector_get_packet_dst_addr(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.pkt); + assert(ud->validate_params.pkt); - const SfIp* ipAddr = ud->validateParams.pkt->ptrs.ip_api.get_dst(); + const SfIp* ipAddr = ud->validate_params.pkt->ptrs.ip_api.get_dst(); lua_checkstack (L, 1); lua_pushnumber(L, ipAddr->get_ip4_value()); return 1; @@ -728,9 +728,9 @@ static int detector_get_packet_dst_addr(lua_State* L) static int detector_get_packet_src_port(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.pkt); + assert(ud->validate_params.pkt); - unsigned int port = ud->validateParams.pkt->ptrs.sp; + unsigned int port = ud->validate_params.pkt->ptrs.sp; lua_checkstack (L, 1); lua_pushnumber(L, port); return 1; @@ -746,9 +746,9 @@ static int detector_get_packet_src_port(lua_State* L) static int detector_get_packet_dst_port(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.pkt); + assert(ud->validate_params.pkt); - unsigned int port = ud->validateParams.pkt->ptrs.dp; + unsigned int port = ud->validate_params.pkt->ptrs.dp; lua_checkstack (L, 1); lua_pushnumber(L, port); return 1; @@ -816,10 +816,10 @@ static int client_init(lua_State*) static int service_add_client(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.asd); + assert(ud->validate_params.asd); - AppId clientAppId = lua_tonumber(L, 2); - AppId serviceId = lua_tonumber(L, 3); + AppId client_app_id = lua_tonumber(L, 2); + AppId service_id = lua_tonumber(L, 3); const char* version = lua_tostring(L, 4); if ( !version ) @@ -828,7 +828,7 @@ static int service_add_client(lua_State* L) return 1; } - ud->add_app(ud->validateParams.asd, serviceId, clientAppId, version); + ud->add_app(ud->validate_params.asd, service_id, client_app_id, version); lua_pushnumber(L, 0); return 1; @@ -837,13 +837,13 @@ static int service_add_client(lua_State* L) static int client_add_application(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.asd); + assert(ud->validate_params.asd); - unsigned int serviceId = lua_tonumber(L, 2); + unsigned int service_id = lua_tonumber(L, 2); unsigned int productId = lua_tonumber(L, 4); const char* version = lua_tostring(L, 5); - ud->add_app(ud->validateParams.asd, - AppInfoManager::get_instance().get_appid_by_service_id(serviceId), + ud->add_app(ud->validate_params.asd, + AppInfoManager::get_instance().get_appid_by_service_id(service_id), AppInfoManager::get_instance().get_appid_by_client_id(productId), version); lua_pushnumber(L, 0); @@ -853,10 +853,10 @@ static int client_add_application(lua_State* L) static int client_add_info(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.asd); + assert(ud->validate_params.asd); const char* info = lua_tostring(L, 2); - ud->add_info(ud->validateParams.asd, info); + ud->add_info(ud->validate_params.asd, info); lua_pushnumber(L, 0); return 1; @@ -865,13 +865,13 @@ static int client_add_info(lua_State* L) static int client_add_user(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.asd); + assert(ud->validate_params.asd); const char* userName = lua_tostring(L, 2); - unsigned int serviceId = lua_tonumber(L, 3); + unsigned int service_id = lua_tonumber(L, 3); - ud->add_user(ud->validateParams.asd, userName, - AppInfoManager::get_instance().get_appid_by_service_id(serviceId), 1); + ud->add_user(ud->validate_params.asd, userName, + AppInfoManager::get_instance().get_appid_by_service_id(service_id), true); lua_pushnumber(L, 0); return 1; @@ -880,10 +880,10 @@ static int client_add_user(lua_State* L) static int client_add_payload(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.asd); + assert(ud->validate_params.asd); unsigned int payloadId = lua_tonumber(L, 2); - ud->add_payload(ud->validateParams.asd, + ud->add_payload(ud->validate_params.asd, AppInfoManager::get_instance().get_appid_by_payload_id(payloadId)); lua_pushnumber(L, 0); @@ -903,10 +903,10 @@ static int client_add_payload(lua_State* L) static int detector_get_flow(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.asd); + assert(ud->validate_params.asd); auto df = new DetectorFlow(); - df->asd = ud->validateParams.asd; + df->asd = ud->validate_params.asd; UserData::push(L, DETECTORFLOW, df); df->myLuaState = L; @@ -922,10 +922,10 @@ static int detector_add_http_pattern(lua_State* L) int index = 1; // Verify detector user data and that we are not in packet context - assert(!(*UserData::check(L, DETECTOR, index))->validateParams.pkt); + assert(!(*UserData::check(L, DETECTOR, index))->validate_params.pkt); - enum httpPatternType pType = (enum httpPatternType)lua_tointeger(L, ++index); - if (pType < HTTP_PAYLOAD || pType > HTTP_URL) + enum httpPatternType pat_type = (enum httpPatternType)lua_tointeger(L, ++index); + if (pat_type < HTTP_PAYLOAD || pat_type > HTTP_URL) { ErrorMessage("Invalid HTTP pattern type."); return 0; @@ -944,20 +944,19 @@ static int detector_add_http_pattern(lua_State* L) uint32_t payload = lua_tointeger(L, ++index); /*uint32_t payload_type =*/ lua_tointeger(L, ++index); - size_t pattern_size = 0; - const char* tmpString = lua_tolstring(L, ++index, &pattern_size); - if ( tmpString == nullptr || pattern_size == 0) + const char* tmp_string = lua_tolstring(L, ++index, &pattern_size); + if ( tmp_string == nullptr || pattern_size == 0) { ErrorMessage("Invalid HTTP pattern string."); return 0; } - uint8_t* pattern_str = (uint8_t*)snort_strdup(tmpString); + uint8_t* pattern_str = (uint8_t*)snort_strdup(tmp_string); uint32_t appId = lua_tointeger(L, ++index); AppInfoManager& app_info_manager = AppInfoManager::get_instance(); HTTPListElement* element = (HTTPListElement*)snort_calloc(sizeof(HTTPListElement)); - DetectorHTTPPattern* pattern = &element->detectorHTTPPattern; + DetectorHTTPPattern* pattern = &element->detector_http_pattern; pattern->seq = seq; pattern->service_id = app_info_manager.get_appid_by_service_id(service_id); pattern->client_app = app_info_manager.get_appid_by_client_id(client_app); @@ -970,10 +969,10 @@ static int detector_add_http_pattern(lua_State* L) // the legacy client app or payload tables. We will use the appId instead. This is only for // user-agents that ID clients. if you want a user-agent to ID a payload, include it in the // payload database. If you want a host pattern ID, use the other API. - if (!service_id && !client_app && !payload && pType == 2) + if (!service_id && !client_app && !payload && pat_type == 2) pattern->client_app = appId; - HttpPatternMatchers::get_instance()->insert_http_pattern_element(pType, element); + HttpPatternMatchers::get_instance()->insert_http_pattern_element(pat_type, element); app_info_manager.set_app_info_active(pattern->service_id); app_info_manager.set_app_info_active(pattern->client_app); app_info_manager.set_app_info_active(pattern->payload); @@ -988,20 +987,20 @@ static int detector_add_ssl_cert_pattern(lua_State* L) int index = 1; // Verify detector user data and that we are not in packet context - assert(!(*UserData::check(L, DETECTOR, index))->validateParams.pkt); + assert(!(*UserData::check(L, DETECTOR, index))->validate_params.pkt); uint8_t type = lua_tointeger(L, ++index); AppId app_id = (AppId)lua_tointeger(L, ++index); size_t pattern_size = 0; - const char* tmpString = lua_tolstring(L, ++index, &pattern_size); - if (!tmpString || !pattern_size) + const char* tmp_string = lua_tolstring(L, ++index, &pattern_size); + if (!tmp_string || !pattern_size) { ErrorMessage("Invalid SSL Host pattern string"); return 0; } #ifdef REMOVED_WHILE_NOT_IN_USE - uint8_t* pattern_str = (uint8_t*)snort_strdup(tmpString); + uint8_t* pattern_str = (uint8_t*)snort_strdup(tmp_string); if (!ssl_add_cert_pattern(pattern_str, pattern_size, type, app_id, &ud->appid_config->serviceSslConfig)) { @@ -1023,20 +1022,20 @@ static int detector_add_dns_host_pattern(lua_State* L) int index = 1; // Verify detector user data and that we are not in packet context - assert(!(*UserData::check(L, DETECTOR, index))->validateParams.pkt); + assert(!(*UserData::check(L, DETECTOR, index))->validate_params.pkt); uint8_t type = lua_tointeger(L, ++index); AppId app_id = (AppId)lua_tointeger(L, ++index); size_t pattern_size = 0; - const char* tmpString = lua_tolstring(L, ++index, &pattern_size); - if (!tmpString || !pattern_size) + const char* tmp_string = lua_tolstring(L, ++index, &pattern_size); + if (!tmp_string || !pattern_size) { ErrorMessage("LuaDetectorApi:Invalid DNS Host pattern string"); return 0; } - uint8_t* pattern_str = (uint8_t*)snort_strdup(tmpString); + uint8_t* pattern_str = (uint8_t*)snort_strdup(tmp_string); if (!dns_add_host_pattern(pattern_str, pattern_size, type, app_id)) { snort_free(pattern_str); @@ -1051,21 +1050,21 @@ static int detector_add_ssl_cname_pattern(lua_State* L) int index = 1; // Verify detector user data and that we are not in packet context - assert(!(*UserData::check(L, DETECTOR, index))->validateParams.pkt); + assert(!(*UserData::check(L, DETECTOR, index))->validate_params.pkt); uint8_t type = lua_tointeger(L, ++index); AppId app_id = (AppId)lua_tointeger(L, ++index); size_t pattern_size = 0; - const char* tmpString = lua_tolstring(L, ++index, &pattern_size); - if (!tmpString || !pattern_size) + const char* tmp_string = lua_tolstring(L, ++index, &pattern_size); + if (!tmp_string || !pattern_size) { ErrorMessage("Invalid SSL Host pattern string"); return 0; } #ifdef REMOVED_WHILE_NOT_IN_USE - uint8_t* pattern_str = (uint8_t*)snort_strdup(tmpString); + uint8_t* pattern_str = (uint8_t*)snort_strdup(tmp_string); if (!ssl_add_cname_pattern(pattern_str, pattern_size, type, app_id, &ud->appid_config->serviceSslConfig)) { @@ -1087,7 +1086,7 @@ static int detector_add_host_port_application(lua_State* L) SfIp ip_addr; // Verify detector user data and that we are not in packet context - assert(!(*UserData::check(L, DETECTOR, index))->validateParams.pkt); + assert(!(*UserData::check(L, DETECTOR, index))->validate_params.pkt); uint8_t type = lua_tointeger(L, ++index); AppId app_id = (AppId)lua_tointeger(L, ++index); @@ -1119,19 +1118,19 @@ static int detector_add_content_type_pattern(lua_State* L) size_t stringSize = 0; // Verify detector user data and that we are not in packet context - assert(!(*UserData::check(L, DETECTOR, index))->validateParams.pkt); + assert(!(*UserData::check(L, DETECTOR, index))->validate_params.pkt); - const char* tmpString = lua_tolstring(L, ++index, &stringSize); - if (!tmpString || !stringSize) + const char* tmp_string = lua_tolstring(L, ++index, &stringSize); + if (!tmp_string || !stringSize) { ErrorMessage("Invalid HTTP Header string"); return 0; } - uint8_t* pattern = (uint8_t*)snort_strdup(tmpString); + uint8_t* pattern = (uint8_t*)snort_strdup(tmp_string); AppId appId = lua_tointeger(L, ++index); HTTPListElement* element = (HTTPListElement*)snort_calloc(sizeof(HTTPListElement)); - DetectorHTTPPattern* detector = &element->detectorHTTPPattern; + DetectorHTTPPattern* detector = &element->detector_http_pattern; detector->pattern = pattern; detector->pattern_size = strlen((char*)pattern); detector->appId = appId; @@ -1146,7 +1145,7 @@ static inline int get_detector_user_data(lua_State* L, int index, { // Verify detector user data and that we are not in packet context *detector_user_data = UserData::check(L, DETECTOR, index); - if (!*detector_user_data || (**detector_user_data)->validateParams.pkt) + if (!*detector_user_data || (**detector_user_data)->validate_params.pkt) { ErrorMessage("%s", errorString); return -1; @@ -1219,17 +1218,17 @@ static inline int get_chp_pattern_type(lua_State* L, int index, PatternType* pat static inline int get_chp_pattern_data_and_size(lua_State* L, int index, char** pattern_data, size_t* pattern_size) { - const char* tmpString; // Lua owns this pointer + const char* tmp_string; // Lua owns this pointer *pattern_size = 0; *pattern_data = nullptr; - tmpString = lua_tolstring(L, index, pattern_size); + tmp_string = lua_tolstring(L, index, pattern_size); // non-empty pattern required - if (!tmpString || !*pattern_size) + if (!tmp_string || !*pattern_size) { ErrorMessage("LuaDetectorApi:Invalid CHP Action PATTERN string."); return -1; } - *pattern_data = snort_strdup(tmpString); + *pattern_data = snort_strdup(tmp_string); return 0; } @@ -1249,11 +1248,10 @@ static inline int get_chp_action_type(lua_State* L, int index, ActionType* actio static inline int get_chp_action_data(lua_State* L, int index, char** action_data) { // An empty string is translated into a nullptr pointer because the action data is optional - const char* tmpString; // Lua owns this pointer size_t action_data_size = 0; - tmpString = lua_tolstring(L, index, &action_data_size); + const char* tmp_string = lua_tolstring(L, index, &action_data_size); if (action_data_size) - *action_data = snort_strdup(tmpString); + *action_data = snort_strdup(tmp_string); else *action_data = nullptr; @@ -1490,7 +1488,7 @@ static int detector_port_only_service(lua_State* L) int index = 1; // Verify detector user data and that we are not in packet context - assert(!(*UserData::check(L, DETECTOR, index))->validateParams.pkt); + assert(!(*UserData::check(L, DETECTOR, index))->validate_params.pkt); AppId appId = lua_tointeger(L, ++index); uint16_t port = lua_tointeger(L, ++index); @@ -1629,7 +1627,7 @@ static int detector_add_af_application(lua_State* L) int index = 1; // Verify detector user data and that we are not in packet context - assert(!(*UserData::check(L, DETECTOR, index))->validateParams.pkt); + assert(!(*UserData::check(L, DETECTOR, index))->validate_params.pkt); ApplicationId indicator = (ApplicationId)lua_tointeger(L, ++index); ApplicationId forecast = (ApplicationId)lua_tointeger(L, ++index); @@ -1642,10 +1640,9 @@ static int detector_add_af_application(lua_State* L) static int detector_add_url_application(lua_State* L) { int index = 1; - const char* tmpString; // Verify detector user data and that we are not in packet context - assert(!(*UserData::check(L, DETECTOR, index))->validateParams.pkt); + assert(!(*UserData::check(L, DETECTOR, index))->validate_params.pkt); uint32_t service_id = lua_tointeger(L, ++index); uint32_t client_app = lua_tointeger(L, ++index); @@ -1654,50 +1651,50 @@ static int detector_add_url_application(lua_State* L) /*uint32_t payload_type =*/ lua_tointeger(L, ++index); /* Verify that host pattern is a valid string */ - size_t hostPatternSize = 0; - uint8_t* hostPattern = nullptr; - tmpString = lua_tolstring(L, ++index, &hostPatternSize); - if (!tmpString || !hostPatternSize) + size_t host_pattern_size = 0; + uint8_t* host_pattern = nullptr; + const char* tmp_string = lua_tolstring(L, ++index, &host_pattern_size); + if (!tmp_string || !host_pattern_size) { ErrorMessage("Invalid host pattern string."); return 0; } else - hostPattern = (uint8_t*)snort_strdup(tmpString); + host_pattern = (uint8_t*)snort_strdup(tmp_string); /* Verify that path pattern is a valid string */ - size_t pathPatternSize = 0; - uint8_t* pathPattern = nullptr; - tmpString = lua_tolstring(L, ++index, &pathPatternSize); - if (!tmpString || !pathPatternSize ) + size_t path_pattern_size = 0; + uint8_t* path_pattern = nullptr; + tmp_string = lua_tolstring(L, ++index, &path_pattern_size); + if (!tmp_string || !path_pattern_size ) { ErrorMessage("Invalid path pattern string."); - snort_free(hostPattern); + snort_free(host_pattern); return 0; } else - pathPattern = (uint8_t*)snort_strdup(tmpString); + path_pattern = (uint8_t*)snort_strdup(tmp_string); /* Verify that scheme pattern is a valid string */ size_t schemePatternSize; uint8_t* schemePattern = nullptr; - tmpString = lua_tolstring(L, ++index, &schemePatternSize); - if (!tmpString || !schemePatternSize ) + tmp_string = lua_tolstring(L, ++index, &schemePatternSize); + if (!tmp_string || !schemePatternSize ) { ErrorMessage("Invalid scheme pattern string."); - snort_free(pathPattern); - snort_free(hostPattern); + snort_free(path_pattern); + snort_free(host_pattern); return 0; } else - schemePattern = (uint8_t*)snort_strdup(tmpString); + schemePattern = (uint8_t*)snort_strdup(tmp_string); /* Verify that query pattern is a valid string */ - size_t queryPatternSize; - uint8_t* queryPattern = nullptr; - tmpString = lua_tolstring(L, ++index, &queryPatternSize); - if (tmpString && queryPatternSize) - queryPattern = (uint8_t*)snort_strdup(tmpString); + size_t query_pattern_size; + uint8_t* query_pattern = nullptr; + tmp_string = lua_tolstring(L, ++index, &query_pattern_size); + if (tmp_string && query_pattern_size) + query_pattern = (uint8_t*)snort_strdup(tmp_string); uint32_t appId = lua_tointeger(L, ++index); AppInfoManager& app_info_manager = AppInfoManager::get_instance(); @@ -1707,12 +1704,12 @@ static int detector_add_url_application(lua_State* L) pattern->userData.client_app = app_info_manager.get_appid_by_client_id(client_app); pattern->userData.payload = app_info_manager.get_appid_by_payload_id(payload); pattern->userData.appId = appId; - pattern->userData.query.pattern = queryPattern; - pattern->userData.query.patternSize = queryPatternSize; - pattern->patterns.host.pattern = hostPattern; - pattern->patterns.host.patternSize = (int)hostPatternSize; - pattern->patterns.path.pattern = pathPattern; - pattern->patterns.path.patternSize = (int)pathPatternSize; + pattern->userData.query.pattern = query_pattern; + pattern->userData.query.patternSize = query_pattern_size; + pattern->patterns.host.pattern = host_pattern; + pattern->patterns.host.patternSize = (int)host_pattern_size; + pattern->patterns.path.pattern = path_pattern; + pattern->patterns.path.patternSize = (int)path_pattern_size; pattern->patterns.scheme.pattern = schemePattern; pattern->patterns.scheme.patternSize = (int)schemePatternSize; HttpPatternMatchers::get_instance()->insert_url_pattern(pattern); @@ -1728,10 +1725,9 @@ static int detector_add_url_application(lua_State* L) static int detector_add_rtmp_url(lua_State* L) { int index = 1; - const char* tmpString; // Verify detector user data and that we are not in packet context - assert(!(*UserData::check(L, DETECTOR, index))->validateParams.pkt); + assert(!(*UserData::check(L, DETECTOR, index))->validate_params.pkt); uint32_t service_id = lua_tointeger(L, ++index); uint32_t client_app = lua_tointeger(L, ++index); @@ -1740,44 +1736,44 @@ static int detector_add_rtmp_url(lua_State* L) /*uint32_t payload_type =*/ lua_tointeger(L, ++index); /* Verify that host pattern is a valid string */ - size_t hostPatternSize = 0; - tmpString = lua_tolstring(L, ++index, &hostPatternSize); - if (!tmpString || !hostPatternSize) + size_t host_pattern_size = 0; + const char* tmp_string = lua_tolstring(L, ++index, &host_pattern_size); + if (!tmp_string || !host_pattern_size) { ErrorMessage("Invalid host pattern string."); return 0; } - uint8_t* hostPattern = (uint8_t*)snort_strdup(tmpString); + uint8_t* host_pattern = (uint8_t*)snort_strdup(tmp_string); /* Verify that path pattern is a valid string */ - size_t pathPatternSize = 0; - tmpString = lua_tolstring(L, ++index, &pathPatternSize); - if (!tmpString || !pathPatternSize) + size_t path_pattern_size = 0; + tmp_string = lua_tolstring(L, ++index, &path_pattern_size); + if (!tmp_string || !path_pattern_size) { ErrorMessage("Invalid path pattern string."); - snort_free(hostPattern); + snort_free(host_pattern); return 0; } - uint8_t* pathPattern = (uint8_t*)snort_strdup(tmpString); + uint8_t* path_pattern = (uint8_t*)snort_strdup(tmp_string); /* Verify that scheme pattern is a valid string */ size_t schemePatternSize; - tmpString = lua_tolstring(L, ++index, &schemePatternSize); - if (!tmpString || !schemePatternSize) + tmp_string = lua_tolstring(L, ++index, &schemePatternSize); + if (!tmp_string || !schemePatternSize) { ErrorMessage("Invalid scheme pattern string."); - snort_free(pathPattern); - snort_free(hostPattern); + snort_free(path_pattern); + snort_free(host_pattern); return 0; } - uint8_t* schemePattern = (uint8_t*)snort_strdup(tmpString); + uint8_t* schemePattern = (uint8_t*)snort_strdup(tmp_string); /* Verify that query pattern is a valid string */ - size_t queryPatternSize; - uint8_t* queryPattern = nullptr; - tmpString = lua_tolstring(L, ++index, &queryPatternSize); - if (tmpString && queryPatternSize) - queryPattern = (uint8_t*)snort_strdup(tmpString); + size_t query_pattern_size; + uint8_t* query_pattern = nullptr; + tmp_string = lua_tolstring(L, ++index, &query_pattern_size); + if (tmp_string && query_pattern_size) + query_pattern = (uint8_t*)snort_strdup(tmp_string); uint32_t appId = lua_tointeger(L, ++index); @@ -1791,12 +1787,12 @@ static int detector_add_rtmp_url(lua_State* L) pattern->userData.client_app = client_app; pattern->userData.payload = payload; pattern->userData.appId = appId; - pattern->userData.query.pattern = queryPattern; - pattern->userData.query.patternSize = queryPatternSize; - pattern->patterns.host.pattern = hostPattern; - pattern->patterns.host.patternSize = (int)hostPatternSize; - pattern->patterns.path.pattern = pathPattern; - pattern->patterns.path.patternSize = (int)pathPatternSize; + pattern->userData.query.pattern = query_pattern; + pattern->userData.query.patternSize = query_pattern_size; + pattern->patterns.host.pattern = host_pattern; + pattern->patterns.host.patternSize = (int)host_pattern_size; + pattern->patterns.path.pattern = path_pattern; + pattern->patterns.path.patternSize = (int)path_pattern_size; pattern->patterns.scheme.pattern = schemePattern; pattern->patterns.scheme.patternSize = (int)schemePatternSize; HttpPatternMatchers::get_instance()->insert_rtmp_url_pattern(pattern); @@ -1816,7 +1812,7 @@ static int detector_add_sip_user_agent(lua_State* L) int index = 1; // Verify detector user data and that we are not in packet context - assert(!(*UserData::check(L, DETECTOR, index))->validateParams.pkt); + assert(!(*UserData::check(L, DETECTOR, index))->validate_params.pkt); uint32_t client_app = lua_tointeger(L, ++index); const char* clientVersion = lua_tostring(L, ++index); @@ -1844,41 +1840,36 @@ static int detector_add_sip_user_agent(lua_State* L) static int create_custom_application(lua_State* L) { int index = 1; - const char* tmpString; // Verify detector user data and that we are not in packet context - assert(!(*UserData::check(L, DETECTOR, index))->validateParams.pkt); + assert(!(*UserData::check(L, DETECTOR, index))->validate_params.pkt); /* Verify that host pattern is a valid string */ size_t appNameLen = 0; - tmpString = lua_tolstring(L, ++index, &appNameLen); - if (!tmpString || !appNameLen) + const char* tmp_string = lua_tolstring(L, ++index, &appNameLen); + if (!tmp_string || !appNameLen) { ErrorMessage("Invalid appName string."); lua_pushnumber(L, APP_ID_NONE); return 1; /*number of results */ } - AppInfoTableEntry* entry = AppInfoManager::get_instance().add_dynamic_app_entry(tmpString); - + AppInfoTableEntry* entry = AppInfoManager::get_instance().add_dynamic_app_entry(tmp_string); if (entry) - { lua_pushnumber(L, entry->appId); - return 1; /*number of results */ - } - - lua_pushnumber(L, APP_ID_NONE); + else + lua_pushnumber(L, APP_ID_NONE); return 1; /*number of results */ } static int add_client_application(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.pkt); - unsigned int serviceAppId = lua_tonumber(L, 2); - unsigned int clientAppId = lua_tonumber(L, 3); + assert(ud->validate_params.pkt); + unsigned int service_app_id = lua_tonumber(L, 2); + unsigned int client_app_id = lua_tonumber(L, 3); - ud->add_app(ud->validateParams.asd, serviceAppId, clientAppId, ""); + ud->add_app(ud->validate_params.asd, service_app_id, client_app_id, ""); lua_pushnumber(L, 0); return 1; } @@ -1887,7 +1878,7 @@ static int add_client_application(lua_State* L) * * @param Lua_State* - Lua state variable. * @param detector/stack - detector object - * @param serviceId/stack - id of service postively identified on this flow. + * @param service_id/stack - id of service postively identified on this flow. * @param vendorName/stack - name of vendor of service. This is optional. * @param version/stack - version of service. This is optional. * @return int - Number of elements on stack, which is always 1. @@ -1896,14 +1887,14 @@ static int add_client_application(lua_State* L) static int add_service_application(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.pkt && ud->validateParams.asd); - unsigned serviceId = lua_tonumber(L, 2); + assert(ud->validate_params.pkt && ud->validate_params.asd); + unsigned service_id = lua_tonumber(L, 2); - /*Phase2 - discuss RNAServiceSubtype will be maintained on lua side therefore the last + /*Phase2 - discuss AppIdServiceSubtype will be maintained on lua side therefore the last parameter on the following call is nullptr. Subtype is not displayed on DC at present. */ - unsigned retValue = ud->add_service(ud->validateParams.asd, ud->validateParams.pkt, - ud->validateParams.dir, serviceId, nullptr, nullptr, nullptr); + unsigned retValue = ud->add_service(ud->validate_params.asd, ud->validate_params.pkt, + ud->validate_params.dir, service_id, nullptr, nullptr, nullptr); lua_pushnumber(L, retValue); return 1; @@ -1912,10 +1903,10 @@ static int add_service_application(lua_State* L) static int add_payload_application(lua_State* L) { auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.asd); + assert(ud->validate_params.asd); - unsigned int payloadAppId = lua_tonumber(L, 2); - ud->add_payload(ud->validateParams.asd, payloadAppId); + unsigned payload_app_id = lua_tonumber(L, 2); + ud->add_payload(ud->validate_params.asd, payload_app_id); lua_pushnumber(L, 0); return 1; @@ -1926,11 +1917,11 @@ static int add_http_pattern(lua_State* L) int index = 1; // Verify detector user data and that we are not in packet context - assert(!(*UserData::check(L, DETECTOR, index))->validateParams.pkt); + assert(!(*UserData::check(L, DETECTOR, index))->validate_params.pkt); /* Verify valid pattern type */ - enum httpPatternType pType = (enum httpPatternType)lua_tointeger(L, ++index); - if (pType < HTTP_PAYLOAD || pType > HTTP_URL) + enum httpPatternType pat_type = (enum httpPatternType)lua_tointeger(L, ++index); + if (pat_type < HTTP_PAYLOAD || pat_type > HTTP_URL) { ErrorMessage("Invalid HTTP pattern type."); return 0; @@ -1944,9 +1935,9 @@ static int add_http_pattern(lua_State* L) return 0; } - uint32_t serviceAppId = lua_tointeger(L, ++index); - uint32_t clienAppId = lua_tointeger(L, ++index); - uint32_t payloadAppId = lua_tointeger(L, ++index); + uint32_t service_app_id = lua_tointeger(L, ++index); + uint32_t client_app_id = lua_tointeger(L, ++index); + uint32_t payload_app_id = lua_tointeger(L, ++index); /* Verify that pattern is a valid string */ size_t pattern_size = 0; @@ -1959,20 +1950,20 @@ static int add_http_pattern(lua_State* L) } HTTPListElement* element = (HTTPListElement*)snort_calloc(sizeof(HTTPListElement)); - DetectorHTTPPattern* pattern = &element->detectorHTTPPattern; + DetectorHTTPPattern* pattern = &element->detector_http_pattern; pattern->seq = seq; - pattern->service_id = serviceAppId; - pattern->client_app = clienAppId; - pattern->payload = payloadAppId; + pattern->service_id = service_app_id; + pattern->client_app = client_app_id; + pattern->payload = payload_app_id; pattern->pattern = pattern_str; pattern->pattern_size = (int)pattern_size; pattern->appId = APP_ID_NONE; - HttpPatternMatchers::get_instance()->insert_http_pattern_element(pType, element); + HttpPatternMatchers::get_instance()->insert_http_pattern_element(pat_type, element); AppInfoManager& app_info_manager = AppInfoManager::get_instance(); - app_info_manager.set_app_info_active(serviceAppId); - app_info_manager.set_app_info_active(clienAppId); - app_info_manager.set_app_info_active(payloadAppId); + app_info_manager.set_app_info_active(service_app_id); + app_info_manager.set_app_info_active(client_app_id); + app_info_manager.set_app_info_active(payload_app_id); return 0; } @@ -1980,72 +1971,71 @@ static int add_http_pattern(lua_State* L) static int add_url_pattern(lua_State* L) { int index = 1; - const char* tmpString; // Verify detector user data and that we are not in packet context - assert(!(*UserData::check(L, DETECTOR, index))->validateParams.pkt); + assert(!(*UserData::check(L, DETECTOR, index))->validate_params.pkt); - uint32_t serviceAppId = lua_tointeger(L, ++index); + uint32_t service_app_id = lua_tointeger(L, ++index); uint32_t clienAppId = lua_tointeger(L, ++index); - uint32_t payloadAppId = lua_tointeger(L, ++index); + uint32_t payload_app_id = lua_tointeger(L, ++index); /* Verify that host pattern is a valid string */ - size_t hostPatternSize = 0; - uint8_t* hostPattern = nullptr; - tmpString = lua_tolstring(L, ++index, &hostPatternSize); - if ( !tmpString || !hostPatternSize ) + size_t host_pattern_size = 0; + uint8_t* host_pattern = nullptr; + const char* tmp_string = lua_tolstring(L, ++index, &host_pattern_size); + if ( !tmp_string || !host_pattern_size ) { ErrorMessage("Invalid host pattern string."); return 0; } - hostPattern = (uint8_t* )snort_strdup(tmpString); + host_pattern = (uint8_t* )snort_strdup(tmp_string); /* Verify that path pattern is a valid string */ - size_t pathPatternSize = 0; - uint8_t* pathPattern = nullptr; - tmpString = lua_tolstring(L, ++index, &pathPatternSize); - if ( !tmpString || !pathPatternSize ) + size_t path_pattern_size = 0; + uint8_t* path_pattern = nullptr; + tmp_string = lua_tolstring(L, ++index, &path_pattern_size); + if ( !tmp_string || !path_pattern_size ) { ErrorMessage("Invalid path pattern string."); - snort_free(hostPattern); + snort_free(host_pattern); return 0; } - pathPattern = (uint8_t*)snort_strdup(tmpString); + path_pattern = (uint8_t*)snort_strdup(tmp_string); /* Verify that scheme pattern is a valid string */ size_t schemePatternSize; uint8_t* schemePattern = nullptr; - tmpString = lua_tolstring(L, ++index, &schemePatternSize); - if (!tmpString || !schemePatternSize) + tmp_string = lua_tolstring(L, ++index, &schemePatternSize); + if (!tmp_string || !schemePatternSize) { ErrorMessage("Invalid scheme pattern string."); - snort_free(pathPattern); - snort_free(hostPattern); + snort_free(path_pattern); + snort_free(host_pattern); return 0; } - schemePattern = (uint8_t*)snort_strdup(tmpString); + schemePattern = (uint8_t*)snort_strdup(tmp_string); /* Allocate memory for data structures */ DetectorAppUrlPattern* pattern = (DetectorAppUrlPattern*)snort_calloc(sizeof(DetectorAppUrlPattern)); - pattern->userData.service_id = serviceAppId; + pattern->userData.service_id = service_app_id; pattern->userData.client_app = clienAppId; - pattern->userData.payload = payloadAppId; + pattern->userData.payload = payload_app_id; pattern->userData.appId = APP_ID_NONE; pattern->userData.query.pattern = nullptr; pattern->userData.query.patternSize = 0; - pattern->patterns.host.pattern = hostPattern; - pattern->patterns.host.patternSize = (int)hostPatternSize; - pattern->patterns.path.pattern = pathPattern; - pattern->patterns.path.patternSize = (int)pathPatternSize; + pattern->patterns.host.pattern = host_pattern; + pattern->patterns.host.patternSize = (int)host_pattern_size; + pattern->patterns.path.pattern = path_pattern; + pattern->patterns.path.patternSize = (int)path_pattern_size; pattern->patterns.scheme.pattern = schemePattern; pattern->patterns.scheme.patternSize = (int)schemePatternSize; HttpPatternMatchers::get_instance()->insert_app_url_pattern(pattern); AppInfoManager& app_info_manager = AppInfoManager::get_instance(); - app_info_manager.set_app_info_active(serviceAppId); + app_info_manager.set_app_info_active(service_app_id); app_info_manager.set_app_info_active(clienAppId); - app_info_manager.set_app_info_active(payloadAppId); + app_info_manager.set_app_info_active(payload_app_id); return 0; } @@ -2077,7 +2067,7 @@ static int add_port_pattern_client(lua_State* L) if (appId <= APP_ID_NONE || !pattern || !patternSize || (protocol != IpProtocol::TCP && protocol != IpProtocol::UDP)) { - ErrorMessage("addPortPatternClient(): Invalid input in %s\n", ud->name.c_str()); + ErrorMessage("addPortPatternClient(): Invalid input in %s\n", ud->get_name().c_str()); return 0; } @@ -2089,7 +2079,7 @@ static int add_port_pattern_client(lua_State* L) memcpy(pPattern->pattern, pattern, patternSize); pPattern->length = patternSize; pPattern->offset = position; - pPattern->detectorName = snort_strdup(ud->name.c_str()); + pPattern->detectorName = snort_strdup(ud->get_name().c_str()); PatternClientDetector::insert_client_port_pattern(pPattern); AppInfoManager::get_instance().set_app_info_active(appId); @@ -2130,7 +2120,7 @@ static int add_port_pattern_service(lua_State* L) memcpy(pPattern->pattern, pattern, patternSize); pPattern->length = patternSize; pPattern->offset = position; - pPattern->detectorName = snort_strdup(ud->name.c_str()); + pPattern->detectorName = snort_strdup(ud->get_name().c_str()); PatternServiceDetector::insert_service_port_pattern(pPattern); AppInfoManager::get_instance().set_app_info_active(appId); @@ -2143,7 +2133,7 @@ static int detector_add_sip_server(lua_State* L) int index = 1; // Verify detector user data and that we are not in packet context - assert(!(*UserData::check(L, DETECTOR, index))->validateParams.pkt); + assert(!(*UserData::check(L, DETECTOR, index))->validate_params.pkt); uint32_t client_app = lua_tointeger(L, ++index); const char* clientVersion = lua_tostring(L, ++index); @@ -2198,7 +2188,7 @@ static int create_future_flow(lua_State* L) SfIp server_addr; int16_t snort_app_id = 0; auto& ud = *UserData::check(L, DETECTOR, 1); - assert(ud->validateParams.pkt); + assert(ud->validate_params.pkt); char* pattern = (char*)lua_tostring(L, 2); if (!convert_string_to_address(pattern, &client_addr)) @@ -2225,12 +2215,12 @@ static int create_future_flow(lua_State* L) snort_app_id = entry->snortId; } - AppIdSession* fp = AppIdSession::create_future_session(ud->validateParams.pkt, &client_addr, + AppIdSession* fp = AppIdSession::create_future_session(ud->validate_params.pkt, &client_addr, client_port, &server_addr, server_port, proto, snort_app_id, APPID_EARLY_SESSION_FLAG_FW_RULE); if (fp) { - fp->serviceAppId = service_app_id; + fp->service_app_id = service_app_id; fp->client_app_id = client_app_id; fp->payload_app_id = payload_app_id; fp->set_session_flags(APPID_SESSION_SERVICE_DETECTED | APPID_SESSION_NOT_A_SERVICE | @@ -2428,41 +2418,41 @@ int register_detector(lua_State* L) LuaDetector::~LuaDetector() { // release the reference of the userdata on the lua side - if ( detectorUserDataRef != LUA_REFNIL ) - luaL_unref(myLuaState, LUA_REGISTRYINDEX, detectorUserDataRef); + if ( detector_user_data_ref != LUA_REFNIL ) + luaL_unref(my_lua_state, LUA_REGISTRYINDEX, detector_user_data_ref); } int LuaDetector::lua_validate(AppIdDiscoveryArgs& args) { Profile lua_detector_context(luaCustomPerfStats); - validateParams.data = args.data; - validateParams.size = args.size; - validateParams.dir = args.dir; - validateParams.asd = args.asd; - validateParams.pkt = args.pkt; - const char* validateFn = packageInfo.validateFunctionName.c_str(); + validate_params.data = args.data; + validate_params.size = args.size; + validate_params.dir = args.dir; + validate_params.asd = args.asd; + validate_params.pkt = args.pkt; + const char* validateFn = package_info.validateFunctionName.c_str(); - if ( (!validateFn) || !lua_checkstack(myLuaState, 1) ) + if ( (!validateFn) || !lua_checkstack(my_lua_state, 1) ) { ErrorMessage("lua detector %s: invalid LUA %s\n", - packageInfo.name.c_str(), lua_tostring(myLuaState, -1)); - validateParams.pkt = nullptr; + package_info.name.c_str(), lua_tostring(my_lua_state, -1)); + validate_params.pkt = nullptr; return APPID_ENULL; } - lua_getglobal(myLuaState, validateFn); + lua_getglobal(my_lua_state, validateFn); DebugFormat(DEBUG_APPID, "lua detector %s validating: Lua Memory usage %d\n", - packageInfo.name.c_str(), lua_gc(myLuaState, LUA_GCCOUNT, 0)); + package_info.name.c_str(), lua_gc(my_lua_state, LUA_GCCOUNT, 0)); - if ( lua_pcall(myLuaState, 0, 1, 0) ) + if ( lua_pcall(my_lua_state, 0, 1, 0) ) { // Runtime Lua errors are suppressed in production code since detectors are written for // efficiency and with defensive minimum checks. Errors are dealt as exceptions // that dont impact processing by other detectors or future packets by the same detector. ErrorMessage("lua detector %s: error validating %s\n", - packageInfo.name.c_str(), lua_tostring(myLuaState, -1)); - validateParams.pkt = nullptr; + package_info.name.c_str(), lua_tostring(my_lua_state, -1)); + validate_params.pkt = nullptr; return APPID_ENULL; } @@ -2470,17 +2460,17 @@ int LuaDetector::lua_validate(AppIdDiscoveryArgs& args) LuaDetectorManager::free_detector_flows(); /* retrieve result */ - if ( !lua_isnumber(myLuaState, -1) ) + if ( !lua_isnumber(my_lua_state, -1) ) { - ErrorMessage("lua detector %s: returned non-numeric value\n", packageInfo.name.c_str()); - validateParams.pkt = nullptr; + ErrorMessage("lua detector %s: returned non-numeric value\n", package_info.name.c_str()); + validate_params.pkt = nullptr; return APPID_ENULL; } - int rc = lua_tonumber(myLuaState, -1); - lua_pop(myLuaState, 1); - DebugFormat(DEBUG_APPID, "lua detector %s: status: %d\n", packageInfo.name.c_str(), rc); - validateParams.pkt = nullptr; + int rc = lua_tonumber(my_lua_state, -1); + lua_pop(my_lua_state, 1); + DebugFormat(DEBUG_APPID, "lua detector %s: status: %d\n", package_info.name.c_str(), rc); + validate_params.pkt = nullptr; return rc; } diff --git a/src/network_inspectors/appid/lua_detector_api.h b/src/network_inspectors/appid/lua_detector_api.h index dc8e1b670..b45998b28 100644 --- a/src/network_inspectors/appid/lua_detector_api.h +++ b/src/network_inspectors/appid/lua_detector_api.h @@ -64,12 +64,12 @@ public: LuaDetector() { } virtual ~LuaDetector(); - ValidateParameters validateParams; - lua_State* myLuaState= nullptr; - int detectorUserDataRef = 0; // key into LUA_REGISTRYINDEX - DetectorPackageInfo packageInfo; + ValidateParameters validate_params; + lua_State* my_lua_state= nullptr; + int detector_user_data_ref = 0; // key into LUA_REGISTRYINDEX + DetectorPackageInfo package_info; bool is_client = false; - unsigned int serviceId = APP_ID_UNKNOWN; + unsigned int service_id = APP_ID_UNKNOWN; int lua_validate(AppIdDiscoveryArgs&); }; diff --git a/src/network_inspectors/appid/lua_detector_flow_api.cc b/src/network_inspectors/appid/lua_detector_flow_api.cc index 938104160..fd3ced9a3 100644 --- a/src/network_inspectors/appid/lua_detector_flow_api.cc +++ b/src/network_inspectors/appid/lua_detector_flow_api.cc @@ -158,7 +158,7 @@ static int create_detector_flow(lua_State* L) SfIp daddr; auto& detector_data = *UserData::check(L, DETECTOR, 1); - assert(detector_data->validateParams.pkt); + assert(detector_data->validate_params.pkt); char* pattern = (char*)lua_tostring(L, 2); size_t patternLen = lua_strlen (L, 2); @@ -208,7 +208,7 @@ static int create_detector_flow(lua_State* L) LuaDetectorManager::add_detector_flow(detector_flow); - detector_flow->asd = AppIdSession::create_future_session(detector_data->validateParams.pkt, + detector_flow->asd = AppIdSession::create_future_session(detector_data->validate_params.pkt, &saddr, sport, &daddr, dport, proto, 0, 0); if (!detector_flow->asd) diff --git a/src/network_inspectors/appid/lua_detector_module.cc b/src/network_inspectors/appid/lua_detector_module.cc index c963feb71..4223111fc 100644 --- a/src/network_inspectors/appid/lua_detector_module.cc +++ b/src/network_inspectors/appid/lua_detector_module.cc @@ -96,7 +96,6 @@ static lua_State* create_lua_state(AppIdModuleConfig* mod_config) register_detector_flow_api(L); lua_pop(L, 1); - /*The garbage-collector pause controls how long the collector waits before starting a new cycle. Larger values make the collector less aggressive. Values smaller than 100 mean the collector will not wait to start a new @@ -113,12 +112,13 @@ static lua_State* create_lua_state(AppIdModuleConfig* mod_config) lua_gc(L, LUA_GCSETSTEPMUL, 200); char new_lua_path[PATH_MAX]; - lua_getglobal( L, "package" ); - lua_getfield( L, -1, "path" ); - const char * cur_lua_path = lua_tostring(L, -1); + lua_getglobal(L, "package"); + lua_getfield(L, -1, "path"); + const char* cur_lua_path = lua_tostring(L, -1); if (cur_lua_path && (strlen(cur_lua_path))) { - snprintf(new_lua_path, sizeof(new_lua_path) - 1, "%s;%s/odp/libs/?.lua;%s/custom/libs/?.lua", + snprintf(new_lua_path, sizeof(new_lua_path) - 1, + "%s;%s/odp/libs/?.lua;%s/custom/libs/?.lua", cur_lua_path, mod_config->app_detector_dir, mod_config->app_detector_dir); } else @@ -127,10 +127,10 @@ static lua_State* create_lua_state(AppIdModuleConfig* mod_config) mod_config->app_detector_dir, mod_config->app_detector_dir); } - lua_pop( L, 1 ); - lua_pushstring( L, new_lua_path); - lua_setfield( L, -2, "path" ); - lua_pop( L, 1 ); + lua_pop(L, 1); + lua_pushstring(L, new_lua_path); + lua_setfield(L, -2, "path"); + lua_pop(L, 1); return L; } @@ -147,17 +147,17 @@ LuaDetectorManager::~LuaDetectorManager() { for ( auto& detector : allocated_detectors ) { - auto L = detector->myLuaState; + auto L = detector->my_lua_state; - lua_getglobal(L, detector->packageInfo.cleanFunctionName.c_str()); + lua_getglobal(L, detector->package_info.cleanFunctionName.c_str()); if ( lua_isfunction(L, -1) ) { /*first parameter is DetectorUserData */ - lua_rawgeti(L, LUA_REGISTRYINDEX, detector->detectorUserDataRef); + lua_rawgeti(L, LUA_REGISTRYINDEX, detector->detector_user_data_ref); if ( lua_pcall(L, 1, 1, 0) ) { ErrorMessage("Could not cleanup the %s client app element: %s\n", - detector->packageInfo.name.c_str(), lua_tostring(L, -1)); + detector->package_info.name.c_str(), lua_tostring(L, -1)); } } } @@ -284,14 +284,14 @@ static LuaDetector* create_lua_detector(lua_State* L, const char* detectorName, LuaClientDetector* cd = new LuaClientDetector(&ClientDiscovery::get_instance(), detectorName, proto); cd->is_client = true; - cd->isCustom = is_custom; - cd->minimum_matches = cd->packageInfo.minimum_matches; - cd->packageInfo.client_detector = true; - get_lua_field(L, -1, "init", cd->packageInfo.initFunctionName); - get_lua_field(L, -1, "clean", cd->packageInfo.cleanFunctionName); - get_lua_field(L, -1, "validate", cd->packageInfo.validateFunctionName); - get_lua_field(L, -1, "minimum_matches", cd->packageInfo.minimum_matches); - cd->packageInfo.name = detector_name; + cd->set_custom_detector(is_custom); + cd->set_minimum_matches(cd->package_info.minimum_matches); + cd->package_info.client_detector = true; + get_lua_field(L, -1, "init", cd->package_info.initFunctionName); + get_lua_field(L, -1, "clean", cd->package_info.cleanFunctionName); + get_lua_field(L, -1, "validate", cd->package_info.validateFunctionName); + get_lua_field(L, -1, "minimum_matches", cd->package_info.minimum_matches); + cd->package_info.name = detector_name; detector = cd; lua_pop(L, 1); // pop client table } @@ -305,14 +305,14 @@ static LuaDetector* create_lua_detector(lua_State* L, const char* detectorName, LuaServiceDetector* sd = new LuaServiceDetector(&ServiceDiscovery::get_instance(), detectorName, proto); sd->is_client = false; - sd->isCustom = is_custom; - sd->serviceId = APP_ID_UNKNOWN; - sd->packageInfo.client_detector = false; - get_lua_field(L, -1, "init", sd->packageInfo.initFunctionName); - get_lua_field(L, -1, "clean", sd->packageInfo.cleanFunctionName); - get_lua_field(L, -1, "validate", sd->packageInfo.validateFunctionName); - get_lua_field(L, -1, "minimum_matches", sd->packageInfo.minimum_matches); - sd->packageInfo.name = detector_name; + sd->set_custom_detector(is_custom); + sd->service_id = APP_ID_UNKNOWN; + sd->package_info.client_detector = false; + get_lua_field(L, -1, "init", sd->package_info.initFunctionName); + get_lua_field(L, -1, "clean", sd->package_info.cleanFunctionName); + get_lua_field(L, -1, "validate", sd->package_info.validateFunctionName); + get_lua_field(L, -1, "minimum_matches", sd->package_info.minimum_matches); + sd->package_info.name = detector_name; detector = sd; } @@ -323,12 +323,12 @@ static LuaDetector* create_lua_detector(lua_State* L, const char* detectorName, if ( detector ) { - detector->myLuaState = L; + detector->my_lua_state = L; UserData::push(L, DETECTOR, detector); // add a lua reference so the detector doesn't get garbage-collected lua_pushvalue(L, -1); - detector->detectorUserDataRef = luaL_ref(L, LUA_REGISTRYINDEX); + detector->detector_user_data_ref = luaL_ref(L, LUA_REGISTRYINDEX); } return detector; @@ -399,25 +399,25 @@ void LuaDetectorManager::activate_lua_detectors() for ( auto ld : allocated_detectors ) { auto detector = static_cast(ld); - auto L = detector->myLuaState; + auto L = detector->my_lua_state; - lua_getglobal(L, detector->packageInfo.initFunctionName.c_str()); + lua_getglobal(L, detector->package_info.initFunctionName.c_str()); if (!lua_isfunction(L, -1)) { ErrorMessage("Detector %s: does not contain DetectorInit() function\n", - detector->name.c_str()); + detector->get_name().c_str()); return; } /*first parameter is DetectorUserData */ - lua_rawgeti(L, LUA_REGISTRYINDEX, detector->detectorUserDataRef); + lua_rawgeti(L, LUA_REGISTRYINDEX, detector->detector_user_data_ref); /*second parameter is a table containing configuration stuff. */ // ... which is empty.??? lua_newtable(L); if ( lua_pcall(L, 2, 1, 0) ) ErrorMessage("Could not initialize the %s client app element: %s\n", - detector->name.c_str(), lua_tostring(L, -1)); + detector->get_name().c_str(), lua_tostring(L, -1)); ++num_active_lua_detectors; } @@ -425,7 +425,7 @@ void LuaDetectorManager::activate_lua_detectors() lua_tracker_size = compute_lua_tracker_size(MAX_MEMORY_FOR_LUA_DETECTORS, num_active_lua_detectors); for ( auto& detector : allocated_detectors ) - set_lua_tracker_size(detector->myLuaState, lua_tracker_size); + set_lua_tracker_size(detector->my_lua_state, lua_tracker_size); } void LuaDetectorManager::list_lua_detectors() @@ -442,12 +442,12 @@ void LuaDetectorManager::list_lua_detectors() for ( auto& ld : allocated_detectors ) { const char* name; - mem = lua_gc(ld->myLuaState, LUA_GCCOUNT, 0); + mem = lua_gc(ld->my_lua_state, LUA_GCCOUNT, 0); totalMem += mem; if ( ld->is_client ) - name = static_cast(ld)->name.c_str(); + name = static_cast(ld)->get_name().c_str(); else - name = static_cast(ld)->name.c_str(); + name = static_cast(ld)->get_name().c_str(); LogMessage("\tDetector %s: Lua Memory usage %zu kb\n", name, mem); } diff --git a/src/network_inspectors/appid/service_plugins/service_bootp.cc b/src/network_inspectors/appid/service_plugins/service_bootp.cc index 48415b5bf..b30e22467 100644 --- a/src/network_inspectors/appid/service_plugins/service_bootp.cc +++ b/src/network_inspectors/appid/service_plugins/service_bootp.cc @@ -287,7 +287,7 @@ int BootpServiceDetector::validate(AppIdDiscoveryArgs& args) } success: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { asd->set_session_flags(APPID_SESSION_CONTINUE); add_service(asd, args.pkt, args.dir, APP_ID_DHCP, nullptr, nullptr, nullptr); @@ -296,14 +296,14 @@ success: return APPID_SUCCESS; inprocess: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { service_inprocess(asd, args.pkt, args.dir); } return APPID_INPROCESS; fail: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { fail_service(asd, args.pkt, args.dir); } @@ -311,7 +311,7 @@ fail: return APPID_NOMATCH; not_compatible: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { incompatible_data(asd, args.pkt, args.dir); } diff --git a/src/network_inspectors/appid/service_plugins/service_detector.cc b/src/network_inspectors/appid/service_plugins/service_detector.cc index 777fe0eb4..0bccb5ce1 100644 --- a/src/network_inspectors/appid/service_plugins/service_detector.cc +++ b/src/network_inspectors/appid/service_plugins/service_detector.cc @@ -42,11 +42,6 @@ ServiceDetector::ServiceDetector() flow_data_index = service_module_index++ | APPID_SESSION_DATA_SERVICE_MODSTATE_BIT; } -int ServiceDetector::validate(AppIdDiscoveryArgs&) -{ - return APPID_SUCCESS; -} - void ServiceDetector::register_appid(AppId appId, unsigned extractsInfo) { AppInfoTableEntry* pEntry = AppInfoManager::get_instance().get_app_info_entry(appId); @@ -93,18 +88,18 @@ int ServiceDetector::add_service(AppIdSession* asd, const Packet* pkt, int dir, if (vendor) { - if (asd->serviceVendor) - snort_free(asd->serviceVendor); - asd->serviceVendor = snort_strdup(vendor); + if (asd->service_vendor) + snort_free(asd->service_vendor); + asd->service_vendor = snort_strdup(vendor); } if (version) { - if (asd->serviceVersion) - snort_free(asd->serviceVersion); - asd->serviceVersion = snort_strdup(version); + if (asd->service_version) + snort_free(asd->service_version); + asd->service_version = snort_strdup(version); } - asd->set_session_flags(APPID_SESSION_SERVICE_DETECTED); - asd->serviceAppId = appId; + asd->set_service_detected(); + asd->service_app_id = appId; if (asd->get_session_flags(APPID_SESSION_IGNORE_HOST)) return APPID_SUCCESS; @@ -140,30 +135,31 @@ int ServiceDetector::add_service(AppIdSession* asd, const Packet* pkt, int dir, asd->service_ip = *ip; asd->service_port = port; - ServiceDiscoveryState* sds = AppIdServiceState::get(ip, asd->protocol, port, asd->is_decrypted()); + ServiceDiscoveryState* sds = AppIdServiceState::get(ip, asd->protocol, port, + asd->is_decrypted()); if ( !sds ) - sds = AppIdServiceState::add(ip, asd->protocol, port, asd->is_decrypted()); + sds = AppIdServiceState::add(ip, asd->protocol, port, asd->is_decrypted()); sds->set_service_id_valid(this); return APPID_SUCCESS; } int ServiceDetector::add_service_consume_subtype(AppIdSession* asd, const Packet* pkt, int dir, - AppId appId, const char* vendor, const char* version, RNAServiceSubtype* subtype) + AppId appId, const char* vendor, const char* version, AppIdServiceSubtype* subtype) { asd->subtype = subtype; return add_service(asd, pkt, dir, appId, vendor, version); } int ServiceDetector::add_service(AppIdSession* asd, const Packet* pkt, int dir, AppId appId, - const char* vendor, const char* version, const RNAServiceSubtype* subtype) + const char* vendor, const char* version, const AppIdServiceSubtype* subtype) { - RNAServiceSubtype* new_subtype = nullptr; + AppIdServiceSubtype* new_subtype = nullptr; for (; subtype; subtype = subtype->next) { - RNAServiceSubtype* tmp_subtype = (RNAServiceSubtype*)snort_calloc( - sizeof(RNAServiceSubtype)); + AppIdServiceSubtype* tmp_subtype = (AppIdServiceSubtype*)snort_calloc( + sizeof(AppIdServiceSubtype)); if (subtype->service) tmp_subtype->service = snort_strdup(subtype->service); diff --git a/src/network_inspectors/appid/service_plugins/service_detector.h b/src/network_inspectors/appid/service_plugins/service_detector.h index 5472e0eac..056401575 100644 --- a/src/network_inspectors/appid/service_plugins/service_detector.h +++ b/src/network_inspectors/appid/service_plugins/service_detector.h @@ -34,15 +34,14 @@ public: virtual ~ServiceDetector() { } virtual void do_custom_init() override { } - virtual int validate(AppIdDiscoveryArgs&) override; virtual void register_appid(AppId, unsigned extractsInfo) override; int service_inprocess(AppIdSession*, const Packet*, int dir); int add_service(AppIdSession*, const Packet*, int dir, AppId, const char* vendor, const char* version); int add_service(AppIdSession*, const Packet*, int dir, AppId, const char* vendor, - const char* version, const RNAServiceSubtype*); + const char* version, const AppIdServiceSubtype*); int add_service_consume_subtype(AppIdSession*, const Packet*, int dir, AppId, - const char* vendor, const char* version, RNAServiceSubtype*); + const char* vendor, const char* version, AppIdServiceSubtype*); int incompatible_data(AppIdSession*, const Packet*, int dir); int fail_service(AppIdSession*, const Packet*, int dir); diff --git a/src/network_inspectors/appid/service_plugins/service_discovery.cc b/src/network_inspectors/appid/service_plugins/service_discovery.cc index 960edd39b..29312ead1 100644 --- a/src/network_inspectors/appid/service_plugins/service_discovery.cc +++ b/src/network_inspectors/appid/service_plugins/service_discovery.cc @@ -76,7 +76,12 @@ #include "protocols/packet.h" #include "protocols/tcp.h" +#ifdef REG_TEST +#include "service_regtest.h" +#endif + static THREAD_LOCAL ServiceDetector* ftp_service = nullptr; + ProfileStats serviceMatchPerfStats; ServiceDiscovery::ServiceDiscovery() @@ -140,6 +145,11 @@ void ServiceDiscovery::initialize() new TftpServiceDetector(this); new TimbuktuServiceDetector(this); new TnsServiceDetector(this); +#ifdef REG_TEST + new RegTestServiceDetector(this); + new RegTestServiceDetector1(this); + new RegTestServiceDetector2(this); +#endif for ( auto kv : tcp_detectors ) kv.second->initialize(); @@ -177,7 +187,7 @@ int ServiceDiscovery::add_service_port(AppIdDetector* detector, const ServiceDet else { ErrorMessage("Invalid protocol (%u) specified for service %s.\n", - (unsigned)pp.proto, service->name.c_str()); + (unsigned)pp.proto, service->get_name().c_str()); return 0; } @@ -245,7 +255,8 @@ void ServiceDiscovery::match_services_by_pattern(AppIdSession* asd, const Packet if (patterns) { ServiceMatch* match_list = nullptr; - patterns->find_all((char*)pkt->data, pkt->dsize, &pattern_match, false, (void*)&match_list); + patterns->find_all((char*)pkt->data, pkt->dsize, &pattern_match, false, + (void*)&match_list); std::vector smOrderedList; for (ServiceMatch* sm = match_list; sm; sm = sm->next) @@ -335,34 +346,28 @@ void ServiceDiscovery::get_next_service(const Packet* p, const int dir, { auto proto = asd->protocol; - /* If NEW, just advance onto trying ports. */ - if (asd->service_search_state == SESSION_SERVICE_ID_STATE::START) + /* See if there are any port detectors to try. If not, move onto patterns. */ + if ( asd->service_search_state == SESSION_SERVICE_SEARCH_STATE::PORT ) { - asd->service_search_state = SESSION_SERVICE_ID_STATE::PORT; - sds->service = nullptr; + get_port_based_services(proto, + (dir == APP_ID_FROM_RESPONDER) ? p->ptrs.sp : p->ptrs.dp, asd); + asd->service_search_state = SESSION_SERVICE_SEARCH_STATE::PATTERN; } - /* See if there are any port detectors to try. If not, move onto patterns. */ - if (asd->service_search_state == SESSION_SERVICE_ID_STATE::PORT) - get_port_based_services(proto, (uint16_t)((dir == APP_ID_FROM_RESPONDER) ? p->ptrs.sp : - p->ptrs.dp), asd); - - asd->service_search_state = SESSION_SERVICE_ID_STATE::PATTERN; - - if (asd->service_search_state == SESSION_SERVICE_ID_STATE::PATTERN) + if ( asd->service_search_state == SESSION_SERVICE_SEARCH_STATE::PATTERN) { /* If we haven't found anything yet, try to see if we get any hits * first with UDP reversed services before moving onto pattern matches. */ if (dir == APP_ID_FROM_INITIATOR) { - if (!asd->get_session_flags(APPID_SESSION_ADDITIONAL_PACKET) + if ( !asd->get_session_flags(APPID_SESSION_ADDITIONAL_PACKET) && (proto == IpProtocol::UDP) && !asd->tried_reverse_service ) { asd->tried_reverse_service = true; ServiceDiscoveryState* rsds = AppIdServiceState::get(p->ptrs.ip_api.get_src(), proto, p->ptrs.sp, asd->is_decrypted()); - if ( rsds && rsds->service ) - asd->service_candidates.push_back(rsds->service); + if ( rsds && rsds->get_service() ) + asd->service_candidates.push_back(rsds->get_service()); else if ( udp_reversed_services[p->ptrs.sp].size() ) { asd->service_candidates.insert(asd->service_candidates.end(), @@ -379,12 +384,10 @@ void ServiceDiscovery::get_next_service(const Packet* p, const int dir, else { match_services_by_pattern(asd, p, proto); - sds->state = SERVICE_ID_STATE::SEARCHING_BRUTE_FORCE; + sds->set_state(SERVICE_ID_STATE::SEARCHING_BRUTE_FORCE); return; } } - - /* Don't do anything if it was in VALID or BRUTE FORCE. */ } int ServiceDiscovery::identify_service(AppIdSession* asd, Packet* p, int dir) @@ -395,14 +398,14 @@ int ServiceDiscovery::identify_service(AppIdSession* asd, Packet* p, int dir) /* Get packet info. */ auto proto = asd->protocol; - if (asd->service_ip.is_set()) + if ( asd->service_ip.is_set() ) { ip = &asd->service_ip; port = asd->service_port; } else { - if (dir == APP_ID_FROM_RESPONDER) + if ( dir == APP_ID_FROM_RESPONDER ) { ip = p->ptrs.ip_api.get_src(); port = p->ptrs.sp; @@ -414,60 +417,48 @@ int ServiceDiscovery::identify_service(AppIdSession* asd, Packet* p, int dir) } } - /* Get host tracker state. */ ServiceDiscoveryState* sds = AppIdServiceState::get(ip, proto, port, asd->is_decrypted()); if ( !sds ) sds = AppIdServiceState::add(ip, proto, port, asd->is_decrypted()); - if( asd->service_search_state == SESSION_SERVICE_ID_STATE::START ) + if ( asd->service_search_state == SESSION_SERVICE_SEARCH_STATE::START ) { - asd->service_search_state = SESSION_SERVICE_ID_STATE::PORT; + asd->service_search_state = SESSION_SERVICE_SEARCH_STATE::PORT; - if( sds->state == SERVICE_ID_STATE::FAILED ) + if ( sds->get_state() == SERVICE_ID_STATE::FAILED ) { fail_service(asd, p, dir, nullptr); return APPID_NOMATCH; } + if ( !asd->service_detector ) { /* If a valid service already exists in host tracker, give it a try. */ - if ( sds->state == SERVICE_ID_STATE::VALID ) - asd->service_detector = sds->service; - else if ( ( sds->state == SERVICE_ID_STATE::SEARCHING_BRUTE_FORCE ) - && (!asd->service_candidates.size() ) ) + if ( sds->get_state() == SERVICE_ID_STATE::VALID ) + asd->service_detector = sds->get_service(); + else if ( !asd->service_candidates.size() ) { - if (!sds->brute_force_mgr) - sds->brute_force_mgr = new AppIdDetectorList(proto); - - sds->service = sds->brute_force_mgr->next(); - if( sds->service ) - asd->service_detector = sds->service; - else - sds->state = SERVICE_ID_STATE::FAILED; + asd->service_detector = sds->select_detector_by_brute_force(proto); } } } AppIdDiscoveryArgs args(p->data, p->dsize, dir, asd, p); - args.config = asd->config; - args.session_logging_enabled = asd->session_logging_enabled; - args.session_logging_id = asd->session_logging_id; - - /* If we already have a service to try, then try it out. */ - if (asd->service_detector) + if ( asd->service_detector ) { ret = asd->service_detector->validate(args); if (ret == APPID_NOT_COMPATIBLE) asd->got_incompatible_services = true; if (asd->session_logging_enabled) LogMessage("AppIdDbg %s %s returned %d\n", asd->session_logging_id, - asd->service_detector->name.c_str(), ret); + asd->service_detector->get_name().c_str(), ret); } else { /* See if we've got more detector(s) to add to the candidate list. */ - if ( (asd->service_search_state == PORT) - || ((asd->service_search_state == PATTERN) && (dir == APP_ID_FROM_RESPONDER)) ) + if ( ( asd->service_search_state == SESSION_SERVICE_SEARCH_STATE::PORT ) + || ( ( asd->service_search_state == SESSION_SERVICE_SEARCH_STATE::PATTERN ) + && (dir == APP_ID_FROM_RESPONDER ) ) ) { get_next_service(p, dir, asd, sds); } @@ -481,13 +472,13 @@ int ServiceDiscovery::identify_service(AppIdSession* asd, Packet* p, int dir) int result; result = service->validate(args); - if (result == APPID_NOT_COMPATIBLE) + if ( result == APPID_NOT_COMPATIBLE ) asd->got_incompatible_services = true; - if (asd->session_logging_enabled) + if ( asd->session_logging_enabled ) LogMessage("AppIdDbg %s %s returned %d\n", - asd->session_logging_id, service->name.c_str(), result); + asd->session_logging_id, service->get_name().c_str(), result); - if (result == APPID_SUCCESS) + if ( result == APPID_SUCCESS ) { ret = APPID_SUCCESS; asd->service_detector = service; @@ -501,10 +492,10 @@ int ServiceDiscovery::identify_service(AppIdSession* asd, Packet* p, int dir) } /* If we tried everything and found nothing, then fail. */ - if (ret != APPID_SUCCESS) + if ( ret != APPID_SUCCESS ) { - if ( (asd->service_candidates.size() == 0) - && (sds->state == SERVICE_ID_STATE::SEARCHING_BRUTE_FORCE) ) + if ( ( asd->service_candidates.size() == 0 ) + && ( sds->get_state() == SERVICE_ID_STATE::SEARCHING_BRUTE_FORCE ) ) { fail_service(asd, p, dir, nullptr); ret = APPID_NOMATCH; @@ -512,11 +503,11 @@ int ServiceDiscovery::identify_service(AppIdSession* asd, Packet* p, int dir) } } - if (asd->service_detector != nullptr) + if ( asd->service_detector ) { - sds->reset_time = 0; + sds->set_reset_time(0); } - else if (dir == APP_ID_FROM_RESPONDER) // bidirectional exchange unknown service + else if ( dir == APP_ID_FROM_RESPONDER ) // bidirectional exchange unknown service { if (asd->session_logging_enabled) LogMessage("AppIdDbg %s no RNA service detector\n", asd->session_logging_id); @@ -526,7 +517,7 @@ int ServiceDiscovery::identify_service(AppIdSession* asd, Packet* p, int dir) } /* Handle failure exception cases in states. */ - if ((ret != APPID_INPROCESS) && (ret != APPID_SUCCESS)) + if ( ( ret != APPID_INPROCESS ) && ( ret != APPID_SUCCESS ) ) { const SfIp* tmp_ip; if (dir == APP_ID_FROM_RESPONDER) @@ -535,18 +526,7 @@ int ServiceDiscovery::identify_service(AppIdSession* asd, Packet* p, int dir) tmp_ip = p->ptrs.ip_api.get_src(); if (asd->got_incompatible_services) - { - if (sds->invalid_client_count < STATE_ID_INVALID_CLIENT_THRESHOLD) - { - if (sds->last_invalid_client.fast_equals_raw(*tmp_ip)) - sds->invalid_client_count++; - else - { - sds->invalid_client_count += 3; - sds->last_invalid_client = *tmp_ip; - } - } - } + sds->update_service_incompatiable(tmp_ip); sds->set_service_id_failed(asd, tmp_ip); } @@ -554,149 +534,146 @@ int ServiceDiscovery::identify_service(AppIdSession* asd, Packet* p, int dir) return ret; } -int AddFTPServiceState(AppIdSession* asd) +int ServiceDiscovery::add_ftp_service_state(AppIdSession& asd) { if (!ftp_service) return -1; - return asd->add_flow_data_id(21, ftp_service); + return asd.add_flow_data_id(21, ftp_service); } -bool ServiceDiscovery::do_service_discovery(AppIdSession& asd, IpProtocol protocol, int direction, - AppId client_app_id, AppId payload_app_id, Packet* p) +bool ServiceDiscovery::do_service_discovery(AppIdSession& asd, Packet* p, int direction) { - AppInfoTableEntry* entry = nullptr; bool isTpAppidDiscoveryDone = false; - if (asd.service_disco_state != APPID_DISCO_STATE_FINISHED) - { - Profile serviceMatchPerfStats_profile_context(serviceMatchPerfStats); - uint32_t prevRnaServiceState = asd.service_disco_state; + Profile serviceMatchPerfStats_profile_context(serviceMatchPerfStats); + uint32_t prevRnaServiceState = asd.service_disco_state; - if (asd.service_disco_state == APPID_DISCO_STATE_NONE && p->dsize) + if (asd.service_disco_state == APPID_DISCO_STATE_NONE && p->dsize) + { + if (p->flow->get_session_flags() & SSNFLAG_MIDSTREAM) { - if (p->flow->get_session_flags() & SSNFLAG_MIDSTREAM) + // Unless it could be ftp control + if ( asd.protocol == IpProtocol::TCP && ( p->ptrs.sp == 21 || p->ptrs.dp == 21 ) + && !( p->ptrs.tcph->is_fin() || p->ptrs.tcph->is_rst() ) ) { - // Unless it could be ftp control - if (protocol == IpProtocol::TCP && (p->ptrs.sp == 21 || p->ptrs.dp == 21) - && !(p->ptrs.tcph->is_fin() || p->ptrs.tcph->is_rst())) - { - asd.set_session_flags(APPID_SESSION_CLIENT_DETECTED | - APPID_SESSION_NOT_A_SERVICE | APPID_SESSION_SERVICE_DETECTED); - if (!AddFTPServiceState(&asd)) - { - asd.set_session_flags(APPID_SESSION_CONTINUE); - if (p->ptrs.dp != 21) - asd.set_session_flags(APPID_SESSION_RESPONDER_SEEN); - } - asd.service_disco_state = APPID_DISCO_STATE_STATEFUL; - } - else + asd.set_session_flags(APPID_SESSION_CLIENT_DETECTED | + APPID_SESSION_NOT_A_SERVICE | APPID_SESSION_SERVICE_DETECTED); + if ( !ServiceDiscovery::add_ftp_service_state(asd) ) { - asd.set_session_flags(APPID_SESSION_MID | APPID_SESSION_SERVICE_DETECTED); - asd.service_disco_state = APPID_DISCO_STATE_FINISHED; + asd.set_session_flags(APPID_SESSION_CONTINUE); + if (p->ptrs.dp != 21) + asd.set_session_flags(APPID_SESSION_RESPONDER_SEEN); } + asd.service_disco_state = APPID_DISCO_STATE_STATEFUL; + } + else + { + asd.set_session_flags(APPID_SESSION_MID | APPID_SESSION_SERVICE_DETECTED); + asd.service_disco_state = APPID_DISCO_STATE_FINISHED; } - else if (is_third_party_appid_available(asd.tpsession)) + } + else if (is_third_party_appid_available(asd.tpsession)) + { + if (asd.tp_app_id > APP_ID_NONE) { - if (asd.tp_app_id > APP_ID_NONE) + //tp has positively identified appId, Dig deeper only if sourcefire + // detector identifies additional information or flow is UDP reveresed. + AppInfoTableEntry* entry = asd.app_info_mgr->get_app_info_entry(asd.tp_app_id); + if ( entry && entry->service_detector && + ( ( entry->flags & APPINFO_FLAG_SERVICE_ADDITIONAL ) || + ( ( entry->flags & APPINFO_FLAG_SERVICE_UDP_REVERSED ) && + asd.protocol == IpProtocol::UDP && + asd.get_session_flags(APPID_SESSION_INITIATOR_MONITORED | + APPID_SESSION_RESPONDER_MONITORED) ) ) ) { - //tp has positively identified appId, Dig deeper only if sourcefire - // detector identifies additional information or flow is UDP reveresed. - if ( ( entry = asd.app_info_mgr->get_app_info_entry(asd.tp_app_id)) && - entry->service_detector && - ( ( entry->flags & APPINFO_FLAG_SERVICE_ADDITIONAL ) || - ( ( entry->flags & APPINFO_FLAG_SERVICE_UDP_REVERSED ) && - protocol == IpProtocol::UDP && - asd.get_session_flags(APPID_SESSION_INITIATOR_MONITORED | - APPID_SESSION_RESPONDER_MONITORED) ) ) ) - { - asd.free_flow_data_by_mask(APPID_SESSION_DATA_SERVICE_MODSTATE_BIT); - asd.service_detector = entry->service_detector; - asd.service_disco_state = APPID_DISCO_STATE_STATEFUL; - } - else - asd.stop_rna_service_inspection(p, direction); + asd.free_flow_data_by_mask(APPID_SESSION_DATA_SERVICE_MODSTATE_BIT); + asd.service_detector = entry->service_detector; + asd.service_disco_state = APPID_DISCO_STATE_STATEFUL; } else - asd.service_disco_state = APPID_DISCO_STATE_STATEFUL; + asd.stop_rna_service_inspection(p, direction); } else asd.service_disco_state = APPID_DISCO_STATE_STATEFUL; } + else + asd.service_disco_state = APPID_DISCO_STATE_STATEFUL; + } - //stop rna inspection as soon as tp has classified a valid AppId later in the session - if (asd.service_disco_state == APPID_DISCO_STATE_STATEFUL && - prevRnaServiceState == APPID_DISCO_STATE_STATEFUL && - !asd.get_session_flags(APPID_SESSION_NO_TPI) && - is_third_party_appid_available(asd.tpsession) && - asd.tp_app_id > APP_ID_NONE && asd.tp_app_id < SF_APPID_MAX) + //stop rna inspection as soon as tp has classified a valid AppId later in the session + if ( asd.service_disco_state == APPID_DISCO_STATE_STATEFUL && + prevRnaServiceState == APPID_DISCO_STATE_STATEFUL && + !asd.get_session_flags(APPID_SESSION_NO_TPI) && + is_third_party_appid_available(asd.tpsession) && + asd.tp_app_id > APP_ID_NONE && asd.tp_app_id < SF_APPID_MAX) + { + AppInfoTableEntry* entry = asd.app_info_mgr->get_app_info_entry(asd.tp_app_id); + if ( entry && entry->service_detector && + !(entry->flags & APPINFO_FLAG_SERVICE_ADDITIONAL) ) { - entry = asd.app_info_mgr->get_app_info_entry(asd.tp_app_id); - if (entry && entry->service_detector && !(entry->flags & - APPINFO_FLAG_SERVICE_ADDITIONAL)) - { - if (asd.session_logging_enabled) - LogMessage("AppIdDbg %s Stop service detection\n", asd.session_logging_id); - asd.stop_rna_service_inspection(p, direction); - } + if (asd.session_logging_enabled) + LogMessage("AppIdDbg %s Stop service detection\n", asd.session_logging_id); + asd.stop_rna_service_inspection(p, direction); } + } - // Check to see if we want to stop any detectors for SIP/RTP. - if (asd.service_disco_state != APPID_DISCO_STATE_FINISHED) + // Check to see if we want to stop any detectors for SIP/RTP. + if (asd.service_disco_state != APPID_DISCO_STATE_FINISHED) + { + if (asd.tp_app_id == APP_ID_SIP) { - if ( asd.tp_app_id == APP_ID_SIP ) - { - // TP needs to see its own future flows and does a better - // job of it than we do, so stay out of its way, and don't - // waste time (but we will still get the Snort callbacks - // for any of our own future flows). Shut down our detectors. - asd.serviceAppId = APP_ID_SIP; - asd.stop_rna_service_inspection(p, direction); - asd.service_disco_state = APPID_DISCO_STATE_FINISHED; - } - else if ( (asd.tp_app_id == APP_ID_RTP) || (asd.tp_app_id == APP_ID_RTP_AUDIO) - || (asd.tp_app_id == APP_ID_RTP_VIDEO) ) - { - // No need for anybody to keep wasting time once we've - // found RTP - Shut down our detectors. - asd.serviceAppId = asd.tp_app_id; - asd.stop_rna_service_inspection(p, direction); - asd.service_disco_state = APPID_DISCO_STATE_FINISHED; - // - Shut down TP. - thirdparty_appid_module->session_state_set(asd.tpsession, TP_STATE_TERMINATED); - // - Just ignore everything from now on. - asd.set_session_flags(APPID_SESSION_IGNORE_FLOW); - } + // TP needs to see its own future flows and does a better + // job of it than we do, so stay out of its way, and don't + // waste time (but we will still get the Snort callbacks + // for any of our own future flows). Shut down our detectors. + asd.service_app_id = APP_ID_SIP; + asd.stop_rna_service_inspection(p, direction); + asd.service_disco_state = APPID_DISCO_STATE_FINISHED; } - - if (asd.service_disco_state == APPID_DISCO_STATE_STATEFUL) + else if ((asd.tp_app_id == APP_ID_RTP) || (asd.tp_app_id == APP_ID_RTP_AUDIO) || + (asd.tp_app_id == APP_ID_RTP_VIDEO)) { - identify_service(&asd, p, direction); - isTpAppidDiscoveryDone = true; - //to stop executing validator after service has been detected by RNA. - if (asd.get_session_flags(APPID_SESSION_SERVICE_DETECTED | - APPID_SESSION_CONTINUE) == APPID_SESSION_SERVICE_DETECTED) - asd.service_disco_state = APPID_DISCO_STATE_FINISHED; + // No need for anybody to keep wasting time once we've + // found RTP - Shut down our detectors. + asd.service_app_id = asd.tp_app_id; + asd.stop_rna_service_inspection(p, direction); + asd.service_disco_state = APPID_DISCO_STATE_FINISHED; + // - Shut down TP. + thirdparty_appid_module->session_state_set(asd.tpsession, TP_STATE_TERMINATED); + // - Just ignore everything from now on. + asd.set_session_flags(APPID_SESSION_IGNORE_FLOW); + } + } - if (asd.serviceAppId == APP_ID_DNS && asd.config->mod_config->dns_host_reporting - && asd.dsession && asd.dsession->host) - { - size_t size = asd.dsession->host_len; - dns_host_scan_hostname((const uint8_t*)(asd.dsession->host), size, &client_app_id, - &payload_app_id); - asd.set_client_app_id_data(client_app_id, nullptr); - } - else if (asd.serviceAppId == APP_ID_RTMP) - asd.examine_rtmp_metadata(); - else if (asd.get_session_flags(APPID_SESSION_SSL_SESSION) && asd.tsession) - asd.examine_ssl_metadata(p); - - if (asd.tp_app_id <= APP_ID_NONE && asd.get_session_flags( - APPID_SESSION_SERVICE_DETECTED | APPID_SESSION_NOT_A_SERVICE | - APPID_SESSION_IGNORE_HOST) == APPID_SESSION_SERVICE_DETECTED) - { - asd.sync_with_snort_id(asd.serviceAppId, p); - } + if (asd.service_disco_state == APPID_DISCO_STATE_STATEFUL) + { + identify_service(&asd, p, direction); + isTpAppidDiscoveryDone = true; + //to stop executing validator after service has been detected by RNA. + if (asd.get_session_flags(APPID_SESSION_SERVICE_DETECTED | + APPID_SESSION_CONTINUE) == APPID_SESSION_SERVICE_DETECTED) + asd.service_disco_state = APPID_DISCO_STATE_FINISHED; + + if (asd.service_app_id == APP_ID_DNS && asd.config->mod_config->dns_host_reporting + && asd.dsession && asd.dsession->host) + { + AppId client_app_id = APP_ID_NONE; + AppId payload_app_id = APP_ID_NONE; + size_t size = asd.dsession->host_len; + dns_host_scan_hostname((const uint8_t*)(asd.dsession->host), size, &client_app_id, + &payload_app_id); + asd.set_client_app_id_data(client_app_id, nullptr); + } + else if (asd.service_app_id == APP_ID_RTMP) + asd.examine_rtmp_metadata(); + else if (asd.get_session_flags(APPID_SESSION_SSL_SESSION) && asd.tsession) + asd.examine_ssl_metadata(p); + + if (asd.tp_app_id <= APP_ID_NONE && asd.get_session_flags( + APPID_SESSION_SERVICE_DETECTED | APPID_SESSION_NOT_A_SERVICE | + APPID_SESSION_IGNORE_HOST) == APPID_SESSION_SERVICE_DETECTED) + { + asd.sync_with_snort_id(asd.service_app_id, p); } } @@ -717,17 +694,17 @@ int ServiceDiscovery::incompatible_data(AppIdSession* asd, const Packet* pkt, in ServiceDiscoveryState* sds = AppIdServiceState::get(ip, asd->protocol, port, asd->is_decrypted()); - asd->free_flow_data_by_id(service->flow_data_index); + asd->free_flow_data_by_id(service->get_flow_data_index()); // ignore fails while searching with port/pattern selected detectors if ( !asd->service_detector && asd->service_candidates.size() ) return APPID_SUCCESS; - asd->set_session_flags(APPID_SESSION_SERVICE_DETECTED); + asd->set_service_detected(); asd->clear_session_flags(APPID_SESSION_CONTINUE); - asd->serviceAppId = APP_ID_NONE; + asd->service_app_id = APP_ID_NONE; - if ( asd->get_session_flags(APPID_SESSION_IGNORE_HOST | APPID_SESSION_UDP_REVERSED ) ) + if ( asd->get_session_flags(APPID_SESSION_IGNORE_HOST | APPID_SESSION_UDP_REVERSED) ) return APPID_SUCCESS; if ( dir == APP_ID_FROM_INITIATOR ) @@ -736,13 +713,13 @@ int ServiceDiscovery::incompatible_data(AppIdSession* asd, const Packet* pkt, in return APPID_SUCCESS; } - if (!asd->service_ip.is_set()) + if ( !asd->service_ip.is_set() ) { asd->service_ip = *ip; if (!asd->service_port) asd->service_port = port; } - sds->reset_time = 0; + sds->set_reset_time(0); return APPID_SUCCESS; } @@ -753,13 +730,13 @@ int ServiceDiscovery::fail_service(AppIdSession* asd, const Packet* pkt, int dir uint16_t port = asd->service_port ? asd->service_port : pkt->ptrs.sp; if ( service ) - asd->free_flow_data_by_id(service->flow_data_index); + asd->free_flow_data_by_id(service->get_flow_data_index()); if ( !asd->service_detector && asd->service_candidates.size() ) - return APPID_SUCCESS; + return APPID_SUCCESS; - asd->serviceAppId = APP_ID_NONE; - asd->set_session_flags(APPID_SESSION_SERVICE_DETECTED); + asd->service_app_id = APP_ID_NONE; + asd->set_service_detected(); asd->clear_session_flags(APPID_SESSION_CONTINUE); /* detectors should be careful in marking session UDP_REVERSED otherwise the same detector @@ -788,9 +765,9 @@ int ServiceDiscovery::fail_service(AppIdSession* asd, const Packet* pkt, int dir if ( !sds ) { sds = AppIdServiceState::add(ip, asd->protocol, port, asd->is_decrypted()); - sds->service = service; + sds->set_service(service); } - sds->reset_time = 0; + sds->set_reset_time(0); return APPID_SUCCESS; } diff --git a/src/network_inspectors/appid/service_plugins/service_discovery.h b/src/network_inspectors/appid/service_plugins/service_discovery.h index ff423b65e..1290ed5c8 100644 --- a/src/network_inspectors/appid/service_plugins/service_discovery.h +++ b/src/network_inspectors/appid/service_plugins/service_discovery.h @@ -50,7 +50,7 @@ enum SERVICE_HOST_INFO_CODE * at the beginning of the flow, then independently do service discovery, and * synchronize findings at the end of service discovery by the flow. */ -enum SESSION_SERVICE_ID_STATE +enum SESSION_SERVICE_SEARCH_STATE { START = 0, PORT, @@ -58,9 +58,6 @@ enum SESSION_SERVICE_ID_STATE PENDING }; -void FailInProcessService(AppIdSession*, const AppIdConfig*); -int AddFTPServiceState(AppIdSession*); - class ServiceDiscovery : public AppIdDiscovery { public: @@ -74,14 +71,11 @@ public: ServiceDetector* get_next_tcp_detector(AppIdDetectorsIterator&); ServiceDetector* get_next_udp_detector(AppIdDetectorsIterator&); - bool do_service_discovery(AppIdSession&, IpProtocol, int, AppId, AppId, Packet*); + bool do_service_discovery(AppIdSession&, Packet*, int); int identify_service(AppIdSession*, Packet*, int dir); int fail_service(AppIdSession*, const Packet*, int dir, ServiceDetector*); int incompatible_data(AppIdSession*, const Packet*, int dir, ServiceDetector*); - - std::map > tcp_services; - std::map > udp_services; - std::map > udp_reversed_services; + static int add_ftp_service_state(AppIdSession&); private: ServiceDiscovery(); @@ -89,6 +83,11 @@ private: void get_next_service(const Packet*, const int dir, AppIdSession*, ServiceDiscoveryState*); void get_port_based_services(IpProtocol, uint16_t port, AppIdSession*); void match_services_by_pattern(AppIdSession*, const Packet*, IpProtocol); + + std::map > tcp_services; + std::map > udp_services; + std::map > udp_reversed_services; }; #endif + diff --git a/src/network_inspectors/appid/service_plugins/service_ftp.cc b/src/network_inspectors/appid/service_plugins/service_ftp.cc index 68f526a45..9053c6c03 100644 --- a/src/network_inspectors/appid/service_plugins/service_ftp.cc +++ b/src/network_inspectors/appid/service_plugins/service_ftp.cc @@ -25,9 +25,9 @@ #include "service_ftp.h" +#include "appid_inspector.h" #include "appid_module.h" #include "app_info_table.h" -#include "service_util.h" #include "protocols/packet.h" #define FTP_PORT 21 @@ -90,7 +90,7 @@ FtpServiceDetector::FtpServiceDetector(ServiceDiscovery* sd) name = "ftp"; proto = IpProtocol::TCP; detectorType = DETECTOR_TYPE_DECODER; - ftp_data_app_id = add_appid_protocol_reference("ftp-data"); + ftp_data_app_id = AppIdInspector::get_inspector()->add_appid_protocol_reference("ftp-data"); tcp_patterns = { @@ -800,20 +800,19 @@ static inline void WatchForCommandResult(ServiceFTPData* fd, AppIdSession* asd, void FtpServiceDetector::InitializeDataSession(AppIdSession* asd, AppIdSession* fp) { - unsigned encryptedFlag = - asd->get_session_flags(APPID_SESSION_ENCRYPTED | APPID_SESSION_DECRYPTED); - if (encryptedFlag == APPID_SESSION_ENCRYPTED) + uint64_t flags = asd->get_session_flags(APPID_SESSION_ENCRYPTED | APPID_SESSION_DECRYPTED); + if (flags == APPID_SESSION_ENCRYPTED) { - fp->serviceAppId = APP_ID_FTPSDATA; + fp->service_app_id = APP_ID_FTPSDATA; } else { - encryptedFlag = 0; // change (APPID_SESSION_ENCRYPTED | APPID_SESSION_DECRYPTED) case to - // zeroes. - fp->serviceAppId = APP_ID_FTP_DATA; + flags = 0; // change (APPID_SESSION_ENCRYPTED | APPID_SESSION_DECRYPTED) case to + // zeroes. + fp->service_app_id = APP_ID_FTP_DATA; } - initialize_expected_session(asd, fp, APPID_SESSION_IGNORE_ID_FLAGS | encryptedFlag); + initialize_expected_session(asd, fp, APPID_SESSION_IGNORE_ID_FLAGS | flags); } int FtpServiceDetector::validate(AppIdDiscoveryArgs& args) @@ -1223,23 +1222,23 @@ int FtpServiceDetector::validate(AppIdDiscoveryArgs& args) default: case APPID_INPROCESS: inprocess: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) service_inprocess(asd, pkt, dir); return APPID_INPROCESS; case APPID_SUCCESS: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { - uint64_t encryptedFlag = asd->get_session_flags( - APPID_SESSION_ENCRYPTED | APPID_SESSION_DECRYPTED); + uint64_t flags = asd->get_session_flags(APPID_SESSION_ENCRYPTED + | APPID_SESSION_DECRYPTED); // FTPS only when encrypted==1 decrypted==0 - add_service(asd, pkt, dir, encryptedFlag == APPID_SESSION_ENCRYPTED ? + add_service(asd, pkt, dir, flags == APPID_SESSION_ENCRYPTED ? APP_ID_FTPS : APP_ID_FTP_CONTROL, fd->vendor[0] ? fd->vendor : nullptr, fd->version[0] ? fd->version : nullptr, nullptr); - if (encryptedFlag == APPID_SESSION_ENCRYPTED) + if (flags == APPID_SESSION_ENCRYPTED) appid_stats.ftps_flows++; else appid_stats.ftp_flows++; @@ -1248,7 +1247,7 @@ inprocess: case APPID_NOMATCH: fail: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) fail_service(asd, pkt, dir); asd->clear_session_flags(APPID_SESSION_CONTINUE); return APPID_NOMATCH; diff --git a/src/network_inspectors/appid/service_plugins/service_mdns.cc b/src/network_inspectors/appid/service_plugins/service_mdns.cc index e1d1e8ad7..e4a7ed885 100644 --- a/src/network_inspectors/appid/service_plugins/service_mdns.cc +++ b/src/network_inspectors/appid/service_plugins/service_mdns.cc @@ -313,7 +313,7 @@ int MdnsServiceDetector::analyze_user(AppIdSession* asd, const Packet* pkt, uint user_index++; } - add_user(asd, user_name, APP_ID_MDNS, 1); + add_user(asd, user_name, APP_ID_MDNS, true); break; } @@ -366,7 +366,7 @@ int MdnsServiceDetector::analyze_user(AppIdSession* asd, const Packet* pkt, uint memcpy(user_name, user_name_bkp + user_index, user_name_len - user_index); user_name[ user_name_len - user_index ] = '\0'; - add_user(asd, user_name, APP_ID_MDNS, 1); + add_user(asd, user_name, APP_ID_MDNS, true); return 1; } else diff --git a/src/network_inspectors/appid/service_plugins/service_netbios.cc b/src/network_inspectors/appid/service_plugins/service_netbios.cc index 476775fbe..ecf416087 100644 --- a/src/network_inspectors/appid/service_plugins/service_netbios.cc +++ b/src/network_inspectors/appid/service_plugins/service_netbios.cc @@ -993,7 +993,7 @@ int NbssServiceDetector::validate(AppIdDiscoveryArgs& args) if (retval == -1) goto inprocess; - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { if (add_service(asd, pkt, dir, nd->serviceAppId, nullptr, nullptr, nullptr) == APPID_SUCCESS) @@ -1005,14 +1005,14 @@ int NbssServiceDetector::validate(AppIdDiscoveryArgs& args) return APPID_SUCCESS; inprocess: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { service_inprocess(asd, pkt, dir); } return APPID_INPROCESS; fail: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { fail_service(asd, pkt, dir); } @@ -1113,7 +1113,7 @@ int NbdgmServiceDetector::validate(AppIdDiscoveryArgs& args) if (end-data >= (int)sizeof(NB_SMB_BANNER) && !memcmp(data, NB_SMB_BANNER, sizeof(NB_SMB_BANNER))) { - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) serviceAppId = APP_ID_NETBIOS_DGM; data += sizeof(NB_SMB_BANNER); @@ -1172,7 +1172,7 @@ not_mailslot: } fail: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { fail_service(asd, pkt, dir); } @@ -1180,7 +1180,7 @@ fail: return APPID_NOMATCH; success: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { if (dir == APP_ID_FROM_RESPONDER) { @@ -1195,7 +1195,7 @@ success: return APPID_SUCCESS; inprocess: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { service_inprocess(asd, pkt, dir); } diff --git a/src/network_inspectors/appid/service_plugins/service_regtest.cc b/src/network_inspectors/appid/service_plugins/service_regtest.cc new file mode 100644 index 000000000..8b01f6e74 --- /dev/null +++ b/src/network_inspectors/appid/service_plugins/service_regtest.cc @@ -0,0 +1,219 @@ +//-------------------------------------------------------------------------- +// Copyright (C) 2016-2017 Cisco and/or its affiliates. All rights reserved. +// +// This program is free software; you can redistribute it and/or modify it +// under the terms of the GNU General Public License Version 2 as published +// by the Free Software Foundation. You may not use, modify or distribute +// this program under any other version of the GNU General Public License. +// +// This program is distributed in the hope that it will be useful, but +// WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// General Public License for more details. +// +// You should have received a copy of the GNU General Public License along +// with this program; if not, write to the Free Software Foundation, Inc., +// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +//-------------------------------------------------------------------------- + +// service_regtest.cc author davis mcpherson + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#include "service_regtest.h" + +#include "appid_module.h" +#include "app_info_table.h" + +#ifdef REG_TEST + +#define REGTEST_BANNER "REGTEST PORT MATCH " +#define REGTEST1_BANNER "REGTEST1 PATTERN MATCH " +#define REGTEST2_BANNER "REGTEST2 BRUTE FORCE " + +RegTestServiceDetector::RegTestServiceDetector(ServiceDiscovery* sd) +{ + handler = sd; + name = "regtest"; + proto = IpProtocol::TCP; + detectorType = DETECTOR_TYPE_DECODER; + + appid_registry = + { + { APP_ID_REGTEST, APPINFO_FLAG_SERVICE_ADDITIONAL } + }; + + service_ports = + { + { 1066, IpProtocol::TCP, false }, + }; + + handler->register_detector(name, this, proto); +} + +RegTestServiceDetector::~RegTestServiceDetector() +{ +} + +int RegTestServiceDetector::validate(AppIdDiscoveryArgs& args) +{ + unsigned v_off = strlen(REGTEST_BANNER); + char version[4]; + char* v; + + const unsigned char* p; + + if (!args.size || (args.dir != APP_ID_FROM_RESPONDER)) + goto inprocess; + + if (strncmp(REGTEST_BANNER, (char*)args.data, v_off)) + goto fail; + + if (!isdigit(args.data[v_off]) || !isdigit(args.data[v_off + 1]) || !isdigit(args.data[v_off + + 2])) + goto fail; + + v = version; + p = &args.data[v_off]; + for (unsigned i = 0; i < 3; i++) + { + *v = *p; + v++; + p++; + } + *v = 0; + add_service(args.asd, args.pkt, args.dir, APP_ID_REGTEST, nullptr, version, nullptr); + return APPID_SUCCESS; + +inprocess: + service_inprocess(args.asd, args.pkt, args.dir); + return APPID_INPROCESS; + +fail: + fail_service(args.asd, args.pkt, args.dir); + return APPID_NOMATCH; +} + +RegTestServiceDetector1::RegTestServiceDetector1(ServiceDiscovery* sd) +{ + handler = sd; + name = "regtest1"; + proto = IpProtocol::TCP; + detectorType = DETECTOR_TYPE_DECODER; + + tcp_patterns = + { + { (uint8_t*)REGTEST1_BANNER, sizeof(REGTEST1_BANNER) - 1, 0, 0, 0 }, + }; + + appid_registry = + { + { APP_ID_REGTEST1, APPINFO_FLAG_SERVICE_ADDITIONAL } + }; + + handler->register_detector(name, this, proto); +} + +RegTestServiceDetector1::~RegTestServiceDetector1() +{ +} + +int RegTestServiceDetector1::validate(AppIdDiscoveryArgs& args) +{ + char version[4]; + char* v; + const unsigned char* p; + unsigned v_off = strlen(REGTEST1_BANNER); + + if (!args.size || (args.dir != APP_ID_FROM_RESPONDER)) + goto inprocess; + + if (strncmp(REGTEST1_BANNER, (char*)args.data, v_off)) + goto fail; + + if (!isdigit(args.data[v_off]) || !isdigit(args.data[v_off + 1]) || !isdigit(args.data[v_off + + 2])) + goto fail; + + v = version; + p = &args.data[v_off]; + for (unsigned i = 0; i < 3; i++) + { + *v = *p; + v++; + p++; + } + *v = 0; + add_service(args.asd, args.pkt, args.dir, APP_ID_REGTEST1, nullptr, version, nullptr); + return APPID_SUCCESS; + +inprocess: + service_inprocess(args.asd, args.pkt, args.dir); + return APPID_INPROCESS; + +fail: + fail_service(args.asd, args.pkt, args.dir); + return APPID_NOMATCH; +} + +RegTestServiceDetector2::RegTestServiceDetector2(ServiceDiscovery* sd) +{ + handler = sd; + name = "regtest2"; + proto = IpProtocol::TCP; + detectorType = DETECTOR_TYPE_DECODER; + + appid_registry = + { + { APP_ID_REGTEST2, APPINFO_FLAG_SERVICE_ADDITIONAL } + }; + + handler->register_detector(name, this, proto); +} + +RegTestServiceDetector2::~RegTestServiceDetector2() +{ +} + +int RegTestServiceDetector2::validate(AppIdDiscoveryArgs& args) +{ + char version[4]; + char* v; + const unsigned char* p; + unsigned v_off = strlen(REGTEST2_BANNER); + + if (!args.size || (args.dir != APP_ID_FROM_RESPONDER)) + goto inprocess; + + if (strncmp(REGTEST2_BANNER, (char*)args.data, v_off)) + goto fail; + + if (!isdigit(args.data[v_off]) || !isdigit(args.data[v_off + 1]) || !isdigit(args.data[v_off + + 2])) + goto fail; + + v = version; + p = &args.data[v_off]; + for (unsigned i = 0; i < 3; i++) + { + *v = *p; + v++; + p++; + } + *v = 0; + add_service(args.asd, args.pkt, args.dir, APP_ID_REGTEST2, nullptr, version, nullptr); + return APPID_SUCCESS; + +inprocess: + service_inprocess(args.asd, args.pkt, args.dir); + return APPID_INPROCESS; + +fail: + fail_service(args.asd, args.pkt, args.dir); + return APPID_NOMATCH; +} + +#endif + diff --git a/src/network_inspectors/appid/service_plugins/service_util.h b/src/network_inspectors/appid/service_plugins/service_regtest.h similarity index 52% rename from src/network_inspectors/appid/service_plugins/service_util.h rename to src/network_inspectors/appid/service_plugins/service_regtest.h index f52e52824..c09cd2dce 100644 --- a/src/network_inspectors/appid/service_plugins/service_util.h +++ b/src/network_inspectors/appid/service_plugins/service_regtest.h @@ -1,6 +1,5 @@ //-------------------------------------------------------------------------- -// Copyright (C) 2014-2017 Cisco and/or its affiliates. All rights reserved. -// Copyright (C) 2005-2013 Sourcefire, Inc. +// Copyright (C) 2016-2017 Cisco and/or its affiliates. All rights reserved. // // This program is free software; you can redistribute it and/or modify it // under the terms of the GNU General Public License Version 2 as published @@ -17,40 +16,43 @@ // 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. //-------------------------------------------------------------------------- -// service_util.h author Sourcefire Inc. +// service_regtest.h author davis mcpherson -#ifndef SERVICE_UTIL_H -#define SERVICE_UTIL_H +#ifndef SERVICE_REGTEST_H +#define SERVICE_REGTEST_H -#include +#ifdef REG_TEST +#include "service_detector.h" -#include "main/snort_config.h" -#include "target_based/snort_protocols.h" +class ServiceDiscovery; -inline const uint8_t* service_strstr(const uint8_t* haystack, unsigned haystack_len, - const uint8_t* needle, unsigned needle_len) +class RegTestServiceDetector : public ServiceDetector { - const uint8_t* h_end = haystack + haystack_len; - - for (const uint8_t* p = haystack; h_end-p >= (int)needle_len; p++) - { - if (memcmp(p, needle, needle_len) == 0) - { - return p; - } - } - return nullptr; -} - -inline int16_t add_appid_protocol_reference(const char* protocol) +public: + RegTestServiceDetector(ServiceDiscovery*); + ~RegTestServiceDetector(); + + int validate(AppIdDiscoveryArgs&) override; +}; + +class RegTestServiceDetector1 : public ServiceDetector +{ +public: + RegTestServiceDetector1(ServiceDiscovery*); + ~RegTestServiceDetector1(); + + int validate(AppIdDiscoveryArgs&) override; +}; + +class RegTestServiceDetector2 : public ServiceDetector { - static std::mutex apr_mutex; +public: + RegTestServiceDetector2(ServiceDiscovery*); + ~RegTestServiceDetector2(); - apr_mutex.lock(); - int16_t id = snort_conf->proto_ref->add(protocol); - apr_mutex.unlock(); - return id; -} + int validate(AppIdDiscoveryArgs&) override; +}; +#endif #endif diff --git a/src/network_inspectors/appid/service_plugins/service_rexec.cc b/src/network_inspectors/appid/service_plugins/service_rexec.cc index 7da063f0d..44ed81415 100644 --- a/src/network_inspectors/appid/service_plugins/service_rexec.cc +++ b/src/network_inspectors/appid/service_plugins/service_rexec.cc @@ -25,9 +25,9 @@ #include "service_rexec.h" +#include "appid_inspector.h" #include "appid_module.h" #include "app_info_table.h" -#include "service_util.h" #include "protocols/packet.h" #define REXEC_PORT 512 @@ -60,7 +60,7 @@ RexecServiceDetector::RexecServiceDetector(ServiceDiscovery* sd) proto = IpProtocol::TCP; detectorType = DETECTOR_TYPE_DECODER; - app_id = add_appid_protocol_reference("rexec"); + app_id = AppIdInspector::get_inspector()->add_appid_protocol_reference("rexec"); appid_registry = { @@ -273,12 +273,12 @@ int RexecServiceDetector::validate(AppIdDiscoveryArgs& args) } inprocess: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) service_inprocess(asd, pkt, dir); return APPID_INPROCESS; success: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { add_service(asd, pkt, dir, APP_ID_EXEC, nullptr, nullptr, nullptr); appid_stats.rexec_flows++; @@ -286,7 +286,7 @@ success: return APPID_SUCCESS; bail: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { incompatible_data(asd, pkt, dir); } @@ -294,7 +294,7 @@ bail: return APPID_NOT_COMPATIBLE; fail: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { fail_service(asd, pkt, dir); } diff --git a/src/network_inspectors/appid/service_plugins/service_rpc.cc b/src/network_inspectors/appid/service_plugins/service_rpc.cc index acdea71c5..96a18e88e 100644 --- a/src/network_inspectors/appid/service_plugins/service_rpc.cc +++ b/src/network_inspectors/appid/service_plugins/service_rpc.cc @@ -34,8 +34,8 @@ #endif #include "appid_module.h" +#include "appid_inspector.h" #include "app_info_table.h" -#include "service_util.h" #include "log/messages.h" #include "protocols/packet.h" @@ -184,7 +184,7 @@ RpcServiceDetector::RpcServiceDetector(ServiceDiscovery* sd) struct rpcent* rpc; RPCProgram* prog; - app_id = add_appid_protocol_reference("sunrpc"); + app_id = AppIdInspector::get_inspector()->add_appid_protocol_reference("sunrpc"); if (!rpc_programs) { @@ -452,8 +452,8 @@ int RpcServiceDetector::rpc_udp_validate(AppIdDiscoveryArgs& args) { static char subname[64]; ServiceRPCData* rd; - RNAServiceSubtype sub; - RNAServiceSubtype* subtype; + AppIdServiceSubtype sub; + AppIdServiceSubtype* subtype; uint32_t program = 0; const char* pname = nullptr; int rval; @@ -494,12 +494,12 @@ done: switch (rval) { case APPID_INPROCESS: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) service_inprocess(asd, pkt, dir); return APPID_INPROCESS; case APPID_SUCCESS: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { if (pname && *pname) { @@ -524,7 +524,7 @@ done: return APPID_SUCCESS; case APPID_NOT_COMPATIBLE: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { incompatible_data(asd, pkt, dir); } @@ -532,7 +532,7 @@ done: return APPID_NOT_COMPATIBLE; case APPID_NOMATCH: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { fail_service(asd, pkt, dir); } @@ -555,8 +555,8 @@ int RpcServiceDetector::rpc_tcp_validate(AppIdDiscoveryArgs& args) const ServiceRPCReply* reply; static char subname[64]; - RNAServiceSubtype sub; - RNAServiceSubtype* subtype; + AppIdServiceSubtype sub; + AppIdServiceSubtype* subtype; uint32_t program = 0; const char* pname = nullptr; @@ -856,12 +856,12 @@ done: { case APPID_INPROCESS: inprocess: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) service_inprocess(asd, pkt, dir); return APPID_INPROCESS; case APPID_SUCCESS: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) { if (pname && *pname) { @@ -885,14 +885,14 @@ inprocess: return APPID_SUCCESS; case APPID_NOT_COMPATIBLE: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) incompatible_data(asd, pkt, dir); asd->clear_session_flags(APPID_SESSION_CONTINUE); return APPID_NOT_COMPATIBLE; case APPID_NOMATCH: fail: - if (!asd->get_session_flags(APPID_SESSION_SERVICE_DETECTED)) + if (!asd->is_service_detected()) fail_service(asd, pkt, dir); asd->clear_session_flags(APPID_SESSION_CONTINUE); return APPID_NOMATCH; diff --git a/src/network_inspectors/appid/service_plugins/service_rshell.cc b/src/network_inspectors/appid/service_plugins/service_rshell.cc index 1a05d9c72..fe6b652d3 100644 --- a/src/network_inspectors/appid/service_plugins/service_rshell.cc +++ b/src/network_inspectors/appid/service_plugins/service_rshell.cc @@ -25,9 +25,9 @@ #include "service_rshell.h" +#include "appid_inspector.h" #include "appid_module.h" #include "app_info_table.h" -#include "service_util.h" #include "protocols/packet.h" #define RSHELL_PORT 514 @@ -59,7 +59,7 @@ RshellServiceDetector::RshellServiceDetector(ServiceDiscovery* sd) name = "rshell"; proto = IpProtocol::TCP; detectorType = DETECTOR_TYPE_DECODER; - app_id = add_appid_protocol_reference("rsh-error"); + app_id = AppIdInspector::get_inspector()->add_appid_protocol_reference("rsh-error"); appid_registry = { @@ -273,7 +273,7 @@ int RshellServiceDetector::validate(AppIdDiscoveryArgs& args) case RSHELL_STATE_STDERR_CONNECT_SYN_ACK: if (rd->parent && rd->parent->state == RSHELL_STATE_SERVER_CONNECT) rd->parent->state = RSHELL_STATE_USERNAME; - asd->set_session_flags(APPID_SESSION_SERVICE_DETECTED); + asd->set_service_detected(); return APPID_SUCCESS; default: goto bail; diff --git a/src/network_inspectors/appid/service_plugins/service_rtmp.cc b/src/network_inspectors/appid/service_plugins/service_rtmp.cc index 7211bc4ac..f9b589257 100644 --- a/src/network_inspectors/appid/service_plugins/service_rtmp.cc +++ b/src/network_inspectors/appid/service_plugins/service_rtmp.cc @@ -25,6 +25,7 @@ #include "service_rtmp.h" +#include "appid_http_session.h" #include "appid_module.h" #include "app_info_table.h" @@ -418,38 +419,34 @@ parse_rtmp_message_fail: int RtmpServiceDetector::validate(AppIdDiscoveryArgs& args) { ServiceRTMPData* ss; - AppIdSession* asd = args.asd; - const uint8_t* data = args.data; - const int dir = args.dir; - uint16_t size = args.size; - if (!size) + if (!args.size) goto inprocess; - ss = (ServiceRTMPData*)data_get(asd); + ss = (ServiceRTMPData*)data_get(args.asd); if (!ss) { ss = (ServiceRTMPData*)snort_calloc(sizeof(ServiceRTMPData)); - data_add(asd, ss, &rtmp_free); + data_add(args.asd, ss, &rtmp_free); } /* Client -> Server */ - if (dir == APP_ID_FROM_INITIATOR) + if (args.dir == APP_ID_FROM_INITIATOR) { /* Consume this packet. */ - while (size > 0) + while (args.size > 0) { switch (ss->client_state) { case RTMP_STATE_INIT: /* C0 is just a version number. Must be valid. */ - if (*data != RTMP_VER_3) + if (*args.data != RTMP_VER_3) { goto fail; } ss->client_state = RTMP_STATE_SENT_HANDSHAKE0; - data += 1; - size -= 1; + args.data += 1; + args.size -= 1; break; case RTMP_STATE_SENT_HANDSHAKE0: @@ -459,18 +456,18 @@ int RtmpServiceDetector::validate(AppIdDiscoveryArgs& args) /* fall through */ case RTMP_STATE_SENDING_HANDSHAKE1: - if (size < ss->client_bytes_left) + if (args.size < ss->client_bytes_left) { /* We've still got more to get next time around. */ - ss->client_bytes_left -= size; - size = 0; + ss->client_bytes_left -= args.size; + args.size = 0; } else { /* We've gotten all of the bytes that we wanted. */ ss->client_state = RTMP_STATE_SENT_HANDSHAKE1; - data += ss->client_bytes_left; - size -= ss->client_bytes_left; + args.data += ss->client_bytes_left; + args.size -= ss->client_bytes_left; } break; @@ -486,23 +483,23 @@ int RtmpServiceDetector::validate(AppIdDiscoveryArgs& args) /* fall through */ case RTMP_STATE_SENDING_HANDSHAKE2: - if (size < ss->client_bytes_left) + if (args.size < ss->client_bytes_left) { /* We've still got more to get next time around. */ - ss->client_bytes_left -= size; - size = 0; + ss->client_bytes_left -= args.size; + args.size = 0; } else { /* We've gotten all of the bytes that we wanted. */ ss->client_state = RTMP_STATE_SENT_HANDSHAKE2; - data += ss->client_bytes_left; - size -= ss->client_bytes_left; + args.data += ss->client_bytes_left; + args.size -= ss->client_bytes_left; } break; case RTMP_STATE_SENT_HANDSHAKE2: - if (parse_rtmp_message(&data, &size, ss)) + if (parse_rtmp_message(&args.data, &args.size, ss)) { /* Got our connect command. We're done. */ ss->client_state = RTMP_STATE_DONE; @@ -516,7 +513,7 @@ int RtmpServiceDetector::validate(AppIdDiscoveryArgs& args) case RTMP_STATE_DONE: /* We're done with client, so just blindly consume all data. */ - size = 0; + args.size = 0; break; default: @@ -525,10 +522,10 @@ int RtmpServiceDetector::validate(AppIdDiscoveryArgs& args) } } /* Server -> Client */ - else if (dir == APP_ID_FROM_RESPONDER) + else if (args.dir == APP_ID_FROM_RESPONDER) { /* Consume this packet. */ - while (size > 0) + while (args.size > 0) { switch (ss->server_state) { @@ -539,13 +536,13 @@ int RtmpServiceDetector::validate(AppIdDiscoveryArgs& args) goto fail; } /* S0 is just a version number. Must be valid. */ - if (*data != RTMP_VER_3) + if (*args.data != RTMP_VER_3) { goto fail; } ss->server_state = RTMP_STATE_SENT_HANDSHAKE0; - data += 1; - size -= 1; + args.data += 1; + args.size -= 1; break; case RTMP_STATE_SENT_HANDSHAKE0: @@ -555,18 +552,18 @@ int RtmpServiceDetector::validate(AppIdDiscoveryArgs& args) /* fall through */ case RTMP_STATE_SENDING_HANDSHAKE1: - if (size < ss->server_bytes_left) + if (args.size < ss->server_bytes_left) { /* We've still got more to get next time around. */ - ss->server_bytes_left -= size; - size = 0; + ss->server_bytes_left -= args.size; + args.size = 0; } else { /* We've gotten all of the bytes that we wanted. */ ss->server_state = RTMP_STATE_SENT_HANDSHAKE1; - data += ss->server_bytes_left; - size -= ss->server_bytes_left; + args.data += ss->server_bytes_left; + args.size -= ss->server_bytes_left; } break; @@ -582,19 +579,19 @@ int RtmpServiceDetector::validate(AppIdDiscoveryArgs& args) /* fall through */ case RTMP_STATE_SENDING_HANDSHAKE2: - if (size < ss->server_bytes_left) + if (args.size < ss->server_bytes_left) { /* We've still got more to get next time around. */ - ss->server_bytes_left -= size; - size = 0; + ss->server_bytes_left -= args.size; + args.size = 0; break; /* Not done yet. */ } else { /* We've gotten all of the bytes that we wanted. */ ss->server_state = RTMP_STATE_SENT_HANDSHAKE2; - data += ss->server_bytes_left; - size -= ss->server_bytes_left; + args.data += ss->server_bytes_left; + args.size -= ss->server_bytes_left; } /* fall through */ @@ -605,7 +602,7 @@ int RtmpServiceDetector::validate(AppIdDiscoveryArgs& args) case RTMP_STATE_DONE: /* We're done with server, so just blindly consume all data. */ - size = 0; + args.size = 0; break; default: @@ -622,52 +619,53 @@ int RtmpServiceDetector::validate(AppIdDiscoveryArgs& args) } /* Give up if it's taking us too long to figure out this thing. */ - if (asd->session_packet_count >= asd->config->mod_config->rtmp_max_packets) + if (args.asd->session_packet_count >= args.asd->config->mod_config->rtmp_max_packets) { goto fail; } inprocess: - service_inprocess(asd, args.pkt, dir); + service_inprocess(args.asd, args.pkt, args.dir); return APPID_INPROCESS; fail: snort_free(ss->swfUrl); snort_free(ss->pageUrl); ss->swfUrl = ss->pageUrl = nullptr; - fail_service(asd, args.pkt, dir); + fail_service(args.asd, args.pkt, args.dir); return APPID_NOMATCH; success: if (ss->swfUrl != nullptr) { - if (!asd->hsession) - asd->hsession = (HttpSession*)snort_calloc(sizeof(HttpSession)); + if (!args.asd->hsession) + args.asd->hsession = new AppIdHttpSession(args.asd); - if (asd->hsession->url == nullptr) + if (args.asd->hsession->url == nullptr) { - asd->hsession->url = ss->swfUrl; - asd->scan_flags |= SCAN_HTTP_HOST_URL_FLAG; + args.asd->hsession->url = ss->swfUrl; + args.asd->scan_flags |= SCAN_HTTP_HOST_URL_FLAG; } else snort_free(ss->swfUrl); ss->swfUrl = nullptr; } + if (ss->pageUrl != nullptr) { - if (!asd->hsession) - asd->hsession = (HttpSession*)snort_calloc(sizeof(HttpSession)); + if (!args.asd->hsession) + args.asd->hsession = new AppIdHttpSession(args.asd); - if (!asd->config->mod_config->referred_appId_disabled && - (asd->hsession->referer == nullptr)) - asd->hsession->referer = ss->pageUrl; + if (!args.asd->config->mod_config->referred_appId_disabled && + (args.asd->hsession->referer == nullptr)) + args.asd->hsession->referer = ss->pageUrl; else snort_free(ss->pageUrl); ss->pageUrl = nullptr; } - add_service(asd, args.pkt, dir, APP_ID_RTMP, nullptr, nullptr, nullptr); + add_service(args.asd, args.pkt, args.dir, APP_ID_RTMP, nullptr, nullptr, nullptr); appid_stats.rtmp_flows++; return APPID_SUCCESS; } diff --git a/src/network_inspectors/appid/service_plugins/service_snmp.cc b/src/network_inspectors/appid/service_plugins/service_snmp.cc index 8b2f8d0a2..6ade1524c 100644 --- a/src/network_inspectors/appid/service_plugins/service_snmp.cc +++ b/src/network_inspectors/appid/service_plugins/service_snmp.cc @@ -25,9 +25,9 @@ #include "service_snmp.h" +#include "appid_inspector.h" #include "appid_module.h" #include "app_info_table.h" -#include "service_util.h" #include "log/messages.h" #include "protocols/packet.h" @@ -96,7 +96,7 @@ SnmpServiceDetector::SnmpServiceDetector(ServiceDiscovery* sd) proto = IpProtocol::UDP; detectorType = DETECTOR_TYPE_DECODER; - app_id = add_appid_protocol_reference("snmp"); + app_id = AppIdInspector::get_inspector()->add_appid_protocol_reference("snmp"); udp_patterns = { @@ -476,7 +476,7 @@ int SnmpServiceDetector::validate(AppIdDiscoveryArgs& args) { asd->set_session_flags(APPID_SESSION_SERVICE_DETECTED | APPID_SESSION_NOT_A_SERVICE); asd->clear_session_flags(APPID_SESSION_CONTINUE); - asd->serviceAppId = APP_ID_SNMP; + asd->service_app_id = APP_ID_SNMP; break; } sd->state = SNMP_STATE_RESPONSE; diff --git a/src/network_inspectors/appid/service_plugins/service_ssl.cc b/src/network_inspectors/appid/service_plugins/service_ssl.cc index effc37f01..ec76549df 100644 --- a/src/network_inspectors/appid/service_plugins/service_ssl.cc +++ b/src/network_inspectors/appid/service_plugins/service_ssl.cc @@ -967,7 +967,7 @@ AppId getSslServiceAppId(short srcPort) } } -bool isSslServiceAppId(AppId appId) +bool is_service_over_ssl(AppId appId) { switch (appId) { diff --git a/src/network_inspectors/appid/service_plugins/service_ssl.h b/src/network_inspectors/appid/service_plugins/service_ssl.h index fdc856d29..cfae444f2 100644 --- a/src/network_inspectors/appid/service_plugins/service_ssl.h +++ b/src/network_inspectors/appid/service_plugins/service_ssl.h @@ -36,7 +36,7 @@ public: }; AppId getSslServiceAppId(short srcPort); -bool isSslServiceAppId(AppId); +bool is_service_over_ssl(AppId); void service_ssl_clean(); int ssl_detector_process_patterns(); int ssl_scan_hostname(const uint8_t*, size_t, AppId*, AppId*); diff --git a/src/network_inspectors/appid/service_plugins/service_tftp.cc b/src/network_inspectors/appid/service_plugins/service_tftp.cc index 7f20da026..2780fbe25 100644 --- a/src/network_inspectors/appid/service_plugins/service_tftp.cc +++ b/src/network_inspectors/appid/service_plugins/service_tftp.cc @@ -25,9 +25,9 @@ #include "service_tftp.h" +#include "appid_inspector.h" #include "appid_module.h" #include "app_info_table.h" -#include "service_util.h" #include "protocols/packet.h" #define TFTP_PORT 69 @@ -72,7 +72,7 @@ TftpServiceDetector::TftpServiceDetector(ServiceDiscovery* sd) proto = IpProtocol::UDP; detectorType = DETECTOR_TYPE_DECODER; - app_id = add_appid_protocol_reference("tftp"); + app_id = AppIdInspector::get_inspector()->add_appid_protocol_reference("tftp"); appid_registry = { diff --git a/src/network_inspectors/appid/service_state.cc b/src/network_inspectors/appid/service_state.cc index 9e25e2b06..30d3e9df0 100644 --- a/src/network_inspectors/appid/service_state.cc +++ b/src/network_inspectors/appid/service_state.cc @@ -47,17 +47,32 @@ ServiceDiscoveryState::~ServiceDiscoveryState() delete brute_force_mgr; } +ServiceDetector* ServiceDiscoveryState::select_detector_by_brute_force(IpProtocol proto) +{ + if ( state == SERVICE_ID_STATE::SEARCHING_BRUTE_FORCE ) + { + if ( !brute_force_mgr ) + brute_force_mgr = new AppIdDetectorList(proto); + + service = brute_force_mgr->next(); + if ( !service ) + state = SERVICE_ID_STATE::FAILED; + } + + return service; +} + void ServiceDiscoveryState::set_service_id_valid(ServiceDetector* sd) { service = sd; reset_time = 0; - if (state != SERVICE_ID_STATE::VALID) + if ( state != SERVICE_ID_STATE::VALID ) { state = SERVICE_ID_STATE::VALID; valid_count = 0; } - if(!valid_count) + if ( !valid_count ) { detract_count = 0; last_detract.clear(); @@ -65,7 +80,7 @@ void ServiceDiscoveryState::set_service_id_valid(ServiceDetector* sd) last_invalid_client.clear(); } - if (valid_count < STATE_ID_MAX_VALID_COUNT) + if ( valid_count < STATE_ID_MAX_VALID_COUNT) valid_count++; } @@ -75,16 +90,19 @@ void ServiceDiscoveryState::set_service_id_valid(ServiceDetector* sd) * - invalid_client_count: If our service detector search had trouble * simply because of unrecognized client data, then consider retrying * the search again. */ -void ServiceDiscoveryState::set_service_id_failed(AppIdSession* asd, const SfIp* client_ip) +void ServiceDiscoveryState::set_service_id_failed(AppIdSession* asd, const SfIp* client_ip, + unsigned invalid_delta) { + invalid_client_count += invalid_delta; + /* If we had a valid detector, check for too many fails. If so, start * search sequence again. */ - if (state == SERVICE_ID_STATE::VALID) + if ( state == SERVICE_ID_STATE::VALID ) { /* Too many invalid clients? If so, count it as an invalid detect. */ - if (invalid_client_count >= STATE_ID_INVALID_CLIENT_THRESHOLD) + if ( invalid_client_count >= STATE_ID_INVALID_CLIENT_THRESHOLD ) { - if (valid_count <= 1) + if ( valid_count <= 1 ) { state = SERVICE_ID_STATE::SEARCHING_PORT_PATTERN; invalid_client_count = 0; @@ -100,7 +118,7 @@ void ServiceDiscoveryState::set_service_id_failed(AppIdSession* asd, const SfIp* invalid_client_count = 0; } } - else if (invalid_client_count == 0) + else if ( invalid_client_count == 0 ) { // Just a plain old fail. If too many of these happen, start search process over. if (last_detract.fast_eq6(*client_ip)) @@ -125,13 +143,27 @@ void ServiceDiscoveryState::set_service_id_failed(AppIdSession* asd, const SfIp* } } else if ( ( state == SERVICE_ID_STATE::SEARCHING_PORT_PATTERN ) && - ( asd->service_search_state == SESSION_SERVICE_ID_STATE::PENDING ) && - ( !asd->service_candidates.size() ) ) + ( asd->service_search_state == SESSION_SERVICE_SEARCH_STATE::PENDING ) && + ( !asd->service_candidates.size() ) ) { state = SEARCHING_BRUTE_FORCE; } } +void ServiceDiscoveryState::update_service_incompatiable(const SfIp* ip) +{ + if ( invalid_client_count < STATE_ID_INVALID_CLIENT_THRESHOLD ) + { + if ( last_invalid_client.fast_equals_raw(*ip) ) + invalid_client_count++; + else + { + invalid_client_count += 3; + last_invalid_client = *ip; + } + } +} + class AppIdServiceStateKey { public: @@ -207,7 +239,7 @@ ServiceDiscoveryState* AppIdServiceState::add(const SfIp* ip, IpProtocol proto, std::map::iterator it; it = service_state_cache->find(ssk); - if ( it == service_state_cache->end()) + if ( it == service_state_cache->end() ) { ss = new ServiceDiscoveryState; (*service_state_cache)[ssk] = ss; @@ -231,7 +263,7 @@ ServiceDiscoveryState* AppIdServiceState::get(const SfIp* ip, IpProtocol proto, std::map::iterator it; it = service_state_cache->find(ssk); - if ( it != service_state_cache->end()) + if ( it != service_state_cache->end() ) ss = it->second; return ss; @@ -248,7 +280,7 @@ void AppIdServiceState::remove(const SfIp* ip, IpProtocol proto, uint16_t port, std::map::iterator it; it = service_state_cache->find(ssk); - if ( it != service_state_cache->end()) + if ( it != service_state_cache->end() ) { delete it->second; service_state_cache->erase(it); @@ -263,22 +295,22 @@ void AppIdServiceState::remove(const SfIp* ip, IpProtocol proto, uint16_t port, } } -void AppIdServiceState::check_reset(AppIdSession* asd, const SfIp* ip, uint16_t port ) +void AppIdServiceState::check_reset(AppIdSession* asd, const SfIp* ip, uint16_t port) { ServiceDiscoveryState* sds = AppIdServiceState::get(ip, IpProtocol::TCP, port, asd->is_decrypted()); - - if (sds) + if ( sds ) { - if (!sds->reset_time) - sds->reset_time = packet_time(); - else if ((packet_time() - sds->reset_time) >= 60) + if ( !sds->get_reset_time() ) + sds->set_reset_time(packet_time() ); + else if ( ( packet_time() - sds->get_reset_time() ) >= 60 ) { AppIdServiceState::remove(ip, IpProtocol::TCP, port, asd->is_decrypted()); asd->set_session_flags(APPID_SESSION_SERVICE_DELETED); } } } + void AppIdServiceState::dump_stats(void) { // FIXIT-L - do we need to keep ipv4 and ipv6 separate? diff --git a/src/network_inspectors/appid/service_state.h b/src/network_inspectors/appid/service_state.h index 38ba0b9db..0aa105f8e 100644 --- a/src/network_inspectors/appid/service_state.h +++ b/src/network_inspectors/appid/service_state.h @@ -45,9 +45,9 @@ public: AppIdDetectorList(IpProtocol proto) { if (proto == IpProtocol::TCP) - detectors = &ServiceDiscovery::get_instance().tcp_detectors; + detectors = ServiceDiscovery::get_instance().get_tcp_detectors(); else - detectors = &ServiceDiscovery::get_instance().udp_detectors; + detectors = ServiceDiscovery::get_instance().get_udp_detectors(); dit = detectors->begin(); } @@ -75,9 +75,43 @@ class ServiceDiscoveryState public: ServiceDiscoveryState(); ~ServiceDiscoveryState(); + ServiceDetector* select_detector_by_brute_force(IpProtocol proto); void set_service_id_valid(ServiceDetector* sd); - void set_service_id_failed(AppIdSession* asd, const SfIp* client_ip); + void set_service_id_failed(AppIdSession* asd, const SfIp* client_ip, unsigned invalid_delta = + 0); + void update_service_incompatiable(const SfIp* ip); + SERVICE_ID_STATE get_state() const + { + return state; + } + + void set_state(SERVICE_ID_STATE state) + { + this->state = state; + } + + ServiceDetector* get_service() const + { + return service; + } + + void set_service(ServiceDetector* service) + { + this->service = service; + } + + time_t get_reset_time() const + { + return reset_time; + } + + void set_reset_time(time_t resetTime) + { + reset_time = resetTime; + } + +private: SERVICE_ID_STATE state; ServiceDetector* service = nullptr; AppIdDetectorList* brute_force_mgr = nullptr; @@ -104,7 +138,7 @@ public: static ServiceDiscoveryState* add(const SfIp*, IpProtocol, uint16_t port, bool decrypted); static ServiceDiscoveryState* get(const SfIp*, IpProtocol, uint16_t port, bool decrypted); static void remove(const SfIp*, IpProtocol, uint16_t port, bool decrypted); - static void check_reset(AppIdSession* asd, const SfIp* ip, uint16_t port ); + static void check_reset(AppIdSession* asd, const SfIp* ip, uint16_t port); static void dump_stats(); }; diff --git a/src/network_inspectors/appid/test/Makefile.am b/src/network_inspectors/appid/test/Makefile.am index 9d6586dc9..29a81919a 100644 --- a/src/network_inspectors/appid/test/Makefile.am +++ b/src/network_inspectors/appid/test/Makefile.am @@ -2,7 +2,10 @@ AM_DEFAULT_SOURCE_EXT = .cc check_PROGRAMS = \ -appid_http_event_test +appid_http_event_test \ +appid_api_test \ +appid_detector_test \ +app_info_table_test TESTS = $(check_PROGRAMS) @@ -10,5 +13,24 @@ appid_http_event_test_CPPFLAGS = -I$(top_srcdir)/src/network_inspectors/appid @A appid_http_event_test_LDADD = \ ../appid_stats_counter.o \ +../../../sfip/sf_ip.o \ +@CPPUTEST_LDFLAGS@ + +appid_api_test_CPPFLAGS = -I$(top_srcdir)/src/network_inspectors/appid @AM_CPPFLAGS@ @CPPUTEST_CPPFLAGS@ + +appid_api_test_LDADD = \ +../appid_stats_counter.o \ +../../../sfip/sf_ip.o \ +@CPPUTEST_LDFLAGS@ + +app_info_table_test_CPPFLAGS = -I$(top_srcdir)/src/network_inspectors/appid @AM_CPPFLAGS@ @CPPUTEST_CPPFLAGS@ +app_info_table_test_LDADD = \ +../appid_stats_counter.o \ +@CPPUTEST_LDFLAGS@ + +appid_detector_test_CPPFLAGS = -I$(top_srcdir)/src/network_inspectors/appid @AM_CPPFLAGS@ @CPPUTEST_CPPFLAGS@ +appid_detector_test_LDADD = \ +../appid_stats_counter.o \ +../../../sfip/sf_ip.o \ @CPPUTEST_LDFLAGS@ diff --git a/src/network_inspectors/appid/test/appMapping.data b/src/network_inspectors/appid/test/appMapping.data new file mode 100644 index 000000000..b0484490a --- /dev/null +++ b/src/network_inspectors/appid/test/appMapping.data @@ -0,0 +1,3237 @@ +2 3COM-TSMUX 0 0 0 +4 914CG 0 0 0 +5 ACA Services 0 0 0 +6 ACI 0 0 0 +7 ACR-NEMA 0 0 0 +9 ActiveSync 0 121 0 +10 AD Backup 0 0 0 +11 AD DRS 0 0 0 +12 AD DSAOP 0 0 0 +13 AD DSROL 0 0 0 +14 AD NSP 0 0 0 +16 AD Restore 0 0 0 +17 ADrive 0 0 24 +18 AD XDS 0 0 0 +19 AED512 0 0 0 +20 AFP 0 0 0 +22 AJP 20043 0 0 ajp +23 Alias 0 0 0 +24 Amazon 0 0 90 +26 ANSA Notify 0 0 0 +27 ANSA REX Trader 0 0 0 +29 Applejuice 20038 0 0 applejuice +30 AppleShare 0 0 0 +32 Apple Update 0 290 1585 +33 ARCISDMS 0 0 0 +34 Ariel 0 0 0 +35 ARNS 0 0 0 +37 ASA 0 0 0 +38 Astraweb 0 0 1445 +41 auditd 0 0 0 +42 AUDIT 0 0 0 +44 AVG 0 0 0 +45 Avira Download/Update 0 134 0 +46 Avocent 0 0 0 +47 Backblaze 0 0 112 +48 Backpack 0 0 26 +49 Battlefield 20039 0 0 battlefield +52 BFTP 0 0 0 +53 BGMP 0 0 0 +54 BH611 0 0 0 +55 BHEVENT 0 0 0 +56 BHFHS 0 0 0 +57 BHMDS 0 0 0 +58 Bing 0 0 114 +59 BitDefender 0 0 1775 +60 BITS 0 280 0 +61 BitTorrent 38 229 1349 bt +62 Blackboard 0 0 28 +63 Blackjack 0 0 0 +64 BlazeFS 0 0 0 +65 Britton Lee IDM 0 0 0 +66 Bnet 0 0 0 +67 Cableport AX 0 0 0 +68 CAICCI 20045 0 0 caicci +70 CAP 0 0 0 +71 CDC 0 0 0 +74 Check Point 20046 0 0 checkpoint +76 Cisco DRP 0 0 0 +77 Cisco FNATIVE 0 0 0 +78 Cisco GDP 0 0 0 +79 Cisco SLA 0 0 0 +80 Cisco SYSMAINT 0 0 0 +81 Cisco TNATIVE 0 0 0 +82 Citrix CGP 0 0 0 +84 Citrix IMA 0 0 0 +85 Citrix Jedi 0 0 0 +86 Citrix Licensing 0 0 0 +87 Citrix Online 0 0 1822 +88 Citrix RTMP 0 0 0 +89 Citrix SLG 0 0 0 +90 Citrix WANScaler 0 0 0 +91 CL1 0 0 0 +92 Clearcase 0 0 0 +93 CLOANTO 0 0 0 +94 CMIP 0 0 0 +95 Coda Auth 0 0 0 +96 Commvault 20171 0 1474 commvault +97 CompressNET 0 0 0 +98 COMSCM 0 0 0 +99 CORBA 0 0 0 +106 DASP 0 0 0 +107 DATEX-ASN 0 0 0 +108 dBase 0 0 0 +109 DCAP 0 0 0 +110 DCCP 0 0 0 +111 DCP 0 0 0 +112 DEC Auth 0 0 0 +113 DEC LaDebug 0 0 0 +114 DECVMS 0 0 0 +115 DEOS 0 0 0 +116 DHCPv6 20004 0 0 dhcpv6-server +117 Digg 0 0 31 +118 Direct Connect 20040 0 0 direct_connect +119 PDRE 0 0 0 +120 DIXIE 0 0 0 +121 DLS 0 0 0 +122 DNA-CML 0 0 0 +123 DNSIX 0 0 0 +124 DPSI 0 0 0 +125 Dropbox 0 300 98 +126 DSFGW 0 0 0 +127 DSP3270 0 0 0 +128 DSP 0 0 0 +129 DSSETUP 0 0 0 +130 DTAG 0 0 0 +131 DTK 0 0 0 +132 eBay 0 0 1551 +133 eBay Bid 0 0 32 +134 eBay Search 0 0 33 +135 eBay Watch 0 0 34 +136 eBuddy 0 0 35 +138 EMBLNDT 0 0 0 +139 EMFIS Data 0 0 0 +140 EntrustTime 0 0 0 +141 Epmap 0 0 0 +142 ERPC 0 0 0 +143 Eset 0 490 1774 +145 ESRO 0 0 0 +147 ETOS 0 0 0 +149 Facebook Apps 0 0 852 +150 Fark 0 0 36 +151 Farmville 0 0 440 +153 FastTrack 0 51 0 +154 Fatmen 0 0 0 +155 FileMaker 0 0 0 +158 FlashGet 0 52 0 +159 Flickr 0 0 225 +160 Flixster 0 219 0 +161 FogBugz 0 0 120 +162 F-Prot 0 0 1812 +163 FreeCast 0 0 831 +164 FriendFeed 0 0 1700 +165 FTP 8 0 0 ftp +166 FTP Data 36 0 0 ftp-data +167 FTPS Data 20132 0 0 ftpsdata +168 FTPS 20131 0 0 ftps +169 FXP 0 0 0 +170 GACP 0 0 0 +171 Ganglia 20047 0 0 ganglia +172 Genesis PPP 0 0 0 +173 Genie 0 0 0 +174 GENRAD 0 0 0 +175 Giganews 0 492 0 +176 GIOP 20048 0 0 giop +177 GIST 0 0 0 +178 Google APIs 0 0 1254 +179 Google App Engine 0 326 1052 +180 Google Drive 0 0 285 +182 Google Talk Gadget 0 460 0 +184 Google 0 0 872 +185 Google Translate 0 0 1295 +187 GoToMeeting 0 0 124 +188 GPFS 0 0 0 +190 Groupwise 20075 84 0 groupwise +192 Gss X License Verification 0 0 0 +193 ITU H.225 0 0 0 +194 ITU H.245 0 0 0 +197 Hassle 0 0 0 +198 HDAP 0 0 0 +199 HEMS 0 0 0 +200 HiveStor 0 0 0 +201 HL7 20153 262 0 hl7 +202 Hopster 0 0 1501 +205 Windows Live Hotmail 0 0 22 +206 HP Perf 0 0 0 +207 HP VMM 0 0 0 +209 HTTPMGT 0 0 0 +211 Hyper-G 0 0 0 +212 IASD 0 0 0 +214 ICA Browser 20051 0 0 ica_browser +215 ICAD 0 0 0 +216 ICAP 20052 0 0 icap +217 ICA 20050 0 0 ica +218 IceShare 0 55 0 +221 ICP 0 0 0 +222 ICQ2Go 0 0 42 +225 IKE 20064 0 0 isakmp +226 IMGames 0 0 0 +227 IMSP 0 0 0 +228 InBusiness 0 0 0 +229 Informix 20053 0 0 informix +230 InfoSeek 0 0 0 +231 Infostore 0 0 0 +232 IngresNET 0 0 0 +240 ircu 20054 0 0 ircu +243 ATG Live Help 0 0 0 +244 ISI Graphics 0 0 0 +247 Jargon 0 0 0 +248 Kaspersky 0 0 1778 +249 K-Block 0 0 0 +250 KFTPDATA 0 0 0 +251 KFTP 0 0 0 +252 KIS 0 0 0 +253 KNETCMP 0 0 0 +254 Kryptolan 0 0 0 +255 Ktelnet 0 0 0 +256 Kugou 0 58 832 +257 KVM 0 0 0 +258 KWDB 0 0 0 +259 L2TP 0 0 0 +261 Last.fm 0 411 1500 +262 Legent 0 0 0 +263 LINK 0 0 0 +264 Live365 0 0 45 +265 Livemeeting 0 0 1825 +266 Livestation 0 0 47 +267 LLMNR 0 0 0 +269 Locus Map 0 0 0 +270 LogMeIn 0 0 1532 +271 LSARPC 0 0 0 +272 Mafiawars 0 0 904 +273 Magenta Logic 0 0 0 +274 MagicJack 0 0 0 +275 MAILQ 0 0 0 +276 MANET 0 0 0 +277 MAPI 20081 89 0 mapi +278 Masqudialer 0 0 0 +279 MATIP 0 0 0 +280 McAfee 0 489 1773 +281 MC-FTP 0 0 0 +282 McIDAS 0 0 0 +283 mck-ivpip 0 0 0 +285 MediaFire 0 0 243 +287 Meeting Maker 0 0 0 +289 Metagram 0 0 0 +290 MF Cobol 0 0 0 +291 MFTP 0 0 0 +292 Mini SQL 0 0 0 +293 mit-ml-dev 0 0 0 +294 MIT Spooler 0 0 0 +295 Mixi 0 0 50 +296 MobileIP 0 0 0 +297 MortgageWare 0 0 0 +300 MPM 0 0 0 +302 MPTN 0 0 0 +303 MS CRS 0 0 0 +304 MSDN 0 0 423 +305 MSG 0 0 0 +306 MSMQ 0 0 0 +307 MSNP 0 0 0 +308 MSN 0 0 52 +309 MS OLAP 0 0 0 +310 MS Online 0 0 0 +311 MSP 0 0 0 +312 MS SQL 0 0 0 +313 MTA 0 0 0 +317 MySpace 0 0 14 +318 NAMP 0 0 0 +319 Napster 0 0 54 +320 NCED 0 0 0 +321 NCLD 0 0 0 +322 NDS Auth 0 0 0 +324 Netinfo 0 0 0 +325 Netlogon 0 0 0 +326 NetMeeting 0 0 0 +327 NETSC 0 0 0 +328 NetScout 0 0 0 +329 Netware 0 0 0 +330 NFA 0 0 0 +331 NFS 0 0 0 +332 NI FTP 0 0 0 +333 NI Mail 0 0 0 +334 NIP 0 0 0 +335 NNSP 0 0 0 +336 NovaBACKUP 0 0 1574 +337 NPP 0 0 0 +338 NSIIOPS 20130 0 0 nsiiops +339 NSRMP 0 0 0 +340 NSS 0 0 0 +341 NSSTP 0 0 0 +342 NXEdit 0 0 0 +343 NeXTStep 0 0 0 +344 OCBinder 0 0 0 +345 OCServer 0 0 0 +346 OCS 0 0 0 +347 ODMR 0 0 0 +348 OFTP 0 0 0 +349 OFTPS 0 0 0 +350 Onmux 0 0 0 +351 Opalis Robot 0 0 0 +352 Openport 0 0 0 +353 OpenVPN 0 0 0 +355 Oracle SQLNET 0 0 0 +356 Orkut 0 0 55 +357 OSCAR 0 0 0 +358 OSUNMS 0 0 0 +359 Panda 0 494 1776 +360 PartyPoker 0 0 57 +361 PAWSERV 0 0 0 +362 PCMAIL 0 0 0 +363 PDAP 0 0 0 +365 PFTP 0 0 0 +367 PIP 0 0 0 +368 PKIX Timestamp 0 0 0 +369 Plaxo 0 0 1596 +370 POP2 0 0 0 +374 PPStream 0 0 59 +375 PPTP 0 0 0 +376 lpr 21 0 0 ldp +377 PROFILE 0 0 0 +378 PROSPERO 0 0 0 +381 PWDGEN 0 0 0 +382 Qbik 0 0 0 +383 QFT 0 0 0 +384 QMTP 0 0 0 +385 QOTD 0 0 0 +386 QQ 20089 97 1600 qq +387 QuickTime 0 304 3 +388 RAP 0 0 0 +391 Remote Job Service 0 0 0 +392 Remote Telnet 0 0 0 +393 ResCap 0 0 0 +394 RFR 0 0 0 +395 RIP 0 0 0 +396 RIS 0 0 0 +397 RJE 0 0 0 +398 rlogin 29 0 0 login +399 RLP 0 0 0 +400 RMT 0 0 0 +401 RPC2PMAP 0 0 0 +402 RRP 0 0 0 +404 RSVD 0 0 0 +407 RTCP 0 0 0 +408 RTSPS 0 0 0 +409 SAMR 0 0 0 +410 SAP HostControl 0 0 0 +411 TFTP subnet broadcast 0 0 0 +412 Sco I2 Dialog Daemon 0 0 0 +414 SCTP 0 0 0 +415 Second Life 20033 0 0 secondlife +416 SecurSight 0 0 0 +417 Semantix 0 0 0 +418 SEND 0 0 0 +419 SET 0 0 0 +420 SFTP 0 0 0 +421 SGCP 0 0 0 +422 SGMP 0 0 0 +423 Sharepoint 0 0 0 +424 Shrinkwrap 0 0 0 +425 Silverplatter 0 0 0 +426 SIP 20028 30 0 sip +428 Skype Auth 20034 0 0 skype_auth +429 Skype Out 0 0 0 +430 Skype p2p 0 0 0 +431 Skype Probe 0 0 0 +432 Slingbox 0 0 64 +433 SMAKYNET 0 0 0 +434 Smart Session Description Protocol 0 0 0 +435 SMPTE 0 0 0 +436 SMSP 0 0 0 +437 SMUX 0 0 0 +438 SNA Gateway 0 0 0 +439 SNET 0 0 0 +440 SNPP 0 0 0 +441 SoftPC 0 0 0 +442 SoulSeek 20142 61 833 +444 SRC 0 0 0 +445 SRMP 0 0 0 +446 Sender Rewriting Scheme 0 0 0 +447 SSDP 0 0 0 +448 StationLauncher 0 62 0 +449 Stat Service 0 0 0 +450 Store Admin 0 0 0 +451 Su-Mit Telnet 0 0 0 +452 Sun RPC 28 0 0 sunrpc +453 SUPDUP 0 0 0 +454 SuperNews 0 0 1632 +458 Sybase SQL 0 0 0 +459 Symantec System Center 20057 0 0 symantec_system +461 Exchange System Attendant 0 0 0 +462 syslog 20020 0 0 syslog +463 Systat 0 0 0 +464 TACACS+ 20095 103 0 tacacs +466 TCPMUX 0 0 0 +468 Texar 0 0 0 +469 TFTPS 0 0 0 +470 Time 0 0 0 +471 Tmobile 0 0 0 +472 Tobit David 0 0 0 +473 TOR 0 0 0 +474 Tripwire 0 0 0 +475 Tumblr 0 271 255 +476 UAAC 0 0 0 +477 UARPS 0 0 0 +478 UC4 20059 0 0 uc4 +480 UIS 0 0 0 +481 ListProc 0 0 1530 +482 UMA 0 0 0 +483 Unicenter 20044 0 0 unicenter +484 Unidata LDM 0 0 0 +485 Unify 0 0 0 +486 UPS 0 0 0 +487 Usenet 0 0 0 +490 UUCP 0 0 0 +491 Vchat 0 0 0 +492 vettcp 0 0 0 +493 VMNET 0 0 0 +494 VM PWSCS 0 0 0 +495 Vonage 0 0 851 +496 VSLMP 0 0 0 +497 Vuze 0 63 834 +498 WCCP 0 0 0 +499 Webfilter 0 0 0 +500 WebLogic 20042 44 0 weblogic +501 Wikipedia 0 0 187 +502 Windows Live 0 0 1782 +503 Windows Media 0 0 0 +505 WINS 20014 0 0 nameserver +506 Wordpress 0 0 1718 +507 World of Warcraft 0 64 0 +510 Xanga 0 0 1715 +511 Xbone 0 0 0 +513 XDMCP 0 0 0 +514 Xfer 0 0 0 +515 XMPP 0 0 0 +516 XNS Authentication 0 0 0 +517 XNS Clearinghouse 0 0 0 +518 XNS Mail 0 0 0 +519 XNS Time 0 0 0 +520 XNS 0 0 0 +521 Xyplex 0 0 0 +522 Yahoo! Games 0 0 72 +524 Yahoo! 0 126 990 +525 ANSI Z39.50 0 0 0 +526 Zannet 0 0 0 +527 Zebra 0 0 0 +528 Zoho 0 0 1717 +529 Zoho Chat 0 0 75 +530 Zoho Mail 0 0 76 +532 Zoho Wiki 0 0 78 +533 Zynga 0 0 137 +535 1-800-Flowers 0 0 88 +536 100Bao 20068 69 0 100bao +537 2channel 0 0 109 +538 6.pm 0 0 207 +539 Ace Hardware Corporation 0 0 208 +540 Addicting Games 0 0 209 +541 Adobe Software 0 0 21 +542 Adorama 0 0 89 +544 American Express 0 0 110 +545 Android browser 0 49 0 +546 AOL Mail 0 0 13 +547 AOL Instant Messenger 2 19 0 aim +550 Apple Mail 0 7 0 +551 Apple Store 0 0 91 +552 ARCServe 20069 70 0 arcserve +553 Ares 20103 107 0 ares +554 Argos 0 0 92 +555 Atom 0 0 11 +556 Atom.com 0 0 210 +557 Autoblog 0 0 197 +558 AutoTrader.com 0 0 194 +559 B&H Photo Video 0 0 96 +560 Bank of America 0 0 113 +561 Barnes and Noble 0 0 94 +562 Barneys New York 0 0 211 +563 Basecamp 0 0 204 +564 Battle.net 20101 0 0 battle_net +565 BearShare 0 77 0 +566 Bebo 0 0 27 +567 Best Buy 0 0 95 +568 beWeeVee 0 0 283 +569 BGP 3 0 0 bgp +571 BitTorrent tracker 0 25 0 +572 Black & Decker Corporation 0 0 212 +573 Blackberry browser 0 50 0 +574 Blip.tv 0 0 213 +575 Blockbuster 0 0 192 +576 Blogger 0 0 29 +577 Bloomingdales 0 0 214 +578 Blue Nile 0 0 216 +579 Bluefly 0 0 215 +581 CamerasDirect.com.au 0 0 138 +582 Capital One 0 0 115 +583 Car and Driver 0 0 195 +584 CarMax 0 0 139 +585 CDiscount 0 0 140 +586 Character Generator 20000 0 0 chargen +587 Chase 0 0 191 +588 CheapTickets 0 0 218 +589 Chrome 0 46 0 +590 Citi 0 0 116 +591 City Sports 0 0 219 +592 Collabedit 0 0 286 +593 Costco 0 0 141 +594 Craigslist 0 0 206 +595 Crutchfield 0 0 142 +596 cURL 0 36 0 +597 CVS 20070 71 0 cvs +599 DAAP 20073 0 0 daap +600 Dailymotion 0 0 30 +601 David Jones 0 0 220 +602 DB2 20071 72 0 db2 +603 DCE/RPC 5 0 0 dcerpc +604 Deals Direct 0 0 143 +605 Delicious 0 0 221 +606 Dell 0 0 144 +607 Destructoid 0 0 222 +608 deviantART 0 0 287 +609 DHCP 4 0 0 dhcp +611 Dick's Sporting Goods 0 0 193 +612 Diigo 0 0 223 +613 Dillards 0 0 224 +614 Discard 20005 0 0 discard +615 Discover 0 0 117 +616 DNP3 20066 67 0 dnp3 +617 DNS 6 0 0 dns +618 DRDA 20072 73 0 drda +619 Dropbear 0 39 0 +620 Drugstore.com 0 0 145 +621 E*TRADE 0 0 118 +622 Edmunds.com 0 0 146 +623 eDonkey 20080 88 0 edonkey +624 Eudora 0 8 0 +625 Eudora Pro 0 9 0 +626 Evolution 0 5 0 +627 exec 7 0 0 exec +628 Expedia 0 0 147 +629 Facebook 0 161 17 +631 Facebook Comment 0 0 83 +632 Premier Football 0 0 97 +636 Fidelity 0 0 119 +637 Finger 20006 0 0 finger +638 Firefox 0 32 0 +639 Flash Video 0 0 9 +640 Fnac 0 0 148 +641 Foxy 0 80 0 +642 Friendster 0 0 37 +643 Fry's Electronics 0 0 149 +644 FTD 0 0 150 +646 G4 0 0 226 +647 Game Informer 0 0 227 +648 GameSpot 0 0 121 +649 GameSpy 0 0 228 +650 GameStop 0 0 122 +651 GameTrailers 0 0 229 +652 Gawker 0 0 123 +653 generic audio/video 0 0 7 +654 giFT 0 83 0 +655 Gmail 0 0 12 +656 Gnucleus 0 82 0 +657 GnucleusLAN 0 74 0 +658 Gnutella 20030 27 0 gnutella +659 Gnutella2 20074 0 0 gnutella2 +660 Google Analytics 0 218 38 +661 Google Calendar 0 0 39 +662 Google Desktop 0 42 0 +663 Google News 0 0 230 +664 Google Product Search 0 0 151 +665 Google Safebrowsing 0 0 40 +667 Gopher 20008 0 0 gopher +668 gtk-gnutella 0 81 0 +669 Haiku Learning Systems 0 0 231 +670 Home Depot 0 0 152 +671 Hostname server 20009 0 0 hostname +672 Google Earth 0 54 0 +673 Hotline 20077 86 0 hotline +674 House of Fraser 0 0 233 +675 HSBC 0 0 125 +676 HTTP 9 0 0 http +677 Hulu 0 0 41 +678 IBM App 0 0 0 +679 ICQ 0 56 1508 +680 IGN 0 0 126 +682 ImageShack 0 0 235 +683 IMAP 10 127 0 imap +684 Imgur 0 0 236 +685 imo.im 0 0 237 +686 Internet Explorer 0 1 0 +687 IRC 12 0 0 ircd +688 ITU H.323 20076 85 0 itu_h_323 +689 iTunes 0 75 850 +690 J.C. Penney 0 0 154 +691 J&R 0 0 155 +692 Jabber 20078 87 0 jabber +693 Jalopnik 0 0 196 +694 Java RMI 20055 0 0 java_rmi +695 JIRA 0 0 201 +696 Joystiq 0 0 238 +697 KAD 20079 0 0 kad +698 Kay Jewelers 0 0 156 +700 KMail 0 12 0 +701 Kerberos 20011 128 0 kerberos +702 Kmart 0 0 157 +703 Kogan Technologies 0 0 158 +704 Kohl's 0 0 159 +705 Kongregate 0 0 239 +706 Konqueror 0 4 0 +707 Kotaku 0 0 199 +708 Launchpad 0 0 203 +710 LDAP 20012 0 0 ldap +711 Limelight 0 0 43 +712 LimeWire 0 76 0 +713 LinkedIn 0 0 44 +714 LinkedIn Job Search 0 0 87 +715 Linuxconf 20013 0 0 linuxconf +716 LiveJournal 0 0 46 +718 Lokalisten 0 0 106 +719 Lord & Taylor 0 0 240 +720 Lotus Notes 20056 6 0 lotus_notes +721 LOVEFiLM 0 0 241 +722 Lowe's 0 0 160 +723 lsh 0 40 0 +724 Manolito 20084 98 0 manolito +725 Megaco 20085 93 0 megaco +727 Menards 0 0 245 +728 Metacafe 0 0 246 +729 MetaFilter 0 0 79 +730 MGCP 20082 90 0 mgcp +731 Microsoft Update 0 0 15 +732 Microsoft Windows Messenger 0 23 0 +733 Minus 0 0 247 +734 Mixx 0 0 248 +735 MMS 20083 91 0 mms +736 Mobile Safari 0 47 0 +737 Modbus 20067 0 0 modbus +738 Morgan Stanley 0 0 128 +739 Morpheus 0 79 0 +741 MP4 0 0 2 +742 MPEG 0 0 1 +743 MSN Messenger 20035 16 0 msn_messenger +745 Mute 20086 94 0 mute +746 Mutt 0 11 0 +747 MySQL 14 0 0 mysql +748 myUdutu 0 0 274 +749 NCP 20087 95 0 ncp +750 Neckermann 0 0 161 +751 Neiman Marcus 0 0 249 +752 Nessus 20015 0 0 nessus +753 NetBIOS-dgm 15 0 0 netbios-dgm +754 NetBIOS-ns 16 0 0 netbios-ns +755 NetBIOS-ssn (SMB) 17 0 0 netbios-ssn +756 Netflix 0 0 162 +757 Netlog 0 0 290 +758 Netvibes 0 0 107 +759 Newegg 0 0 163 +760 NewsNow 0 0 250 +761 Newsvine 0 0 251 +762 Nico Nico Douga 0 0 80 +763 NNTP 18 0 0 nntp +764 Nordstrom 0 0 252 +765 NSPlayer 0 92 0 +766 ntalk 20016 0 0 ntalk +767 NTP 19 0 0 ntp +768 Office Depot 0 0 164 +769 OfficeMax 0 0 253 +770 oo.com.au 0 0 165 +771 OpenSSH 0 37 0 +773 Oracle Database 0 29 0 +774 TNS/Oracle 20026 0 0 oracle +775 Orbitz 0 0 254 +776 Outlook 0 2 0 +777 Outlook Express 0 3 0 +778 Overstock.com 0 0 166 +779 Pandora 0 298 56 +780 PC-Duo 20065 68 0 pc_duo +781 PcAnywhere 20088 96 0 pcanywhere +782 PeerCast 20092 100 0 peercast +783 PeerEnabler 0 59 0 +784 Photobucket 0 0 81 +785 Picasa 0 41 1294 +786 Poco 20093 101 0 poco +787 Pogo 0 0 58 +788 POP3 20 129 0 pop3 +789 PopCap Games 0 0 256 +790 PopUrls 0 0 257 +791 PostgreSQL 20017 102 0 postgresql +792 Priceline.com 0 275 258 +793 ProFlowers 0 0 167 +794 PuTTY 0 38 0 +795 Quake 20090 99 0 quake +796 Quickflix 0 0 259 +797 Quill Corporation 0 0 260 +798 QVC 0 0 168 +799 Qzone 0 0 288 +800 RADIUS 23 0 0 radius +801 RADIUS-acct 22 0 0 radacct +803 RDP 20029 33 0 rdp +804 Reddit 0 0 61 +805 Redmine 0 0 200 +806 REI 0 0 169 +808 Renren 0 0 289 +809 REVOLVEclothing 0 0 261 +810 Rona 0 0 262 +811 RSS 0 0 10 +812 RTMP 20063 0 0 rtmp +813 RTP 20032 31 0 rtp +814 RTSP 20018 0 0 rtsp +815 Safari 0 45 0 +816 Saks Fifth Avenue 0 0 263 +817 Sam's Club 0 0 171 +818 schuelerVZ 0 0 104 +819 Schwab 0 0 130 +820 Scottrade 0 0 131 +821 Sears 0 0 172 +822 Shareaza 0 78 0 +823 shell 27 0 0 shell +824 Shockwave 0 241 8 +825 Shoplet 0 0 264 +826 ShopNBC 0 0 174 +827 HP Home & Home Office Store 0 0 153 +828 ShopStyle 0 0 265 +829 SHOUTCast Radio 0 0 62 +830 ShowClix 0 0 266 +831 ShowDocument 0 0 284 +832 Skype 0 21 1255 +834 Slashdot 0 0 63 +836 SMTP 30 125 0 smtp +837 SNMP 31 0 0 snmp +839 SOCKS 20019 0 0 socks +840 Soribada 0 0 65 +841 spin.de 0 0 105 +842 Sports Authority 0 0 267 +843 SQL Server 20041 0 0 sql_server +844 Squid 20062 0 0 squid +846 SSH 32 0 0 ssh +847 SSL 33 0 0 ssl +848 Staples 0 0 175 +849 StayFriends 0 0 101 +850 StubHub 0 0 268 +851 studiVZ 0 0 103 +852 StumbleUpon 0 0 66 +853 STUN 20037 0 0 stun +854 Swarovski 0 0 269 +855 T. Rowe Price 0 0 133 +856 TDS 0 43 0 +857 talk 20021 0 0 talk +858 Target 0 0 176 +859 Tchibo 0 0 177 +860 TD Ameritrade 0 327 111 +861 Telnet 34 0 0 telnet +862 TFTP 35 0 0 tftp +863 The Gap 0 0 205 +864 The Sharper Image 0 0 173 +865 ThinkGeek 0 0 178 +866 Thunderbird 0 14 0 +867 Ticketmaster 0 0 179 +868 Tickets.com 0 0 180 +869 TicketsNow 0 0 270 +870 Tiffany & Co. 0 0 271 +871 Tiger Direct 0 0 181 +872 Timbuktu 20031 28 0 timbuktu +873 TinyPic 0 0 272 +874 Tivoli 20058 254 0 tivoli +875 TN3270 20096 104 0 tn3270 +876 TOC 20097 105 0 toc +877 Top Gear 0 0 198 +878 Trac 0 0 202 +880 Travelocity 0 0 182 +881 TripAdvisor 0 0 273 +882 Twitter 0 305 67 +883 Urban Outfitters 0 0 275 +884 Ustream.tv 0 0 68 +885 Vanguard 0 0 134 +886 vCOM 20060 0 0 vcom +887 Vehix 0 0 183 +888 vente-privee.com 0 0 184 +889 Veoh 0 0 276 +890 Verizon Email 0 0 69 +891 Viadeo 0 0 108 +892 Victoria's Secret 0 0 185 +893 Vimeo 0 0 277 +894 VNC 24 34 0 vnc +895 RFB 20023 0 0 vnc-server +898 Docstor 0 0 425 +899 Voyages-sncf.com 0 0 278 +900 Wachovia 0 0 135 +901 Walmart 0 0 186 +902 WAV 0 0 5 +903 Web Of Trust 0 0 279 +904 WebDAV 0 0 16 +905 WebEx 0 0 70 +906 WebSphere MQ 20049 0 0 websphere_mq +907 Wells Fargo 0 0 136 +908 wer-kennt-wen 0 0 102 +909 Wget 0 35 0 +910 Zynga Poker 0 0 422 +911 Windows Live SkyDrive 0 0 132 +912 Windows Media Player 0 48 0 +913 WinMX 20099 0 0 winmx +914 WiZiQ 0 0 280 +915 WMA 0 0 6 +916 WMV 0 0 4 +917 Woot 0 0 188 +918 WX 20061 0 0 wx +919 X font server 20007 0 0 font-service +920 9p.com 0 0 421 +921 Xbox Live 20102 108 0 xbox_live +922 XING 0 0 100 +923 XM Radio Online 0 0 71 +924 Xunlei 20104 109 0 xunlei +925 XWindows 20098 106 0 x11 +926 Yahoo! Voice 0 65 0 +927 Yet ABC 0 66 0 +928 Hightail 0 0 73 +929 YouTube 0 297 74 +930 Zales 0 0 189 +931 Zappos 0 0 190 +932 Zip.ca 0 0 281 +934 FireAMP 20105 110 0 fireamp +936 Yahoo! Messenger 20036 22 0 yahoo_messenger +937 Googlebot 0 288 0 +938 Yelp 0 0 0 +939 Netflix stream 0 0 1672 +940 Docstoc 0 0 424 +941 Grooveshark 0 0 1705 +942 Yahoo! Slurp 0 337 0 +943 Bingbot 0 278 0 +944 iMesh 0 0 1787 +945 Share P2P 0 0 0 +946 Yahoo! Mail 0 0 18 +947 Yahoo! Toolbar 0 0 20 +948 4shared 0 0 23 +949 Megaupload 0 0 48 +950 Salesforce.com 0 0 129 +951 RitzCamera.com 0 0 170 +952 Macy's 0 0 242 +953 whois 20024 0 0 whois +954 echo 20002 0 0 echo +955 daytime 20003 0 0 daytime +956 Ident 20010 0 0 ident +957 Pando 20194 0 1779 +958 TeamViewer 0 0 1637 +959 7digital 0 0 291 +960 Avoidr 0 0 292 +962 Chatroulette 0 0 294 +963 Cyworld 0 0 295 +964 Daum 0 0 296 +965 Deezer 0 0 297 +966 DivShare 0 0 298 +967 dl.free.fr 0 0 299 +970 Evony 0 0 302 +971 FileDropper 0 0 303 +972 Filemail 0 0 304 +973 FileServe 0 0 305 +974 Licorize 0 0 306 +975 folkd 0 0 307 +976 FORA.tv 0 0 308 +977 GMX Mail 0 0 309 +978 GOGOBOX 0 0 310 +979 CiteULike 0 0 311 +980 Habbo 0 0 312 +981 Hushmail 0 0 313 +982 The Hype Machine 0 0 314 +983 ifile.it 0 0 315 +984 iHeartRadio 0 414 316 +985 Issuu 0 0 317 +986 Jamendo 0 0 318 +987 Jango 0 0 319 +988 Justin.tv 0 0 320 +989 Kaixin001 0 0 321 +991 Livestream 0 0 323 +992 Me2day 0 0 324 +993 Megashare 0 0 325 +994 Megashares 0 0 326 +995 MyDownloader 0 0 327 +996 Neopets 0 0 328 +997 Omegle 0 0 329 +999 Mister Wong 0 0 331 +1001 ProxEasy 0 0 333 +1002 Qriocity 0 0 334 +1003 RuneScape 0 0 335 +1004 Schmedley 0 0 336 +1005 Scribd 0 0 337 +1006 Songza 0 0 338 +1007 SoundCloud 0 0 339 +1010 Suresome 0 0 342 +1011 Surrogafier 0 0 343 +1013 Tinychat 0 0 345 +1014 Tudou 0 0 346 +1015 TransferBigFiles.com 0 0 347 +1016 Tuenti 0 0 348 +1017 TurboUpload 0 0 349 +1018 VKontakte 0 0 350 +1019 VTunnel 0 0 351 +1020 Webhard 0 0 352 +1021 Webshots 0 0 353 +1022 Weibo 0 0 354 +1025 WooMe 0 0 357 +1026 Writeboard 0 0 358 +1027 BigUpload 0 0 359 +1028 Clarizen 0 0 360 +1029 Rdio 0 0 361 +1031 56.com 0 0 363 +1032 51.com 0 0 364 +1033 Youku 0 0 365 +1034 Crackle 0 0 366 +1035 RuTube 0 0 367 +1037 Afreeca 0 0 369 +1038 Babelgum 0 0 370 +1040 Octopz 0 0 372 +1041 MOG 0 0 373 +1046 Phanfare 0 0 378 +1047 we7 0 0 379 +1048 FilmOn 0 0 380 +1049 Mibbit 0 0 381 +1050 BigBlueButton 0 0 382 +1051 TwitchTV 0 0 383 +1052 MegaMeeting 0 0 384 +1053 Badoo 0 0 385 +1054 DepositFiles 0 0 386 +1055 CloudMe 0 0 387 +1057 Skyrock 0 0 389 +1060 Jubii 0 0 392 +1061 TotoExpress 0 0 393 +1062 Easy-Share 0 0 394 +1063 TwitPic 0 0 395 +1064 yfrog 0 0 396 +1065 Tagged 0 0 397 +1066 hi5 0 0 398 +1067 Livemocha 0 0 399 +1068 Slacker 0 0 400 +1069 Douban 0 0 401 +1070 Odnoklassniki 0 0 402 +1071 Gaia Online 0 0 403 +1072 MyHeritage 0 0 404 +1073 AutoZone 0 0 405 +1074 Dangdang 0 0 406 +1075 PC Mall 0 0 407 +1076 iCal 0 120 0 +1077 Tesco.com 0 0 409 +1078 xda-developers 0 0 410 +1079 4chan 0 0 411 +1080 NeoGAF 0 0 412 +1081 Rhapsody 0 0 413 +1082 Balatarin 0 0 414 +1084 Movieclips 0 0 416 +1085 RDT 20109 0 0 rdt +1086 Steam 20113 0 0 steam +1087 9P 20106 111 0 9p +1088 MSDP 20111 114 0 msdp +1089 RealAudio 20116 118 417 realaudio +1090 TeamSpeak 20110 113 0 teamspeak +1091 Ventrilo 20112 115 0 ventrilo +1092 Winamp 20117 112 0 winamp +1093 Advanced Packaging Tool 20115 116 0 apt +1094 iWARP 20114 117 0 iwarp +1095 IPP 20108 0 449 ipp +1096 NDMP 20107 0 0 ndmp +1097 rsync 26 0 0 rsync +1098 OPC 0 0 0 +1099 Paltalk Messenger 0 0 0 +1100 Paltalk Chat 0 0 0 +1101 Paltalk File Transfer 20195 0 0 paltalkfilexfer +1102 Paltalk Video 0 0 0 +1103 Paltalk Voice 0 0 0 +1105 Windows Update 0 328 0 +1106 Google+ 0 0 0 +1107 AOL Instant Messenger Netscape 0 0 0 +1108 IMO 0 0 0 +1109 PC Connection 0 0 408 +1110 ASF 0 0 0 +1111 DDM-SSL 20118 0 0 ddm_ssl +1112 SMTPS 20119 0 0 smtps +1113 NNTPS 20120 0 0 nntps +1114 IMAPS 20121 0 0 imaps +1115 SShell 20122 0 0 sshell +1116 LDAPS 20123 0 0 ldaps +1117 TELNETS 20124 0 0 telnets +1118 IRCS 20125 0 0 ircs +1119 POP3S 20126 0 0 pop3s +1120 MS Global Catalog Secure 20127 0 0 msgblcatsec +1121 SF MGMT 20128 0 0 sf_mgmt +1122 HTTPS 20129 0 0 https +1123 Tweet 0 0 418 +1124 Adobe Connect 0 0 419 +1125 BitTornado 0 119 0 +1126 Skype Tunneling 0 0 0 +1127 Applejuice GUI 0 0 0 +1129 CafeMom 0 0 427 +1132 MetaCrawler 0 0 430 +1133 Mininova 0 0 431 +1134 PayPal 0 0 432 +1135 Pinterest 0 185 433 +1136 The Pirate Bay 0 0 434 +1137 Technorati 0 0 435 +1138 Torrentz 0 0 436 +1139 TypePad 0 0 437 +1140 Hotspot Shield 20133 0 1502 hotspot_shield +1141 Zabbix 20134 0 0 zabbix +1142 Zabbix Trap 20135 0 0 zabbix_trap +1143 WhatsApp 0 0 1689 +1144 Munin 20136 0 1830 munin +1145 ASProxy 0 0 0 asproxy +1146 Google Toolbar 0 122 0 +1147 DynGate 0 0 0 +1148 Pinger 0 0 1595 +1149 Line2 0 0 1529 +1150 SCCM 0 0 1799 +1151 SCCM Remote Control 0 0 0 +1152 Steam browser 0 0 0 +1153 Steam DLC 0 0 0 +1154 Steam gaming 0 0 0 +1155 Steam social networking 0 0 0 +1156 Hamachi 0 0 0 +1157 Tetris Battle 0 0 438 +1158 Spotify 0 123 575 +1159 Bubble Witch Saga 0 0 439 +1161 Diamond Dash 0 0 442 +1162 Angry Birds 0 0 443 +1163 Words With Friends 0 0 444 +1164 Castleville 0 0 445 +1166 Cityville 0 0 448 +1167 About.com 0 0 1408 +1168 Answers.com 0 0 1434 +1169 Classmates 0 0 1466 +1170 CNET 0 0 1140 +1171 CNET Download 0 0 1157 +1172 DomainTools 0 0 1540 +1173 IBM 0 0 1506 +1175 Open Webmail 0 0 1580 +1176 SlideShare 0 0 1621 +1177 Sourceforge 0 0 1628 +1178 SurveyMonkey 0 0 1633 +1180 w3schools.com 0 0 1712 +1181 Weebly 0 0 1716 +1183 Google Maps 0 0 1780 +1184 APNS 0 0 0 +1185 Apple sites 0 0 1105 +1186 Facetime 0 0 0 +1187 iCloud 0 0 691 +1189 PCoIP 0 0 0 +1190 CNN.com 0 0 450 +1191 IMDB 0 0 451 +1192 NBC News 0 0 452 +1193 Mint.com 0 0 453 +1194 Apple Trailers 0 0 454 +1195 Dictionary.com 0 0 455 +1196 Bild.de 0 0 456 +1197 Bing Maps 0 0 457 +1198 Google Finance 0 0 458 +1200 TCX Flash 0 0 0 +1201 TCX Multimedia 0 0 0 +1202 TCX Sound 0 0 0 +1203 TCX USB 0 0 0 +1205 12306.cn 0 0 1399 +1206 126.com 0 0 1400 +1207 39.net 0 0 1406 +1208 Aizhan 0 0 1432 +1209 Bet365 0 0 1451 +1210 Brothersoft 0 0 1457 +1211 Brighttalk 0 0 1455 +1212 Enet 0 0 1549 +1213 Envato 0 0 1547 +1214 ExtraTorrent 0 0 1352 +1215 Glype Proxy 0 0 1781 +1216 goo.ne.jp 0 0 1720 +1217 Image Venue 0 0 1511 +1218 KAT 0 0 1710 +1219 Leboncoin 0 0 1525 +1220 Multiupload 0 0 1708 +1221 MSN2Go 0 0 1707 +1222 Netease 0 0 1570 +1223 Online File Folder 0 0 1579 +1224 Putlocker 0 0 1034 +1225 Raging Bull 0 0 1605 +1226 Soku 0 0 1626 +1227 Theme Forest 0 0 1767 +1228 Webs 0 0 1728 +1229 Bejeweled Chrome Extension 0 0 459 +1230 Google Play Books 0 0 460 +1231 Google Play Music 0 0 461 +1232 Google Reader 0 246 462 +1233 Instagram 0 124 463 +1234 DoubleDownCasino 0 0 464 +1236 Family Tree 0 0 466 +1237 Playdom 0 0 467 +1238 iAstrology 0 0 468 +1239 Social Empires 0 0 469 +1240 Mesmo Games 0 0 470 +1241 Daily Horoscope 0 0 471 +1243 Slotomania 0 0 473 +1244 Bubble Saga 0 0 474 +1245 Pool Live 0 0 475 +1247 Monster World 0 0 477 +1248 21 Questions 0 0 478 +1250 BranchOut 0 0 480 +1252 Bejeweled Blitz 0 0 482 +1253 Washington Post Social Reader 0 0 483 +1254 Bubble Island 0 0 484 +1256 4399.com 0 0 1407 +1257 AdF.ly 0 0 1412 +1258 Admin5 0 0 1417 +1259 Bloomberg 0 0 1392 +1260 Datei.to 0 0 1484 +1261 Mozilla 0 0 1565 +1262 Wretch 0 0 1714 +1263 Y8 0 0 1727 +1264 Avast 0 130 888 +1265 Allmyapps 0 131 0 +1267 Evernote 0 133 0 +1280 Seamonkey 0 147 0 +1282 Facebook search 0 0 841 +1283 Facebook event 0 0 842 +1284 Facebook Status Update 0 0 843 +1285 Facebook video chat 0 0 844 +1286 Facebook Message 0 0 845 +1287 Facebook video 0 0 846 +1288 Opera 0 149 0 +1290 AdobeAIR 0 151 0 +1296 SSL client 0 0 0 +1297 FireAMP SSL 0 0 0 +1298 Wooga 0 0 0 +1299 The New York Times 0 0 487 +1300 Twitter Link Service 0 0 488 +1301 Yahoo! Finance 0 0 489 +1302 Silverlight 0 0 490 +1303 Isoball 0 0 491 +1304 GO.com 0 0 492 +1305 OnLive 0 0 493 +1306 Ad Advisor 0 0 494 +1307 Ad Mob 0 0 495 +1308 Ad Marvel 0 0 496 +1309 Naver 0 384 497 +1310 Advertising.com 0 0 498 +1312 Burstly 0 0 500 +1313 Doubleclick 0 0 501 +1314 Ad Nexus 0 0 502 +1315 Pubmatic 0 0 503 +1316 Pulse360 0 0 504 +1317 Kanoodle 0 0 505 +1318 Greystripe 0 0 506 +1319 iAd 0 0 507 +1322 Acrobat.com 0 0 906 +1326 Box 0 0 217 +1327 Pandora TV 0 0 839 +1332 CBS 0 0 980 +1335 USA Today 0 0 1108 +1336 Microsoft Ads 0 0 508 +1337 Millennial Media 0 0 509 +1338 Weather Underground 0 0 510 +1340 Clubbox 0 0 512 +1341 Kiwoom 0 0 513 +1342 DCinside 0 0 514 +1343 Nate 0 0 515 +1344 Fileguri 0 0 516 +1345 Baidu 0 0 517 +1346 Babylon 0 0 518 +1357 Samsung 0 0 1046 +1360 TweetDeck 0 0 522 +1361 CanvasRider 0 0 523 +1362 ZEDO 0 0 524 +1363 eHow 0 0 525 +1364 ESPN 0 0 526 +1365 Comcast 0 0 527 +1366 Fox News 0 0 528 +1367 Weather.com 0 251 529 +1368 Weather.gov 0 0 530 +1369 Outbrain 0 0 531 +1370 The Huffington Post 0 0 532 +1371 Ask.com 0 0 533 +1372 OptMD 0 0 534 +1373 GoDaddy 0 0 535 +1374 Etsy 0 0 536 +1375 Conduit 0 0 537 +1376 BBC 0 0 538 +1378 Indeed 0 0 540 +1379 Publishers Clearing House 0 0 541 +1380 AT&T 0 0 542 +1381 Aweber 0 0 543 +1382 Fox Sports 0 0 544 +1383 Searchnu 0 0 545 +1384 Search-Result.com 0 0 546 +1385 Official Major League Baseball 0 0 547 +1386 RoadRunner 0 0 548 +1387 Drudge Report 0 0 549 +1388 Verizon Wireless 0 0 550 +1389 ABC 0 248 551 +1390 Wall Street Journal 0 0 552 +1391 Daily Mail 0 0 553 +1392 Amazon Web Services 0 0 554 +1393 CloudFront 0 0 555 +1398 Sourcefire.com 0 0 560 +1399 Taobao 0 0 561 +1400 Planetarium 0 0 562 +1401 Engadget 0 158 563 +1402 Flipboard 0 159 564 +1403 TED 0 160 565 +1405 KakaoTalk 0 162 1071 +1406 Flurry Analytics 0 0 566 +1407 Apple Stocks 0 163 0 +1408 Ubuntu Software Center 0 0 567 +1409 Ubuntu Update Manager 0 0 568 +1411 Python-httplib 0 166 0 +1412 Eclipse Updates 0 0 569 +1413 Eclipse 0 167 907 +1414 Eclipse Marketplace 0 0 570 +1415 Apple Mobile Yahoo API 0 0 571 +1416 Weather 0 168 0 +1417 NASA 0 0 572 +1418 NATO 0 0 573 +1419 AOL 0 0 574 +1420 NOAA 0 0 576 +1421 WeatherBug 0 169 577 +1422 FC2 0 0 578 +1423 Microsoft 0 0 579 +1424 Google Adsense 0 0 580 +1425 AdNetwork.net 0 0 581 +1426 Localytics 0 0 582 +1427 Nokia Maps 0 0 583 +1428 SymantecUpdates 0 293 584 +1429 Wolfram Alpha 0 171 585 +1430 Libwww-Perl 0 170 0 +1431 Norton AntiVirus 0 172 0 +1440 FastCGI 20137 181 0 fast_cgi +1441 TPNCP 20138 0 0 tpncp +1449 Kuaibo 0 0 586 +1450 SMPP 20139 0 0 smpp +1451 Kismet 20140 0 0 kismet +1456 Sports Illustrated 0 0 710 +1457 CPX Interactive 0 0 711 +1458 VeriSign 0 0 712 +1459 CBS Sports 0 0 713 +1460 Chartbeat 0 0 714 +1461 InsightExpress 0 0 715 +1480 Zillow 0 0 720 +1481 Monster.com 0 0 721 +1482 MapQuest 0 0 722 +1483 Swagbucks 0 0 723 +1484 Verizon 0 0 724 +1485 Wikia 0 0 725 +1486 TMZ 0 0 726 +1487 ShopAtHome 0 0 727 +1488 Asia Times Online 0 0 728 +1489 HootSuite 0 0 729 +1490 Coupons.com 0 0 730 +1491 CareerBuilder.com 0 0 731 +1492 Commission Junction 0 0 732 +1493 Fiverr 0 0 733 +1494 Backpage.com 0 0 734 +1495 LivingSocial 0 0 735 +1496 AllRecipes 0 0 736 +1497 Yellow Pages 0 0 737 +1498 Bleacher Report 0 0 738 +1499 Stack Overflow 0 0 739 +1500 U.S.Bank 0 0 740 +1501 Ancestry.com 0 0 741 +1502 WebMD 0 0 742 +1503 Trulia 0 0 743 +1504 Slickdeals 0 0 744 +1505 Business Insider 0 0 745 +1506 People.com 0 0 746 +1507 Reuters 0 0 747 +1508 BuzzFeed 0 0 748 +1509 California.gov 0 0 749 +1510 Southwest Airlines 0 0 750 +1511 NIH 0 0 751 +1512 WhitePages Inc 0 0 752 +1513 MGID 0 0 753 +1514 EarthLink 0 0 754 +1515 Disney 0 0 755 +1516 POLITICO.com 0 0 756 +1517 NY Daily News 0 0 757 +1518 Examiner.com 0 0 758 +1519 RetailMeNot 0 0 759 +1520 AddThis 0 0 760 +1521 StatCounter 0 0 761 +1522 OkCupid 0 0 762 +1523 Patch.com 0 0 763 +1524 Legacy.com 0 0 764 +1525 Realtor.com 0 0 765 +1526 Intuit 0 0 766 +1527 The Blaze 0 0 767 +1528 HostGator 0 0 768 +1529 Food Network 0 0 769 +1530 ClickBank 0 0 770 +1531 Cox 0 0 771 +1532 Mashable 0 0 772 +1533 AccuWeather 0 0 773 +1534 Sprint 0 0 774 +1535 Goodreads 0 0 775 +1536 LiveStrong.com 0 0 776 +1537 RealClearPolitics 0 0 777 +1538 Manta 0 0 778 +1539 Empower Network 0 0 779 +1540 CNBC 0 0 780 +1541 Widget Media 0 0 781 +1542 Inbox.com 0 0 782 +1543 Shutterfly 0 0 783 +1544 Neteller 0 0 784 +1545 T Mobile 0 0 785 +1546 Walgreens 0 0 786 +1547 WorldstarHipHop 0 0 787 +1548 NPR 0 0 788 +1549 Kayak 0 0 789 +1550 ToysRUs 0 0 790 +1551 Mail.Ru 0 0 791 +1552 Sohu.com 0 0 792 +1553 1&1 Internet 0 0 793 +1554 Ameba 0 0 794 +1555 Avaya 0 0 795 +1556 Axifile 0 0 796 +1557 Snort.org 0 0 797 +1558 Disqus 0 0 798 +1559 Infusionsoft 0 0 799 +1560 IMRWorldWide 0 0 800 +1561 Alisoft 0 0 801 +1562 Salesforce.com Live Agent 0 0 802 +1565 QVOD 20141 186 805 +1567 Fab.com 0 0 806 +1568 Square Inc. 0 0 807 +1569 Java Update 0 187 1837 +1570 Xlite SIP Client 0 0 0 +1571 X-PRO SIP Client 0 0 0 +1572 Nero SIP Client 0 0 0 +1573 ClearSea SIP Client 0 0 0 +1575 Dooble 0 189 0 +1576 Lynx 0 192 0 +1578 Epiphany 0 191 0 +1579 Chimera2 0 190 0 +1581 Links 0 197 0 +1582 Midori 0 196 0 +1583 NetSurf 0 195 0 +1584 rekonq 0 193 0 +1585 wApua 0 194 0 +1589 Comodo Dragon 0 203 0 +1592 PaleMoon 0 206 0 +1593 Wyzo 0 207 0 +1595 BioDigital Human 0 0 0 +1596 Apple Developer 0 0 692 +1597 Geewa 0 0 0 +1598 GoToMyPC 0 0 873 +1599 King.com 0 0 937 +1601 USPS 0 0 1127 +1602 Xcode 0 233 0 +1603 Siri 0 0 0 +1604 Bria 0 0 0 +1605 sipXecs 0 0 0 +1606 Linphone 0 0 0 +1607 OpenSIPS 0 0 0 +1608 TextMe 0 0 0 +1609 FreeSWITCH 0 0 0 +1610 Asterisk PBX 0 0 0 +1611 textPlus 0 223 0 +1612 Cisco SIP Gateway 0 0 0 +1613 Nuance Voice Platform 0 0 0 +1614 Shutterstock 0 0 808 +1615 Aili 0 0 809 +1616 Yandex 0 0 810 +1617 Adcash 0 0 811 +1618 The Guardian 0 0 812 +1619 Yieldmanager 0 0 862 +1620 The Telegraph 0 0 813 +1621 Livedoor 0 0 814 +1622 WarriorForum 0 0 815 +1623 Indiatimes 0 0 816 +1624 Rediff.com 0 0 817 +1625 Spiegel Online 0 0 818 +1626 UOL 0 0 819 +1627 Jingdong (360buy.com) 0 0 820 +1628 The Xinhuanet 0 0 821 +1630 ShowMyPC 0 0 1615 +1645 Airtime 0 0 0 +1646 CSDN 0 0 822 +1647 Taringa 0 0 823 +1648 Aliexpress 0 0 824 +1649 58 City 0 0 825 +1650 LeTV 0 0 826 +1651 Tianya 0 0 827 +1652 Rakuten 0 0 828 +1653 Snapchat 0 188 0 +1654 500px 0 0 829 +1655 Airbnb 0 0 0 +1656 Invitemedia 0 0 830 +1657 Urban Airship 0 0 835 +1659 Akamai 0 0 837 +1660 Loyalty Innovations 0 0 838 +1661 Avaya Live 0 0 0 +1662 DirBuster 0 208 0 +1663 YY 20143 209 1693 +1664 Dwolla 0 0 848 +1665 Google Remote Desktop 0 0 0 +1666 Magicland 0 0 853 +1667 LINE 0 210 1528 +1668 Fancy 0 0 854 +1669 ChatON 0 0 0 +1670 GitHub 0 0 855 +1671 Trend Micro 0 0 856 +1672 Ogg 0 0 0 +1673 WebM 0 0 0 +1675 QualysGuard 0 0 858 +1676 Flexera Software 0 211 859 +1677 OsiriX 0 212 860 +1678 PACS 20144 0 0 pacs +1679 DICOM 0 213 0 +1680 Mac App Store 0 214 0 +1681 AirPlay 0 215 0 +1682 AirTunes 20145 0 0 airtunes +1683 Apple TV 0 216 0 +1684 Google Talk Audio 0 0 0 +1692 Java 0 217 0 +1693 Google Talk Video 0 0 0 +1695 SOUNDROP 0 0 861 +1696 IPsec 0 0 0 +1697 eBuddy XMS 0 0 0 +1699 Android Client 0 220 0 +1700 Vine 0 221 867 +1702 MyLife 0 0 863 +1703 Ning 0 0 864 +1704 Gravatar 0 0 865 +1705 Kickstarter 0 0 866 +1707 Linux Mint 0 0 869 +1709 The Washington Post 0 0 871 +1711 Pandora Audio 0 0 559 +1719 Elinks 0 198 0 +1754 Playstation.com 0 0 880 +1755 MDNS 20146 0 0 mdns +1756 VLC Media Player 0 224 874 +1757 Raptr 0 225 875 +1758 UPnP 0 284 0 +1759 AIM Express 0 0 878 +1760 Silk 0 283 0 +1761 PS3 web browser 0 285 0 +1763 PS3 Messenger 0 226 0 +1764 Playstation Store 0 0 877 +1765 PS3 Downloads 0 0 876 +1766 PS3 Updater 0 227 0 +1767 PS3 Home Client 0 228 0 +1769 Nokia 0 0 881 +1770 Nokia Music 0 0 882 +1771 Nokia Store 0 0 883 +1772 PBS 0 0 884 +1774 ArtStack 0 0 885 +1775 TRUSTe 0 0 886 +1776 DoubleVerify 0 0 887 +1777 WSDD 20167 230 0 wsdd +1779 FDSSDP 0 231 0 +1780 Exchange 0 484 1692 +1781 2Leep 0 0 889 +1782 Bizrate 0 0 890 +1783 People Of Walmart 0 0 891 +1784 Cute Overload 0 0 892 +1785 Cheezburger 0 0 893 +1787 Pop Salad 0 0 895 +1788 theCHIVE 0 296 896 +1789 TruuConfessions 0 0 897 +1790 ZergNet 0 0 898 +1791 WhereCoolThingsHappen 0 0 899 +1792 H&R Block 0 0 900 +1793 Constant Contact 0 0 901 +1794 Pivotal Tracker 0 0 902 +1795 Tempo 0 232 903 +1796 Podio 0 0 905 +1797 LivePerson 0 0 908 +1798 Mention 0 0 909 +1799 Feedly 0 0 910 +1800 IPFIX 20147 0 0 ipfix +1801 Mailbox 0 0 0 +1802 Minecraft 20192 469 911 minecraft +1803 Rotten Tomatoes 0 0 912 +1804 Amazon Ads System 0 0 913 +1805 MTv 0 0 914 +1806 Tightrope Interactive 0 234 915 +1808 Glympse 0 0 916 +1809 Honeywell Control Station/NIF Server 20148 0 0 honeywell +1810 TuneIn 0 235 917 +1811 Honeywell Experion DSA Server Monitor 20149 0 0 experion +1812 Backupgrid 0 0 919 +1813 Carbonite 0 236 920 +1814 iBackup 0 0 924 +1815 JustCloud 0 0 921 +1816 jdistatic 0 0 922 +1817 MyPCBackup 0 0 923 +1818 SOS Online Backup 0 0 936 +1819 SugarSync 0 0 925 +1820 ZipCloud 0 0 926 +1822 PubNub 0 0 927 +1824 Wii Shop Channel 0 0 929 +1826 Nintendo WFC 0 0 931 +1827 FiOS TV 0 238 932 +1829 Vdio 0 0 933 +1830 Redbox 0 0 934 +1831 Google Fiber 0 0 935 +1939 NBA 0 0 1078 +1955 Reduxmedia 0 0 1107 +1988 NBC 0 0 938 +1989 RedOrbit 0 0 939 +1990 Space.com 0 0 940 +1991 SockShare 0 0 941 +1992 BitGravity 0 0 942 +1993 PixelMags 0 0 943 +1994 Zmags 0 0 944 +1995 GNOME 0 0 945 +1996 ESTsoft 0 0 946 +1997 Cabal Online 0 0 947 +1998 ALTools 0 0 948 +1999 GIFSoup.com 0 0 949 +2000 Slate Magazine 0 0 950 +2001 I Waste So Much Time 0 0 951 +2002 Biography.com 0 0 952 +2003 Ubuntu 0 0 953 +2004 Comedy Central 0 0 954 +2005 Wired.com 0 0 955 +2006 E! Online 0 0 956 +2007 NHL.com 0 0 957 +2008 Presto 0 0 958 +2009 Twitter Music 0 243 0 +2010 MacPorts 0 244 960 +2011 Philips Hue 0 245 961 +2012 Baiduspider 0 247 0 +2013 K9 Web Protection 0 249 962 +2014 Bing Bar 0 250 0 +2015 Redbox Instant 0 0 963 +2016 TopTenREVIEWS 0 0 964 +2017 Adweek 0 0 965 +2018 The Week Magazine 0 0 966 +2019 Brightcove 0 0 967 +2020 Newser 0 0 968 +2021 Simpli.fi 0 0 969 +2032 Google Code project hosting 0 0 971 +2033 Windows Help client 0 252 0 +2034 Roku 0 253 972 +2035 TURN Client 0 255 0 +2036 TURN Channel 20150 0 0 turn +2037 Splunk 0 256 0 +2038 Atlassian 0 0 973 +2040 Prezi 0 0 974 +2041 IFTTT 0 0 975 +2042 OPC-UA 20151 0 0 opcua +2043 NetWorker 20152 0 0 networker +2044 NetWorker Data Setup 0 258 0 +2045 Apple iForgot 0 0 976 +2047 JBoss Remoting 0 259 978 +2048 Fink 0 260 979 +2049 Photo Stream 0 261 0 +2050 FOX 0 0 981 +2051 Washington Times 0 0 982 +2052 NextBus 0 0 983 +2053 OpenBSD 0 0 984 +2054 Associated Press 0 0 985 +2055 WTOP 0 0 986 +2056 OpenSUSE 0 0 987 +2057 Turner Broadcasting System 0 0 988 +2058 NCAA 0 0 989 +2059 DSW 0 0 991 +2060 Po.st 0 0 992 +2061 CheapStuff 0 0 993 +2062 Livefyre 0 0 994 +2063 FreeStreams 0 0 995 +2064 Clear Channel 0 0 996 +2065 GOLF.com 0 0 997 +2066 Glam 0 0 998 +2067 BoldChat 0 0 999 +2068 Intermarkets 0 0 1000 +2069 Woopra 0 0 1001 +2070 OCLC 0 0 1002 +2071 Chosun 0 0 1003 +2072 Ooyala 0 0 1004 +2073 iTunes U 0 0 0 +2074 C-SPAN 0 0 1005 +2082 Game Front 0 0 1006 +2083 BitCoin 20154 263 1007 bitcoin +2084 LiteCoin 20155 264 1008 litecoin +2085 Bitcoin Forum 0 0 0 +2086 lynda.com 0 0 1010 +2087 IDXRad 0 265 0 +2088 PScribe 0 266 0 +2089 Sunquest 0 267 0 +2090 Medipac 0 268 0 +2091 Letterpress 0 269 1011 +2092 Game Center 0 270 1012 +2093 FriendFinder 0 0 1013 +2094 Audible.com 0 0 1014 +2095 Entertainment Weekly 0 0 1015 +2096 Epic 0 272 0 +2097 UPMC 0 273 0 +2102 Docstoc Upload 0 0 1016 +2103 Speedtest 0 0 1017 +2104 Boxnet Upload SSL 0 0 1018 +2105 Flickr Upload 0 0 1019 +2106 Scribd Upload 0 0 1020 +2107 Youtube Upload 0 0 1021 +2110 Voxer 0 274 1024 +2111 Windows Azure 0 0 1025 +2112 Starbucks 0 276 1026 +2113 iTunes Music 0 277 0 +2116 Adblade 0 0 1027 +2118 BackWeb 0 0 1029 +2119 Blackberry sites 0 0 1030 +2120 Djpod 0 0 1031 +2121 Microsoft download 0 0 1032 +2122 Microsoft AutoUpdate 0 279 0 +2123 MyOnlineArcade 0 0 1033 +2124 SmugMug 0 0 1035 +2126 USAA 0 0 1037 +2127 wimp.com 0 0 1038 +2128 Zendesk 0 0 1039 +2129 Auditude 0 0 1040 +2130 Show My Weather 0 0 1041 +2131 MobiTV 0 0 1042 +2132 TV Guide 0 0 1043 +2133 iFunny 0 301 1044 +2134 Telenav 0 0 1045 +2135 Vlingo 0 0 1047 +2136 Media Hub 0 0 1048 +2137 CheapOAir 0 0 1049 +2138 Crunchyroll 0 0 1050 +2139 Eventbrite 0 0 1051 +2140 J.P. Morgan 0 0 1261 +2141 GoBank 0 0 0 +2142 Path 0 0 1053 +2143 Intel 0 0 1054 +2144 AMD 0 0 1055 +2145 Asus 0 0 1056 +2146 Acer 0 0 1057 +2147 Gateway 0 0 1058 +2148 Toshiba 0 0 1059 +2149 Motorola 0 0 1060 +2150 Nvidia 0 0 1061 +2151 Channel Intelligence 0 0 1062 +2152 Progressive 0 0 1063 +2153 State Farm 0 0 1064 +2154 Allstate 0 0 1065 +2155 Geico 0 0 1066 +2156 Liberty Mutual 0 0 1067 +2157 Ensighten 0 0 1068 +2158 Maxymiser 0 0 1069 +2159 News Distribution Network 0 0 1070 +2160 Jetsetz 0 0 1072 +2161 StudentUniverse 0 0 1073 +2162 PerfectIBE 0 0 1074 +2163 Funny or Die 0 0 1075 +2164 CollegeHumor 0 0 1076 +2165 Zombo.com 0 0 1077 +2170 NovaMov 0 0 1079 +2171 Viki 0 0 1080 +2172 PNC Bank 0 0 1081 +2173 Red Hat 0 0 1082 +2174 United Airlines 0 0 1083 +2176 TextNow 0 0 1085 +2177 FedEx 0 0 1086 +2178 American Airlines 0 0 1087 +2179 Nuance 0 0 1088 +2180 Al Jazeera 0 0 1089 +2181 Wimbledon 0 0 1090 +2182 MLive 0 0 1091 +2183 Times Union 0 0 1092 +2184 beRecruited 0 0 1093 +2185 Bitbucket 0 0 1094 +2186 Detroit Free Press 0 0 1095 +2187 jJcast 0 0 1096 +2188 Michigan Radio 0 0 1097 +2189 De Telegraaf 0 0 1098 +2190 ooVoo 0 0 1099 +2191 The Daily Beast 0 0 1100 +2192 The Free Dictionary 0 0 1101 +2193 The Onion 0 0 1102 +2195 WeatherLink 0 0 1103 +2196 Yahoo! Calendar 0 0 1104 +2197 GVFS 0 281 0 +2198 Yammer 0 282 1106 +2202 ksfetch 0 286 0 +2203 Google Update 0 287 0 +2204 Googlebot Image Search 0 289 0 +2205 Abonti 0 291 0 +2206 Zapier 0 292 1109 +2207 Collider 0 0 1110 +2208 WordReference.com 0 0 1111 +2209 Microsoft Word 0 294 0 +2210 Microsoft Powerpoint 0 295 0 +2211 Yandex Bot 0 299 0 +2212 MJ12 Bot 0 302 0 +2213 Microsoft CryptoAPI 0 303 0 +2214 FrostWire 0 306 1112 +2215 Media Stream Daemon 0 307 0 +2217 OCSPD 0 309 0 +2218 5by5 Radio 0 310 1113 +2219 Acoon.de 0 311 1114 +2220 Anipang 0 312 0 +2221 Apple PubSub 0 313 0 +2222 ArcGIS 0 314 1115 +2223 Blekko 0 0 1116 +2224 BlekkoBot 0 315 0 +2225 Boingo 0 316 1117 +2226 Easou Spider 0 317 0 +2227 FeedBurner 0 318 0 +2228 Feedly Fetcher 0 319 0 +2229 Genieo Web Filter 0 320 1118 +2230 PHP 0 321 0 +2231 Apple Syndication 0 322 0 +2232 Android Download Manager 0 323 0 +2233 Bitcasa 0 324 1119 +2234 Sony 0 0 1120 +2235 Zootool 0 0 1121 +2236 WeTransfer 0 0 1122 +2237 Storify 0 0 1123 +2238 SpeedRunsLive 0 0 1124 +2240 WDT 0 0 1125 +2241 Twitterrific 0 325 1126 +2242 The Seattle Times 0 0 1128 +2243 Readability 0 0 1129 +2244 Postini 0 0 1130 +2245 Oracle sites 0 0 1131 +2246 Okta 0 0 1132 +2247 Nike 0 0 1133 +2248 Libsyn 0 0 1134 +2249 JetSetMe 0 0 1135 +2250 Investopedia 0 0 1136 +2251 The Hollywood Reporter 0 0 1137 +2252 John's Background Switcher 0 329 0 +2253 AppleCoreMedia 0 330 0 +2254 HLN 0 0 1138 +2255 FFFFOUND! 0 0 1139 +2256 CNET TV 0 0 1141 +2257 Fifth Third Bank 0 0 0 +2258 Android Music 0 331 0 +2261 Adap.tv 0 0 1142 +2262 Feedfetcher 0 332 0 +2263 GSA Crawler 0 333 0 +2264 Kraken 0 334 0 +2265 MagPie 0 335 0 +2267 Sogou web spider 0 338 0 +2268 Voilabot 0 339 0 +2269 Drugs.com 0 0 1143 +2270 Campfire 0 0 1144 +2271 AudioDocumentary.org 0 0 1145 +2273 Quick Look 0 341 0 +2274 NVIDIA Update 0 342 0 +2275 Connexion client 0 343 0 +2276 PS3 Community Agent 0 344 0 +2277 PSP Activity Agent 0 345 0 +2278 PSP Community Agent 0 346 0 +2279 MS Office Existence Discovery 0 347 0 +2280 MS Office Protocol Discovery 0 348 0 +2282 Rainmeter WebParser 0 350 0 +2283 reCAPTCHA 0 351 0 +2284 simple-get 0 352 0 +2285 Wood TV8 0 0 1146 +2286 App.net 0 0 1147 +2287 Malware Defense System 0 353 0 +2288 Microsoft Excel 0 354 0 +2289 Microsoft NCSI 0 355 1148 +2290 Microsoft WNS 0 356 0 +2291 Moodlebot 0 357 0 +2292 Windows Phone Browser 0 358 0 +2296 HTTP Tunnel 0 0 0 +2297 XProtectUpdater 0 360 0 +2298 Xenu Link Sleuth 0 361 0 +2299 uTorrent 0 362 0 +2300 URLAppendBot 0 363 0 +2301 Tiny Tiny RSS 0 364 0 +2302 Tinder 0 365 1150 +2303 Sage 0 366 0 +2305 Radian6 CommentReader 0 368 0 +2306 Powermarks 0 369 0 +2307 PDF Expert 0 370 0 +2308 Google PageSpeed 0 371 0 +2309 Owlinbot 0 372 0 +2310 Yeti Bot 0 373 0 +2311 TPKT 20163 0 0 tpkt +2312 COTP 20164 0 0 cotp +2313 ISO MMS 20165 0 0 isomms +2314 Q.931 20166 0 0 q931 +2315 PubSubHubbub 0 375 0 +2316 ndgsa-crawler 0 376 0 +2317 Microsoft Access 0 377 0 +2318 Dr. Watson 0 378 0 +2319 NetSight 0 379 0 +2320 Ovi Browser 0 380 0 +2321 Penultimate 0 381 0 +2322 Boxoh 0 0 1149 +2323 OSSProxy 0 382 0 +2324 NetNewsWire 0 383 0 +2325 050plus 0 0 1804 +2326 Business Intelligence 0 0 0 +2327 MaxDB 0 0 0 +2328 NetWeaver 0 0 0 +2329 urlgrabber 0 385 0 +2330 Apache Nutch 0 386 1151 +2331 MobileAsset 0 387 0 +2332 MCStats 0 388 0 +2333 MapMyFitness 0 389 0 +2334 JikeSpider 0 390 0 +2335 Infinity Blade 0 391 1152 +2336 Mediabot 0 392 0 +2337 Feed43 0 393 0 +2338 Dragon Dictate 0 394 0 +2339 Coc Coc bot 0 395 0 +2341 FinTS 0 0 0 +2345 AD File Replication Service 0 0 0 +2346 2345.com 0 0 1402 +2347 Forbes 0 0 1758 +2348 Freee TV 0 0 1766 +2349 IKEA.com 0 0 1510 +2350 Pchome 0 0 1583 +2351 TechInline 0 0 1639 +2352 wikidot 0 0 1711 +2353 Quote.com 0 0 1603 +2354 CBS Interactive 0 0 1460 +2355 CLDAP 0 0 0 +2356 Hupu 0 0 1505 +2357 Foursquare 0 0 1703 +2358 The Internet Archive 0 0 1729 +2359 Doof 0 0 1541 +2360 Adenin 0 0 1543 +2361 Groupon 0 0 1699 +2363 Match.com 0 0 1536 +2364 Meetup 0 0 1554 +2365 MyWebSearch 0 0 1568 +2366 Uploading.com 0 0 1730 +2367 Viber 0 0 0 +2368 Fring 0 497 1803 +2369 Fring A/V 0 0 0 +2370 ADNStream 0 0 1418 +2371 China.com 0 0 1463 +2372 In.com 0 0 1784 +2373 it168 0 0 1519 +2374 Letitbit 0 0 1527 +2375 MUZU TV 0 0 1566 +2376 NFL.com 0 0 1811 +2377 Squidoo 0 0 1631 +2378 wetpaint entertainment 0 0 1809 +2379 Tango 0 0 1635 +2380 PPTV 0 0 1598 +2381 Apple Maps 0 468 1586 +2382 SendSpace 0 0 1613 +2383 Sogou 0 0 1625 +2384 Chinaren 0 0 1464 +2385 17173.com 0 0 1401 +2386 Alibaba 0 0 1429 +2387 Tmall 0 0 1783 +2388 Etao 0 0 1545 +2389 Aliyun 0 0 1430 +2390 Naverisk 0 0 1569 +2391 Funshion 0 0 1810 +2392 Funshion Video 0 0 0 +2393 Google Talk File Exchange 0 0 0 +2400 Tokbox 0 0 0 +2401 iCall 0 0 1507 +2402 OCSP 0 0 0 +2403 Google ads 0 0 1768 +2404 RichRelevance 0 0 1609 +2405 Quantcast 0 0 1602 +2406 Turn Analytics 0 0 0 +2407 Mediaplex 0 0 0 +2408 Scorecard Research 0 0 1612 +2409 Tribal Fusion 0 0 0 +2411 SPC Media 0 0 1629 +2412 ValueClick 0 0 0 +2413 AppNexus 0 0 1443 +2414 Adconion Media Group 0 0 1411 +2415 OpenX 0 0 1581 +2416 MediaMath 0 0 1539 +2417 Rubicon Project 0 0 1611 +2418 Innovation Interactive 0 0 0 +2419 33Across 0 0 1405 +2420 Akamai NetSession Interface 0 396 0 +2421 AhrefsBot 0 397 0 +2422 AddThis Bot 0 398 0 +2423 IMTransferAgent 0 399 0 +2424 The Atlantic 0 0 1153 +2425 Svpply 0 0 1154 +2426 StreetFire 0 0 1155 +2427 Southern Living 0 0 1156 +2428 Buffer 0 0 1170 +2429 Coupa 0 0 1158 +2430 The Escapist Magazine 0 0 1159 +2431 Pocket 0 0 1160 +2432 Grantland 0 0 1161 +2433 The Independent 0 0 1162 +2434 Instapaper 0 0 1163 +2435 KBS 0 0 1164 +2437 Pinboard 0 0 1166 +2438 Pushover 0 0 1167 +2439 Realview TV 0 0 1168 +2440 Dots 0 401 1169 +2451 Improve Digital 0 0 1512 +2452 BlueKai 0 0 1393 +2453 Triggit 0 0 0 +2454 Admeld 0 0 1415 +2455 iPerceptions 0 0 1517 +2456 Atlas Advertiser Suite 0 0 1446 +2457 BRSRVR 0 0 0 +2458 Compete 0 0 1472 +2459 BRCDN 0 0 0 +2460 Silverpop 0 0 1616 +2461 Infonline 0 0 1514 +2462 comScore 0 0 1552 +2463 Komli Media 0 0 1520 +2464 MediaMind 0 0 0 +2465 Lotame 0 0 1533 +2466 Krux 0 0 1522 +2467 AudienceScience 0 0 1447 +2468 Nielsen 0 0 1573 +2469 Google Play 0 0 0 +2470 Android.com 0 0 1433 +2471 PDBox 0 0 1584 +2472 PDBox P2P 0 0 0 +2474 Lync 0 0 1644 +2475 RTP Audio 0 0 0 +2476 RTP Video 0 0 0 +2477 Yahoo! Messenger Chat 0 0 0 +2478 Yahoo! Messenger SMS 0 0 1827 +2479 Yahoo! Messenger Audio 0 0 0 +2480 Yahoo! Messenger Video 0 0 0 +2481 East Money 0 0 1544 +2482 Blokus 0 0 1391 +2483 Freelancer 0 0 1704 +2484 Goal 0 491 1769 +2485 HubPages 0 0 1504 +2486 Marca 0 0 1535 +2487 Telly 0 0 1641 +2488 Wikispaces 0 0 1737 +2490 Chinauma 0 0 1465 +2491 adSage 0 0 1423 +2492 247 Inc. 0 0 1404 +2493 24/7 Media 0 0 1403 +2494 SLI Systems 0 0 1620 +2495 OwnerIQ 0 0 1297 +2496 Monetate 0 0 1561 +2497 AdReady 0 0 1421 +2499 The Trade Desk 0 0 1762 +2500 AdGear 0 0 1413 +2501 MediaV 0 0 1553 +2502 ClickTale 0 0 1468 +2503 Adtech 0 0 1425 +2504 Amobee 0 0 1427 +2505 LeadBolt 0 0 1524 +2506 Mobile Theory 0 0 1560 +2507 Mojiva 0 0 1557 +2508 Nexage 0 0 1572 +2509 Drawbridge 0 0 1542 +2510 Evidon 0 0 1736 +2511 Brilig 0 0 1456 +2512 Casale 0 0 1459 +2513 Chango 0 0 1461 +2514 Criteo 0 0 1480 +2515 Dotomi 0 0 1722 +2516 Effective Measure 0 0 1550 +2517 eXelate 0 0 1735 +2518 Exponential Interactive 0 0 1756 +2519 Vibrant 0 0 1732 +2520 LiveRail 0 0 1531 +2521 Luminate 0 0 1534 +2522 Media6Degrees 0 0 1734 +2523 Media Innovation Group 0 0 1760 +2525 Motrixi 0 0 1564 +2526 eyeReturn 0 0 1723 +2527 InSkin Media 0 0 1515 +2528 Cognitive Match 0 0 1471 +2529 Connextra 0 0 1478 +2530 Optimizely 0 0 1582 +2531 Ohana 0 0 1577 +2532 Integral Ad Science 0 0 1516 +2533 Proclivity 0 0 1599 +2534 TubeMogul 0 0 1725 +2535 CloudFlare 0 0 1469 +2536 TLVMedia 0 0 1733 +2537 Neustar Information Services 0 0 1491 +2538 AdXpose 0 0 1426 +2539 EQ Ads 0 0 1546 +2540 TowerData 0 0 1607 +2541 Xaxis 0 0 1741 +2542 DataLogicx 0 0 1483 +2544 Nugg 0 0 1576 +2545 Yabuka 0 0 1726 +2546 Ybrant Digital 0 0 1713 +2547 Aggregate Knowledge 0 0 1428 +2548 SpotXchange 0 0 1630 +2549 X Plus One 0 0 1745 +2551 NetSeer 0 0 1571 +2552 Core Audience 0 0 1354 +2553 Resonate Networks 0 0 1608 +2554 engage BDR 0 0 1548 +2555 Connexity 0 0 1477 +2556 Adometry 0 0 1420 +2557 Bizo 0 0 1436 +2558 Brightroll 0 0 1454 +2559 Federated Media 0 0 1702 +2560 Six Apart 0 0 1618 +2561 MaxPoint Interactive 0 0 1537 +2563 Rocket Fuel 0 0 1610 +2564 RadiumOne 0 0 1604 +2565 Admasters 0 0 1409 +2566 contnet 0 0 1479 +2567 eNovance 0 0 1753 +2568 Smart AdServer 0 0 1622 +2569 ADMETA 0 0 1416 +2570 Adify 0 0 1740 +2571 ContextWeb 0 0 1721 +2572 cXense 0 0 1482 +2573 Caraytech 0 0 1458 +2574 Freewheel 0 0 1742 +2575 AdJuggler 0 0 1414 +2576 BV! Media 0 0 1746 +2577 Adtegrity 0 0 1452 +2578 AOL Ads 0 0 1435 +2579 Compuware 0 0 1473 +2580 Dynamic Logic 0 0 1701 +2581 Aptean 0 0 1444 +2582 Polldaddy 0 0 1597 +2583 Undertone 0 0 1738 +2584 VoiceFive 0 0 1731 +2585 ClickBooth 0 0 1467 +2586 MyBuys 0 0 1567 +2587 Webtrends 0 0 1739 +2588 Telecom Express 0 0 1759 +2589 DC Storm 0 0 1747 +2590 Skimlinks 0 0 1619 +2591 Crowd Science 0 0 1481 +2592 Olive Media 0 0 1578 +2593 Mixpanel 0 0 1558 +2594 Tritone Hosting 0 0 1353 +2595 MdotM 0 0 1538 +2596 Telemetry 0 0 1640 +2597 CNZZ 0 0 1470 +2598 HowardForums 0 0 1503 +2599 Softonic 0 0 1623 +2600 Booking.com 0 0 1394 +2601 Concur 0 0 1476 +2602 TeacherTube 0 0 1636 +2603 Rambler 0 0 1606 +2604 EarthCam 0 0 1233 +2605 Boxcar.io 0 0 1453 +2606 Softpedia 0 0 1624 +2607 TechCrunch 0 0 1638 +2608 Hyves 0 0 0 +2609 LA Times 0 0 1523 +2610 China News 0 0 1462 +2611 Nico Nico Douga Video 0 0 0 +2612 NateOn Video Chat 0 0 0 +2613 NateOn 0 0 0 +2614 NateOn Remote Control 0 0 0 +2615 NateOn Voice 0 0 0 +2616 NateOn File Transfer 0 0 0 +2617 Aliwangwang 0 504 1802 +2618 WeChat 0 0 1823 +2619 WeChat login 0 0 0 +2620 WeChat media 0 0 0 +2621 WeChat message 0 0 0 +2622 WeChat heartbeat 0 0 0 +2623 WeChat update 0 0 0 +2624 Nokia sync 0 0 0 +2625 Nokia message 0 0 0 +2626 Xbox Live sites 0 0 1771 +2627 Windows Phone sites 0 0 1772 +2628 SopCast 0 0 1627 +2629 Freegate 0 0 0 +2630 Nimbuzz 0 500 1806 +2631 N-World 0 0 0 +2632 Nimbuzz MMS 0 0 0 +2633 FIX 0 0 0 +2634 Ultrasurf 0 0 0 +2635 ShareThis 0 0 1614 +2636 LOCKSS 0 400 0 +2637 Dump Truck 0 0 0 +2638 GOMTV Remote Control 0 0 1805 +2639 GOMTV.net 0 0 1791 +2640 GOMTV.com 0 496 1790 +2641 GoToWebinar 0 0 0 +2642 GoToTraining 0 0 0 +2643 Citrix GoToMeeting Platform 0 0 0 +2644 VyprVPN Login 0 0 0 +2645 Tunnelbear Login 0 0 0 +2646 Ivacy Login 0 0 0 +2648 Hide My Ass! 0 0 1208 +2650 VEVO.com 0 0 1172 +2651 PNAS 0 0 1173 +2652 HBO 0 0 1174 +2653 Stitcher 0 0 1175 +2654 Panoramio 0 0 1176 +2655 Cisco 0 0 1177 +2656 The Baltimore Sun 0 0 1178 +2657 Dilbert.com 0 0 1179 +2658 Google URL Shortener 0 0 1180 +2659 Hotels.com 0 0 1181 +2660 JSTOR 0 0 1182 +2661 Xiami.com 0 0 1184 +2662 INRIX 0 405 1185 +2663 Lijit 0 0 1186 +2664 Moat 0 0 1187 +2665 Ando Media 0 0 1188 +2666 Break.com 0 0 1189 +2667 BitTorrent Sync 20156 407 0 bittorrent_sync +2668 Printer Pro Desktop 0 408 0 +2669 Apple Music 0 0 1190 +2680 ibVPN Login 0 0 1205 +2681 Hideman Login 0 0 1206 +2682 Cloudnymous Login 0 0 0 +2683 VMware vCenter client 0 0 0 +2684 NAT-PMP 20160 0 0 nat-pmp +2685 Python urllib 0 406 0 +2686 Genieo 0 0 1209 +2687 Mathworks 0 0 1210 +2688 GoodSync 0 0 1211 +2689 UpToDate 0 0 1212 +2690 New Relic 0 0 1213 +2691 WorldCat 0 0 1214 +2692 SPOOLSS 0 0 0 +2693 UltraViolet 0 0 1813 +2694 Apple App Store 0 409 0 +2695 SecurityKiss 0 0 1215 +2696 Fuyin.TV 0 0 1216 +2697 SHOWTIME ANYTIME 0 0 1217 +2698 Drupal 0 0 1218 +2699 Sky.com 0 0 1219 +2700 Arizona Public Media 0 0 1220 +2701 EA Games 0 0 1221 +2702 Copy 0 0 1222 +2703 TomTom 0 0 1223 +2704 OpenDNS 0 0 1224 +2705 Gizmodo 0 0 1225 +2706 SimplePie 0 422 1226 +2707 Sophos Live Protection 0 423 1227 +2708 Android Asynchronous Http Client 0 410 0 +2709 VMware Server Console 20161 412 0 vmware-vsphere +2710 MixBit 0 0 1228 +2711 HBO GO 0 413 1231 +2712 Integromedb Crawler 0 415 0 +2713 Twitter4J 0 416 0 +2714 msnbot 0 417 0 +2715 Pingdom 0 418 0 +2716 PHP-SOAP 0 419 0 +2717 Leap Motion sites 0 0 0 +2718 RealPlayer Cloud 0 420 0 +2719 Google Cloud Messaging 0 0 0 +2720 BJNP 0 0 0 +2721 WebSocket 0 0 0 +2722 CA Certificate 0 0 0 +2723 CR List 0 0 0 +2724 iBooks 0 421 1234 +2725 iTunes Store 0 424 0 +2726 RealNetworks 0 0 1232 +2727 Sametime 20162 0 0 sametime +2728 blinkx 0 0 1235 +2729 Garmin 0 0 1236 +2732 Nexon 0 0 1239 +2733 PointRoll 0 0 1240 +2734 Samsung Push Notification 0 0 0 +2735 TVonline.cc 0 0 1241 +2736 Airspace 0 0 0 +2737 BesTV 0 0 1242 +2738 Zippyshare 0 0 1243 +2739 Dropcam 0 0 1244 +2740 GTA Online 0 0 1245 +2741 KakaoTalk Audio 0 0 0 +2742 Secure RTCP 0 0 0 +2743 SRTP 0 0 0 +2744 SRTP Audio 0 0 0 +2745 SRTP Video 0 0 0 +2746 Remote Ctrl from iPhone/iPad 0 425 0 +2747 Rockstar Games 0 426 1246 +2748 iRODS 20168 0 0 irods +2749 Nest Thermostat 0 427 1247 +2750 CTV 0 0 1248 +2751 CTV News 0 0 1249 +2752 Indiegogo 0 0 1250 +2753 KVOA.com 0 0 1251 +2754 MailChimp 0 0 1252 +2755 MovieTickets.com 0 0 1253 +2756 Comcast Mail 0 0 1256 +2757 Coursera 0 0 1257 +2758 XBMC 0 428 1258 +2759 Network PID Checker 20169 430 0 +2760 Gazprom Media 0 0 1259 +2761 Tvigle 0 0 1260 +2762 Bandcamp 0 0 1262 +2763 NetBackup 20170 431 0 netbackup +2764 Bluehost 0 0 1264 +2765 SFGate 0 0 1265 +2766 Library of Congress 0 0 1266 +2767 OverBlog 0 0 1267 +2768 BBB 0 0 1268 +2769 AddToAny 0 0 1269 +2770 TIME.com 0 0 1270 +2771 Phoca 0 0 1271 +2772 phpBB 0 0 1272 +2773 HugeDomains.com 0 0 1273 +2774 GNU Project 0 0 1274 +2775 Lycos 0 0 1275 +2776 ConnMan 0 432 1276 +2777 Creative Commons 0 0 1277 +2778 NAI 0 0 1278 +2779 Joomla 0 0 1279 +2780 TinyURL 0 0 1280 +2781 Amazon Cloud Player 0 433 0 +2782 Jimdo 0 0 1281 +2783 Stanford University 0 0 1282 +2784 Harvard University 0 0 1283 +2785 eRecht24 0 0 1284 +2786 European Union 0 0 1285 +2787 bitly 0 0 1286 +2788 Viddler 0 0 1287 +2789 Merriam-Webster 0 0 1288 +2790 Websense 0 0 1289 +2791 Zbigz 0 0 1290 +2792 Zulily 0 0 1291 +2793 Zattoo 0 434 1292 +2794 Xfire 20172 435 1293 +2795 Freenet 0 0 0 +2796 Lync Audio 0 0 0 +2797 Lync Video 0 0 0 +2798 Lync Media 0 0 0 +2799 Lync Share 0 0 0 +2800 Lync Control 0 0 0 +2801 Skype File Transfer 0 0 0 +2802 Parallels 20173 0 1296 +2803 Eyejot 0 0 1298 +2804 Dogpile 0 0 1299 +2805 DuckDuckGo 0 0 1300 +2806 Instagram Images 0 0 0 +2807 Instagram Video 0 0 0 +2809 Vagaa 0 0 0 +2810 Exchange Online 0 0 1847 +2811 MS CDN 0 0 0 +2812 Office 365 0 0 1378 +2813 Sharepoint Online 0 0 1795 +2814 Camo Proxy 0 0 1301 +2815 Tencent 0 0 1302 +2816 Picsearch 0 0 1311 +2817 Fetion 0 0 1312 +2818 Fluxiom 0 0 1313 +2820 LeapFILE 0 0 1315 +2822 Okurin 0 0 1317 +2823 RayFile 0 0 1318 +2824 Fotki 0 0 1319 +2825 CrossLoop 0 0 1320 +2826 eRoom 0 0 1321 +2827 Glide 0 0 1322 +2828 GREE 0 0 1323 +2830 Wii 0 0 1303 +2831 Shopkick 0 436 1304 +2832 Hangame 0 0 1305 +2833 SugarCRM 0 0 1306 +2834 Megaproxy 0 0 1307 +2835 KProxy 0 0 1308 +2836 Guardster 0 0 1309 +2837 FlyProxy 0 0 1310 +2838 Coral CDN 0 0 1325 +2839 Pastebin.com 0 0 1326 +2840 Zhihu.com 0 0 1327 +2841 Twiddla 0 0 1328 +2843 Quora 0 0 1330 +2844 Yahoo! Mobage 0 0 1331 +2845 Pogoplug 0 437 1332 +2846 Adobe Analytics 0 0 1786 +2847 Ado Tube 0 0 1419 +2848 AdRoll 0 0 1422 +2849 AdSame 0 0 1424 +2850 AD-X Tracking 0 0 1410 +2851 Allegro.pl 0 0 1431 +2852 Autohome.com.cn 0 0 1448 +2853 BlueLithium 0 0 0 +2854 Ganji 0 0 1724 +2855 Hao123.com 0 0 1706 +2856 Ifeng.com 0 0 1509 +2857 BBC iPlayer 0 0 1829 +2858 iStock 0 0 1518 +2859 Kooora.com 0 0 1521 +2860 Mercado Livre 0 0 1555 +2861 MLN Advertising 0 0 1559 +2862 Mop.com 0 0 1562 +2863 Motley Fool 0 0 1563 +2864 SiteScout 0 0 1617 +2865 Upfront Digital Media 0 0 0 +2866 Zol.com.cn 0 0 1788 +2867 Bloglovin 0 0 1333 +2869 Baidu Movies 0 442 1334 +2871 Microsoft CRM Dynamics 0 0 0 +2874 Gbridge 20178 440 1335 +2875 Mikogo 0 0 1336 +2876 Songsari 20179 441 1337 +2877 StreamWork 20180 0 0 +2878 Xunlei Kankan 0 0 1338 +2879 Google Groups 0 0 1339 +2880 Google+ Photos 0 0 1340 +2881 Google+ Videos 0 0 1341 +2882 Myspace Photos 0 0 1342 +2883 Myspace Videos 0 0 1343 +2884 FileHost.ro 0 0 1344 +2885 Gyao 0 0 1345 +2886 SPDY 0 0 0 +2887 SVN 0 0 1634 +2888 Quake Live 0 0 1601 +2889 HTTP 2.0 0 0 0 +2890 Sophos Update 0 0 1346 +2891 Glype 0 0 1347 +2892 GMX 0 0 1348 +2893 Sanook.com 0 0 1350 +2894 AMMYY 20181 0 1351 +2895 Dropbox Upload 0 0 1355 +2896 Dropbox Download 0 0 1356 +2897 Dropbox Share 0 0 1357 +2898 R6 FeedFetcher 0 443 0 +2899 VMware Horizon View 0 0 0 +2900 Microsoft Windows Live Services Authentication 0 0 0 +2901 Google Accounts Authentication 0 0 0 +2902 Cisco Phone 0 0 0 +2903 LinkedIn Profile 0 0 1358 +2904 LinkedIn Inbox 0 0 1359 +2905 iTunes iPhone 0 444 0 +2906 iTunes iPod 0 445 0 +2907 iTunes iPad 0 446 0 +2909 Facebook Utilities 0 0 1361 +2910 Facebook Sports 0 0 1362 +2911 Facebook Games 0 0 1363 +2912 Skype Video 0 0 0 +2913 Skype Voice 0 0 0 +2914 YiXin 0 502 1808 +2918 Shareman 0 0 1437 +2919 Sophos RED 0 0 0 +2921 AnyConnect 20182 0 0 anyconnect +2922 AnyConnect SSL Client 0 0 0 +2923 AnyConnect IPSec Client 0 0 0 +2924 iTunes Desktop 0 447 0 +2925 Facebook Photos 0 0 1364 +2926 Yahoo! Accounts 0 0 1366 +2932 WebEx Media 0 0 0 +2933 ESPN Video 0 0 0 +2935 Facebook Applications Other 0 0 1367 +2937 Perforce 20187 451 0 +2938 Bazaarvoice 0 0 1395 +2939 Adobe Flash 0 0 0 +2940 SCCP 20196 505 0 sccp +2941 Tor Directory Services 0 0 0 +2942 Telepresence Control 0 0 0 +2943 Tomatopang 20184 449 1368 +2944 VDOLive 20185 0 0 +2945 DeNA Comm 0 0 1831 +2946 DeNA websites 0 0 1396 +2947 JonDo 0 402 0 +2948 Sina Video 0 0 1397 +2949 SOAP 0 0 0 +2950 Web Services for Devices 0 0 0 +2951 Web Services for Devices Secured 0 0 0 +2952 WSDL Event Receiver 0 0 0 +2954 Yahoo! Flash 0 0 1838 +2955 Crackle Video 0 0 0 +2958 Teredo 0 0 0 +2959 Apple Remote Desktop 20189 0 0 ard +2960 Google Hangouts 0 0 1587 +2961 Google Helpouts 0 0 1588 +2962 WebEx Sharing 0 0 0 +2963 LinkedIn Upload 0 0 1369 +3000 3Com AMP3 0 0 0 +3001 Access Network 0 0 0 +3002 AccessBuilder 0 0 0 +3003 AODV 0 0 0 +3005 ALPES 0 0 0 +3006 Adobe PostScript 0 0 0 +3007 Aeolon Core Protocol 0 0 0 +3008 AgentX 0 0 0 +3009 connendp 0 0 0 +3010 PowerChute 0 0 0 +3011 AMInet 0 0 0 +3012 Apertus Tech Load Distribution 0 0 0 +3013 appleqtcsrvr 0 0 0 +3014 AEP 0 0 0 +3015 NBP 0 0 0 +3016 AppleTalk Routing Maintenance 0 0 0 +3017 AppleTalk Unused 203 0 0 0 +3018 AppleTalk Unused 205 0 0 0 +3019 AppleTalk Unused 207 0 0 0 +3020 AppleTalk Unused 208 0 0 0 +3021 AURP 0 0 0 +3022 AppleTalk Zone Information Protocol 0 0 0 +3023 ApplianceWare Managment Protocol 0 0 0 +3024 ACAP 0 0 0 +3025 Applix ac 0 0 0 +3026 Ariel2 0 0 0 +3027 Ariel3 0 0 0 +3028 AS Server Mapper 0 0 0 +3030 Asipregistry 0 0 0 +3032 Aurora CMGR 0 0 0 +3034 dcLINK 0 0 0 +3035 Avian 0 0 0 +3036 Banyan VIP 0 0 0 +3037 banyan-rpc 0 0 0 +3038 RSH-SPX 0 0 0 +3039 bgs-nsi 0 0 0 +3040 bmpp 0 0 0 +3041 Borland DSJ 0 0 0 +3043 BACnet 0 0 0 +3044 CAB Protocol 0 0 0 +3045 Cabletron Management Protocol 0 0 0 +3046 CadLock 0 0 0 +3047 Call of Duty 0 0 0 +3048 campaign contribution disclosures 0 0 0 +3049 Chat 0 0 0 +3050 Chshell 0 0 0 +3051 CIMPLEX 0 0 0 +3052 Cisco NAC 0 0 0 +3053 Citrix Static 0 0 0 +3054 CMIP/TCP Manager 0 0 0 +3055 CFDP 0 0 0 +3056 Collaborator 0 0 0 +3057 Commerce 0 0 0 +3058 Common Trace Facility 0 0 0 +3059 Covia 0 0 0 +3060 CDDB 0 0 0 +3061 cpq-wbem 0 0 0 +3062 CA Intl License Server 0 0 0 +3063 Synergy 0 0 0 +3064 CSTA 0 0 0 +3065 con 0 0 0 +3066 contentserver 0 0 0 +3067 Corerjd 0 0 0 +3068 Courier Mail Server 0 0 0 +3069 Cray Network Semaphore server 0 0 0 +3070 SFS config server 0 0 0 +3071 Cray Unified Resource Manager 0 0 0 +3072 Creative Partner 0 0 0 +3073 Creative Server 0 0 0 +3074 CRYPTOAdmin 0 0 0 +3075 CSNET Mailbox Name Nameserver 0 0 0 +3076 Customer Ixchange 0 0 0 +3077 cvc_hostd 0 0 0 +3078 CVS pserver 0 0 0 +3079 Cybercash 0 0 0 +3080 cycleserv 0 0 0 +3081 cycleserv2 0 0 0 +3082 Retrospect 0 0 0 +3083 DataRamp Svr 0 0 0 +3084 DataRampSrvSec 0 0 0 +3085 DCE endpoint resolution 0 0 0 +3086 dctp 0 0 0 +3087 DDM DFM 0 0 0 +3088 DDM RRDA 0 0 0 +3089 DEC DLM 0 0 0 +3090 decap 0 0 0 +3091 Decbsrv 0 0 0 +3093 DEI-ICDA 0 0 0 +3094 Desknet's 0 0 0 +3095 device 0 0 0 +3096 DHCP Failover 0 0 0 +3097 DHCP Failover 2 0 0 0 +3098 DHCPv6 Client 0 0 0 +3100 digital-vrc 0 0 0 +3101 Direct TV Software Updates 0 0 0 +3102 Direct TV Tickers 0 0 0 +3103 DirectPlay 0 0 0 +3104 DirectPlay8 0 0 0 +3105 DirecTV Data Catalog 0 0 0 +3106 DirecTV Webcasting 0 0 0 +3107 distcc 0 0 0 +3109 DDM 0 0 0 +3110 DOOM 0 0 0 +3111 DWR 0 0 0 +3112 eDonkey Static 0 0 0 +3113 EMC SmartPackets 0 0 0 +3114 entomb 0 0 0 +3115 Entrust Administration Service Handler 0 0 0 +3116 Entrust-KMSH 0 0 0 +3117 Entrust SPS 0 0 0 +3118 entrust-aaas 0 0 0 +3119 entrust-aams 0 0 0 +3120 errlog copy/server daemon 0 0 0 +3121 ESCP 0 0 0 +3122 eSignal 0 0 0 +3123 XTP 0 0 0 +3124 FCP 0 0 0 +3125 FLEXlm 0 0 0 +3126 FTP Software Agent System 0 0 0 +3127 Fujitsu Device Control 0 0 0 +3128 gdomap 0 0 0 +3129 GDS DataBase 0 0 0 +3130 ginad 0 0 0 +3131 GSI-FTP 0 0 0 +3132 GNU Generation Foundation NCP 678 0 0 0 +3133 GNU Generation Foundation NCP 128 0 0 0 +3134 GKrellM 0 0 0 +3135 GoBoogy 0 0 0 +3136 GotoDevice 0 0 0 +3137 Graphics 0 0 0 +3138 GraphOn Login 0 0 0 +3139 Groove 0 0 0 +3140 3GPP 0 0 0 +3141 ha-cluster 0 0 0 +3142 Hardware Control Protocol Wismar 0 0 0 +3143 HELLO Port 0 0 0 +3144 Heroix Longitude 0 0 0 +3147 Hitachi Universal Storage Platform 0 0 0 +3148 HMMP Indication 0 0 0 +3149 HMMP Operation 0 0 0 +3150 HAP 0 0 0 +3151 HP Network Management Center. 0 0 0 +3153 HTTP RPC Ep Map 0 0 0 +3154 Hybrid Point of Presence 0 0 0 +3155 Hyperwave-ISP 0 0 0 +3156 iafdbase 0 0 0 +3157 IAFServer 0 0 0 +3158 IBM Director 0 0 0 +3160 IBM NetView DM 0 0 0 +3161 IBM NetView DM/6000 Server/Client 0 0 0 +3162 ICL coNETion locate server 0 0 0 +3163 ICL coNETion server info 0 0 0 +3164 idfp 0 0 0 +3165 IEEE-MMS-SSL 0 0 0 +3167 IMP Logical Address Maintenance 0 0 0 +3168 Intecourier 0 0 0 +3169 Integra Software Management Environment 0 0 0 +3172 IBP 0 0 0 +3173 Internet Configuration Manager 0 0 0 +3176 Internet telephony tool 0 0 0 +3177 CU-SeeMe 0 0 0 +3178 IPX over UDP 0 0 0 +3179 intrinsa 0 0 0 +3180 ipcd 0 0 0 +3181 ipdd 0 0 0 +3182 Kali 0 0 0 +3183 IRC-SERV 0 0 0 +3184 ISO ILL Protocol 0 0 0 +3185 ISO Transport Class 2 Non-Control over TCP 0 0 0 +3186 ISO SAP 0 0 0 +3188 ISO-TP0 0 0 0 +3189 itm-mcell-s 0 0 0 +3191 Kerberos Administration 0 0 0 +3192 Key Server 0 0 0 +3193 Klogin 0 0 0 +3194 Konspire2b 0 0 0 +3195 kpasswd 0 0 0 +3196 kshell 0 0 0 +3197 LDP 0 0 0 +3198 lanserver 0 0 0 +3199 LWAPP 0 0 0 +3201 ljk-login 0 0 0 +3202 Locus PC-Interface Conn Server 0 0 0 +3203 Loglogic 0 0 0 +3204 MacOS Server Admin 0 0 0 +3205 MSA 0 0 0 +3206 Mailbox-LM 0 0 0 +3207 maitrd 0 0 0 +3208 Management Utility 0 0 0 +3209 mcns-sec 0 0 0 +3210 mdc-portmapper 0 0 0 +3211 Memcomm 0 0 0 +3212 Meregister 0 0 0 +3214 Meter 0 0 0 +3215 micom-pfs 0 0 0 +3217 Micromuse-lm 0 0 0 +3218 Microsoft Global Catalog 0 0 0 +3220 Microsoft Rome 0 0 0 +3221 Microsoft Shuttle 0 0 0 +3222 Microsoft System Center Operations Manager 0 0 0 +3224 MIT ML Device 0 0 0 +3225 MobilIP-MN 0 0 0 +3226 Mobility XE protocol 0 0 0 +3227 Mondex 0 0 0 +3228 Monitor 0 0 0 +3229 MPM FLAGS Protocol 0 0 0 +3230 MS Exchange Routing 0 0 0 +3231 msg-icp 0 0 0 +3232 Bundle Discovery Protocol 0 0 0 +3233 MRM 0 0 0 +3234 Multiling HTTP 0 0 0 +3237 Mylex-mapd 0 0 0 +3238 nCube License Manager 0 0 0 +3239 Nest Protocol 0 0 0 +3240 netGW 0 0 0 +3241 Netix MPP 0 0 0 +3242 Netnews 0 0 0 +3243 Netnews Administration System 0 0 0 +3244 Netop Remote Control 0 0 0 +3245 Network based Rev. Cont. Sys. 0 0 0 +3247 Network Innovations Multiplex 0 0 0 +3248 Nmap 0 0 0 +3250 NQS 0 0 0 +3252 Network Systems 0 0 0 +3253 Networked Media Streaming Protocol 0 0 0 +3254 New who 0 0 0 +3255 NFS Lock Daemon Manager 0 0 0 +3257 nlogin 0 0 0 +3258 Novadigm EDM 0 0 0 +3259 Novell Netware over IP 0 0 0 +3260 NPMP Trap 0 0 0 +3261 npmp-gui 0 0 0 +3262 npmp-local 0 0 0 +3263 NSW User System FE 0 0 0 +3264 OBEX 0 0 0 +3265 OCS_CMU 0 0 0 +3266 Ohimsrv 0 0 0 +3267 Omginitialrefs 0 0 0 +3268 Omserv 0 0 0 +3269 opalis-rdv 0 0 0 +3270 openvms-sysipc 0 0 0 +3271 Operations Manager - Health Service 0 0 0 +3272 oracle 0 0 0 +3273 Oracle coauthor 0 0 0 +3274 Oracle Names 0 0 0 +3275 Oracle Net8 Cman 0 0 0 +3276 Oracle Net8 CMan Admin 0 0 0 +3277 Oracle TCP/IP Listener 0 0 0 +3278 Orbix 2000 Config 0 0 0 +3279 Orbix 2000 Locator 0 0 0 +3280 Orbix 2000 Locator over SSL 0 0 0 +3282 P10 0 0 0 +3283 Parsec Gameserver 0 0 0 +3285 PassGo Technologies Service 0 0 0 +3286 Password Change 0 0 0 +3287 PDL data streaming port 0 0 0 +3289 POV-Ray 0 0 0 +3290 Personal Link 0 0 0 +3291 Pharos psrserver 0 0 0 +3292 Philips Video-Conferencing 0 0 0 +3293 Phonebook 0 0 0 +3294 Photuris 0 0 0 +3295 PIM-RP-DISC 0 0 0 +3296 pirp 0 0 0 +3297 Plus Fives MUMPS 0 0 0 +3298 PTP Event 0 0 0 +3299 PAPI 0 0 0 +3300 PRM Node Man 0 0 0 +3301 PRM Sys Man 0 0 0 +3302 PTC Name Service 0 0 0 +3303 PTP General 0 0 0 +3304 pump 0 0 0 +3305 PureNoise 0 0 0 +3306 qrh 0 0 0 +3308 QMQP 0 0 0 +3310 Quotad 0 0 0 +3312 Radio Control Protocol 0 0 0 +3313 Rational Method Composer 0 0 0 +3315 Radmin 0 0 0 +3316 RDA 0 0 0 +3317 RMCP 0 0 0 +3318 Remote Method Invocation Activation 0 0 0 +3319 rmtis 0 0 0 +3320 Remote-KIS 0 0 0 +3321 RemoteFS 0 0 0 +3322 repcmd 0 0 0 +3323 repscmd 0 0 0 +3326 RRH 0 0 0 +3327 RLZ Dbase 0 0 0 +3328 rmiregistry 0 0 0 +3329 Rmonitor 0 0 0 +3331 netvmg-traceroute 0 0 0 +3332 RSVP Tunnel 0 0 0 +3333 rtip 0 0 0 +3334 RUSHD 0 0 0 +3335 Russell Info Sci Calendar Manager 0 0 0 +3336 rxe 0 0 0 +3337 SANity 0 0 0 +3338 SAP 0 0 0 +3339 SCC Security 0 0 0 +3340 SCO Desktop Administration Server 0 0 0 +3341 SCO System Administration Server 0 0 0 +3342 SCO Web Server Manager 3 0 0 0 +3343 SCO WebServer Manager 0 0 0 +3344 scohelp 0 0 0 +3345 SST 0 0 0 +3346 scx-proxy 0 0 0 +3347 SDNS-KMP 0 0 0 +3349 SILC 0 0 0 +3350 Secure IRC 0 0 0 +3351 SMID 0 0 0 +3353 SNNTP 0 0 0 +3354 SIFT 0 0 0 +3355 srvloc 0 0 0 +3356 sFlow 0 0 0 +3357 Siam 0 0 0 +3358 SAFT 0 0 0 +3359 SNTP-HEARTBEAT 0 0 0 +3361 Sitara Dir 0 0 0 +3362 Sitara Management 0 0 0 +3363 Sitara Server 0 0 0 +3364 Skronk 0 0 0 +3366 smpnameres 0 0 0 +3367 smsd 0 0 0 +3369 Softros LAN Messenger 0 0 0 +3370 Sonar 0 0 0 +3371 SURF 0 0 0 +3372 SPMP 0 0 0 +3373 spsc 0 0 0 +3374 ss7ns 0 0 0 +3375 STMF 0 0 0 +3376 Stock IXChange 0 0 0 +3377 streettalk 0 0 0 +3378 STUN over TLS 0 0 0 +3379 Submit Protocol 0 0 0 +3380 SUBNTBCST_TFTP 0 0 0 +3381 Sun IPC server 0 0 0 +3382 SUNDR 0 0 0 +3383 Survey Measurement 0 0 0 +3384 SRVFP 0 0 0 +3385 SynOptics SNMP Relay 0 0 0 +3386 SynOptics Trap 0 0 0 +3387 SNARE 0 0 0 +3388 BB 0 0 0 +3389 TDP 0 0 0 +3390 TeamSound 0 0 0 +3391 Technical Analysis Software 0 0 0 +3392 Teedtap 0 0 0 +3393 tell 0 0 0 +3394 TenFold 0 0 0 +3395 TESLA 0 0 0 +3396 TIA/EIA/IS-99 modem client 0 0 0 +3397 TIA/EIA/IS-99 modem server 0 0 0 +3398 Timeserver 0 0 0 +3399 tinc 0 0 0 +3400 TNS CML 0 0 0 +3401 Tobit David Replica 0 0 0 +3402 TPIP 0 0 0 +3404 Transport Independent Convergence 0 0 0 +3405 trin00 0 0 0 +3406 Ulpnet 0 0 0 +3407 Unix time 0 0 0 +3408 User Location Protocol 0 0 0 +3409 UTMPCD 0 0 0 +3410 utmpsd 0 0 0 +3411 uuidgen 0 0 0 +3412 VACDSM-APP 0 0 0 +3413 VACDSM-SWS 0 0 0 +3414 VATP 0 0 0 +3415 vemmi 0 0 0 +3416 Vid 0 0 0 +3417 Videotex 0 0 0 +3418 Virtual Presence Protocol 0 0 0 +3419 VMware Fault Domain Manager 0 0 0 +3420 vnas 0 0 0 +3421 VPPS-Via 0 0 0 +3422 vsinet 0 0 0 +3423 VVPS-Qua 0 0 0 +3424 WAP connectionless session service 0 0 0 +3425 WAP Push 0 0 0 +3426 WAP Push OTA-HTTP port 0 0 0 +3427 WAP Push OTA-HTTP secure 0 0 0 +3428 WAP Push Secure 0 0 0 +3429 WAP secure connectionless session service 0 0 0 +3430 WAP Session Service Secure 0 0 0 +3431 WAP Session Service 0 0 0 +3432 WAP vCal 0 0 0 +3433 WAP vCal Secure 0 0 0 +3434 WAP vCard 0 0 0 +3435 WAP vCard Secure 0 0 0 +3436 War-rock 0 0 0 +3437 whoami 0 0 0 +3438 WLCCP 0 0 0 +3439 World Fusion 0 0 0 +3440 wpgs 0 0 0 +3442 xact-backup 0 0 0 +3443 xvttp 0 0 0 +3501 ICMP 0 0 0 +3504 IP in IP 0 0 0 +3505 ST 0 0 0 +3507 CBT 0 0 0 +3508 EGP 0 0 0 +3509 IGRP 0 0 0 +3510 BBN RCC 0 0 0 +3511 NVP 0 0 0 +3513 Argus 0 0 0 +3514 Emission Control Protocol 0 0 0 +3515 Cross Net Debugger 0 0 0 +3516 CHAOSNet 0 0 0 +3519 DCN Measurement Subsystems 0 0 0 +3520 HMP 0 0 0 +3521 Packet Radio Measurement 0 0 0 +3523 Trunk-1 Protocol 0 0 0 +3524 Trunk-2 Protocol 0 0 0 +3525 Leaf-1 0 0 0 +3526 Leaf-2 0 0 0 +3527 Reliable Datagram Protocol 0 0 0 +3528 IRTP 0 0 0 +3529 TP4 0 0 0 +3530 NETBLT 0 0 0 +3531 MFE 0 0 0 +3534 TPCP 0 0 0 +3535 IDPR 0 0 0 +3537 DDP 0 0 0 +3538 IDPR Control Message 0 0 0 +3539 TP++ 0 0 0 +3540 IL 0 0 0 +3541 IPv6 encapsulation 0 0 0 +3542 SDRP 0 0 0 +3545 IDRP 0 0 0 +3548 DSR 0 0 0 +3549 BNA 0 0 0 +3552 i-nlsp 0 0 0 +3553 Swipe 0 0 0 +3554 NARP 0 0 0 +3555 IP Mobility 0 0 0 +3557 SKIP 0 0 0 +3558 ICMP for IPv6 0 0 0 +3561 any host 0 0 0 +3562 cFTP 0 0 0 +3564 SATNET and Backroom EXPAK 0 0 0 +3566 RVD 0 0 0 +3567 Pluribus Packet Core 0 0 0 +3569 SATNET Monitoring 0 0 0 +3571 IPCU 0 0 0 +3572 CP Network Executive 0 0 0 +3573 CP Heart Beat 0 0 0 +3574 Wang Span 0 0 0 +3575 PVP 0 0 0 +3576 SATNET 0 0 0 +3577 SUN NDP 0 0 0 +3578 Wideband Monitoring 0 0 0 +3579 Wideband EXPAK 0 0 0 +3582 VMTP 0 0 0 +3584 TTP 0 0 0 +3585 NSFNET-IGP 0 0 0 +3587 TCF 0 0 0 +3588 EIGRP 0 0 0 +3589 OSPF 0 0 0 +3590 Sprite RPC 0 0 0 +3591 Locus ARP 0 0 0 +3592 MTP 0 0 0 +3593 AX.25 0 0 0 +3595 MICP 0 0 0 +3596 Semaphore Sec Pro 0 0 0 +3597 EtherIP 0 0 0 +3598 Encapsulation Header 0 0 0 +3600 GMTP 0 0 0 +3601 IFMP 0 0 0 +3602 PNNI 0 0 0 +3604 ARIS 0 0 0 +3605 SCPS 0 0 0 +3606 QNX 0 0 0 +3607 Active Networks 0 0 0 +3609 SNP 0 0 0 +3610 Compaq-Peer 0 0 0 +3611 IPX over IP 0 0 0 +3612 VRRP 0 0 0 +3613 PGM RTP 0 0 0 +3616 D-II 0 0 0 +3617 IATP 0 0 0 +3618 Schedule Transfer Protocol 0 0 0 +3619 SRP 0 0 0 +3620 UTI 0 0 0 +3621 SMP 0 0 0 +3622 SM 0 0 0 +3623 PTP 0 0 0 +3624 ISIS 0 0 0 +3625 Fire 0 0 0 +3626 Combat Radio Transport Protocol 0 0 0 +3627 Combat Radio User Datagram 0 0 0 +3628 SSCOPMCE 0 0 0 +3629 IPLT 0 0 0 +3630 SPS 0 0 0 +3631 PIPE 0 0 0 +3633 iFCP 0 0 0 +3634 RSVP-E2E-IGNORE 0 0 0 +3637 MPLS 0 0 0 +3639 HIP 0 0 0 +3640 Amazon Cloud Drive 0 0 0 +3641 Amazon Cloud Drive Download 0 0 0 +3642 Amazon Cloud Drive Upload 0 0 0 +3643 Amazon Cloud Drive Authenticate 0 0 0 +3645 Google+ Location Tagging 0 0 0 +3646 Myspace Music 0 0 0 +3648 Kik Messenger 0 453 1370 +3649 Cisco Jabber Audio 0 0 0 +3650 Cisco Jabber Video 0 0 1800 +3651 SmartFox 0 0 0 +3652 VPNReactor 0 0 1789 +3653 CyberGhost VPN 0 0 1785 +3654 GRE 0 0 0 +3655 Alipay 0 0 1526 +3656 Crittercism 0 0 1492 +3657 Delta Search 0 0 1493 +3658 Fluent 0 0 0 +3659 MelOn 0 0 1494 +3670 Microsoft Store 0 0 1495 +3671 news.com.au 0 0 1496 +3672 OpenCandy 0 0 1497 +3673 Soso 0 0 1498 +3674 Woolik 0 0 1499 +3675 Sina 0 0 0 +3676 Airsoft Powerburst 0 0 0 +3677 GSS HTTP 0 0 0 +3678 NetWall 0 0 0 +3679 Eudora Set 0 0 0 +3680 Service Status Update 0 0 0 +3681 ESRO-EMSDP V1.3 0 0 0 +3682 OLSR 0 0 0 +3683 PKIX-3 CA/RA 0 0 0 +3684 Oracle Remote Data Base 0 0 0 +3685 ISCSI 0 0 0 +3686 Tapeware 0 0 0 +3687 IAX 0 0 0 +3688 CVSup 0 0 0 +3689 MSOC File Transfer 0 0 0 +3690 McAfee AutoUpdate 0 0 0 +3691 AMANDA 0 0 0 +3692 Oracle Business Intelligence 0 0 0 +3693 webster 0 0 0 +3694 tn-tl-fd1 0 0 0 +3695 GGP 0 0 0 +3696 MERIT Internodal Protocol 0 0 0 +3699 UDP Lite 0 0 0 +3700 PHP Proxy 0 0 0 +3701 Achetez Facile 0 0 1763 +3702 Ad4mat 0 0 1751 +3703 Betclic 0 0 0 +3704 Beweb 0 0 0 +3705 Cedexis 0 0 1748 +3706 GG 0 501 1807 +3707 GG Media 0 0 0 +3708 HTFacile 0 0 0 +3709 HWCDN 0 0 0 +3710 Itsfogo 0 0 0 +3711 L'equipe.fr 0 0 1709 +3712 Ligatus 0 0 1749 +3713 LINE Games 0 495 1777 +3714 LINE Media 0 493 0 +3715 1000mercis 0 0 1764 +3716 Piksel 0 0 1743 +3717 Proxistore 0 0 1765 +3718 SASCDN 0 0 0 +3719 Surikate 0 0 1752 +3720 Videoplaza 0 0 0 +3721 VIEWON 0 0 1750 +3722 Viewsurf 0 0 1761 +3723 Weborama 0 0 1757 +3724 XiTi 0 0 1755 +3725 Zanox 0 0 1754 +3726 WebEx Connect 0 0 0 +3727 QQ Games 0 454 0 +3728 easyMule 0 0 1371 +3730 Yik Yak 0 470 1372 +3733 OpenDoor 0 467 1450 +3734 Crunchyroll Video 0 0 0 +3735 OneDrive 0 483 1377 +3736 LinkedIn Contacts 0 0 1379 +3737 Rackspace 0 0 1380 +3738 ServiceNow 0 0 1381 +3739 T-Online 0 0 1382 +3740 Web.de 0 0 1383 +3741 Workday 0 0 1384 +3742 AppNeta 0 0 0 +3743 Blizzard Client 0 0 0 +3744 Blizzard Downloader 0 0 1828 +3745 Blizzard 0 0 1832 +3746 Blizzard Game Data 0 0 0 +3747 Battle.net Desktop 0 0 0 +3748 Battle.net Protocol 0 0 0 +3749 Battle.net site 0 0 1820 +3751 Pathtest 0 0 0 +3752 Pathview 0 0 0 +3753 Slingbox Media 0 0 0 +3754 Spotflux 0 0 1794 +3755 USAIP 0 0 1796 +3756 Yahoo! Douga 0 0 1385 +3757 Yahoo! Box 0 0 1386 +3761 BJNP Discovery 0 0 0 +3762 Crazy Browser 0 204 0 +3763 GreenBrowser 0 205 0 +3764 CometBird 0 202 0 +3765 Flock 0 199 0 +3766 Arora 0 200 0 +3767 Facebook Notes 0 0 1360 +3769 Compressed PPP 0 0 0 +3770 CCP 0 0 0 +3771 PPP 0 0 0 +3772 PAP 0 0 0 +3773 LCP 0 0 0 +3774 IPCP 0 0 0 +3775 IPv6CP 0 0 0 +3776 CHAP 0 0 0 +3777 Browzar 0 201 0 +3778 IEC 60870-5-104 20191 0 0 iec-104 +3779 Iperf 0 0 0 +3781 ITU T.120 0 0 0 +3782 Clip2Net 0 461 1387 +3783 Clip2Net Upload 0 0 1388 +3784 LogMeIn Rescue 0 462 1389 +3785 Mendeley 0 463 1390 +3786 Onehub 0 0 0 +3787 ZumoDrive 0 464 0 +3789 eFax 0 466 1439 +3790 Yesky 0 0 1440 +3791 100ye.com 0 0 1441 +3792 Yahoo! Screen 0 0 1643 +3793 Amazon Instant Video 0 482 1690 +3795 Playstation Games 0 0 1798 +3796 Playstation Match 0 0 0 +3798 TISTORY 0 0 1485 +3799 DioDeo 0 0 1486 +3800 Egloos 0 0 1487 +3801 Lineage 0 0 1488 +3802 MapleStory 0 0 1489 +3803 ezhelp 0 0 1490 +3804 Bonjour 0 0 0 +3805 Level 3 0 0 1744 +3806 Net2Phone 0 0 1797 +3807 Net2Phone Media 0 0 0 +3808 PJL 0 0 0 +3809 SoftEther 0 0 0 +3810 Speedtest Upload 0 0 0 +3811 Channel 4 0 0 1770 +3812 Opera Mini 0 0 0 +3815 MissLee 0 0 1591 +3816 Mgoon 0 0 1592 +3817 QDown 0 0 1593 +3818 SBS 0 0 1594 +3819 C3 Metrics 0 0 0 +3820 Oracle CRMOD 0 0 0 +3821 LeadLander 0 0 0 +3822 Bootstrap CDN 0 0 1642 +3823 keyholetv 0 0 0 +3824 COSEM 0 0 0 +3825 Microsoft FrontPage Server Extensions 0 0 0 +3826 GOOSE 0 0 0 +3827 GSE 0 0 0 +3830 XMPP File Transfer 0 0 0 +3832 Scopia 0 0 0 +3833 GTP Control 0 0 0 +3834 GTP User 0 0 0 +3835 GTP Prime 0 0 0 +3836 RIPng 0 0 0 +3837 Aurora 0 0 0 +3838 BaiduHi 0 503 1824 +3839 Diameter 0 0 0 +3841 FASP 0 0 0 +3842 IGMP 0 0 0 +3843 ISO IP 0 0 0 +3844 WSP 0 0 0 +3846 Ad Master 0 0 1645 +3847 Ad Tech 0 0 1646 +3848 Yahoo! Box Download 0 0 0 +3849 Yahoo! Box Upload 0 0 0 +3850 Yahoo! MP4 0 0 0 +3851 Yahoo! Shockwave 0 0 0 +3852 GREE Games 0 0 0 +3853 GungHo Online Entertainment 0 0 0 +3854 Mobaga Town 0 0 0 +3855 UULA 0 0 0 +3856 Netflow 0 0 0 +3857 TunnelBear 0 0 0 +3858 HipChat 0 0 1647 +3859 ITV 0 0 0 +3860 HTTP/SSL Tunnel 0 0 0 +3861 ShareFile Upload SSL 0 0 1022 +3862 PIM 0 0 0 +3863 IPComp 0 0 0 +3864 PARC Universal Packet 0 0 0 +3865 IDP 0 0 0 +3866 360 Safeguard 0 0 1648 +3867 Neobux 0 0 1649 +3868 People's Daily 0 0 1650 +3869 Vube 0 0 1651 +3870 Kickass Torrents 0 0 1652 +3871 China Daily 0 0 1653 +3872 Guangming Online 0 0 1654 +3873 RevenueHits 0 0 1655 +3874 AMQP 0 0 0 +3875 AMQPS 0 0 0 +3876 Info.com 0 0 1656 +3877 Code42 0 0 0 +3878 CrashPlan 0 0 0 +3879 MPEG Transport Stream 0 0 0 +3880 QQ Cloud 0 0 0 +3881 QQ Shopping 0 0 0 +3882 QQ Mail 0 0 0 +3883 QQ Pay 0 0 0 +3884 QQ Weiyun 0 0 0 +3885 Gmail attachment 0 0 1657 +3886 ESP 0 0 0 +3887 Adobe Creative Cloud 0 0 0 +3888 Autodesk 0 0 1793 +3889 Blackbaud 0 0 0 +3890 Demandbase 0 0 1814 +3891 Intralinks 0 0 1815 +3892 NetSuite 0 0 0 +3893 Onavo 0 0 0 +3894 Onavo Count 0 0 0 +3895 Onavo Extend 0 0 0 +3896 Oracle Marketing Cloud 0 0 0 +3897 Plista 0 0 1819 +3898 Scopia Audio 0 0 0 +3899 Scopia Video 0 0 0 +3901 SuccessFactors 0 0 0 +3910 Wow 0 0 1658 +3911 Webcrawler 0 0 1659 +3921 Wikipedia Edit 0 0 0 +3922 ADP 0 0 0 +3923 ADP GlobalView 0 0 0 +3924 ADP Resource 0 0 0 +3925 ADP Streamline 0 0 0 +3926 ADP TotalSource 0 0 0 +3927 ADP Vantage 0 0 0 +3928 ADP Workforce Now 0 0 0 +3929 Benefitfocus 0 0 0 +3930 Cerner Corporation 0 0 0 +3931 Conviva 0 0 1817 +3932 Cornerstone OnDemand 0 0 0 +3933 Dealertrack 0 0 0 +3934 Microsoft Dynamics CRM 0 0 0 +3935 QuickBase 0 0 0 +3936 QuickBooks 0 0 0 +3937 Quicken 0 0 0 +3938 TurboTax 0 0 0 +3939 Jive 0 0 0 +3940 Marketo 0 0 1816 +3941 QQ Music 0 0 0 +3942 QQ Video 0 0 0 +3943 Siteimprove 0 0 1818 +3944 Ultimate Software 0 0 0 +3945 Veeva 0 0 0 +3946 Hulu Video 0 0 1671 +3947 MQTT 20193 471 0 mqtt +3948 RSVP 0 0 0 +3949 CAPWAP 0 0 0 +3950 Asana 0 0 0 +3951 Baydin 0 0 0 +3952 Boomerang 0 0 0 +3953 Cloudsponge 0 0 0 +3954 Cvent 0 0 0 +3955 DocuSign 0 0 0 +3956 Draw.io 0 0 0 +3957 Gantter 0 0 0 +3958 IAX2 0 0 0 +3959 InQuest Technologies 0 0 0 +3960 Inspectlet 0 0 0 +3961 Lucidchart 0 0 0 +3962 Rapportive 0 0 0 +3963 SlideRocket 0 0 0 +3964 Smartapp 0 0 0 +3965 TripIt 0 0 0 +3966 UEFA 0 0 0 +3967 WarLight 0 0 0 +3968 Zomato 0 0 0 +3969 Crashlytics 0 0 0 +3970 Flipkart 0 472 1673 +3971 Cisco Jabber 0 473 0 +3972 IRC file transfer 0 0 0 +3973 VXLan 0 0 0 +3974 WhatsApp Voice 0 0 0 +3975 WhatsApp Location 0 0 0 +3976 WhatsApp Media Message 0 0 0 +3977 Starsports 0 0 1674 +3978 ESPNcricinfo 0 0 1675 +3979 Microsoft Visual Studio 0 0 1676 +3980 BlueStacks 0 474 1677 +3981 JetBrains 0 475 1678 +3982 Youdao Dictionary 0 476 1679 +3983 JetBrains update 0 0 1680 +3984 JetBrains plugins 0 0 1681 +3985 JetBrains feature 0 0 1682 +3986 BlueStacks update 0 0 1683 +3987 BlueStacks download 0 0 1684 +3988 BlueStacks apps 0 0 1685 +3989 F-secure 0 477 1686 +3990 Malwarebytes 0 478 1687 +3991 SUPERAntiSpyware 0 479 1688 +3992 Periscope 0 480 1691 +3993 Meerkat 0 481 0 +3994 ZenMate 0 0 0 +3996 ibVPN 0 0 0 +3997 Storehouse 0 0 0 +3998 Avaya Audio 0 0 0 +3999 Avaya Video 0 0 0 +4000 Internet Download Manager 0 0 0 +4001 Wi-Fi Calling 0 0 0 +4002 FTP Active 0 0 0 +4003 FTP Passive 0 0 0 +4004 Eve Online 0 0 0 +4005 CCP Games 0 0 1826 +4006 Mojang 0 0 0 +4007 VMware vMotion 0 0 0 +4010 WPS Office 0 486 1698 +4012 Apple Pipeline 0 0 1696 +4013 Kontiki 0 488 1697 +4014 Brewster 0 0 0 +4015 MPLS Unicast 0 0 0 +4016 EA Download Manager 0 487 1695 +4017 Seterus 0 0 0 +4019 JoinMe 0 0 0 +4020 After School 0 0 0 +4021 CloudApp 0 0 0 +4022 HSRP 0 0 0 +4023 QUIC 0 0 0 +4024 Rapidgator 0 0 0 +4025 Skype Photo 0 0 0 +4026 Skype Video Message 0 0 0 +4027 Syncplicity 0 0 0 +4028 Gom VPN 0 0 0 +4029 IxChariot 0 0 0 +4030 ZRTP 0 0 0 +4031 Winny 0 0 0 +4032 AppGlu 0 0 0 +4033 I2P 0 0 0 +4034 Jungle Disk 0 0 0 +4035 Ninite 0 0 0 +4036 SpiderOak 0 0 0 +4037 Uploaded 0 0 0 +4038 Wondershare 0 0 1833 +4039 Western Digital 0 0 1834 +4040 WD softwares Download/Update 0 0 1835 +4041 Hola 0 0 1836 +4043 Baidu Yun 0 0 0 +4044 Spinrilla 0 0 0 +4045 Slack 0 0 0 +4046 Burnbook 0 0 0 +4047 skyZIP 0 0 0 +4048 Facebook VoIP 0 0 0 +4049 Yandex Disk 0 0 0 +4050 Naver Blog 0 0 1839 +4051 Naver Cafe 0 0 1840 +4052 Daum Blog 0 0 1841 +4053 Daum Cafe 0 0 1842 +4054 Naver Mail 0 0 1843 +4055 Daum Mail 0 0 1844 +4056 Kakao Story 0 0 1845 +4057 Edge 0 506 0 +4058 uProxy 0 0 0 +4059 Yandex AppMetrica 0 0 0 +4060 Yandex Images 0 0 0 +4061 Yandex Email 0 0 0 +4062 Yandex Maps 0 0 0 +4063 Yandex Money 0 0 0 +4064 Yandex Market 0 0 0 +4065 Yandex Music 0 0 0 +4066 Yandex Translate 0 0 0 +4067 Yandex Video 0 0 0 +4068 Facebook Like 0 0 1846 +4069 Sway 0 0 1848 +4070 Office 365 Planner 0 0 1849 +4071 Office for iPad 0 0 1850 +4072 Office Mobile 0 0 1851 +4073 Messenger 0 0 1852 +4075 Psiphon 0 0 0 +4076 Tanium 20197 0 0 tanium +4077 Fiesta 0 0 0 +4078 Blackbox 0 0 1853 +4079 Google Checkout 0 0 0 +4080 Cisco Spark 0 0 0 +4081 Microsoft Web Platform Installer 0 507 1854 +4082 DotVPN 0 0 0 +4083 Yemonisoni 0 0 0 +4084 SuperVPN 0 0 0 +4085 MoPub 0 0 0 +4086 MobileCore 0 0 0 +4087 Addictive Mobility 0 0 0 +4088 Avocarrot 0 0 0 +4089 Synology DSM 0 508 1855 +4090 LiveJournal Post 0 0 1856 +4091 Mail.ru Attachment 0 0 1857 +4092 Betternet 0 0 0 +4093 Boom Beach 0 0 0 +4094 Browsec 0 0 0 +4095 Clash of Clans 0 0 0 +4096 Frozenway 0 0 0 +4097 Supercell 0 0 0 +5001 ENIP 20501 359 0 +10000 RegTestPort 0 0 0 +10001 RegTestPat 0 0 0 +10002 RegTestBrute 0 0 0 diff --git a/src/network_inspectors/appid/test/app_info_table_test.cc b/src/network_inspectors/appid/test/app_info_table_test.cc new file mode 100644 index 000000000..a60bda0e4 --- /dev/null +++ b/src/network_inspectors/appid/test/app_info_table_test.cc @@ -0,0 +1,154 @@ +//-------------------------------------------------------------------------- +// Copyright (C) 2016-2017 Cisco and/or its affiliates. All rights reserved. +// +// This program is free software; you can redistribute it and/or modify it +// under the terms of the GNU General Public License Version 2 as published +// by the Free Software Foundation. You may not use, modify or distribute +// this program under any other version of the GNU General Public License. +// +// This program is distributed in the hope that it will be useful, but +// WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// General Public License for more details. +// +// You should have received a copy of the GNU General Public License along +// with this program; if not, write to the Free Software Foundation, Inc., +// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +//-------------------------------------------------------------------------- + +// appid_info_table_test.cc author davis mcpherson + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#include "network_inspectors/appid/app_info_table.cc" + +#include + +#include "protocols/protocol_ids.h" +#include "appid_mock_inspector.h" + +#include +#include + +char* snort_strdup(const char* str) +{ + assert(str); + size_t n = strlen(str) + 1; + char* p = (char*)snort_alloc(n); + memcpy(p, str, n); + return p; +} + +void ErrorMessage(const char*,...) { } +void WarningMessage(const char*,...) { } +void LogMessage(const char*,...) { } +void ParseWarning(WarningGroup, const char*, ...) { } + +#ifdef DEBUG_MSGS +void Debug::print(const char*, int, uint64_t, const char*, ...) { } +#endif + +const char* UT_TEST_APP_NAME_001 = "ut_app_001"; +const char* UT_TEST_APP_NAME_002 = "ut_app_002"; +const char* UT_TEST_APP_NAME_TOO_LONG = + "ut_app78901234567890123456789012345678901234567890123456789012345"; + +#define UT_TEST_APP_ID_001 111 +#define UT_TEST_APP_ID_002 222 + +AppInfoManager& app_info_mgr = AppInfoManager::get_instance(); + +AppInfoTableEntry* add_static_entry(AppId id, const char* name) +{ + AppInfoTableEntry* entry = new AppInfoTableEntry(id, snort_strdup(name)); + entry->app_name_key = snort_strdup(name); + entry->serviceId = id; + entry->clientId = id; + entry->payloadId = id; + app_info_table[id] = entry; + bool rc = add_entry_to_app_info_name_table(entry->app_name_key, entry); + CHECK_TRUE(rc); + return entry; +} + +TEST_GROUP(app_info_table) +{ + void setup() + { + MemoryLeakWarningPlugin::turnOffNewDeleteOverloads(); + } + + void teardown() + { + app_info_mgr.cleanup_appid_info_table(); + MemoryLeakWarningPlugin::turnOnNewDeleteOverloads(); + } +}; + +TEST(app_info_table, get_app_name) +{ + AppInfoTableEntry* entry = add_static_entry(UT_TEST_APP_ID_001, UT_TEST_APP_NAME_001); + CHECK_TRUE(entry); + entry = app_info_mgr.add_dynamic_app_entry(UT_TEST_APP_NAME_002); + CHECK_TRUE(entry); + const char* app_name = app_info_mgr.get_app_name(UT_TEST_APP_ID_001); + STRCMP_EQUAL(app_name, UT_TEST_APP_NAME_001); +} + +TEST(app_info_table, dump_app_info_table) +{ + AppInfoTableEntry* entry = add_static_entry(UT_TEST_APP_ID_001, UT_TEST_APP_NAME_001); + CHECK_TRUE(entry); + entry = app_info_mgr.add_dynamic_app_entry(UT_TEST_APP_NAME_002); + CHECK_TRUE(entry); + app_info_mgr.dump_app_info_table(); +} + +TEST(app_info_table, add_dynamic_app_entry) +{ + AppInfoTableEntry* entry = app_info_mgr.add_dynamic_app_entry(nullptr); + CHECK_TRUE(!entry); + entry = app_info_mgr.add_dynamic_app_entry(UT_TEST_APP_NAME_TOO_LONG); + CHECK_TRUE(!entry); + entry = app_info_mgr.add_dynamic_app_entry(UT_TEST_APP_NAME_002); + CHECK_TRUE(entry); + CHECK_TRUE(entry->appId == SF_APPID_DYNAMIC_MIN); + entry = app_info_mgr.get_app_info_entry(entry->appId); + CHECK_TRUE(entry); + CHECK_TRUE(entry->appId == SF_APPID_DYNAMIC_MIN); +} + +TEST(app_info_table, duplicate_app_info_entry) +{ + AppInfoTableEntry* entry = add_static_entry(UT_TEST_APP_ID_001, UT_TEST_APP_NAME_001); + bool rc = add_entry_to_app_info_name_table(entry->app_name_key, entry); + CHECK_TRUE(!rc); +} + +TEST(app_info_table, get_app_info_priority) +{ + AppInfoTableEntry* entry = add_static_entry(UT_TEST_APP_ID_001, UT_TEST_APP_NAME_001); + CHECK_TRUE(entry); + unsigned priority = app_info_mgr.get_app_info_priority(UT_TEST_APP_ID_001); + CHECK_TRUE(priority == APP_PRIORITY_DEFAULT); + priority = app_info_mgr.get_app_info_priority(UT_TEST_APP_ID_002); + CHECK_TRUE(priority == 0); +} + +TEST(app_info_table, get_static_app_info_entry) +{ + AppId appid = SF_APPID_CSD_MIN + 1; + AppId mapped_id; + + mapped_id = get_static_app_info_entry(appid); + CHECK_TRUE(mapped_id == (SF_APPID_BUILDIN_MAX + appid - SF_APPID_CSD_MIN)); +} + +int main(int argc, char** argv) +{ + int return_value = CommandLineTestRunner::RunAllTests(argc, argv); + return return_value; +} + diff --git a/src/network_inspectors/appid/test/appid.conf b/src/network_inspectors/appid/test/appid.conf new file mode 100644 index 000000000..59c20c6d1 --- /dev/null +++ b/src/network_inspectors/appid/test/appid.conf @@ -0,0 +1,52 @@ +appid ssl_reinspect 1185 +appid ssl_reinspect 184 +appid ssl_reinspect 882 +appid ssl_reinspect 689 +appid ssl_reinspect 524 +appid ssl_reinspect 1392 +appid ssl_reinspect 1357 +appid ssl_reinspect 1105 +appid ssl_reinspect 1659 +appid ssl_reinspect 502 +appid ssl_reinspect 533 +appid ssl_reinspect 1233 +appid app_priority 1659 1 +navl plugins.CIFS.disabled 1 +navl plugins.FACEBOOK.disabled 1 +navl plugins.EDONKEY.disabled 1 +navl plugins.ORACLE.disabled 1 +navl plugins.GNUTELLA.disabled 1 +navl plugins.MDNS.disabled 1 +navl plugins.QIK.disabled 1 +navl plugins.VPNREACTOR.disabled 1 +navl plugins.IMAP.disabled 1 +navl plugins.SMTP.disabled 1 +navl plugins.POP3.disabled 1 +navl plugins.FTPCTRL.disabled 1 +navl tcp.accept_nohandshake 1 +navl bittorrent.aggressiveness 1 +navl skype.monitor_service 1 +navl ultrasurf.cache_size_limit 2048 +navl tls.subclassify_alpn 0 +appid referred_appid 2032 1520 1306 1307 1308 1310 1311 1312 1313 1314 1315 1316 137 1318 1319 1336 1337 1362 1372 1373 1424 1425 1457 1491 1619 1656 1659 1720 1721 1722 1723 1724 1725 1726 1729 1730 1731 1732 1733 1734 1735 1736 1737 1738 1739 1740 1741 1742 1743 1744 1745 1746 1747 1748 1750 1751 1752 1776 1778 1804 1850 1851 1852 1853 1854 1855 1856 1857 1858 1859 1860 1861 1862 1863 1864 1865 1866 1867 1869 1873 1874 1875 1876 1877 1878 1879 1881 1882 1883 1884 1885 1886 1888 1889 1890 1891 1892 1893 1894 1895 1896 1897 1898 1899 1900 1903 1904 1905 1906 1907 1908 1909 1910 1912 1913 1919 1920 1921 1923 1924 1925 1926 1928 1929 1930 1931 1933 1934 1935 1936 1937 1938 1940 1941 1942 1943 1944 1945 1946 1947 1948 1949 1950 1951 1953 1955 1956 1957 1958 1959 1960 +appid referred_appId 1964 1963 1964 1966 1969 1970 1972 1973 1975 1976 1977 1978 1979 1980 1981 1983 1984 1985 1986 1987 629 882 711 1393 1727 1728 1821 1992 1993 1806 1822 2022 2021 2129 2131 1460 1369 1392 2057 2062 1560 665 1458 929 761 2151 2157 2158 2159 2162 2019 2072 1508 1063 2261 2664 2690 3873 3867 2535 4059 +appid defer_to_navl 853 +appid defer_to_navl 2886 +appid defer_to_thirdparty 853 +appid defer_to_thirdparty 2886 +appid chp_body_max_bytes 1024 +appid ssl_squelch 1653 +appid ignore_navl_appid 617 +appid ignore_navl_appid 2628 +appid ignore_navl_appid 3971 +appid ignore_navl_appid 964 +appid ignore_thirdparty_appid 964 +appid ignore_navl_appid 1309 +appid ignore_thirdparty_appid 1309 +appid ignore_thirdparty_appid 617 +appid ignore_thirdparty_appid 2628 +appid ignore_thirdparty_appid 3971 +appid ignore_navl_appid 716 +appid ignore_thirdparty_appid 716 +appid tp_client_app 4000 +appid http2_detection enabled diff --git a/src/network_inspectors/appid/test/appid_api_test.cc b/src/network_inspectors/appid/test/appid_api_test.cc new file mode 100644 index 000000000..e38a0c5e6 --- /dev/null +++ b/src/network_inspectors/appid/test/appid_api_test.cc @@ -0,0 +1,739 @@ +//-------------------------------------------------------------------------- +// Copyright (C) 2016-2017 Cisco and/or its affiliates. All rights reserved. +// +// This program is free software; you can redistribute it and/or modify it +// under the terms of the GNU General Public License Version 2 as published +// by the Free Software Foundation. You may not use, modify or distribute +// this program under any other version of the GNU General Public License. +// +// This program is distributed in the hope that it will be useful, but +// WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// General Public License for more details. +// +// You should have received a copy of the GNU General Public License along +// with this program; if not, write to the Free Software Foundation, Inc., +// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +//-------------------------------------------------------------------------- + +// appid_api_test.cc author davis mcpherson + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#include "network_inspectors/appid/appid_api.cc" + +#include + +#include "framework/data_bus.h" +#include "protocols/protocol_ids.h" +#include "service_inspectors/http_inspect/http_msg_header.h" +#include "thirdparty_appid_api.h" + +#include "appid_mock_definitions.h" +#include "appid_mock_http_session.h" +#include "appid_mock_session.h" + +#include +#include + +void BootpServiceDetector::AppIdFreeDhcpData(DHCPData* data) +{ + delete data; +} + +void BootpServiceDetector::AppIdFreeDhcpInfo(DHCPInfo* info) +{ + delete info; +} + +void NbdgmServiceDetector::AppIdFreeSMBData(FpSMBData* data) +{ + delete data; +} + +const char* AppInfoManager::get_app_name(AppId) +{ + return test_app_name; +} + +int32_t AppInfoManager::get_appid_by_name(const char*) +{ + return APPID_UT_ID; +} + +AppInfoManager& app_info_mgr = AppInfoManager::get_instance(); + +Flow* flow = nullptr; +AppIdSession* mock_session = nullptr; + +TEST_GROUP(appid_api) +{ + void setup() + { + MemoryLeakWarningPlugin::turnOffNewDeleteOverloads(); + flow = new Flow; + mock_session = new AppIdSession(IpProtocol::TCP, nullptr, 1492); + mock_session->hsession = init_http_session(mock_session); + flow->set_flow_data(mock_session); + } + + void teardown() + { + delete mock_session; + delete flow; + MemoryLeakWarningPlugin::turnOnNewDeleteOverloads(); + } +}; + +TEST(appid_api, get_application_name) +{ + const char* app_name = appid_api.get_application_name(1066); + STRCMP_EQUAL(app_name, test_app_name); +} + +TEST(appid_api, get_application_id) +{ + AppId id = appid_api.get_application_id(test_app_name); + CHECK_EQUAL(id, 1492); +} + +TEST(appid_api, get_service_app_id) +{ + AppId id = appid_api.get_service_app_id(nullptr); + CHECK_EQUAL(id, APP_ID_NONE); + id = appid_api.get_service_app_id(mock_session); + CHECK_EQUAL(id, APPID_UT_ID); +} + +TEST(appid_api, get_port_service_app_id) +{ + AppId id = appid_api.get_port_service_app_id(nullptr); + CHECK_EQUAL(id, APP_ID_NONE); + id = appid_api.get_port_service_app_id(mock_session); + CHECK_EQUAL(id, APPID_UT_ID + 3); +} + +TEST(appid_api, get_only_service_app_id) +{ + AppId id = appid_api.get_only_service_app_id(nullptr); + CHECK_EQUAL(id, APP_ID_NONE); + id = appid_api.get_only_service_app_id(mock_session); + CHECK_EQUAL(id, APPID_UT_ID); +} + +TEST(appid_api, get_misc_app_id) +{ + AppId id = appid_api.get_misc_app_id(nullptr); + CHECK_EQUAL(id, APP_ID_NONE); + id = appid_api.get_misc_app_id(mock_session); + CHECK_EQUAL(id, APPID_UT_ID); +} + +TEST(appid_api, get_client_app_id) +{ + AppId id = appid_api.get_client_app_id(nullptr); + CHECK_EQUAL(id, APP_ID_NONE); + id = appid_api.get_client_app_id(mock_session); + CHECK_EQUAL(id, APPID_UT_ID); +} + +TEST(appid_api, get_payload_app_id) +{ + AppId id = appid_api.get_payload_app_id(nullptr); + CHECK_EQUAL(id, APP_ID_NONE); + id = appid_api.get_payload_app_id(mock_session); + CHECK_EQUAL(id, APPID_UT_ID); +} + +TEST(appid_api, get_referred_app_id) +{ + AppId id = appid_api.get_referred_app_id(nullptr); + CHECK_EQUAL(id, APP_ID_NONE); + id = appid_api.get_referred_app_id(mock_session); + CHECK_EQUAL(id, APPID_UT_ID); +} + +TEST(appid_api, get_fw_service_app_id) +{ + AppId id = appid_api.get_fw_service_app_id(nullptr); + CHECK_EQUAL(id, APP_ID_NONE); + id = appid_api.get_fw_service_app_id(mock_session); + CHECK_EQUAL(id, APPID_UT_ID); +} + +TEST(appid_api, get_fw_misc_app_id) +{ + AppId id = appid_api.get_fw_misc_app_id(nullptr); + CHECK_EQUAL(id, APP_ID_NONE); + id = appid_api.get_fw_misc_app_id(mock_session); + CHECK_EQUAL(id, APPID_UT_ID); +} + +TEST(appid_api, get_fw_client_app_id) +{ + AppId id = appid_api.get_fw_client_app_id(nullptr); + CHECK_EQUAL(id, APP_ID_NONE); + id = appid_api.get_fw_client_app_id(mock_session); + CHECK_EQUAL(id, APPID_UT_ID); +} + +TEST(appid_api, get_fw_payload_app_id) +{ + AppId id = appid_api.get_fw_payload_app_id(nullptr); + CHECK_EQUAL(id, APP_ID_NONE); + id = appid_api.get_fw_payload_app_id(mock_session); + CHECK_EQUAL(id, APPID_UT_ID); +} + +TEST(appid_api, get_fw_referred_app_id) +{ + AppId id = appid_api.get_fw_referred_app_id(nullptr); + CHECK_EQUAL(id, APP_ID_NONE); + id = appid_api.get_fw_referred_app_id(mock_session); + CHECK_EQUAL(id, APPID_UT_ID); +} + +TEST(appid_api, get_flow_type) +{ + APPID_FLOW_TYPE ft = appid_api.get_flow_type(nullptr); + CHECK_EQUAL(ft, APPID_FLOW_TYPE_IGNORE); + ft = appid_api.get_flow_type(mock_session); + CHECK_EQUAL(ft, APPID_FLOW_TYPE_NORMAL); +} + +TEST(appid_api, get_service_port) +{ + short sp = appid_api.get_service_port(nullptr); + CHECK_EQUAL(sp, 0); + sp = appid_api.get_service_port(mock_session); + CHECK_EQUAL(sp, APPID_UT_SERVICE_PORT); +} + +TEST(appid_api, get_http_user_agent) +{ + const char* val = appid_api.get_http_user_agent(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_http_user_agent(mock_session); + STRCMP_EQUAL(val, USERAGENT); +} + +TEST(appid_api, get_http_host) +{ + const char* val = appid_api.get_http_host(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_http_host(mock_session); + STRCMP_EQUAL(val, HOST); +} + +TEST(appid_api, get_http_url) +{ + const char* val = appid_api.get_http_url(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_http_url(mock_session); + STRCMP_EQUAL(val, URL); +} + +TEST(appid_api, get_http_referer) +{ + const char* val = appid_api.get_http_referer(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_http_referer(mock_session); + STRCMP_EQUAL(val, REFERER); +} + +TEST(appid_api, get_http_uri) +{ + const char* val = appid_api.get_http_uri(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_http_uri(mock_session); + STRCMP_EQUAL(val, URI); +} + +TEST(appid_api, get_http_new_url) +{ + init_hsession_new_fields(mock_session->hsession); + + const char* val = appid_api.get_http_new_url(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_http_new_url(mock_session); + STRCMP_EQUAL(val, URI); +} + +TEST(appid_api, get_http_response_code) +{ + const char* val = appid_api.get_http_response_code(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_http_response_code(mock_session); + STRCMP_EQUAL(val, RESPONSE_CODE); +} + +TEST(appid_api, get_http_cookie) +{ + const char* val = appid_api.get_http_cookie(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_http_cookie(mock_session); + STRCMP_EQUAL(val, COOKIE); +} + +TEST(appid_api, get_http_new_cookie) +{ + init_hsession_new_fields(mock_session->hsession); + + const char* val = appid_api.get_http_new_cookie(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_http_new_cookie(mock_session); + STRCMP_EQUAL(val, NEW_COOKIE); +} + +TEST(appid_api, free_http_new_field) +{ + init_hsession_new_fields(mock_session->hsession); + + for (unsigned i = 0; i <= HTTP_FIELD_MAX; i++) + { + const char* val = appid_api.get_http_new_field(mock_session, (HTTP_FIELD_ID)i); + CHECK_TRUE(val) + appid_api.free_http_new_field(mock_session, (HTTP_FIELD_ID)i); + CHECK_TRUE(!mock_session->hsession->new_field[i]); + } +} + +TEST(appid_api, get_http_new_field) +{ + init_hsession_new_fields(mock_session->hsession); + + const char* val = appid_api.get_http_new_field(nullptr, REQ_AGENT_FID); + CHECK_TRUE(!val); + val = appid_api.get_http_new_field(mock_session, REQ_HOST_FID); + STRCMP_EQUAL(val, HOST); + val = appid_api.get_http_new_field(mock_session, REQ_REFERER_FID); + STRCMP_EQUAL(val, REFERER); + val = appid_api.get_http_new_field(mock_session, REQ_URI_FID); + STRCMP_EQUAL(val, URI); + val = appid_api.get_http_new_field(mock_session, REQ_COOKIE_FID); + STRCMP_EQUAL(val, NEW_COOKIE); + val = appid_api.get_http_new_field(mock_session, REQ_BODY_FID); + STRCMP_EQUAL(val, REQ_BODY); + val = appid_api.get_http_new_field(mock_session, RSP_CONTENT_TYPE_FID); + STRCMP_EQUAL(val, CONTENT_TYPE); + val = appid_api.get_http_new_field(mock_session, RSP_LOCATION_FID); + STRCMP_EQUAL(val, LOCATION); + val = appid_api.get_http_new_field(mock_session, RSP_BODY_FID); + STRCMP_EQUAL(val, RSP_BODY); + val = appid_api.get_http_new_field(mock_session, REQ_AGENT_FID); + STRCMP_EQUAL(val, USERAGENT); + val = appid_api.get_http_new_field(mock_session, (HTTP_FIELD_ID)(HTTP_FIELD_MAX + 1)); + CHECK_TRUE(!val); +} + +TEST(appid_api, get_http_content_type) +{ + const char* val = appid_api.get_http_content_type(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_http_content_type(mock_session); + STRCMP_EQUAL(val, CONTENT_TYPE); +} + +TEST(appid_api, get_http_location) +{ + const char* val = appid_api.get_http_location(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_http_location(mock_session); + STRCMP_EQUAL(val, LOCATION); +} + +TEST(appid_api, get_http_body) +{ + const char* val = appid_api.get_http_body(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_http_body(mock_session); + STRCMP_EQUAL(val, RSP_BODY); +} + +TEST(appid_api, get_http_request_body) +{ + const char* val = appid_api.get_http_request_body(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_http_request_body(mock_session); + STRCMP_EQUAL(val, REQ_BODY); +} + +TEST(appid_api, get_http_uri_offset) +{ + uint16_t val = appid_api.get_http_uri_offset(nullptr); + CHECK_TRUE(val == 0); + val = appid_api.get_http_uri_offset(mock_session); + CHECK_TRUE(val == URI_OFFSET); + val = appid_api.get_http_uri_end_offset(nullptr); + CHECK_TRUE(val == 0); + val = appid_api.get_http_uri_end_offset(mock_session); + CHECK_TRUE(val == URI_OFFSET + strlen(URI)); +} + +TEST(appid_api, get_http_cookie_offset) +{ + uint16_t val = appid_api.get_http_cookie_offset(nullptr); + CHECK_TRUE(val == 0); + val = appid_api.get_http_cookie_offset(mock_session); + CHECK_TRUE(val == COOKIE_OFFSET); + val = appid_api.get_http_cookie_end_offset(nullptr); + CHECK_TRUE(val == 0); + val = appid_api.get_http_cookie_end_offset(mock_session); + CHECK_TRUE(val == COOKIE_OFFSET + strlen(NEW_COOKIE)); +} + +TEST(appid_api, get_http_search) +{ + SEARCH_SUPPORT_TYPE val = appid_api.get_http_search(nullptr); + CHECK_TRUE(val == NOT_A_SEARCH_ENGINE); + val = appid_api.get_http_search(mock_session); + CHECK_TRUE(val == NOT_A_SEARCH_ENGINE); + mock_session->search_support_type = SUPPORTED_SEARCH_ENGINE; + val = appid_api.get_http_search(mock_session); + CHECK_TRUE(val == SUPPORTED_SEARCH_ENGINE); + mock_session->search_support_type = UNSUPPORTED_SEARCH_ENGINE; + val = appid_api.get_http_search(mock_session); + CHECK_TRUE(val == UNSUPPORTED_SEARCH_ENGINE); + mock_session->search_support_type = NOT_A_SEARCH_ENGINE; + val = appid_api.get_http_search(mock_session); + CHECK_TRUE(val == NOT_A_SEARCH_ENGINE); +} + +TEST(appid_api, get_http_xff_addr) +{ + SfIp expected_ip_xff; + + expected_ip_xff.pton(AF_INET, APPID_UT_XFF_IP_ADDR); + + SfIp* val = appid_api.get_http_xff_addr(nullptr); + CHECK_TRUE(val == 0); + val = appid_api.get_http_xff_addr(mock_session); + CHECK_TRUE(val->fast_eq4(expected_ip_xff)); +} + +TEST(appid_api, get_tls_host) +{ + const char* val = appid_api.get_tls_host(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_tls_host(mock_session); + STRCMP_EQUAL(val, APPID_UT_TLS_HOST); +} + +TEST(appid_api, get_service_ip) +{ + SfIp expected_ip; + + expected_ip.pton(AF_INET, APPID_UT_SERVICE_IP_ADDR); + + SfIp* val = appid_api.get_service_ip(nullptr); + CHECK_TRUE(val == 0); + val = appid_api.get_service_ip(mock_session); + CHECK_TRUE(val->fast_eq4(expected_ip)); +} + +TEST(appid_api, get_initiator_ip) +{ + SfIp expected_ip; + + expected_ip.pton(AF_INET, APPID_UT_INITIATOR_IP_ADDR); + + SfIp* val = appid_api.get_initiator_ip(nullptr); + CHECK_TRUE(val == 0); + val = appid_api.get_initiator_ip(mock_session); + CHECK_TRUE(val->fast_eq4(expected_ip)); +} + +TEST(appid_api, get_netbios_name) +{ + const char* val = appid_api.get_netbios_name(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_netbios_name(mock_session); + STRCMP_EQUAL(val, APPID_UT_NETBIOS_NAME); + snort_free((void*)val); + val = appid_api.get_netbios_name(nullptr); + CHECK_TRUE(!val); +} + +TEST(appid_api, is_ssl_session_decrypted) +{ + bool val = appid_api.is_ssl_session_decrypted(nullptr); + CHECK_TRUE(!val); + val = appid_api.is_ssl_session_decrypted(mock_session); + CHECK_TRUE(!val); + is_session_decrypted = true; + val = appid_api.is_ssl_session_decrypted(mock_session); + CHECK_TRUE(val); +} + +TEST(appid_api, is_appid_inspecting_session) +{ + bool val = appid_api.is_appid_inspecting_session(nullptr); + CHECK_TRUE(!val); + mock_session->service_disco_state = APPID_DISCO_STATE_STATEFUL; + val = appid_api.is_appid_inspecting_session(mock_session); + CHECK_TRUE(val); + mock_session->service_disco_state = APPID_DISCO_STATE_FINISHED; + mock_session->set_session_flags(APPID_SESSION_HTTP_SESSION | APPID_SESSION_CONTINUE); + val = appid_api.is_appid_inspecting_session(mock_session); + CHECK_TRUE(val); + mock_session->clear_session_flags(APPID_SESSION_HTTP_SESSION | APPID_SESSION_CONTINUE); + mock_session->set_session_flags(APPID_SESSION_ENCRYPTED); + val = appid_api.is_appid_inspecting_session(mock_session); + CHECK_TRUE(val); + mock_session->set_session_flags(APPID_SESSION_DECRYPTED); + mock_session->session_packet_count = SSL_WHITELIST_PKT_LIMIT; + val = appid_api.is_appid_inspecting_session(mock_session); + CHECK_TRUE(val); + + // 2nd if in is_appid_inspecting_session + mock_session->clear_session_flags(APPID_SESSION_DECRYPTED); + mock_session->set_session_flags(APPID_SESSION_CLIENT_DETECTED); + val = appid_api.is_appid_inspecting_session(mock_session); + CHECK_TRUE(!val); + mock_session->set_session_flags(APPID_SESSION_CLIENT_GETS_SERVER_PACKETS); + val = appid_api.is_appid_inspecting_session(mock_session); + CHECK_TRUE(val); + mock_session->client_disco_state = APPID_DISCO_STATE_FINISHED; + val = appid_api.is_appid_inspecting_session(mock_session); + CHECK_TRUE(!val); + + // 3rd if in is_appid_inspecting_session + mock_session->session_packet_count = MAX_SFTP_PACKET_COUNT; + val = appid_api.is_appid_inspecting_session(mock_session); + CHECK_TRUE(!val); + mock_session->payload_app_id = APP_ID_SFTP; + val = appid_api.is_appid_inspecting_session(mock_session); + CHECK_TRUE(!val); + mock_session->session_packet_count = MAX_SFTP_PACKET_COUNT - 1; + val = appid_api.is_appid_inspecting_session(mock_session); + CHECK_TRUE(!val); + mock_session->payload_app_id = APP_ID_NONE; + mock_session->tp_app_id = APP_ID_SSH; + val = appid_api.is_appid_inspecting_session(mock_session); + CHECK_TRUE(val); +} + +TEST(appid_api, get_user_name) +{ + AppId service; + bool isLoginSuccessful; + + char* val = appid_api.get_user_name(nullptr, &service, &isLoginSuccessful); + CHECK_TRUE(!val); + val = appid_api.get_user_name(mock_session, &service, &isLoginSuccessful); + STRCMP_EQUAL(val, APPID_UT_USERNAME); + CHECK_TRUE(service == APPID_UT_ID); + CHECK_TRUE(!isLoginSuccessful); + mock_session->set_session_flags(APPID_SESSION_LOGIN_SUCCEEDED); + snort_free(val); + val = appid_api.get_user_name(mock_session, &service, &isLoginSuccessful); + CHECK_TRUE(!val); + CHECK_TRUE(service == APPID_UT_ID); + CHECK_TRUE(isLoginSuccessful); +} + +TEST(appid_api, is_appid_available) +{ + bool val = appid_api.is_appid_available(nullptr); + CHECK_TRUE(!val); + val = appid_api.is_appid_available(mock_session); + CHECK_TRUE(val); + mock_session->set_session_flags(APPID_SESSION_NO_TPI); + val = appid_api.is_appid_available(mock_session); + CHECK_TRUE(val); +} + +TEST(appid_api, get_client_version) +{ + char* val = appid_api.get_client_version(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_client_version(mock_session); + STRCMP_EQUAL(val, APPID_UT_CLIENT_VERSION); +} + +TEST(appid_api, get_appid_session_attribute) +{ + uint64_t flags = 0x0000000000000001; + + for ( unsigned i = 0; i < 64; i++ ) + { + flags <<= i; + mock_session->set_session_flags(flags); + uint64_t fv = appid_api.get_appid_session_attribute(mock_session, flags); + CHECK_TRUE((fv & flags) == flags); + mock_session->clear_session_flags(flags); + fv = appid_api.get_appid_session_attribute(mock_session, flags); + CHECK_TRUE((fv & flags) == 0) + } +} + +TEST(appid_api, get_service_info) +{ + char* serviceVendor; + char* serviceVersion; + AppIdServiceSubtype* serviceSubtype; + + appid_api.get_service_info(nullptr, &serviceVendor, &serviceVersion, &serviceSubtype); + CHECK_TRUE(!serviceVendor); + CHECK_TRUE(!serviceVersion); + CHECK_TRUE(!serviceSubtype); + appid_api.get_service_info(mock_session, &serviceVendor, &serviceVersion, &serviceSubtype); + STRCMP_EQUAL(serviceVendor, APPID_UT_SERVICE_VENDOR); + STRCMP_EQUAL(serviceVersion, APPID_UT_SERVICE_VERSION); + STRCMP_EQUAL(serviceSubtype->service, APPID_UT_SERVICE); + STRCMP_EQUAL(serviceSubtype->vendor, APPID_UT_SERVICE_VENDOR); + STRCMP_EQUAL(serviceSubtype->version, APPID_UT_SERVICE_VERSION); +} + +TEST(appid_api, appid_dns_api) +{ + uint8_t query_len; + + char* val = appid_api.get_dns_query(nullptr, &query_len); + CHECK_TRUE(!val); + val = appid_api.get_dns_query(mock_session, &query_len); + STRCMP_EQUAL(val, APPID_ID_UT_DNS_HOST); + CHECK_TRUE(query_len == strlen(APPID_ID_UT_DNS_HOST)); + + uint16_t qoff = appid_api.get_dns_query_offset(nullptr); + CHECK_TRUE(qoff == 0); + qoff = appid_api.get_dns_query_offset(mock_session); + CHECK_TRUE(qoff == APPID_UT_DNS_HOST_OFFSET); + + uint16_t rt = appid_api.get_dns_record_type(nullptr); + CHECK_TRUE(rt == 0); + rt = appid_api.get_dns_record_type(mock_session); + CHECK_TRUE(rt == APPID_UT_DNS_PATTERN_CNAME_REC); + + uint8_t rc = appid_api.get_dns_response_type(nullptr); + CHECK_TRUE(rc == 0); + rc = appid_api.get_dns_response_type(mock_session); + CHECK_TRUE(rc == APPID_UT_DNS_NOERROR); + + uint32_t ttl = appid_api.get_dns_ttl(nullptr); + CHECK_TRUE(ttl == 0); + ttl = appid_api.get_dns_ttl(mock_session); + CHECK_TRUE(ttl == APPID_UT_DNS_TTL); +} + +TEST(appid_api, dhcp_fp_data) +{ + DHCPData* val = appid_api.get_dhcp_fp_data(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_dhcp_fp_data(mock_session); + CHECK_TRUE(!val); + val = new DHCPData; + mock_session->add_flow_data(val, APPID_SESSION_DATA_DHCP_FP_DATA, nullptr); + val = appid_api.get_dhcp_fp_data(mock_session); + CHECK_TRUE(val); + appid_api.free_dhcp_fp_data(mock_session, val); + val = appid_api.get_dhcp_fp_data(mock_session); + CHECK_TRUE(!val); +} + +TEST(appid_api, dhcp_info) +{ + DHCPInfo* val = appid_api.get_dhcp_info(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_dhcp_info(mock_session); + CHECK_TRUE(!val); + val = new DHCPInfo; + mock_session->add_flow_data(val, APPID_SESSION_DATA_DHCP_INFO, nullptr); + val = appid_api.get_dhcp_info(mock_session); + CHECK_TRUE(val); + appid_api.free_dhcp_info(mock_session, val); + val = appid_api.get_dhcp_info(mock_session); + CHECK_TRUE(!val); +} + +TEST(appid_api, smb_fp_data) +{ + FpSMBData* val = appid_api.get_smb_fp_data(nullptr); + CHECK_TRUE(!val); + val = appid_api.get_smb_fp_data(mock_session); + CHECK_TRUE(!val); + val = new FpSMBData; + mock_session->add_flow_data(val, APPID_SESSION_DATA_SMB_DATA, nullptr); + val = appid_api.get_smb_fp_data(mock_session); + CHECK_TRUE(val); + appid_api.free_smb_fp_data(mock_session, val); + val = appid_api.get_smb_fp_data(mock_session); + CHECK_TRUE(!val); +} + +TEST(appid_api, is_http_inspection_done) +{ + bool val = appid_api.is_http_inspection_done(nullptr); + CHECK_TRUE(val); + val = appid_api.is_http_inspection_done(mock_session); + CHECK_TRUE(val); +} + +TEST(appid_api, produce_ha_state) +{ + AppIdSessionHA appHA, cmp_buf; + + memset((void*)&appHA, 0, sizeof(appHA)); + memset((void*)&cmp_buf, 0, sizeof(cmp_buf)); + mock_session->common.flow_type = APPID_FLOW_TYPE_IGNORE; + mock_session->common.flags |= APPID_SESSION_SERVICE_DETECTED | APPID_SESSION_HTTP_SESSION; + uint32_t val = appid_api.produce_ha_state(flow, (uint8_t*)&appHA); + CHECK_TRUE(val == sizeof(appHA)); + CHECK_TRUE(memcmp(&appHA, &cmp_buf, val) == 0); + mock_session->common.flow_type = APPID_FLOW_TYPE_NORMAL; + val = appid_api.produce_ha_state(flow, (uint8_t*)&appHA); + CHECK_TRUE(val == sizeof(appHA)); + CHECK_TRUE(appHA.appId[0] == APPID_UT_ID); + CHECK_TRUE(appHA.appId[1] == APPID_UT_ID + 1); + CHECK_TRUE(appHA.appId[2] == APPID_UT_ID + 2); + CHECK_TRUE(appHA.appId[3] == APPID_UT_ID + 3); + CHECK_TRUE(appHA.appId[4] == APPID_UT_ID + 4); + CHECK_TRUE(appHA.appId[5] == APPID_UT_ID + 5); + CHECK_TRUE(appHA.appId[6] == APPID_UT_ID + 6); + CHECK_TRUE(appHA.appId[7] == APPID_UT_ID + 7); + CHECK_TRUE(appHA.flags == (APPID_HA_FLAGS_APP | APPID_HA_FLAGS_TP_DONE + | APPID_HA_FLAGS_SVC_DONE | APPID_HA_FLAGS_HTTP)); + + delete mock_session; + mock_session = nullptr; + mock_flow_data= nullptr; + SfIp ip; + ip.pton(AF_INET, "192.168.1.222"); + val = appid_api.consume_ha_state(flow, (uint8_t*)&appHA, 0, IpProtocol::TCP, &ip, 1066); + mock_session = (AppIdSession*)flow->get_flow_data(AppIdSession::flow_id); + CHECK_TRUE(mock_session); + CHECK_TRUE(mock_session->tp_app_id == appHA.appId[0]); + CHECK_TRUE(mock_session->service_app_id == appHA.appId[1]); + CHECK_TRUE(mock_session->client_service_app_id == appHA.appId[2]); + CHECK_TRUE(mock_session->port_service_id == appHA.appId[3]); + CHECK_TRUE(mock_session->payload_app_id == appHA.appId[4]); + CHECK_TRUE(mock_session->tp_payload_app_id == appHA.appId[5]); + CHECK_TRUE(mock_session->client_app_id == appHA.appId[6]); + CHECK_TRUE(mock_session->misc_app_id == appHA.appId[7]); + CHECK_TRUE(mock_session->service_disco_state == APPID_DISCO_STATE_FINISHED); + CHECK_TRUE(mock_session->client_disco_state == APPID_DISCO_STATE_FINISHED); + + // test logic when service app is ftp control + appHA.appId[1] = APP_ID_FTP_CONTROL; + delete mock_session; + mock_session = nullptr; + mock_flow_data= nullptr; + val = appid_api.consume_ha_state(flow, (uint8_t*)&appHA, 0, IpProtocol::TCP, &ip, 1066); + mock_session = (AppIdSession*)flow->get_flow_data(AppIdSession::flow_id); + CHECK_TRUE(mock_session); + uint64_t flags = mock_session->get_session_flags(APPID_SESSION_CLIENT_DETECTED | + APPID_SESSION_NOT_A_SERVICE | APPID_SESSION_SERVICE_DETECTED); + CHECK_TRUE(flags == (APPID_SESSION_CLIENT_DETECTED | APPID_SESSION_NOT_A_SERVICE + | APPID_SESSION_SERVICE_DETECTED)); + CHECK_TRUE(mock_session->service_app_id == APP_ID_FTP_CONTROL); + CHECK_TRUE(mock_session->service_disco_state == APPID_DISCO_STATE_STATEFUL); + CHECK_TRUE(mock_session->client_disco_state == APPID_DISCO_STATE_FINISHED); +} + +int main(int argc, char** argv) +{ + return CommandLineTestRunner::RunAllTests(argc, argv); +} + diff --git a/src/network_inspectors/appid/test/appid_detector_test.cc b/src/network_inspectors/appid/test/appid_detector_test.cc new file mode 100644 index 000000000..f2dec2241 --- /dev/null +++ b/src/network_inspectors/appid/test/appid_detector_test.cc @@ -0,0 +1,114 @@ +//-------------------------------------------------------------------------- +// Copyright (C) 2016-2017 Cisco and/or its affiliates. All rights reserved. +// +// This program is free software; you can redistribute it and/or modify it +// under the terms of the GNU General Public License Version 2 as published +// by the Free Software Foundation. You may not use, modify or distribute +// this program under any other version of the GNU General Public License. +// +// This program is distributed in the hope that it will be useful, but +// WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// General Public License for more details. +// +// You should have received a copy of the GNU General Public License along +// with this program; if not, write to the Free Software Foundation, Inc., +// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +//-------------------------------------------------------------------------- + +// appid_detector_test.cc author davis mcpherson + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#include "network_inspectors/appid/appid_detector.cc" + +#include + +#include "protocols/protocol_ids.h" + +#include "appid_mock_http_session.h" +#include "appid_mock_session.h" + +#include +#include + +char* snort_strdup(const char* str) +{ + assert(str); + size_t n = strlen(str) + 1; + char* p = (char*)snort_alloc(n); + memcpy(p, str, n); + return p; +} + +void ErrorMessage(const char*,...) { } +void WarningMessage(const char*,...) { } +void LogMessage(const char*,...) { } +void ParseWarning(WarningGroup, const char*, ...) { } + +Flow* flow = nullptr; +AppIdSession* mock_session = nullptr; + +class TestDetector : public AppIdDetector +{ +public: + TestDetector() { } + ~TestDetector() { } + + void do_custom_init() override { } + int validate(AppIdDiscoveryArgs&) override { return 0; } + void register_appid(AppId, unsigned) override { } +}; + +TEST_GROUP(appid_detector_tests) +{ + void setup() + { + MemoryLeakWarningPlugin::turnOffNewDeleteOverloads(); + flow = new Flow; + mock_session = new AppIdSession(IpProtocol::TCP, nullptr, 1492); + mock_session->hsession = init_http_session(mock_session); + flow->set_flow_data(mock_session); + } + + void teardown() + { + delete mock_session; + delete flow; + MemoryLeakWarningPlugin::turnOnNewDeleteOverloads(); + } +}; + +TEST(appid_detector_tests, add_info) +{ + const char* info_url = "https://tools.ietf.org/html/rfc793"; + AppIdDetector* ad = new TestDetector; + ad->add_info(mock_session, info_url); + STRCMP_EQUAL(mock_session->hsession->url, URL); + snort_free(mock_session->hsession->url); + mock_session->hsession->url = nullptr; + ad->add_info(mock_session, info_url); + STRCMP_EQUAL(mock_session->hsession->url, info_url); + delete ad; +} + +TEST(appid_detector_tests, add_user) +{ + const char* username = "snorty"; + AppIdDetector* ad = new TestDetector; + ad->add_user(mock_session, username, APPID_UT_ID, true); + STRCMP_EQUAL(mock_session->username, username); + CHECK_TRUE((mock_session->username_service == APPID_UT_ID)); + CHECK_TRUE((mock_session->get_session_flags(APPID_SESSION_LOGIN_SUCCEEDED) + & APPID_SESSION_LOGIN_SUCCEEDED)); + delete ad; +} + +int main(int argc, char** argv) +{ + int return_value = CommandLineTestRunner::RunAllTests(argc, argv); + return return_value; +} + diff --git a/src/network_inspectors/appid/test/appid_http_event_test.cc b/src/network_inspectors/appid/test/appid_http_event_test.cc index 535ccd98a..b34792944 100644 --- a/src/network_inspectors/appid/test/appid_http_event_test.cc +++ b/src/network_inspectors/appid/test/appid_http_event_test.cc @@ -37,29 +37,11 @@ #include "service_inspectors/http_inspect/http_msg_header.h" #include "thirdparty_appid_api.h" -AppIdConfig* pAppidActiveConfig = nullptr; -AppIdApi appid_api; -THREAD_LOCAL ThirdPartyAppIDModule* thirdparty_appid_module = nullptr; - -char* snort_strndup(const char* src, size_t dst_size) -{ - return strndup(src, dst_size); -} - -char* snort_strdup(const char* src) -{ - return strdup(src); -} +#include "appid_mock_definitions.h" +#include "appid_mock_http_session.h" +#include "appid_mock_session.h" -FlowData::FlowData(unsigned, Inspector*) -{ -} - -FlowData::~FlowData() -{ -} - -void Flow::set_application_ids(AppId, AppId, AppId, AppId) { } +AppIdApi appid_api; const char* content_type = nullptr; const char* cookie = nullptr; @@ -73,92 +55,11 @@ const char* uri = nullptr; const char* useragent = nullptr; const char* via = nullptr; -void Field::set(int32_t length, const uint8_t* start, bool own_the_buffer_) -{ - strt = start; - len = length; - own_the_buffer = own_the_buffer_; -} - -Field global_field; - class FakeHttpMsgHeader { }; - -unsigned AppIdSession::flow_id = 0; -AppIdSession* fake_session = nullptr; FakeHttpMsgHeader* fake_msg_header = nullptr; -AppIdSession::AppIdSession(IpProtocol, const SfIp*, uint16_t) : FlowData(flow_id, nullptr) -{ - hsession = nullptr; -} - -AppIdSession::~AppIdSession() -{ - if (!hsession) - return; - - if (hsession->content_type) - snort_free(hsession->content_type); - if (hsession->cookie) - snort_free(hsession->cookie); - if (hsession->host) - snort_free(hsession->host); - if (hsession->location) - snort_free(hsession->location); - if (hsession->referer) - snort_free(hsession->referer); - if (hsession->response_code) - free(hsession->response_code); - if (hsession->server) - snort_free(hsession->server); - if (hsession->uri) - snort_free(hsession->uri); - if (hsession->url) - snort_free(hsession->url); - if (hsession->useragent) - snort_free(hsession->useragent); - if (hsession->via) - snort_free(hsession->via); - if (hsession->x_working_with) - snort_free(hsession->x_working_with); - - snort_free(hsession); -} - -int AppIdSession::process_http_packet(int) -{ - return 0; -} - -AppId AppIdSession::pick_service_app_id() -{ - return 0; -} - -AppId AppIdSession::pick_client_app_id() -{ - return 0; -} - -AppId AppIdSession::pick_payload_app_id() -{ - return 0; -} - -AppId AppIdSession::pick_misc_app_id() -{ - return 0; -} - -AppIdSession* AppIdApi::get_appid_data(Flow*) -{ - mock().actualCall("get_appid_data"); - return fake_session; -} - const uint8_t* HttpEvent::get_content_type(int32_t& length) { global_field.set(0, nullptr); @@ -259,66 +160,56 @@ bool HttpEvent::contains_webdav_method() return true; } -Flow::Flow() { } -Flow::~Flow() { } +Flow* flow = nullptr; +AppIdSession* mock_session = nullptr; -class FakeFlow : public Flow +AppIdSession* AppIdApi::get_appid_data(Flow*) { -}; - -#ifdef DEBUG_MSGS -void Debug::print(const char*, int, uint64_t, const char*, ...) { } -#endif + mock().actualCall("get_appid_data"); + return mock_session; +} TEST_GROUP(appid_http_event) { void setup() { + MemoryLeakWarningPlugin::turnOffNewDeleteOverloads(); + flow = new Flow; + mock_session = new AppIdSession(IpProtocol::TCP, nullptr, 1492); + flow->set_flow_data(mock_session); appid_stats.http_flows = 0; } void teardown() { fake_msg_header = nullptr; - fake_session = nullptr; + delete mock_session; + delete flow; mock().clear(); + MemoryLeakWarningPlugin::turnOnNewDeleteOverloads(); } }; TEST(appid_http_event, handle_null_appid_data) { - FakeFlow flow; HttpEvent event(nullptr); HttpEventHandler event_handler(HttpEventHandler::REQUEST_EVENT); mock().expectOneCall("get_appid_data"); - event_handler.handle(event, &flow); + event_handler.handle(event, flow); mock().checkExpectations(); } TEST(appid_http_event, handle_null_msg_header) { - FakeFlow flow; HttpEvent event(nullptr); - AppIdSession session(IpProtocol::TCP, nullptr, 1492); HttpEventHandler event_handler(HttpEventHandler::REQUEST_EVENT); - fake_session = &session; mock().strictOrder(); mock().expectOneCall("get_appid_data"); - event_handler.handle(event, &flow); + event_handler.handle(event, flow); mock().checkExpectations(); } -const char* CONTENT_TYPE = "html/text"; -const char* COOKIE = "this is my request cookie content"; -const char* HOST = "www.google.com"; -const char* LOCATION = "abc.yahoo.com"; -const char* URI = "/path/to/index.html"; -const char* USERAGENT = "Mozilla/5.0 (Macintosh; Intel Mac OS X)"; -const char* REFERER = "http://www.yahoo.com/search"; -const char* SERVER = "Apache"; -const char* X_WORKING_WITH = "working with string"; -const char* VIA = "via string"; #define RESPONSE_CODE 301 struct TestData @@ -341,12 +232,9 @@ struct TestData void run_event_handler(TestData test_data, TestData* expect_data = nullptr) { - FakeFlow flow; HttpEvent event(nullptr); - AppIdSession session(IpProtocol::TCP, nullptr, 1492); FakeHttpMsgHeader http_msg_header; HttpEventHandler event_handler(test_data.type); - fake_session = &session; fake_msg_header = &http_msg_header; host = test_data.host; @@ -366,26 +254,27 @@ void run_event_handler(TestData test_data, TestData* expect_data = nullptr) mock().strictOrder(); mock().expectOneCall("get_appid_data"); - event_handler.handle(event, &flow); - LONGS_EQUAL(expect_data->scan_flags, session.scan_flags); + event_handler.handle(event, flow); + LONGS_EQUAL(expect_data->scan_flags, mock_session->scan_flags); LONGS_EQUAL(expect_data->http_flows, appid_stats.http_flows); - STRCMP_EQUAL(expect_data->host, session.hsession->host); - STRCMP_EQUAL(expect_data->uri, session.hsession->uri); - STRCMP_EQUAL(expect_data->content_type, session.hsession->content_type); - STRCMP_EQUAL(expect_data->cookie, session.hsession->cookie); - STRCMP_EQUAL(expect_data->location, session.hsession->location); - STRCMP_EQUAL(expect_data->referer, session.hsession->referer); - STRCMP_EQUAL(expect_data->server, session.hsession->server); - STRCMP_EQUAL(expect_data->x_working_with, session.hsession->x_working_with); - STRCMP_EQUAL(expect_data->useragent, session.hsession->useragent); - STRCMP_EQUAL(expect_data->via, session.hsession->via); - if (nullptr == session.hsession->response_code) + STRCMP_EQUAL(expect_data->host, mock_session->hsession->host); + STRCMP_EQUAL(expect_data->uri, mock_session->hsession->uri); + STRCMP_EQUAL(expect_data->content_type, mock_session->hsession->content_type); + STRCMP_EQUAL(expect_data->cookie, mock_session->hsession->cookie); + STRCMP_EQUAL(expect_data->location, mock_session->hsession->location); + STRCMP_EQUAL(expect_data->referer, mock_session->hsession->referer); + STRCMP_EQUAL(expect_data->server, mock_session->hsession->server); + STRCMP_EQUAL(expect_data->x_working_with, mock_session->hsession->x_working_with); + STRCMP_EQUAL(expect_data->useragent, mock_session->hsession->useragent); + STRCMP_EQUAL(expect_data->via, mock_session->hsession->via); + if (nullptr == mock_session->hsession->response_code) { LONGS_EQUAL(0, expect_data->response_code); } else { - LONGS_EQUAL(expect_data->response_code, strtol(session.hsession->response_code, nullptr, + LONGS_EQUAL(expect_data->response_code, strtol(mock_session->hsession->response_code, + nullptr, 10)); } mock().checkExpectations(); diff --git a/src/network_inspectors/appid/test/appid_mock_definitions.h b/src/network_inspectors/appid/test/appid_mock_definitions.h new file mode 100644 index 000000000..2069c10f1 --- /dev/null +++ b/src/network_inspectors/appid/test/appid_mock_definitions.h @@ -0,0 +1,63 @@ +//-------------------------------------------------------------------------- +// Copyright (C) 2016-2017 Cisco and/or its affiliates. All rights reserved. +// +// This program is free software; you can redistribute it and/or modify it +// under the terms of the GNU General Public License Version 2 as published +// by the Free Software Foundation. You may not use, modify or distribute +// this program under any other version of the GNU General Public License. +// +// This program is distributed in the hope that it will be useful, but +// WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// General Public License for more details. +// +// You should have received a copy of the GNU General Public License along +// with this program; if not, write to the Free Software Foundation, Inc., +// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +//-------------------------------------------------------------------------- + +// appid_mock_definitions.h author davis mcpherson + +#ifndef APPID_MOCK_DEFINITIONS_H_ +#define APPID_MOCK_DEFINITIONS_H_ + +class Inspector; +struct ThirdPartyAppIDModule; + +AppIdConfig* pAppidActiveConfig = nullptr; +THREAD_LOCAL ThirdPartyAppIDModule* thirdparty_appid_module = nullptr; + +char* snort_strndup(const char* src, size_t dst_size) +{ + return strndup(src, dst_size); +} + +char* snort_strdup(const char* str) +{ + assert(str); + size_t n = strlen(str) + 1; + char* p = (char*)snort_alloc(n); + memcpy(p, str, n); + return p; +} + +void Field::set(int32_t length, const uint8_t* start, bool own_the_buffer_) +{ + strt = start; + len = length; + own_the_buffer = own_the_buffer_; +} + +Field global_field; + +#ifdef DEBUG_MSGS +void Debug::print(const char*, int, uint64_t, const char*, ...) { } +#endif + +int ServiceDiscovery::add_ftp_service_state(AppIdSession&) +{ + return 0; +} + +#endif + diff --git a/src/network_inspectors/appid/appid_utils/appid_utils.h b/src/network_inspectors/appid/test/appid_mock_flow.h similarity index 58% rename from src/network_inspectors/appid/appid_utils/appid_utils.h rename to src/network_inspectors/appid/test/appid_mock_flow.h index 89c4e1941..a143de21a 100644 --- a/src/network_inspectors/appid/appid_utils/appid_utils.h +++ b/src/network_inspectors/appid/test/appid_mock_flow.h @@ -1,6 +1,5 @@ //-------------------------------------------------------------------------- -// Copyright (C) 2014-2017 Cisco and/or its affiliates. All rights reserved. -// Copyright (C) 2005-2013 Sourcefire, Inc. +// Copyright (C) 2016-2017 Cisco and/or its affiliates. All rights reserved. // // This program is free software; you can redistribute it and/or modify it // under the terms of the GNU General Public License Version 2 as published @@ -17,25 +16,44 @@ // 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. //-------------------------------------------------------------------------- -// appid_utils.h author Sourcefire Inc. +// appid_mock_flow.h author davis mcpherson -#ifndef SFUTIL_H -#define SFUTIL_H +#ifndef APPID_MOCK_FLOW_H_ +#define APPID_MOCK_FLOW_H_ -#include -#include +FlowData::FlowData(unsigned, Inspector*) +{ + next = prev = nullptr; + handler = nullptr; + id = 222; +} + +FlowData::~FlowData() +{ +} -#define MAX_TOKS 256 +FlowData* mock_flow_data = nullptr; -class AppIdUtils +typedef int32_t AppId; +Flow::Flow() { } +Flow::~Flow() { } + +class FakeFlow : public Flow { -public: - static int tokenize(char* data, char* toklist[]); - static int strip(char* data); - static void init_netmasks(uint32_t netmasks[]); - static int split(char* data, char** toklist, int max_toks, const char* separator); - static void dump_hex(FILE*, const uint8_t* data, unsigned len); }; +FlowData* Flow::get_flow_data(unsigned) const +{ + return mock_flow_data; +} + +int Flow::set_flow_data(FlowData* fd) +{ + mock_flow_data = fd; + return 0; +} + +void Flow::set_application_ids(AppId, AppId, AppId, AppId) { } + #endif diff --git a/src/network_inspectors/appid/test/appid_mock_http_session.h b/src/network_inspectors/appid/test/appid_mock_http_session.h new file mode 100644 index 000000000..13ddfe788 --- /dev/null +++ b/src/network_inspectors/appid/test/appid_mock_http_session.h @@ -0,0 +1,114 @@ +//-------------------------------------------------------------------------- +// Copyright (C) 2016-2017 Cisco and/or its affiliates. All rights reserved. +// +// This program is free software; you can redistribute it and/or modify it +// under the terms of the GNU General Public License Version 2 as published +// by the Free Software Foundation. You may not use, modify or distribute +// this program under any other version of the GNU General Public License. +// +// This program is distributed in the hope that it will be useful, but +// WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// General Public License for more details. +// +// You should have received a copy of the GNU General Public License along +// with this program; if not, write to the Free Software Foundation, Inc., +// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +//-------------------------------------------------------------------------- + +// appid_mock_http_session.h author davis mcpherson + +#ifndef APPID_MOCK_HTTP_SESSION_H_ +#define APPID_MOCK_HTTP_SESSION_H_ + +AppIdHttpSession::AppIdHttpSession(AppIdSession* session) : asd(session) { } +AppIdHttpSession::~AppIdHttpSession() +{ + snort_free(body); + snort_free(content_type); + snort_free(cookie); + snort_free(host); + snort_free(location); + snort_free(referer); + snort_free(req_body); + snort_free(response_code); + snort_free(server); + snort_free(uri); + snort_free(url); + snort_free(useragent); + snort_free(via); + snort_free(x_working_with); + delete xffAddr; + + if (new_field_contents) + for ( unsigned i = 0; i < NUMBER_OF_PTYPES; i++) + if (nullptr != new_field[i]) + snort_free(new_field[i]); +} + +int AppIdHttpSession::process_http_packet(int) { return 0; } + +char const* APPID_UT_XFF_IP_ADDR = "192.168.0.1"; +char const* CONTENT_TYPE = "html/text"; +char const* COOKIE = "this is my request cookie content"; +char const* NEW_COOKIE = "request new cookie content is chocolate chip"; +char const* HOST = "www.google.com"; +char const* LOCATION = "abc.yahoo.com"; +char const* URL = "https://www.google.com/path/to/index.html"; +char const* URI = "/path/to/index.html"; +char const* USERAGENT = "Mozilla/5.0 (Macintosh; Intel Mac OS X)"; +char const* REFERER = "http://www.yahoo.com/search"; +char const* SERVER = "Apache"; +char const* X_WORKING_WITH = "working with string"; +char const* VIA = "via string"; +char const* RESPONSE_CODE = "301"; +char const* REQ_BODY = "this is the body of the http request"; +char const* RSP_BODY = "this is the body of the http response"; + +#define URI_OFFSET 22 +#define COOKIE_OFFSET 44 + +void init_hsession_new_fields(AppIdHttpSession* hsession) +{ + hsession->new_field_contents = true; + hsession->new_field[REQ_AGENT_FID] = snort_strdup((char*)(USERAGENT)); + hsession->new_field[REQ_HOST_FID] = snort_strdup((char*)(HOST)); + hsession->new_field[REQ_REFERER_FID] = snort_strdup((char*)(REFERER)); + hsession->new_field[REQ_URI_FID] = snort_strdup((char*)(URI)); + hsession->new_field[REQ_COOKIE_FID] = snort_strdup((char*)(NEW_COOKIE)); + hsession->new_field[REQ_BODY_FID] = snort_strdup((char*)(REQ_BODY)); + hsession->new_field[RSP_CONTENT_TYPE_FID] = snort_strdup((char*)(CONTENT_TYPE)); + hsession->new_field[RSP_LOCATION_FID] = snort_strdup((char*)(LOCATION)); + hsession->new_field[RSP_BODY_FID] = snort_strdup((char*)(RSP_BODY)); +} + +AppIdHttpSession* init_http_session(AppIdSession* asd) +{ + AppIdHttpSession* hsession = new AppIdHttpSession(asd); + SfIp* ip = new SfIp; + ip->pton(AF_INET, APPID_UT_XFF_IP_ADDR); + hsession->xffAddr = ip; + hsession->content_type = snort_strdup((char*)(CONTENT_TYPE)); + hsession->cookie = snort_strdup((char*)(COOKIE)); + hsession->host = snort_strdup((char*)(HOST)); + hsession->location = snort_strdup((char*)(LOCATION)); + hsession->referer = snort_strdup((char*)(REFERER)); + hsession->response_code = snort_strdup((char*)(RESPONSE_CODE)); + hsession->server = snort_strdup((char*)(SERVER)); + hsession->url = snort_strdup((char*)(URL)); + hsession->uri = snort_strdup((char*)(URI)); + hsession->useragent = snort_strdup((char*)(USERAGENT)); + hsession->via = snort_strdup((char*)(VIA)); + hsession->x_working_with = snort_strdup((char*)(X_WORKING_WITH)); + hsession->body = snort_strdup((char*)(RSP_BODY)); + hsession->req_body = snort_strdup((char*)(REQ_BODY)); + hsession->fieldOffset[REQ_URI_FID] = URI_OFFSET; + hsession->fieldEndOffset[REQ_URI_FID] = URI_OFFSET + strlen(URI); + hsession->fieldOffset[REQ_COOKIE_FID] = COOKIE_OFFSET; + hsession->fieldEndOffset[REQ_COOKIE_FID] = COOKIE_OFFSET + strlen(NEW_COOKIE); + + return hsession; +} + +#endif + diff --git a/src/network_inspectors/appid/test/appid_mock_inspector.h b/src/network_inspectors/appid/test/appid_mock_inspector.h new file mode 100644 index 000000000..29f8ddc15 --- /dev/null +++ b/src/network_inspectors/appid/test/appid_mock_inspector.h @@ -0,0 +1,40 @@ +//-------------------------------------------------------------------------- +// Copyright (C) 2016-2017 Cisco and/or its affiliates. All rights reserved. +// +// This program is free software; you can redistribute it and/or modify it +// under the terms of the GNU General Public License Version 2 as published +// by the Free Software Foundation. You may not use, modify or distribute +// this program under any other version of the GNU General Public License. +// +// This program is distributed in the hope that it will be useful, but +// WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// General Public License for more details. +// +// You should have received a copy of the GNU General Public License along +// with this program; if not, write to the Free Software Foundation, Inc., +// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +//-------------------------------------------------------------------------- + +// appid_mock_inspector.h author davis mcpherson + +Inspector::Inspector() +{ + set_api(nullptr); +} + +Inspector::~Inspector() { } +bool Inspector::likes(Packet*) { return true; } +bool Inspector::get_buf(const char*, Packet*, InspectionBuffer&) { return true; } +class StreamSplitter* Inspector::get_splitter(bool) { return nullptr; } + +AppIdInspector::AppIdInspector(const AppIdModuleConfig*) { } +AppIdInspector::~AppIdInspector() { } +AppIdInspector* AppIdInspector::get_inspector() { return new AppIdInspector(nullptr); } +void AppIdInspector::eval(Packet*) { } +int16_t AppIdInspector::add_appid_protocol_reference(char const*) { return 1066; } +bool AppIdInspector::configure(SnortConfig*) { return true; } +void AppIdInspector::show(SnortConfig*) { } +void AppIdInspector::tinit() { } +void AppIdInspector::tterm() { } + diff --git a/src/network_inspectors/appid/test/appid_mock_session.h b/src/network_inspectors/appid/test/appid_mock_session.h new file mode 100644 index 000000000..61b1df3b8 --- /dev/null +++ b/src/network_inspectors/appid/test/appid_mock_session.h @@ -0,0 +1,225 @@ +//-------------------------------------------------------------------------- +// Copyright (C) 2016-2017 Cisco and/or its affiliates. All rights reserved. +// +// This program is free software; you can redistribute it and/or modify it +// under the terms of the GNU General Public License Version 2 as published +// by the Free Software Foundation. You may not use, modify or distribute +// this program under any other version of the GNU General Public License. +// +// This program is distributed in the hope that it will be useful, but +// WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// General Public License for more details. +// +// You should have received a copy of the GNU General Public License along +// with this program; if not, write to the Free Software Foundation, Inc., +// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +//-------------------------------------------------------------------------- + +// appid_mock_session.h author davis mcpherson + +#ifndef APPID_MOCK_SESSION_H_ +#define APPID_MOCK_SESSION_H_ + +#include "appid_mock_flow.h" + +bool is_session_decrypted = false; + +char const* APPID_UT_TLS_HOST = "vpn.topsecret.com"; +char const* APPID_UT_SERVICE_IP_ADDR = "192.168.0.2"; +char const* APPID_UT_INITIATOR_IP_ADDR = "192.168.0.3"; + +char const* APPID_UT_NETBIOS_NAME = "I AM NETBIOS!"; + +char const* APPID_ID_UT_DNS_HOST = "delphi.opendns.com"; +#define APPID_UT_DNS_HOST_OFFSET 22 +#define APPID_UT_DNS_PATTERN_CNAME_REC 5 +#define APPID_UT_DNS_NOERROR 0 +#define APPID_UT_DNS_TTL 5 + +const char* test_app_name = "testapp_1492"; +const AppId APPID_UT_ID = 1492; +const short APPID_UT_SERVICE_PORT = 1066; +const char* APPID_UT_USERNAME = "pigpen"; +const char* APPID_UT_CLIENT_VERSION = "a snorting client"; +const char* APPID_UT_SERVICE = "at your service"; +const char* APPID_UT_SERVICE_VENDOR = "cisco snorty"; +const char* APPID_UT_SERVICE_VERSION = "Version City"; + +AppIdServiceSubtype APPID_UT_SERVICE_SUBTYPE = { nullptr, APPID_UT_SERVICE, + APPID_UT_SERVICE_VENDOR, + APPID_UT_SERVICE_VERSION }; + +unsigned AppIdSession::flow_id = 0; + +AppIdSession::AppIdSession(IpProtocol, const SfIp*, uint16_t) : FlowData(flow_id, nullptr) +{ + port_service_id = APPID_UT_ID; + common.flow_type = APPID_FLOW_TYPE_NORMAL; + service_port = APPID_UT_SERVICE_PORT; + + username_service = APPID_UT_ID; + username = (char*)snort_strdup(APPID_UT_USERNAME); + + client_version = (char*)APPID_UT_CLIENT_VERSION; + + service_vendor = (char*)APPID_UT_SERVICE_VENDOR; + service_version = (char*)APPID_UT_SERVICE_VERSION; + subtype = &APPID_UT_SERVICE_SUBTYPE; + + search_support_type = UNKNOWN_SEARCH_ENGINE; + + tsession = new TlsSession; + tsession->tls_host = (char*)APPID_UT_TLS_HOST; + + service_ip.pton(AF_INET, APPID_UT_SERVICE_IP_ADDR); + common.initiator_ip.pton(AF_INET, APPID_UT_INITIATOR_IP_ADDR); + + netbios_name = (char*)snort_strdup(APPID_UT_NETBIOS_NAME); + + dsession = new DnsSession; + dsession->host = (char*)APPID_ID_UT_DNS_HOST; + dsession->host_len = strlen(APPID_ID_UT_DNS_HOST); + dsession->host_offset = APPID_UT_DNS_HOST_OFFSET; + dsession->record_type = APPID_UT_DNS_PATTERN_CNAME_REC; + dsession->response_type = APPID_UT_DNS_NOERROR; + dsession->ttl = APPID_UT_DNS_TTL; + + tp_app_id = APPID_UT_ID; + service_app_id = APPID_UT_ID + 1; + client_service_app_id = APPID_UT_ID + 2; + port_service_id = APPID_UT_ID + 3; + payload_app_id = APPID_UT_ID + 4; + tp_payload_app_id = APPID_UT_ID + 5; + client_app_id = APPID_UT_ID + 6; + misc_app_id = APPID_UT_ID + 7; +} + +AppIdSession::~AppIdSession() +{ + delete hsession; + delete tsession; + delete dsession; + if (netbios_name) + snort_free(netbios_name); + if (username) + snort_free(username); +} + +DHCPInfo* dhcp_info = nullptr; +DHCPData* dhcp_data = nullptr; +FpSMBData* smb_data = nullptr; + +void* AppIdSession::get_flow_data(unsigned) +{ + return nullptr; +} + +int AppIdSession::add_flow_data(void* data, unsigned type, AppIdFreeFCN) +{ + if ( type == APPID_SESSION_DATA_DHCP_FP_DATA ) + { + dhcp_data = (DHCPData*)data; + set_session_flags(APPID_SESSION_HAS_DHCP_FP); + } + else if ( type == APPID_SESSION_DATA_DHCP_INFO ) + { + dhcp_info = (DHCPInfo*)data; + set_session_flags(APPID_SESSION_HAS_DHCP_INFO); + } + else if ( type == APPID_SESSION_DATA_SMB_DATA ) + { + smb_data = (FpSMBData*)data; + set_session_flags(APPID_SESSION_HAS_SMB_INFO); + } + return 0; +} + +void* AppIdSession::remove_flow_data(unsigned type) +{ + void* data = nullptr; + + if ( type == APPID_SESSION_DATA_DHCP_FP_DATA ) + { + data = dhcp_data; + dhcp_data = nullptr; + clear_session_flags(APPID_SESSION_HAS_DHCP_FP); + } + else if ( type == APPID_SESSION_DATA_DHCP_INFO ) + { + data = dhcp_info; + dhcp_info = nullptr; + clear_session_flags(APPID_SESSION_HAS_DHCP_INFO); + } + else if ( type == APPID_SESSION_DATA_SMB_DATA ) + { + data = smb_data; + smb_data = nullptr; + clear_session_flags(APPID_SESSION_HAS_SMB_INFO); + } + + return data; +} + +AppId AppIdSession::pick_service_app_id() +{ + return APPID_UT_ID; +} + +AppId AppIdSession::pick_misc_app_id() +{ + return APPID_UT_ID; +} + +AppId AppIdSession::pick_client_app_id() +{ + return APPID_UT_ID; +} + +AppId AppIdSession::pick_payload_app_id() +{ + return APPID_UT_ID; +} + +AppId AppIdSession::pick_referred_payload_app_id() +{ + return APPID_UT_ID; +} + +AppId AppIdSession::pick_fw_service_app_id() +{ + return APPID_UT_ID; +} + +AppId AppIdSession::pick_fw_misc_app_id() +{ + return APPID_UT_ID; +} + +AppId AppIdSession::pick_fw_client_app_id() +{ + return APPID_UT_ID; +} + +AppId AppIdSession::pick_fw_payload_app_id() +{ + return APPID_UT_ID; +} + +AppId AppIdSession::pick_fw_referred_payload_app_id() +{ + return APPID_UT_ID; +} + +AppId AppIdSession::pick_only_service_app_id() +{ + return APPID_UT_ID; +} + +bool AppIdSession::is_ssl_session_decrypted() +{ + return is_session_decrypted; +} + +#endif + diff --git a/src/network_inspectors/appid/thirdparty_appid_api.h b/src/network_inspectors/appid/thirdparty_appid_api.h index fca7628ef..6e2f04699 100644 --- a/src/network_inspectors/appid/thirdparty_appid_api.h +++ b/src/network_inspectors/appid/thirdparty_appid_api.h @@ -38,11 +38,11 @@ struct ThirdPartyConfig unsigned chp_body_collection_disabled : 1; unsigned tp_allow_probes : 1; unsigned http_upgrade_reporting_enabled : 1; - char appid_tp_dir[TP_PATH_MAX]; + char appid_tp_dir[TP_PATH_MAX]; unsigned numXffFields; - char** xffFields; + char** xffFields; unsigned oldNumXffFields; - char** oldXffFields; + char** oldXffFields; }; struct ThirdPartyUtils diff --git a/src/network_inspectors/appid/thirdparty_appid_utils.cc b/src/network_inspectors/appid/thirdparty_appid_utils.cc index bdb819c9b..659195f08 100644 --- a/src/network_inspectors/appid/thirdparty_appid_utils.cc +++ b/src/network_inspectors/appid/thirdparty_appid_utils.cc @@ -28,6 +28,7 @@ #include #include "appid_config.h" +#include "appid_http_session.h" #include "app_info_table.h" #include "detector_plugins/http_url_patterns.h" #include "service_plugins/service_ssl.h" @@ -48,6 +49,7 @@ static char const* defaultXffFields[] = { HTTP_XFF_FIELD_X_FORWARDED_FOR, HTTP_XFF_FIELD_TRUE_CLIENT_IP }; ProfileStats tpLibPerfStats; +ProfileStats tpPerfStats; inline int testSSLAppIdForReinspect(AppId app_id) { @@ -59,7 +61,7 @@ inline int testSSLAppIdForReinspect(AppId app_id) return 0; } -#ifdef APPID_UNUSED_CODE +#ifdef REMOVED_WHILE_NOT_IN_USE static int LoadCallback(const char* const path, int /* indent */) { void* handle; @@ -120,7 +122,8 @@ static void getXffFields(void) xffFields = (char**)defaultXffFields; thirdpartyConfig.numXffFields = sizeof(defaultXffFields) / sizeof(defaultXffFields[0]); } - thirdpartyConfig.xffFields = (char**)snort_alloc(thirdpartyConfig.numXffFields * sizeof(char*)); + thirdpartyConfig.xffFields = (char**)snort_alloc(thirdpartyConfig.numXffFields * + sizeof(char*)); for (unsigned i = 0; i < thirdpartyConfig.numXffFields; i++) thirdpartyConfig.xffFields[i] = snort_strndup(xffFields[i], UINT8_MAX); } @@ -157,9 +160,8 @@ void ThirdPartyAppIDInit(AppIdModuleConfig* config) // FIXIT-M need to provide log function and getSnortInstance function to 3rd party utils #ifdef REMOVED_WHILE_NOT_IN_USE - thirdpartyUtils.logMsg = &DebugFormat; - thirdpartyUtils.getSnortInstance = _dpd.getSnortInstance; - + //thirdpartyUtils.logMsg = &DebugFormat; + //thirdpartyUtils.getSnortInstance = _dpd.getSnortInstance; #endif getXffFields(); @@ -195,8 +197,8 @@ void ThirdPartyAppIDReconfigure(void) ret = thirdparty_appid_module->reconfigure(&thirdpartyConfig); for (unsigned i = 0; i < thirdpartyConfig.oldNumXffFields; i++) - snort_free(thirdpartyConfig.oldXffFields[i]); - snort_free(thirdpartyConfig.oldXffFields); + snort_free(thirdpartyConfig.oldXffFields[i]); + snort_free(thirdpartyConfig.oldXffFields); if (ret != 0) { @@ -254,11 +256,6 @@ bool checkThirdPartyReinspect(const Packet* p, AppIdSession* asd) asd->get_session_flags(APPID_SESSION_HTTP_SESSION) && TPIsAppIdDone(asd->tpsession); } -bool checkThirdPartyReinspect(const Packet*, AppIdSession*) -{ - return false; -} - void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, AppId* proto_list, ThirdPartyAppIDAttributeData* attribute_data) { @@ -292,7 +289,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, { if (!asd->hsession) { - asd->hsession = (HttpSession*)snort_calloc(sizeof(HttpSession)); + asd->hsession = new AppIdHttpSession(asd); memset(asd->hsession->ptype_scan_counts, 0, NUMBER_OF_PTYPES * sizeof(asd->hsession->ptype_scan_counts[0])); } @@ -310,7 +307,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, if (asd->hsession->url) { snort_free(asd->hsession->url); - asd->hsession->chp_finished = 0; + asd->hsession->chp_finished = false; } if (asd->get_session_flags(APPID_SESSION_DECRYPTED) && memcmp(attribute_data->spdyRequestScheme, httpScheme, sizeof(httpScheme)- @@ -346,7 +343,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, if (asd->hsession->host) { snort_free(asd->hsession->host); - asd->hsession->chp_finished = 0; + asd->hsession->chp_finished = false; } asd->hsession->host = attribute_data->spdyRequestHost; attribute_data->spdyRequestHost = nullptr; @@ -365,7 +362,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, if (asd->hsession->uri) { free(asd->hsession->uri); - asd->hsession->chp_finished = 0; + asd->hsession->chp_finished = false; } asd->hsession->uri = attribute_data->spdyRequestPath; attribute_data->spdyRequestPath = nullptr; @@ -386,7 +383,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, { snort_free(asd->hsession->host); if (!asd->get_session_flags(APPID_SESSION_APP_REINSPECT)) - asd->hsession->chp_finished = 0; + asd->hsession->chp_finished = false; } asd->hsession->host = attribute_data->httpRequestHost; asd->hsession->host_buflen = attribute_data->httpRequestHostLen; @@ -407,7 +404,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, { snort_free(asd->hsession->url); if (!asd->get_session_flags(APPID_SESSION_APP_REINSPECT)) - asd->hsession->chp_finished = 0; + asd->hsession->chp_finished = false; } //change http to https if session was decrypted. @@ -439,7 +436,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, { snort_free(asd->hsession->uri); if (!asd->get_session_flags(APPID_SESSION_APP_REINSPECT)) - asd->hsession->chp_finished = 0; + asd->hsession->chp_finished = false; } asd->hsession->uri = attribute_data->httpRequestUri; asd->hsession->uri_buflen = attribute_data->httpRequestUriLen; @@ -460,7 +457,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, { snort_free(asd->hsession->via); if (!asd->get_session_flags(APPID_SESSION_APP_REINSPECT)) - asd->hsession->chp_finished = 0; + asd->hsession->chp_finished = false; } asd->hsession->via = attribute_data->httpRequestVia; attribute_data->httpRequestVia = nullptr; @@ -472,7 +469,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, { snort_free(asd->hsession->via); if (!asd->get_session_flags(APPID_SESSION_APP_REINSPECT)) - asd->hsession->chp_finished = 0; + asd->hsession->chp_finished = false; } asd->hsession->via = attribute_data->httpResponseVia; attribute_data->httpResponseVia = nullptr; @@ -484,7 +481,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, { snort_free(asd->hsession->useragent); if (!asd->get_session_flags(APPID_SESSION_APP_REINSPECT)) - asd->hsession->chp_finished = 0; + asd->hsession->chp_finished = false; } asd->hsession->useragent = attribute_data->httpRequestUserAgent; attribute_data->httpRequestUserAgent = nullptr; @@ -516,7 +513,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, { snort_free(asd->hsession->response_code); if (!asd->get_session_flags(APPID_SESSION_APP_REINSPECT)) - asd->hsession->chp_finished = 0; + asd->hsession->chp_finished = false; } asd->hsession->response_code = attribute_data->httpResponseCode; asd->hsession->response_code_buflen = attribute_data->httpResponseCodeLen; @@ -552,7 +549,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, { snort_free(asd->hsession->referer); if (!asd->get_session_flags(APPID_SESSION_APP_REINSPECT)) - asd->hsession->chp_finished = 0; + asd->hsession->chp_finished = false; } asd->hsession->referer = attribute_data->httpRequestReferer; asd->hsession->referer_buflen = attribute_data->httpRequestRefererLen; @@ -573,7 +570,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, { snort_free(asd->hsession->cookie); if (!asd->get_session_flags(APPID_SESSION_APP_REINSPECT)) - asd->hsession->chp_finished = 0; + asd->hsession->chp_finished = false; } asd->hsession->cookie = attribute_data->httpRequestCookie; asd->hsession->cookie_buflen = attribute_data->httpRequestCookieLen; @@ -595,7 +592,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, { snort_free(asd->hsession->content_type); if (!asd->get_session_flags(APPID_SESSION_APP_REINSPECT)) - asd->hsession->chp_finished = 0; + asd->hsession->chp_finished = false; } asd->hsession->content_type = attribute_data->httpResponseContent; asd->hsession->content_type_buflen = attribute_data->httpResponseContentLen; @@ -608,7 +605,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, { snort_free(asd->hsession->location); if (!asd->get_session_flags(APPID_SESSION_APP_REINSPECT)) - asd->hsession->chp_finished = 0; + asd->hsession->chp_finished = false; } asd->hsession->location = attribute_data->httpResponseLocation; asd->hsession->location_buflen = attribute_data->httpResponseLocationLen; @@ -623,7 +620,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, { snort_free(asd->hsession->req_body); if (!asd->get_session_flags(APPID_SESSION_APP_REINSPECT)) - asd->hsession->chp_finished = 0; + asd->hsession->chp_finished = false; } asd->hsession->req_body = attribute_data->httpRequestBody; asd->hsession->req_body_buflen = attribute_data->httpRequestBodyLen; @@ -635,7 +632,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, { snort_free(asd->hsession->body); if (!asd->get_session_flags(APPID_SESSION_APP_REINSPECT)) - asd->hsession->chp_finished = 0; + asd->hsession->chp_finished = false; } asd->hsession->body = attribute_data->httpResponseBody; asd->hsession->body_buflen = attribute_data->httpResponseBodyLen; @@ -673,7 +670,7 @@ void ProcessThirdPartyResults(AppIdSession* asd, Packet* p, int confidence, ThirdPartyAppIDFoundProto(APP_ID_RTSP, proto_list)) { if (!asd->hsession) - asd->hsession = (HttpSession*)snort_calloc(sizeof(HttpSession)); + asd->hsession = new AppIdHttpSession(asd); if (!asd->hsession->url) { @@ -820,7 +817,7 @@ bool do_third_party_discovery(AppIdSession* asd, IpProtocol protocol, const SfIp if (asd->session_logging_enabled) LogMessage("AppIdDbg %s 3rd party allow reinspect http\n", asd->session_logging_id); - asd->clear_http_field(); + asd->reset_session_data(); } if (asd->tp_app_id == APP_ID_SSH && asd->payload_app_id != APP_ID_SFTP && @@ -953,7 +950,7 @@ bool do_third_party_discovery(AppIdSession* asd, IpProtocol protocol, const SfIp APP_ID_SSL)) asd->set_payload_app_id_data(APP_ID_HTTP_SSL_TUNNEL, NULL); - asd->process_http_packet(direction); + asd->hsession->process_http_packet(direction); // If SSL over HTTP tunnel, make sure Snort knows that it's encrypted. if (asd->payload_app_id == APP_ID_HTTP_SSL_TUNNEL) @@ -963,10 +960,10 @@ bool do_third_party_discovery(AppIdSession* asd, IpProtocol protocol, const SfIp APP_ID_HTTP && !asd->get_session_flags(APPID_SESSION_APP_REINSPECT)) { - asd->rna_client_state = APPID_STATE_FINISHED; + asd->client_disco_state = APPID_DISCO_STATE_FINISHED; asd->set_session_flags(APPID_SESSION_CLIENT_DETECTED | APPID_SESSION_SERVICE_DETECTED); - asd->rna_service_state = APPID_STATE_FINISHED; + asd->client_disco_state = APPID_DISCO_STATE_FINISHED; asd->clear_session_flags(APPID_SESSION_CONTINUE); if (direction == APP_ID_FROM_INITIATOR) { @@ -994,11 +991,11 @@ bool do_third_party_discovery(AppIdSession* asd, IpProtocol protocol, const SfIp asd->tp_app_id = porAppId; //SSL policy determines IMAPS/POP3S etc before appId sees first server // packet - asd->portServiceAppId = porAppId; + asd->port_service_id = porAppId; if (asd->session_logging_enabled) LogMessage("AppIdDbg %s SSL is service %d, portServiceAppId %d\n", asd->session_logging_id, - asd->tp_app_id, asd->portServiceAppId); + asd->tp_app_id, asd->port_service_id); } else { @@ -1058,14 +1055,17 @@ void pickHttpXffAddress(AppIdSession* asd, Packet*, ThirdPartyAppIDAttributeData // XFF precedence configuration cannot change for a session. Do not get it again if we already // got it. - char** xffPrecedence = _dpd.sessionAPI->get_http_xff_precedence(p->stream_session, p->flags, &appIdSession->hsession->numXffFields); + char** xffPrecedence = _dpd.sessionAPI->get_http_xff_precedence(p->stream_session, p->flags, + &appIdSession->hsession->numXffFields); if (!xffPrecedence) { xffPrecedence = defaultXffPrecedence; - appIdSession->hsession->numXffFields = sizeof(defaultXffPrecedence) / sizeof(defaultXffPrecedence[0]); + appIdSession->hsession->numXffFields = sizeof(defaultXffPrecedence) / + sizeof(defaultXffPrecedence[0]); } - appIdSession->hsession->xffPrecedence = malloc(appIdSession->hsession->numXffFields * sizeof(char*)); + appIdSession->hsession->xffPrecedence = malloc(appIdSession->hsession->numXffFields * + sizeof(char*)); for (unsigned j = 0; j < appIdSession->hsession->numXffFields; j++) appIdSession->hsession->xffPrecedence[j] = strndup(xffPrecedence[j], UINT8_MAX); @@ -1079,8 +1079,8 @@ void pickHttpXffAddress(AppIdSession* asd, Packet*, ThirdPartyAppIDAttributeData // xffPrecedence array is sorted based on precedence for (unsigned i = 0; - (i < asd->hsession->numXffFields) && asd->hsession->xffPrecedence[i]; - i++) + (i < asd->hsession->numXffFields) && asd->hsession->xffPrecedence[i]; + i++) { for (unsigned j = 0; j < attribute_data->numXffFields; j++) { @@ -1109,7 +1109,8 @@ void pickHttpXffAddress(AppIdSession* asd, Packet*, ThirdPartyAppIDAttributeData } else { - attribute_data->xffFieldValue[j].value[tmp - attribute_data->xffFieldValue[j].value] = '\0'; + attribute_data->xffFieldValue[j].value[tmp - + attribute_data->xffFieldValue[j].value] = '\0'; xff_addr = attribute_data->xffFieldValue[j].value; } diff --git a/src/network_inspectors/appid/thirdparty_appid_utils.h b/src/network_inspectors/appid/thirdparty_appid_utils.h index ae55a3e3f..e48560fcf 100644 --- a/src/network_inspectors/appid/thirdparty_appid_utils.h +++ b/src/network_inspectors/appid/thirdparty_appid_utils.h @@ -37,7 +37,6 @@ struct Packet; extern THREAD_LOCAL ThirdPartyAppIDModule* thirdparty_appid_module; // nullptr means no 3rd // party AppID module - void ThirdPartyAppIDInit(AppIdModuleConfig*); void ThirdPartyAppIDReconfigure(); void ThirdPartyAppIDFini();