⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 pp_ftp.c

📁 入侵检测SNORT.最近更新的基于网络检测的IDS.希望能给大家带来方便.
💻 C
📖 第 1 页 / 共 4 页
字号:
        }        else if (Session->data_chan_state & DATA_CHAN_PASV_CMD_ISSUED)        {            if (ftp_cmd_pipe_index == Session->data_chan_index)            {                if (Session->data_xfer_index == -1)                    ftp_cmd_pipe_index = 0;                Session->data_chan_index = -1;                if (rsp_code == 227)                {                    snort_ip ip;                    u_int16_t port=0;                    const char *ip_begin = req->param_begin;                    IP_CLEAR(ip);                    Session->data_chan_state &= ~DATA_CHAN_PASV_CMD_ISSUED;                    Session->data_chan_state |= DATA_CHAN_PASV_CMD_ACCEPT;                    Session->data_chan_index = -1;                    /* Interpret response message to identify the                     * Server IP/Port.  Server response is inside                     * a pair of ()s.  Find the left (, and use same                     * means to find IP/Port as is done for the PORT                     * command. */                    while ((*ip_begin != '(') &&                           (ip_begin < req->param_end))                    {                        ip_begin++;                    }                    if (ip_begin < req->param_end)                    {                        ip_begin++;                        iRet = getIP(&ip_begin, req->param_end, ')',                                     &ip, &port);                        if (iRet == FTPP_SUCCESS)                        {#ifdef SUP_IP6                            Session->serverIP = ip;#else                            Session->serverIP = htonl(ip);#endif                            Session->serverPort = port;                            IP_CLEAR(Session->clientIP);                            Session->clientPort = 0;                        }                    }                    else                    {                        iRet = FTPP_MALFORMED_FTP_RESPONSE;                    }                }                else                {                    Session->data_chan_index = -1;                    Session->data_chan_state &= ~DATA_CHAN_PASV_CMD_ISSUED;                }            }        }        else if (Session->data_chan_state & DATA_CHAN_PORT_CMD_ISSUED)        {            if (ftp_cmd_pipe_index == Session->data_chan_index)            {                if (Session->data_xfer_index == -1)                    ftp_cmd_pipe_index = 0;                Session->data_chan_index = -1;                if (rsp_code == 200)                {                    Session->data_chan_state &= ~DATA_CHAN_PORT_CMD_ISSUED;                    Session->data_chan_state |= DATA_CHAN_PORT_CMD_ACCEPT;                    Session->data_chan_index = -1;                }                else if (ftp_cmd_pipe_index == Session->data_chan_index)                {                    Session->data_chan_index = -1;                    Session->data_chan_state &= ~DATA_CHAN_PORT_CMD_ISSUED;                }            }        }        else if (Session->data_chan_state & DATA_CHAN_XFER_CMD_ISSUED)        {            if (ftp_cmd_pipe_index == Session->data_xfer_index)            {                if (Session->data_chan_index == -1)                    ftp_cmd_pipe_index = 0;                Session->data_xfer_index = -1;                if ((rsp_code == 150) || (rsp_code == 125))                {                    Session->data_chan_state &= ~DATA_CHAN_XFER_CMD_ISSUED;                    Session->data_chan_state = DATA_CHAN_XFER_STARTED;                    if (!IS_SET(Session->serverIP))                    {                        /* This means we're not in passive mode. */                        /* Server is listening/sending from its own IP,                         * FTP Port -1 */                         /* Client IP, Port specified via PORT command */#ifdef SUP_IP6                        IP_COPY_VALUE(Session->serverIP, GET_SRC_IP(p));#else                        Session->serverIP = p->ip4_header->source.s_addr;#endif                                            /* Can't necessarily guarantee this, especially                         * in the case of a proxy'd connection where the                         * data channel might not be on port 20 (or server                         * port-1).  Comment it out for now.                         */                        /*                        Session->serverPort = ntohs(p->tcph->th_sport) -1;                        */                    }                    if (!IS_SET(Session->clientIP))                    {                        /* This means we're in passive mode. */                        /* Server info is known. */                        /* Client IP is known from response packet, but                         * port is unknown */#ifdef SUP_IP6                        IP_COPY_VALUE(Session->clientIP, GET_DST_IP(p)); #else                        Session->clientIP = p->ip4_header->destination.s_addr;#endif                    }                    if (Session->server_conf->data_chan)                    {                        /* Call into Streams to mark data channel as something                         * to ignore. */#ifdef SUP_IP6                        _dpd.streamAPI->ignore_session(&Session->clientIP,                                Session->clientPort, &Session->serverIP,                                Session->serverPort,                                p->ip4_header->proto, SSN_DIR_BOTH,                                0 /* Not permanent */ );#else                        _dpd.streamAPI->ignore_session(Session->clientIP,                                Session->clientPort, Session->serverIP,                                Session->serverPort,                                p->ip4_header->proto, SSN_DIR_BOTH,                                0 /* Not permanent */ );#endif                    }                }                /* Clear the session info for next transfer -->                 * reset host/port */                IP_CLEAR(Session->serverIP);                IP_CLEAR(Session->clientIP);                Session->serverPort = Session->clientPort = 0;                Session->data_chan_state = NO_STATE;            }        }    } /* if (Session->server_conf->data_chan) */    if (Session->global_conf->encrypted.on)    {        switch(Session->encr_state)        {        case AUTH_TLS_CMD_ISSUED:            if (rsp_code == 234)            {                /* Could check that response msg includes "TLS" */                Session->encr_state = AUTH_TLS_ENCRYPTED;                if (Session->global_conf->encrypted.alert)                {                    /* Alert on encrypted channel */                    ftp_eo_event_log(Session, FTP_EO_ENCRYPTED,                        NULL, NULL);                }                DEBUG_WRAP(DebugMessage(DEBUG_FTPTELNET,                     "FTP stream is now TLS encrypted\n"););            }            break;        case AUTH_SSL_CMD_ISSUED:            if (rsp_code == 234)            {                /* Could check that response msg includes "SSL" */                Session->encr_state = AUTH_SSL_ENCRYPTED;                if (Session->global_conf->encrypted.alert)                {                    /* Alert on encrypted channel */                    ftp_eo_event_log(Session, FTP_EO_ENCRYPTED,                        NULL, NULL);                }                DEBUG_WRAP(DebugMessage(DEBUG_FTPTELNET,                     "FTP stream is now SSL encrypted\n"););            }            break;        case AUTH_UNKNOWN_CMD_ISSUED:            if (rsp_code == 234)            {                Session->encr_state = AUTH_UNKNOWN_ENCRYPTED;                if (Session->global_conf->encrypted.alert)                {                    /* Alert on encrypted channel */                    ftp_eo_event_log(Session, FTP_EO_ENCRYPTED,                        NULL, NULL);                }                DEBUG_WRAP(DebugMessage(DEBUG_FTPTELNET,                    "FTP stream is now encrypted\n"););            }            break;        }    } /* if (Session->global_conf->encrypted.on) */    return iRet;}/* * Function: check_ftp(FTP_SESSION *Session, Packet *p, int iMode) * * Purpose: Handle some trivial validation checks of an FTP packet.  Namely, *          check argument length and some protocol enforcement.   *  *          Wishful: This results in exposing the FTP command (and looking *          at the results) to the rules layer. * * Arguments: Session        => Pointer to session info *            p              => pointer to the current packet struct *            iMode          => Mode indicating server or client checks * * Returns: int => return code indicating error or success * */#define NUL 0x00#define CR 0x0d#define LF 0x0a#define SP 0x20#define DASH 0x2D#define FTP_CMD_OK 0#define FTP_CMD_INV 1#define FTP_RESPONSE_INV 1#define FTP_RESPONSE 2#define FTP_RESPONSE_2BCONT 2#define FTP_RESPONSE_CONT   3#define FTP_RESPONSE_ENDCONT 4int check_ftp(FTP_SESSION  *ftpssn, SFSnortPacket *p, int iMode){    int iRet = FTPP_SUCCESS;    int encrypted = 0;    int space = 0;    long state = FTP_CMD_OK;    int rsp_code = 0;    FTP_CLIENT_REQ *req;    FTP_CMD_CONF *CmdConf = NULL;    const unsigned char *read_ptr;    const unsigned char *end = p->payload + p->payload_size;    if (p->flags & FLAG_ALT_DECODE)        end = _dpd.altBuffer + p->normalized_payload_size;    if (iMode == FTPP_SI_CLIENT_MODE)    {        req = &ftpssn->client.request;        ftp_cmd_pipe_index = 0;    }    else if (iMode == FTPP_SI_SERVER_MODE)        req = (FTP_CLIENT_REQ *)&ftpssn->server.response;    else        return FTPP_INVALID_ARG;    while (req->pipeline_req)    {        state = FTP_CMD_OK;        /* Starts at the beginning of the buffer/line,         * so next up is a command */        read_ptr = (const unsigned char *)req->pipeline_req;             /* but first we ignore leading white space */         while ( (read_ptr < end) &&              (iMode == FTPP_SI_CLIENT_MODE) && isspace(*read_ptr) )             read_ptr++;        req->cmd_begin = (const char *)read_ptr;        while ((read_ptr < end) &&               (*read_ptr != SP) &&               (*read_ptr != CR) &&               (*read_ptr != LF) && /* Check for LF when there wasn't a CR,                                     * protocol violation, but accepted by                                     * some servers. */               (*read_ptr != DASH))        {            /* If the first char is a digit this is a response             * in server mode. */            if (iMode == FTPP_SI_SERVER_MODE)            {                if (isdigit(*read_ptr))                {                    if (state != FTP_RESPONSE_INV)                    {                        state = FTP_RESPONSE;                    }                }                else if (!isascii(*read_ptr))                {                    /* Non-ascii char here?  Bad response */                    state = FTP_RESPONSE_INV;                }            }            /* Or, if this is not a char, this is garbage in client mode */            else if (!isalpha(*read_ptr) && (iMode == FTPP_SI_CLIENT_MODE))            {                state = FTP_CMD_INV;            }            read_ptr++;        }        req->cmd_end = (const char *)read_ptr;        req->cmd_size = req->cmd_end - req->cmd_begin;        if (iMode == FTPP_SI_CLIENT_MODE)        {            if ( ((req->cmd_size != 4) && (req->cmd_size != 3)) ||                 (state == FTP_CMD_INV) )            {                /* Uh, something is very wrong...                 * nonalpha char seen or cmd is not 3 or 4 chars.                 * See if this might be encrypted, ie, non-alpha bytes. */                const unsigned char *ptr = (const unsigned char *)req->cmd_begin;                while (ptr < (const unsigned char *)req->cmd_end)                {                    if (!isalpha((int)(*ptr)))                    {                        if (!isascii((int)(*ptr)))                        {                            encrypted = 1;                        }                        break;                    }                    ptr++;                }            }            if (encrypted)            {                /* If the session wasn't already marked as encrypted...                 * Don't want to double-alert if we've already                 * determined the session is encrypted and we're                 * checking encrypted sessions.                 */                if (ftpssn->encr_state == 0)                {                    ftpssn->encr_state = AUTH_UNKNOWN_ENCRYPTED;                    if (ftpssn->global_conf->encrypted.alert)                    {                        /* Alert on encrypted channel */                        ftp_eo_event_log(ftpssn, FTP_EO_ENCRYPTED,                            NULL, NULL);                    }                    if (!ftpssn->global_conf->check_encrypted_data)                    {                        /* Mark this session & packet as one to ignore */                        _dpd.streamAPI->stop_inspection(p->stream_session_ptr, p,                                                SSN_DIR_BOTH, -1, 0);                    }                    DEBUG_WRAP(DebugMessage(DEBUG_FTPTELNET,                        "FTP client stream is now encrypted\n"););                }                break;            }            else            {                /*                  * Check the list of valid FTP commands as                 * supplied in ftpssn.                 */                if (req->cmd_size > 4)                {                    /* Alert, cmd not found */                    ftp_eo_event_log(ftpssn, FTP_EO_INVALID_CMD, NULL, NULL);                    state = FTP_CMD_INV;                }                else                {                    CmdConf = ftp_cmd_lookup_find(ftpssn->server_conf->cmd_lookup,                                              req->cmd_begin,                                              req->cmd_size,                                              &iRet);                    if ((iRet == FTPP_NOT_FOUND) || (CmdConf == NULL))                    {                        /* Alert, cmd not found */

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -