"Fossies" - the Fresh Open Source Software Archive

Member "snort-2.9.17/src/dynamic-preprocessors/sip/spp_sip.c" (16 Oct 2020, 32845 Bytes) of package /linux/misc/snort-2.9.17.tar.gz:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "spp_sip.c" see the Fossies "Dox" file reference documentation and the latest Fossies "Diffs" side-by-side code changes report: 2.9.16.1_vs_2.9.17.

    1 /* $Id */
    2 
    3 /*
    4  ** Copyright (C) 2014-2020 Cisco and/or its affiliates. All rights reserved.
    5  ** Copyright (C) 2011-2013 Sourcefire, Inc.
    6  **
    7  **
    8  ** This program is free software; you can redistribute it and/or modify
    9  ** it under the terms of the GNU General Public License Version 2 as
   10  ** published by the Free Software Foundation.  You may not use, modify or
   11  ** distribute this program under any other version of the GNU General
   12  ** Public License.
   13  **
   14  ** This program is distributed in the hope that it will be useful,
   15  ** but WITHOUT ANY WARRANTY; without even the implied warranty of
   16  ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   17  ** GNU General Public License for more details.
   18  **
   19  ** You should have received a copy of the GNU General Public License
   20  ** along with this program; if not, write to the Free Software
   21  ** Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
   22  */
   23 
   24 
   25 /*
   26  * SIP preprocessor
   27  *
   28  * This is the main entry point for this preprocessor
   29  *
   30  * Author: Hui Cao
   31  * Date: 03-15-2011
   32  */
   33 
   34 #ifdef HAVE_CONFIG_H
   35 #include "config.h"
   36 #endif  /* HAVE_CONFIG_H */
   37 
   38 #include "sf_types.h"
   39 #include "sf_snort_packet.h"
   40 #include "sf_dynamic_preprocessor.h"
   41 #include "sf_snort_plugin_api.h"
   42 #include "snort_debug.h"
   43 
   44 #include "preprocids.h"
   45 #include "spp_sip.h"
   46 #include "sip_config.h"
   47 #include "sip_roptions.h"
   48 #include "sip_parser.h"
   49 #include "sip_dialog.h"
   50 #include "sip_paf.h"
   51 
   52 #include <assert.h>
   53 #include <stdio.h>
   54 #include <syslog.h>
   55 #include <string.h>
   56 #ifndef WIN32
   57 #include <strings.h>
   58 #include <sys/time.h>
   59 #endif
   60 #include <stdlib.h>
   61 #include <ctype.h>
   62 
   63 #ifdef REG_TEST
   64 #include "reg_test.h"
   65 #endif
   66 
   67 #include "profiler.h"
   68 #ifdef PERF_PROFILING
   69 PreprocStats sipPerfStats;
   70 #endif
   71 
   72 #include "sf_types.h"
   73 
   74 #ifdef DUMP_BUFFER
   75 #include "sip_buffer_dump.h"
   76 #endif
   77 
   78 #ifdef SNORT_RELOAD
   79 #include "appdata_adjuster.h"
   80 #endif
   81 
   82 const int MAJOR_VERSION = 1;
   83 const int MINOR_VERSION = 1;
   84 const int BUILD_VERSION = 1;
   85 
   86 const char *PREPROC_NAME = "SF_SIP";
   87 
   88 #define SetupSIP DYNAMIC_PREPROC_SETUP
   89 
   90 #ifdef TARGET_BASED
   91 int16_t sip_app_id = SFTARGET_UNKNOWN_PROTOCOL;
   92 #endif
   93 
   94 /*
   95  * Session state flags for SIPData::state_flags
   96  */
   97 
   98 #define SIP_FLG_MISSED_PACKETS        (0x10000)
   99 
  100 /*
  101  * Function prototype(s)
  102  */
  103 SIPData * SIPGetNewSession(SFSnortPacket *, tSfPolicyId);
  104 static void SIPInit( struct _SnortConfig *, char* );
  105 static bool SIPGlobalIsEnabled(struct _SnortConfig *sc, tSfPolicyUserContextId sip_config);
  106 static int SIPPolicyIsEnabled(struct _SnortConfig *sc, tSfPolicyUserContextId pContext, tSfPolicyId policyId, void* config);
  107 static int SIPCheckConfig(struct _SnortConfig *);
  108 static void FreeSIPData( void* );
  109 static inline int SIP_Process(SFSnortPacket *, SIPData*);
  110 static void SIPmain( void*, void* );
  111 static inline int CheckSIPPort( uint16_t );
  112 static void SIPFreeConfig(tSfPolicyUserContextId);
  113 static void registerPortsForDispatch( struct _SnortConfig *sc, SIPConfig *policy );
  114 static void registerPortsForReassembly( SIPConfig *policy, int direction );
  115 static void _addPortsToStreamFilter(struct _SnortConfig *, SIPConfig *, tSfPolicyId);
  116 static void SIP_PrintStats(int);
  117 static void DisplaySIPStats (uint16_t type, void *old_context, struct _THREAD_ELEMENT *te, ControlDataSendFunc f);
  118 #ifdef TARGET_BASED
  119 static void _addServicesToStreamFilter(struct _SnortConfig *, tSfPolicyId);
  120 #endif
  121 
  122 static void SIPCleanExit(int, void *);
  123 
  124 /********************************************************************
  125  * Global variables
  126  ********************************************************************/
  127 uint32_t numSessions = 0;
  128 SIP_Stats sip_stats;
  129 SIPConfig *sip_eval_config;
  130 tSfPolicyUserContextId sip_config;
  131 
  132 #ifdef SNORT_RELOAD
  133 static APPDATA_ADJUSTER *ada;
  134 #endif
  135 
  136 static size_t SIP_NumSessions()
  137 {
  138     return (size_t) numSessions;
  139 }
  140 
  141 #ifdef SNORT_RELOAD
  142 static void SIPReload(struct _SnortConfig *, char *, void **);
  143 static int SIPReloadVerify(struct _SnortConfig *, void *);
  144 static void * SIPReloadSwap(struct _SnortConfig *, void *);
  145 static void SIPReloadSwapFree(void *);
  146 #endif
  147 
  148 static SIPMsg sipMsg;
  149 
  150 /* Called at preprocessor setup time. Links preprocessor keyword
  151  * to corresponding preprocessor initialization function.
  152  *
  153  * PARAMETERS:  None.
  154  *
  155  * RETURNS: Nothing.
  156  *
  157  */
  158 void SetupSIP(void)
  159 {
  160     /* Link preprocessor keyword to initialization function
  161      * in the preprocessor list. */
  162 #ifndef SNORT_RELOAD
  163     _dpd.registerPreproc( "sip", SIPInit );
  164 #else
  165     _dpd.registerPreproc("sip", SIPInit, SIPReload,
  166             SIPReloadVerify, SIPReloadSwap, SIPReloadSwapFree);
  167 #endif
  168 #ifdef DUMP_BUFFER
  169     _dpd.registerBufferTracer(getSIPBuffers, SIP_BUFFER_DUMP_FUNC);
  170 #endif
  171 }
  172 
  173 SIPConfig *getParsingSIPConfig(struct _SnortConfig *sc)
  174 {
  175     SIPConfig * sip_parsing_config;
  176 #ifdef SNORT_RELOAD
  177     tSfPolicyUserContextId sip_swap_config = (tSfPolicyUserContextId)_dpd.getRelatedReloadData(sc, "sip");
  178     if (sip_swap_config)
  179         sip_parsing_config = sfPolicyUserDataGetCurrent(sip_swap_config);
  180     else
  181 #endif
  182         sip_parsing_config = sfPolicyUserDataGetCurrent(sip_config);
  183     return sip_parsing_config;
  184 }
  185 
  186 #ifdef REG_TEST
  187 static inline void PrintSIPSize(void)
  188 {
  189     _dpd.logMsg("\nSIP Session Size: %lu\n", (long unsigned int)sizeof(SIPData));
  190 }
  191 #endif
  192 
  193 /* Initializes the SIP preprocessor module and registers
  194  * it in the preprocessor list.
  195  *
  196  * PARAMETERS:
  197  *
  198  * argp:        Pointer to argument string to process for config
  199  *                      data.
  200  *
  201  * RETURNS:     Nothing.
  202  */
  203 static void SIPInit(struct _SnortConfig *sc, char *argp)
  204 {
  205     tSfPolicyId policy_id = _dpd.getParserPolicy(sc);
  206     SIPConfig *pDefaultPolicyConfig = NULL;
  207     SIPConfig *pPolicyConfig = NULL;
  208 
  209 #ifdef REG_TEST
  210     PrintSIPSize();
  211 #endif
  212     /* For SFR CLI */
  213     _dpd.controlSocketRegisterHandler(CS_TYPE_SIP_STATS, NULL, NULL, &DisplaySIPStats);
  214 
  215     if (sip_config == NULL)
  216     {
  217         //create a context
  218         sip_config = sfPolicyConfigCreate();
  219         if (sip_config == NULL)
  220         {
  221             DynamicPreprocessorFatalMessage("Failed to allocate memory "
  222                     "for SIP config.\n");
  223         }
  224 
  225         _dpd.addPreprocConfCheck(sc, SIPCheckConfig);
  226         _dpd.registerPreprocStats(SIP_NAME, SIP_PrintStats);
  227         _dpd.addPreprocExit(SIPCleanExit, NULL, PRIORITY_LAST, PP_SIP);
  228 
  229 #ifdef PERF_PROFILING
  230         _dpd.addPreprocProfileFunc("sip", (void *)&sipPerfStats, 0, _dpd.totalPerfStats, NULL);
  231 #endif
  232 
  233 #ifdef TARGET_BASED
  234         sip_app_id = _dpd.findProtocolReference("sip");
  235         if (sip_app_id == SFTARGET_UNKNOWN_PROTOCOL)
  236             sip_app_id = _dpd.addProtocolReference("sip");
  237 
  238         // register with session to handle applications
  239         _dpd.sessionAPI->register_service_handler( PP_SIP, sip_app_id );
  240 
  241 #endif
  242     }
  243 
  244     sfPolicyUserPolicySet (sip_config, policy_id);
  245     pDefaultPolicyConfig = (SIPConfig *)sfPolicyUserDataGetDefault(sip_config);
  246     pPolicyConfig = (SIPConfig *)sfPolicyUserDataGetCurrent(sip_config);
  247     if ((pPolicyConfig != NULL) && (pDefaultPolicyConfig == NULL))
  248     {
  249         DynamicPreprocessorFatalMessage("SIP preprocessor can only be "
  250                 "configured once.\n");
  251     }
  252 
  253     pPolicyConfig = (SIPConfig *)calloc(1, sizeof(SIPConfig));
  254     if (!pPolicyConfig)
  255     {
  256         DynamicPreprocessorFatalMessage("Could not allocate memory for "
  257                 "SIP preprocessor configuration.\n");
  258     }
  259 
  260     sfPolicyUserDataSetCurrent(sip_config, pPolicyConfig);
  261     SIP_RegRuleOptions(sc);
  262     ParseSIPArgs(pPolicyConfig, (u_char *)argp);
  263 #ifdef SNORT_RELOAD
  264     pDefaultPolicyConfig = (SIPConfig *)sfPolicyUserDataGetDefault(sip_config);
  265     //we don't know the order in which policies are init
  266     //maybe default (policy 0) isn't init until after another policy is init
  267     //however a default policy is guranteed
  268     //avoid core
  269     //Also, if SIP isn't enabled, then why waste memory?
  270 #ifdef REG_TEST
  271     if (REG_TEST_FLAG_RELOAD & getRegTestFlags())
  272     {
  273         printf("SIP-reload SIPInit-before : %p\n", ada);
  274     }
  275 #endif
  276     if (pDefaultPolicyConfig != NULL && ada == NULL && SIPGlobalIsEnabled(sc, sip_config))
  277     {
  278         ada = ada_init(SIP_NumSessions, PP_SIP, (size_t)pDefaultPolicyConfig->maxNumSessions);
  279         if (ada == NULL)
  280             DynamicPreprocessorFatalMessage("Could not allocate memory for SIP ada\n");
  281     }
  282 #ifdef REG_TEST
  283     if (REG_TEST_FLAG_RELOAD & getRegTestFlags())
  284     {
  285         printf("SIP-reload SIPInit-after : %p\n", ada);
  286     }
  287 #endif
  288 #endif
  289 
  290 }
  291 
  292 /*********************************************************************
  293  * Overload PCRE options: this is to support the "H"
  294  *
  295  * For SIP messages, uri Buffers will point to SIP instead of HTTP
  296  *
  297  * Arguments:
  298  *  SFSnortPacket * - pointer to packet structure
  299  *
  300  * Returns:
  301  *  None
  302  *
  303  *********************************************************************/
  304 static inline void SIP_overloadURI(SFSnortPacket *p, SIPMsg *sipMsg)
  305 {
  306     if ( sipMsg->header )
  307         _dpd.setHttpBuffer(HTTP_BUFFER_HEADER, sipMsg->header, sipMsg->headerLen);
  308 
  309     if ( sipMsg->body_data )
  310         _dpd.setHttpBuffer(HTTP_BUFFER_CLIENT_BODY, sipMsg->body_data, sipMsg->bodyLen);
  311 }
  312 
  313 
  314 /*********************************************************************
  315  * Main entry point for SIP processing.
  316  *
  317  * Arguments:
  318  *  SFSnortPacket * - pointer to packet structure
  319  *
  320  * Returns:
  321  *  int -   SIP_SUCCESS
  322  *          SIP_FAILURE
  323  *
  324  *********************************************************************/
  325 static inline int SIP_Process(SFSnortPacket *p, SIPData* sessp)
  326 {
  327     int status;
  328     char* sip_buff = (char*) p->payload;
  329     char* end;
  330     SIP_Roptions *pRopts;
  331 
  332     memset(&sipMsg, 0, SIPMSG_ZERO_LEN);
  333 
  334 
  335     /*Input parameters*/
  336     sipMsg.isTcp = IsTCP(p);
  337 
  338     end =  sip_buff + p->payload_size;
  339 
  340 
  341     status = sip_parse(&sipMsg, sip_buff, end);
  342 
  343     if (SIP_SUCCESS == status)
  344     {
  345         SIP_overloadURI(p, &sipMsg);
  346         /*Update the dialog state*/
  347         SIP_updateDialog(&sipMsg, &(sessp->dialogs), p);
  348     }
  349     /*Update the session data*/
  350     pRopts = &(sessp->ropts);
  351     pRopts->methodFlag = sipMsg.methodFlag;
  352     pRopts->header_data = sipMsg.header;
  353     pRopts->header_len = sipMsg.headerLen;
  354     pRopts->body_len = sipMsg.bodyLen;
  355     pRopts->body_data = sipMsg.body_data;
  356     pRopts->status_code = sipMsg.status_code;
  357 
  358 
  359     DEBUG_WRAP(DebugMessage(DEBUG_SIP, "SIP message header length: %d\n",
  360             sipMsg.headerLen));
  361     DEBUG_WRAP(DebugMessage(DEBUG_SIP, "Parsed method: %.*s, Flag: 0x%x\n",
  362             sipMsg.methodLen, sipMsg.method, sipMsg.methodFlag));
  363     DEBUG_WRAP(DebugMessage(DEBUG_SIP, "Parsed status code:  %d\n",
  364             sipMsg.status_code));
  365     DEBUG_WRAP(DebugMessage(DEBUG_SIP, "Parsed header address: %p.\n",
  366             sipMsg.header));
  367     DEBUG_WRAP(DebugMessage(DEBUG_SIP, "Parsed body address: %p.\n",
  368             sipMsg.body_data));
  369 
  370     sip_freeMsg(&sipMsg);
  371 
  372     return status;
  373 }
  374 /* Main runtime entry point for SIP preprocessor.
  375  * Analyzes SIP packets for anomalies/exploits.
  376  *
  377  * PARAMETERS:
  378  *
  379  * packetp:    Pointer to current packet to process.
  380  * contextp:    Pointer to context block, not used.
  381  *
  382  * RETURNS:     Nothing.
  383  */
  384 static void SIPmain( void* ipacketp, void* contextp )
  385 {
  386     SIPData* sessp = NULL;
  387     uint8_t source = 0;
  388     uint8_t dest = 0;
  389 
  390     SFSnortPacket* packetp;
  391 #ifdef TARGET_BASED
  392     int16_t app_id = SFTARGET_UNKNOWN_PROTOCOL;
  393 #endif
  394     tSfPolicyId policy_id = _dpd.getNapRuntimePolicy();
  395     PROFILE_VARS;
  396 
  397     DEBUG_WRAP(DebugMessage(DEBUG_SIP, "%s\n", SIP_DEBUG__START_MSG));
  398 
  399     packetp = (SFSnortPacket*) ipacketp;
  400     sfPolicyUserPolicySet (sip_config, policy_id);
  401 
  402     // preconditions - what we registered for
  403     assert((IsUDP(packetp) || IsTCP(packetp)) &&
  404         packetp->payload && packetp->payload_size);
  405 
  406     if (IsTCP(packetp))
  407     {
  408         if (!_dpd.readyForProcess(packetp))
  409         {
  410             /* Packet will be rebuilt, so wait for it */
  411             DEBUG_WRAP(DebugMessage(DEBUG_SIP, "Packet will be reassembled\n"));
  412             return;
  413         }
  414         if (_dpd.sessionAPI->get_application_data(packetp->stream_session, PP_SSL) &&
  415             !_dpd.streamAPI->is_session_decrypted(packetp->stream_session))
  416         {
  417             /* Packet is a non-SIP/encrypted SIP one, skip those */
  418             DEBUG_WRAP(DebugMessage(DEBUG_SIP, "Packet is encrypted or not a SIP packet\n"));
  419             return;
  420         }
  421     }
  422 
  423     PREPROC_PROFILE_START(sipPerfStats);
  424 
  425     sip_eval_config = sfPolicyUserDataGetCurrent(sip_config);
  426 
  427     /* Attempt to get a previously allocated SIP block. */
  428     sessp = _dpd.sessionAPI->get_application_data(packetp->stream_session, PP_SIP);
  429     if (sessp != NULL)
  430     {
  431         sip_eval_config = sfPolicyUserDataGet(sessp->config, sessp->policy_id);
  432 
  433     }
  434 
  435     if (sessp == NULL)
  436     {
  437         /* If not doing autodetection, check the ports to make sure this is
  438          * running on an SIP port, otherwise no need to examine the traffic.
  439          */
  440 #ifdef TARGET_BASED
  441         app_id = _dpd.sessionAPI->get_application_protocol_id(packetp->stream_session);
  442         if (app_id == SFTARGET_UNKNOWN_PROTOCOL)
  443         {
  444             DEBUG_WRAP(DebugMessage(DEBUG_SIP, "Unknown protocol - not inspecting.\n"));
  445             DEBUG_WRAP(DebugMessage(DEBUG_SIP, "%s\n", SIP_DEBUG__END_MSG));
  446             PREPROC_PROFILE_END(sipPerfStats);
  447             return;
  448         }
  449 
  450         else if (app_id && (app_id != sip_app_id))
  451         {
  452             DEBUG_WRAP(DebugMessage(DEBUG_SIP, "Not SIP - not inspecting.\n"));
  453             DEBUG_WRAP(DebugMessage(DEBUG_SIP, "%s\n", SIP_DEBUG__END_MSG));
  454             PREPROC_PROFILE_END(sipPerfStats);
  455             return;
  456         }
  457 
  458         else if (!app_id)
  459         {
  460 #endif
  461             source = (uint8_t)CheckSIPPort( packetp->src_port );
  462             dest = (uint8_t)CheckSIPPort( packetp->dst_port );
  463 
  464             if ( !source && !dest )
  465             {
  466                 /* Not one of the ports we care about. */
  467                 DEBUG_WRAP(DebugMessage(DEBUG_SIP, "Not SIP ports - not inspecting.\n"));
  468                 DEBUG_WRAP(DebugMessage(DEBUG_SIP, "%s\n", SIP_DEBUG__END_MSG));
  469                 PREPROC_PROFILE_END(sipPerfStats);
  470                 return;
  471             }
  472 #ifdef TARGET_BASED
  473         }
  474 #endif
  475         /* Check the stream session. If it does not currently
  476          * have our SIP data-block attached, create one.
  477          */
  478         sessp = SIPGetNewSession(packetp, policy_id);
  479 
  480         if ( !sessp )
  481         {
  482             /* Could not get/create the session data for this packet. */
  483             DEBUG_WRAP(DebugMessage(DEBUG_SIP, "Create session error - not inspecting.\n"));
  484             DEBUG_WRAP(DebugMessage(DEBUG_SIP, "%s\n", SIP_DEBUG__END_MSG));
  485             PREPROC_PROFILE_END(sipPerfStats);
  486             return;
  487         }
  488 
  489     }
  490 
  491     /* Don't process if we've missed packets */
  492     if (sessp->state_flags & SIP_FLG_MISSED_PACKETS)
  493     {
  494         DEBUG_WRAP(DebugMessage(DEBUG_SIP, "Missed packets - not inspecting.\n"));
  495         DEBUG_WRAP(DebugMessage(DEBUG_SIP, "%s\n", SIP_DEBUG__END_MSG));
  496         PREPROC_PROFILE_END(sipPerfStats);
  497         return;
  498     }
  499 
  500     /* If we picked up mid-stream or missed any packets (midstream pick up
  501      * means we've already missed packets) set missed packets flag and make
  502      * sure we don't do any more reassembly on this session */
  503     if (IsTCP(packetp))
  504     {
  505         if ((_dpd.sessionAPI->get_session_flags(packetp->stream_session) & SSNFLAG_MIDSTREAM)
  506                 || _dpd.streamAPI->missed_packets(packetp->stream_session, SSN_DIR_BOTH))
  507         {
  508             _dpd.streamAPI->set_reassembly(packetp->stream_session,
  509                     STREAM_FLPOLICY_IGNORE, SSN_DIR_BOTH,
  510                     STREAM_FLPOLICY_SET_ABSOLUTE);
  511 
  512             sessp->state_flags |= SIP_FLG_MISSED_PACKETS;
  513             DEBUG_WRAP(DebugMessage(DEBUG_SIP, "Missed packets - not inspecting.\n"));
  514             DEBUG_WRAP(DebugMessage(DEBUG_SIP, "%s\n", SIP_DEBUG__END_MSG));
  515             PREPROC_PROFILE_END(sipPerfStats);
  516             return;
  517         }
  518     }
  519 
  520     /*
  521      * Start process PAYLOAD
  522      */
  523     SIP_Process(packetp,sessp);
  524 
  525     DEBUG_WRAP(DebugMessage(DEBUG_SIP, "%s\n", SIP_DEBUG__END_MSG));
  526     PREPROC_PROFILE_END(sipPerfStats);
  527 
  528 }
  529 
  530 /**********************************************************************
  531  *  Retrieves the SIP data block registered with the stream
  532  * session associated w/ the current packet. If none exists,
  533  * allocates it and registers it with the stream API.
  534  *
  535  * Arguments:
  536  *
  537  * packetp: Pointer to the packet from which/in which to
  538  *      retrieve/store the SIP data block.
  539  *
  540  * RETURNS: Pointer to an SIP data block, upon success.
  541  *      NULL, upon failure.
  542  **********************************************************************/
  543 SIPData * SIPGetNewSession(SFSnortPacket *packetp, tSfPolicyId policy_id)
  544 {
  545     SIPData* datap = NULL;
  546     static int MaxSessionsAlerted = 0;
  547     /* Sanity check(s) */
  548     assert( packetp );
  549     if ( !packetp->stream_session )
  550     {
  551         return NULL;
  552     }
  553     if(numSessions > ((SIPConfig *)sfPolicyUserDataGetCurrent(sip_config))->maxNumSessions)
  554     {
  555         if (!MaxSessionsAlerted)
  556             ALERT(SIP_EVENT_MAX_SESSIONS,SIP_EVENT_MAX_SESSIONS_STR);
  557         MaxSessionsAlerted = 1;
  558         return NULL;
  559     }
  560     else
  561     {
  562         MaxSessionsAlerted = 0;
  563     }
  564     datap = (SIPData *)calloc(1, sizeof(SIPData));
  565 
  566     if ( !datap )
  567         return NULL;
  568 
  569     /*Register the new SIP data block in the stream session. */
  570     _dpd.sessionAPI->set_application_data(
  571             packetp->stream_session,
  572             PP_SIP, datap, FreeSIPData );
  573             
  574     /* We're interested in this session. Turn on stream reassembly. */
  575     if ( !(_dpd.streamAPI->get_reassembly_direction(packetp->stream_session) & SSN_DIR_BOTH ))
  576     {
  577         _dpd.streamAPI->set_reassembly(packetp->stream_session,
  578                 STREAM_FLPOLICY_FOOTPRINT, SSN_DIR_BOTH, STREAM_FLPOLICY_SET_ABSOLUTE);
  579     }
  580 
  581 #ifdef SNORT_RELOAD
  582     ada_add(ada, (void *)datap, packetp->stream_session);
  583 #endif
  584 
  585     datap->policy_id = policy_id;
  586     datap->config = sip_config;
  587     ((SIPConfig *)sfPolicyUserDataGetCurrent(sip_config))->ref_count++;
  588     numSessions++;
  589     sip_stats.sessions++;
  590     DEBUG_WRAP(DebugMessage(DEBUG_SIP, "Number of sessions created: %u\n", numSessions));
  591 
  592     return datap;
  593 }
  594 
  595 
  596 /***********************************************************************
  597  * Registered as a callback with our SIP data blocks when
  598  * they are added to the underlying stream session. Called
  599  * by the stream preprocessor when a session is about to be
  600  * destroyed.
  601  *
  602  * PARAMETERS:
  603  *
  604  * idatap:  Pointer to the moribund data.
  605  *
  606  * RETURNS: Nothing.
  607  ***********************************************************************/
  608 static void FreeSIPData( void* idatap )
  609 {
  610     SIPData *ssn = (SIPData *)idatap;
  611     SIPConfig *config = NULL;
  612 
  613     if (ssn == NULL)
  614         return;
  615     if (numSessions > 0)
  616         numSessions--;
  617 
  618 #ifdef SNORT_RELOAD
  619     ada_appdata_freed( ada, idatap );
  620 #endif
  621 
  622     /*Free all the dialog data*/
  623     sip_freeDialogs(&ssn->dialogs);
  624 
  625     /*Clean the configuration data*/
  626     if (ssn->config != NULL)
  627     {
  628         config = (SIPConfig *)sfPolicyUserDataGet(ssn->config, ssn->policy_id);
  629     }
  630 
  631     if (config == NULL)
  632     {
  633         free(ssn);
  634         return;
  635     }
  636 
  637     config->ref_count--;
  638     if ((config->ref_count == 0) && (ssn->config != sip_config))
  639     {
  640         sfPolicyUserDataClear (ssn->config, ssn->policy_id);
  641         free(config);
  642 
  643         if (sfPolicyUserPolicyGetActive(ssn->config) == 0)
  644         {
  645             /* No more outstanding configs - free the config array */
  646             SIPFreeConfig(ssn->config);
  647         }
  648 
  649     }
  650 
  651     free(ssn);
  652 }
  653 /* **********************************************************************
  654  * Validates given port as an SIP server port.
  655  *
  656  * PARAMETERS:
  657  *
  658  * port:    Port to validate.
  659  *
  660  * RETURNS: SIP_TRUE, if the port is indeed an SIP server port.
  661  *          SIP_FALSE, otherwise.
  662  ***********************************************************************/
  663 static inline int CheckSIPPort( uint16_t port )
  664 {
  665     if ( sip_eval_config->ports[ PORT_INDEX(port) ] & CONV_PORT( port ) )
  666     {
  667         return SIP_TRUE;
  668     }
  669 
  670     return SIP_FALSE;
  671 }
  672 
  673 static void registerPortsForDispatch( struct _SnortConfig *sc, SIPConfig *policy )
  674 {
  675     if ( _dpd.isPreprocEnabled( sc, PP_APP_ID ) )
  676     {
  677         _dpd.sessionAPI->enable_preproc_all_ports( sc,
  678                                                    PP_SIP,
  679                                                    PROTO_BIT__UDP | PROTO_BIT__TCP ); 
  680     }
  681     else
  682     {
  683         int port;
  684         for ( port = 0; port < MAXPORTS; port++ )
  685         {
  686             if( isPortEnabled( policy->ports, port ) )
  687                 _dpd.sessionAPI->enable_preproc_for_port( sc,
  688                                                           PP_SIP,
  689                                                           PROTO_BIT__UDP | PROTO_BIT__TCP,
  690                                                           port ); 
  691         }
  692     }
  693 }
  694 
  695 static void registerPortsForReassembly( SIPConfig *policy, int direction )
  696 {
  697     uint32_t port;
  698 
  699     for ( port = 0; port < MAXPORTS; port++ )
  700     {
  701         if( isPortEnabled( policy->ports, port ) )
  702             _dpd.streamAPI->register_reassembly_port( NULL, port, direction );
  703     }
  704 }
  705 
  706 static void _addPortsToStreamFilter(struct _SnortConfig *sc, SIPConfig *config, tSfPolicyId policy_id)
  707 {
  708     uint32_t portNum;
  709 
  710     assert(config);
  711     assert(_dpd.streamAPI);
  712 
  713     for (portNum = 0; portNum < MAXPORTS; portNum++)
  714     {
  715         if(config->ports[(portNum/8)] & (1<<(portNum%8)))
  716         {
  717             //Add port the port
  718             _dpd.streamAPI->set_port_filter_status(sc, IPPROTO_UDP, (uint16_t)portNum, PORT_MONITOR_SESSION, policy_id, 1);
  719             _dpd.streamAPI->set_port_filter_status(sc, IPPROTO_TCP, (uint16_t)portNum, PORT_MONITOR_SESSION, policy_id, 1);
  720             register_sip_paf_port(sc, portNum, policy_id);
  721         }
  722     }
  723 }
  724 
  725 #ifdef TARGET_BASED
  726 
  727 static void _addServicesToStreamFilter(struct _SnortConfig *sc, tSfPolicyId policy_id)
  728 {
  729     _dpd.streamAPI->set_service_filter_status(sc, sip_app_id, PORT_MONITOR_SESSION, policy_id, 1);
  730     register_sip_paf_service(sc, sip_app_id, policy_id);
  731 }
  732 #endif
  733 
  734 static int SIPCheckPolicyConfig(struct _SnortConfig *sc, tSfPolicyUserContextId config, tSfPolicyId policy_id, void* pData)
  735 {
  736     SIPConfig *sip_policy = ( SIPConfig * ) pData;
  737 
  738     if ( sip_policy->disabled )
  739         return 0;
  740 
  741     if (!_dpd.isPreprocEnabled(sc, PP_STREAM))
  742     {
  743         _dpd.errMsg("SIPCheckPolicyConfig(): The Stream preprocessor must be enabled.\n");
  744         return -1;
  745     }
  746 
  747     if (policy_id != 0)
  748     {
  749         SIPConfig *default_sip_policy = ( SIPConfig * ) sfPolicyUserDataGetDefault( config );
  750         if(default_sip_policy == NULL)
  751         {
  752             _dpd.errMsg("SIPCheckPolicyConfig(): SIP default policy must be configured\n");
  753             return -1;
  754         }
  755 
  756         sip_policy->maxNumSessions = default_sip_policy->maxNumSessions;
  757      }
  758     
  759     _dpd.setParserPolicy( sc, policy_id );
  760     _dpd.addPreproc( sc, SIPmain, PRIORITY_APPLICATION, PP_SIP, PROTO_BIT__UDP|PROTO_BIT__TCP );
  761 
  762     // register ports with session and stream
  763     registerPortsForDispatch( sc, sip_policy );
  764     registerPortsForReassembly( sip_policy, SSN_DIR_FROM_SERVER | SSN_DIR_FROM_CLIENT );
  765     _addPortsToStreamFilter(sc, sip_policy, policy_id);
  766 
  767 #ifdef TARGET_BASED
  768     _addServicesToStreamFilter(sc, policy_id);
  769 #endif
  770 
  771     return 0;
  772 }
  773 
  774 static bool SIPGlobalIsEnabled(struct _SnortConfig *sc, tSfPolicyUserContextId config)
  775 {
  776    return sfPolicyUserDataIterate(sc, config, SIPPolicyIsEnabled) != 0;
  777 }
  778 
  779 static int SIPPolicyIsEnabled(struct _SnortConfig *sc, tSfPolicyUserContextId pContext, tSfPolicyId policyId, void* config)
  780 {
  781     SIPConfig *sip_policy_config = (SIPConfig *) config;
  782     if (sip_policy_config == NULL || sip_policy_config->disabled)
  783         return 0;
  784 
  785     return 1;
  786 }
  787 
  788 int SIPCheckConfig(struct _SnortConfig *sc)
  789 {
  790     int rval;
  791 
  792     if ((rval = sfPolicyUserDataIterate (sc, sip_config, SIPCheckPolicyConfig)))
  793         return rval;
  794 
  795     return 0;
  796 }
  797 
  798 static void SIPCleanExit(int signal, void *data)
  799 {
  800     if (sip_config != NULL)
  801     {
  802         SIPFreeConfig(sip_config);
  803         sip_config = NULL;
  804 #ifdef SNORT_RELOAD
  805         ada_delete(ada);
  806         ada = NULL;
  807 #endif
  808     }
  809 }
  810 static int SIPFreeConfigPolicy(
  811         tSfPolicyUserContextId config,
  812         tSfPolicyId policyId,
  813         void* pData
  814 )
  815 {
  816     SIPConfig *pPolicyConfig = (SIPConfig *)pData;
  817 
  818     //do any housekeeping before freeing SIPConfig
  819 
  820     sfPolicyUserDataClear (config, policyId);
  821 
  822     SIP_FreeConfig(pPolicyConfig);
  823     return 0;
  824 }
  825 
  826 void SIPFreeConfig(tSfPolicyUserContextId config)
  827 {
  828     if (config == NULL)
  829         return;
  830 
  831     sfPolicyUserDataFreeIterate (config, SIPFreeConfigPolicy);
  832     sfPolicyConfigDelete(config);
  833 }
  834 
  835 static void DisplaySIPStats (uint16_t type, void *old_context, struct _THREAD_ELEMENT *te, ControlDataSendFunc f)
  836 {
  837     char buffer[CS_STATS_BUF_SIZE + 1];
  838     int i = 0;
  839     int len = 0;
  840 
  841     if (sip_stats.sessions) {
  842         len += snprintf(buffer, CS_STATS_BUF_SIZE,  "SIP Preprocessor Statistics\n"
  843             "  Total sessions: "STDu64"\n", sip_stats.sessions);
  844         if (sip_stats.events)
  845             len += snprintf(buffer+len, CS_STATS_BUF_SIZE-len,  "  SIP anomalies : "STDu64"\n", sip_stats.events);
  846 
  847         if (sip_stats.dialogs)
  848             len += snprintf(buffer+len, CS_STATS_BUF_SIZE-len,  "  Total  dialogs: "STDu64"\n", sip_stats.dialogs);
  849 
  850         len += snprintf(buffer+len, CS_STATS_BUF_SIZE-len,  "  Requests: "STDu64"\n", sip_stats.requests[0]);
  851         while (NULL != StandardMethods[i].name && len < CS_STATS_BUF_SIZE) {
  852             len += snprintf(buffer+len, CS_STATS_BUF_SIZE-len,  "%16s:   "STDu64"\n",
  853                     StandardMethods[i].name, sip_stats.requests[StandardMethods[i].methodFlag]);
  854             i++;
  855         }
  856         len += snprintf(buffer+len, CS_STATS_BUF_SIZE-len,  "  Responses: "STDu64"\n", sip_stats.responses[TOTAL_RESPONSES]);
  857         for (i = 1; i <NUM_OF_RESPONSE_TYPES && len < CS_STATS_BUF_SIZE; i++) {
  858             len += snprintf(buffer+len, CS_STATS_BUF_SIZE-len,  "             %dxx:   "STDu64"\n", i, sip_stats.responses[i]);
  859         }
  860         len += snprintf(buffer+len, CS_STATS_BUF_SIZE-len,  " Ignore sessions:   "STDu64"\n"
  861             " Ignore channels:   "STDu64"\n", sip_stats.ignoreSessions, sip_stats.ignoreChannels);
  862     } else {
  863         len = snprintf(buffer, CS_STATS_BUF_SIZE, "SIP Stats not available\n Total Sessions:"STDu64"\n", sip_stats.sessions );
  864     }
  865 
  866     if (-1 == f(te, (const uint8_t *)buffer, len)) {
  867         _dpd.logMsg("Unable to send data to the frontend\n");
  868     }
  869 }
  870 
  871 /******************************************************************
  872  * Print statistics being kept by the preprocessor.
  873  *
  874  * Arguments:
  875  *  int - whether Snort is exiting or not
  876  *
  877  * Returns: None
  878  *
  879  ******************************************************************/
  880 static void SIP_PrintStats(int exiting)
  881 {
  882     int i;
  883     _dpd.logMsg("SIP Preprocessor Statistics\n");
  884     _dpd.logMsg("  Total sessions: "STDu64"\n", sip_stats.sessions);
  885     if (sip_stats.sessions > 0)
  886     {
  887         if (sip_stats.events > 0)
  888             _dpd.logMsg("  SIP anomalies : "STDu64"\n", sip_stats.events);
  889         if (sip_stats.dialogs > 0)
  890             _dpd.logMsg("  Total  dialogs: "STDu64"\n", sip_stats.dialogs);
  891 
  892         _dpd.logMsg("  Requests: "STDu64"\n", sip_stats.requests[0]);
  893         i = 0;
  894         while (NULL != StandardMethods[i].name)
  895         {
  896             _dpd.logMsg("%16s:   "STDu64"\n",
  897                     StandardMethods[i].name, sip_stats.requests[StandardMethods[i].methodFlag]);
  898             i++;
  899         }
  900 
  901         _dpd.logMsg("  Responses: "STDu64"\n", sip_stats.responses[TOTAL_RESPONSES]);
  902         for (i = 1; i <NUM_OF_RESPONSE_TYPES; i++ )
  903         {
  904             _dpd.logMsg("             %dxx:   "STDu64"\n", i, sip_stats.responses[i]);
  905         }
  906 
  907         _dpd.logMsg(" Ignore sessions:   "STDu64"\n", sip_stats.ignoreSessions);
  908         _dpd.logMsg(" Ignore channels:   "STDu64"\n", sip_stats.ignoreChannels);
  909     }
  910 }
  911 #ifdef SNORT_RELOAD
  912 static void SIPReload(struct _SnortConfig *sc, char *args, void **new_config)
  913 {
  914     tSfPolicyUserContextId sip_swap_config = (tSfPolicyUserContextId)*new_config;
  915     tSfPolicyId policy_id = _dpd.getParserPolicy(sc);
  916     SIPConfig *pDefaultPolicyConfig = NULL;
  917     SIPConfig * pPolicyConfig = NULL;
  918 
  919     if (sip_swap_config == NULL)
  920     {
  921         //create a context
  922         sip_swap_config = sfPolicyConfigCreate();
  923         if (sip_swap_config == NULL)
  924         {
  925             DynamicPreprocessorFatalMessage("Failed to allocate memory for SIP config.\n");
  926         }
  927         *new_config = (void *)sip_swap_config;
  928     }
  929 
  930     sfPolicyUserPolicySet (sip_swap_config, policy_id);
  931     pPolicyConfig = (SIPConfig *)sfPolicyUserDataGetCurrent(sip_swap_config);
  932     if (pPolicyConfig != NULL)
  933     {
  934         DynamicPreprocessorFatalMessage("SIP preprocessor can only be configured once.\n");
  935     }
  936 
  937     pPolicyConfig = (SIPConfig *)calloc(1, sizeof(SIPConfig));
  938     if (!pPolicyConfig)
  939     {
  940         DynamicPreprocessorFatalMessage("Could not allocate memory for "
  941                 "SIP preprocessor configuration.\n");
  942     }
  943     sfPolicyUserDataSetCurrent(sip_swap_config, pPolicyConfig);
  944     SIP_RegRuleOptions(sc);
  945     ParseSIPArgs(pPolicyConfig, (u_char *)args);
  946 
  947     pDefaultPolicyConfig = (SIPConfig *)sfPolicyUserDataGetDefault(sip_config);
  948     //we don't know the order in which policies are init
  949     //maybe default (policy 0) isn't init until after another policy is init
  950     //however a default policy is guranteed
  951     //avoid core
  952     //Also, if SIP isn't enabled, then why waste memory?
  953 #ifdef REG_TEST
  954     if (REG_TEST_FLAG_RELOAD & getRegTestFlags())
  955     {
  956         printf("SIP-reload SIPReload-before : %p\n", ada);
  957     }
  958 #endif
  959     if (pDefaultPolicyConfig != NULL && SIPGlobalIsEnabled(sc, sip_swap_config) && ada == NULL)
  960     {
  961         ada = ada_init(SIP_NumSessions, PP_SIP, (size_t)pDefaultPolicyConfig->maxNumSessions);
  962         if (ada == NULL)
  963             DynamicPreprocessorFatalMessage("Could not allocate memory for SIP ada\n");
  964     }
  965 #ifdef REG_TEST
  966     if (REG_TEST_FLAG_RELOAD & getRegTestFlags())
  967     {
  968         printf("SIP-reload SIPReload-after : %p\n", ada);
  969     }
  970 #endif
  971 }
  972 
  973 static int SIPReloadVerify(struct _SnortConfig *sc, void *swap_config)
  974 {
  975     tSfPolicyUserContextId sip_swap_config = (tSfPolicyUserContextId)swap_config;
  976     SIPConfig * default_swap_config = NULL;
  977     SIPConfig * current_default_config = NULL;
  978     int rval;
  979 
  980     if (sip_swap_config == NULL)
  981         return 0;
  982 
  983     // validate each policy and do per policy initialization processing
  984     if ((rval = sfPolicyUserDataIterate (sc, sip_swap_config, SIPCheckPolicyConfig)))
  985         return rval;
  986 
  987     default_swap_config = (SIPConfig *)sfPolicyUserDataGet(sip_swap_config, _dpd.getDefaultPolicy());
  988 
  989     if (sip_config != NULL)
  990     {
  991         current_default_config = (SIPConfig *)sfPolicyUserDataGet(sip_config, _dpd.getDefaultPolicy());
  992         //not possible
  993         if (!current_default_config)
  994             return 0;
  995 
  996         tSfPolicyId policy_id = _dpd.getParserPolicy(sc);
  997         if (!SIPGlobalIsEnabled(sc, sip_swap_config))
  998         {
  999             ada_reload_disable(&ada, sc, "sip-disable-mem-dump", policy_id);
 1000         }
 1001         else if (SIPGlobalIsEnabled(sc, sip_config) && default_swap_config->maxNumSessions < current_default_config->maxNumSessions)
 1002         {
 1003             ada_reload_adjust_register(ada, policy_id, sc, "sip-mem-reloader",
 1004                     (size_t) default_swap_config->maxNumSessions);
 1005         }
 1006     }
 1007 
 1008    return 0;
 1009 }
 1010 
 1011 static int SIPFreeUnusedConfigPolicy(
 1012         tSfPolicyUserContextId config,
 1013         tSfPolicyId policyId,
 1014         void* pData
 1015 )
 1016 {
 1017     SIPConfig *pPolicyConfig = (SIPConfig *)pData;
 1018 
 1019     //do any housekeeping before freeing SIPConfig
 1020     if (pPolicyConfig->ref_count == 0)
 1021     {
 1022         sfPolicyUserDataClear (config, policyId);
 1023         SIP_FreeConfig(pPolicyConfig);
 1024     }
 1025     return 0;
 1026 }
 1027 
 1028 static void * SIPReloadSwap(struct _SnortConfig *sc, void *swap_config)
 1029 {
 1030     tSfPolicyUserContextId sip_swap_config = (tSfPolicyUserContextId)swap_config;
 1031     tSfPolicyUserContextId old_config = sip_config;
 1032 
 1033     if (sip_swap_config == NULL)
 1034         return NULL;
 1035         
 1036     sip_config = sip_swap_config;
 1037 
 1038     sfPolicyUserDataFreeIterate (old_config, SIPFreeUnusedConfigPolicy);
 1039     if (sfPolicyUserPolicyGetActive(old_config) == 0)
 1040     {
 1041         /* No more outstanding configs - free the config array */
 1042         return (void *)old_config;
 1043     }
 1044 
 1045     return NULL;
 1046 }
 1047 
 1048 static void SIPReloadSwapFree(void *data)
 1049 {
 1050     if (data == NULL)
 1051         return;
 1052 
 1053     SIPFreeConfig((tSfPolicyUserContextId)data);
 1054 }
 1055 #endif