static OutputCtx *JsonMSSqlLogInitCtx(ConfNode *cn) { static char default_11g_log_filename[] = "mssql.json"; LogFileCtx *file_ctx = LogFileNewCtx(); if (!file_ctx) { SCLogError(SC_ERR_MSSQL_LOG_GENERIC, "could not create new file_ctx"); return NULL; } if (SCConfLogOpenGeneric(cn, file_ctx, default_11g_log_filename)) { LogFileFreeCtx(file_ctx); return NULL; } LogMSSqlFileCtx *mssqllog_ctx = SCCalloc(sizeof(*mssqllog_ctx), 1); if (unlikely(!mssqllog_ctx )) { LogFileFreeCtx(file_ctx); return NULL; } mssqllog_ctx->file_ctx = file_ctx; OutputCtx *octx = SCCalloc(1, sizeof(*octx)); if (unlikely(!octx)) { LogFileFreeCtx(file_ctx); SCFree(mssqllog_ctx); return NULL; } octx->data = mssqllog_ctx; octx->DeInit = LogMSSqlLogDeinitCtx; SCLogDebug("mssql json log output initialized"); AppLayerParserRegisterLogger(IPPROTO_TCP, ALPROTO_MSSQL); return octx; }
static OutputCtx *JsonDropLogInitCtxSub(ConfNode *conf, OutputCtx *parent_ctx) { if (OutputDropLoggerEnable() != 0) { SCLogError(SC_ERR_CONF_YAML_ERROR, "only one 'drop' logger " "can be enabled"); return NULL; } AlertJsonThread *ajt = parent_ctx->data; JsonDropOutputCtx *drop_ctx = SCCalloc(1, sizeof(*drop_ctx)); if (drop_ctx == NULL) return NULL; OutputCtx *output_ctx = SCCalloc(1, sizeof(OutputCtx)); if (unlikely(output_ctx == NULL)) { JsonDropOutputCtxFree(drop_ctx); return NULL; } if (conf) { const char *extended = ConfNodeLookupChildValue(conf, "alerts"); if (extended != NULL) { if (ConfValIsTrue(extended)) { drop_ctx->flags = LOG_DROP_ALERTS; } } } drop_ctx->file_ctx = ajt->file_ctx; output_ctx->data = drop_ctx; output_ctx->DeInit = JsonDropLogDeInitCtxSub; return output_ctx; }
static OutputCtx *OutputNFSLogInitSub(ConfNode *conf, OutputCtx *parent_ctx) { AlertJsonThread *ajt = parent_ctx->data; LogNFSFileCtx *nfslog_ctx = SCCalloc(1, sizeof(*nfslog_ctx)); if (unlikely(nfslog_ctx == NULL)) { return NULL; } nfslog_ctx->file_ctx = ajt->file_ctx; OutputCtx *output_ctx = SCCalloc(1, sizeof(*output_ctx)); if (unlikely(output_ctx == NULL)) { SCFree(nfslog_ctx); return NULL; } output_ctx->data = nfslog_ctx; output_ctx->DeInit = OutputNFSLogDeInitCtxSub; SCLogDebug("NFS log sub-module initialized."); AppLayerParserRegisterLogger(IPPROTO_TCP, ALPROTO_NFS); AppLayerParserRegisterLogger(IPPROTO_UDP, ALPROTO_NFS); return output_ctx; }
static OutputInitResult OutputIKEv2LogInitSub(ConfNode *conf, OutputCtx *parent_ctx) { OutputInitResult result = { NULL, false }; OutputJsonCtx *ajt = parent_ctx->data; LogIKEv2FileCtx *ikev2log_ctx = SCCalloc(1, sizeof(*ikev2log_ctx)); if (unlikely(ikev2log_ctx == NULL)) { return result; } ikev2log_ctx->file_ctx = ajt->file_ctx; ikev2log_ctx->cfg = ajt->cfg; OutputCtx *output_ctx = SCCalloc(1, sizeof(*output_ctx)); if (unlikely(output_ctx == NULL)) { SCFree(ikev2log_ctx); return result; } output_ctx->data = ikev2log_ctx; output_ctx->DeInit = OutputIKEv2LogDeInitCtxSub; SCLogDebug("IKEv2 log sub-module initialized."); AppLayerParserRegisterLogger(IPPROTO_UDP, ALPROTO_IKEV2); result.ctx = output_ctx; result.ok = true; return result; }
static OutputCtx *InitCtx(ConfNode *conf, AppProto proto, const char *dft_name) { LogFileCtx *ctx = LogFileNewCtx(); if (ctx == NULL) { SCLogError(SC_ERR_JONS_LOG_GENERIC, "couldn't create new file_ctx"); return NULL; } if (SCConfLogOpenGeneric(conf, ctx, dft_name) < 0) { LogFileFreeCtx(ctx); return NULL; } DBJsonLogCtx *jctx = SCCalloc(sizeof(*jctx) , 1); if (unlikely(jctx == NULL)) { LogFileFreeCtx(ctx); return NULL; } jctx->ctx = ctx; OutputCtx *octx = SCCalloc(1, sizeof(*octx)); if (unlikely(octx == NULL)) { LogFileFreeCtx(ctx); SCFree(jctx); return NULL; } octx->data = jctx; octx->DeInit = DeinitCtx; SCLogDebug("log output initialized"); AppLayerParserRegisterLogger(IPPROTO_TCP, proto); return octx; }
static OutputInitResult JsonDropLogInitCtx(ConfNode *conf) { OutputInitResult result = { NULL, false }; if (OutputDropLoggerEnable() != 0) { SCLogError(SC_ERR_CONF_YAML_ERROR, "only one 'drop' logger " "can be enabled"); return result; } JsonDropOutputCtx *drop_ctx = SCCalloc(1, sizeof(*drop_ctx)); if (drop_ctx == NULL) return result; drop_ctx->file_ctx = LogFileNewCtx(); if (drop_ctx->file_ctx == NULL) { JsonDropOutputCtxFree(drop_ctx); return result; } if (SCConfLogOpenGeneric(conf, drop_ctx->file_ctx, DEFAULT_LOG_FILENAME, 1) < 0) { JsonDropOutputCtxFree(drop_ctx); return result; } OutputCtx *output_ctx = SCCalloc(1, sizeof(OutputCtx)); if (unlikely(output_ctx == NULL)) { JsonDropOutputCtxFree(drop_ctx); return result; } if (conf) { const char *extended = ConfNodeLookupChildValue(conf, "alerts"); if (extended != NULL) { if (ConfValIsTrue(extended)) { drop_ctx->flags = LOG_DROP_ALERTS; } } extended = ConfNodeLookupChildValue(conf, "flows"); if (extended != NULL) { if (strcasecmp(extended, "start") == 0) { g_droplog_flows_start = 1; } else if (strcasecmp(extended, "all") == 0) { g_droplog_flows_start = 0; } else { SCLogWarning(SC_ERR_CONF_YAML_ERROR, "valid options for " "'flow' are 'start' and 'all'"); } } } output_ctx->data = drop_ctx; output_ctx->DeInit = JsonDropLogDeInitCtx; result.ctx = output_ctx; result.ok = true; return result; }
/** \internal */ static int SetupEngineForPacketHeader(SigGroupHead *sgh, int sm_type, PrefilterPacketHeaderHashCtx *hctx, _Bool (*Compare)(PrefilterPacketHeaderValue v, void *), void (*Match)(DetectEngineThreadCtx *det_ctx, Packet *p, const void *pectx)) { Signature *s = NULL; uint32_t sig = 0; uint32_t sig_offset = 0; PrefilterPacketHeaderCtx *ctx = SCCalloc(1, sizeof(PrefilterPacketHeaderCtx)); if (ctx == NULL) return -1; ctx->v1 = hctx->v1; ctx->type = hctx->type; ctx->value = hctx->value; ctx->sigs_cnt = hctx->cnt; ctx->sigs_array = SCCalloc(ctx->sigs_cnt, sizeof(SigIntId)); if (ctx->sigs_array == NULL) { SCFree(ctx); return -1; } for (sig = 0; sig < sgh->sig_cnt; sig++) { s = sgh->match_array[sig]; if (s == NULL) continue; if (s->prefilter_sm == NULL || s->prefilter_sm->type != sm_type) continue; uint16_t type = 0; uint16_t value = 0; GetExtraMatch(s, &type, &value); if (Compare(ctx->v1, s->prefilter_sm->ctx) && ctx->type == type && ctx->value == value) { SCLogDebug("appending sid %u on %u", s->id, sig_offset); ctx->sigs_array[sig_offset] = s->num; sig_offset++; s->flags |= SIG_FLAG_PREFILTER; } } SCLogDebug("%s: ctx %p extra type %u extra value %u, sig cnt %u", sigmatch_table[sm_type].name, ctx, ctx->type, ctx->value, ctx->sigs_cnt); PrefilterAppendEngine(sgh, Match, ctx, PrefilterPacketHeaderFree, sigmatch_table[sm_type].name); return 0; }
/** \brief Create a new tls log LogFileCtx. * \param conf Pointer to ConfNode containing this loggers configuration. * \return NULL if failure, LogFileCtx* to the file_ctx if succesful * */ static OutputCtx *LogTlsLogInitCtx(ConfNode *conf) { if (OutputTlsLoggerEnable() != 0) { SCLogError(SC_ERR_CONF_YAML_ERROR, "only one 'tls' logger " "can be enabled"); return NULL; } LogFileCtx* file_ctx = LogFileNewCtx(); if (file_ctx == NULL) { SCLogError(SC_ERR_TLS_LOG_GENERIC, "LogTlsLogInitCtx: Couldn't " "create new file_ctx"); return NULL; } if (SCConfLogOpenGeneric(conf, file_ctx, DEFAULT_LOG_FILENAME, 1) < 0) { goto filectx_error; } LogTlsFileCtx *tlslog_ctx = SCCalloc(1, sizeof(LogTlsFileCtx)); if (unlikely(tlslog_ctx == NULL)) goto filectx_error; tlslog_ctx->file_ctx = file_ctx; const char *extended = ConfNodeLookupChildValue(conf, "extended"); if (extended == NULL) { tlslog_ctx->flags |= LOG_TLS_DEFAULT; } else { if (ConfValIsTrue(extended)) { tlslog_ctx->flags |= LOG_TLS_EXTENDED; } } OutputCtx *output_ctx = SCCalloc(1, sizeof(OutputCtx)); if (unlikely(output_ctx == NULL)) goto tlslog_error; output_ctx->data = tlslog_ctx; output_ctx->DeInit = LogTlsLogDeInitCtx; SCLogDebug("TLS log output initialized"); /* enable the logger for the app layer */ AppLayerParserRegisterLogger(IPPROTO_TCP, ALPROTO_TLS); return output_ctx; tlslog_error: SCFree(tlslog_ctx); filectx_error: LogFileFreeCtx(file_ctx); return NULL; }
/** \internal * \brief turn values into a u8 hash map * \todo improve error handling * \todo deduplicate sigs arrays */ static int SetupEngineForPacketHeaderPrefilterPacketU8HashCtx(SigGroupHead *sgh, int sm_type, uint32_t *counts, void (*Set)(PrefilterPacketHeaderValue *v, void *), _Bool (*Compare)(PrefilterPacketHeaderValue v, void *), void (*Match)(DetectEngineThreadCtx *det_ctx, Packet *p, const void *pectx)) { Signature *s = NULL; uint32_t sig = 0; uint32_t cnt = 0; PrefilterPacketU8HashCtx *ctx = SCCalloc(1, sizeof(PrefilterPacketU8HashCtx)); if (ctx == NULL) return -1; int i; for (i = 0; i < 256; i++) { if (counts[i] == 0) continue; ctx->array[i] = SCCalloc(1, sizeof(SigsArray)); BUG_ON(ctx->array[i] == NULL); ctx->array[i]->cnt = counts[i]; ctx->array[i]->sigs = SCCalloc(ctx->array[i]->cnt, sizeof(SigIntId)); BUG_ON(ctx->array[i]->sigs == NULL); } for (sig = 0; sig < sgh->sig_cnt; sig++) { s = sgh->match_array[sig]; if (s == NULL) continue; if (s->prefilter_sm == NULL || s->prefilter_sm->type != sm_type) continue; PrefilterPacketHeaderValue v; memset(&v, 0, sizeof(v)); Set(&v, s->prefilter_sm->ctx); ApplyToU8Hash(ctx, v, s); s->flags |= SIG_FLAG_PREFILTER; cnt++; } if (cnt) { PrefilterAppendEngine(sgh, Match, ctx, PrefilterPacketU8HashCtxFree, sigmatch_table[sm_type].name); } else { PrefilterPacketU8HashCtxFree(ctx); } return 0; }
/** * \brief Parses and adds Netfilter queue(s). * * \param string with the queue number or range * * \retval 0 on success. * \retval -1 on failure. */ int NFQParseAndRegisterQueues(const char *queues) { uint16_t queue_start = 0; uint16_t queue_end = 0; uint16_t num_queues = 1; // if argument is correct, at least one queue will be created // Either "id" or "start:end" format (e.g., "12" or "0:5") int count = sscanf(queues, "%hu:%hu", &queue_start, &queue_end); if (count < 1) { SCLogError(SC_ERR_INVALID_ARGUMENT, "specified queue(s) argument '%s' is not " "valid (allowed queue numbers are 0-65535)", queues); return -1; } // Do we have a range? if (count == 2) { // Sanity check if (queue_start > queue_end) { SCLogError(SC_ERR_INVALID_ARGUMENT, "start queue's number %d is greater than " "ending number %d", queue_start, queue_end); return -1; } num_queues = queue_end - queue_start + 1; // +1 due to inclusive range } g_nfq_t = (NFQThreadVars *)SCCalloc(num_queues, sizeof(NFQThreadVars)); if (g_nfq_t == NULL) { SCLogError(SC_ERR_MEM_ALLOC, "Unable to allocate NFQThreadVars"); exit(EXIT_FAILURE); } g_nfq_q = (NFQQueueVars *)SCCalloc(num_queues, sizeof(NFQQueueVars)); if (g_nfq_q == NULL) { SCLogError(SC_ERR_MEM_ALLOC, "Unable to allocate NFQQueueVars"); SCFree(g_nfq_t); exit(EXIT_FAILURE); } do { if (NFQRegisterQueue(queue_start) != 0) { return -1; } } while (++queue_start <= queue_end); return 0; }
static OutputInitResult OutputFlowLogInitSub(ConfNode *conf, OutputCtx *parent_ctx) { OutputInitResult result = { NULL, false }; OutputJsonCtx *ojc = parent_ctx->data; LogJsonFileCtx *flow_ctx = SCMalloc(sizeof(LogJsonFileCtx)); if (unlikely(flow_ctx == NULL)) return result; OutputCtx *output_ctx = SCCalloc(1, sizeof(OutputCtx)); if (unlikely(output_ctx == NULL)) { SCFree(flow_ctx); return result; } flow_ctx->file_ctx = ojc->file_ctx; flow_ctx->cfg = ojc->cfg; output_ctx->data = flow_ctx; output_ctx->DeInit = OutputFlowLogDeinitSub; result.ctx = output_ctx; result.ok = true; return result; }
static OutputInitResult OutputFlowLogInit(ConfNode *conf) { OutputInitResult result = { NULL, false }; LogFileCtx *file_ctx = LogFileNewCtx(); if(file_ctx == NULL) { SCLogError(SC_ERR_FLOW_LOG_GENERIC, "couldn't create new file_ctx"); return result; } if (SCConfLogOpenGeneric(conf, file_ctx, DEFAULT_LOG_FILENAME, 1) < 0) { LogFileFreeCtx(file_ctx); return result; } LogJsonFileCtx *flow_ctx = SCMalloc(sizeof(LogJsonFileCtx)); if (unlikely(flow_ctx == NULL)) { LogFileFreeCtx(file_ctx); return result; } OutputCtx *output_ctx = SCCalloc(1, sizeof(OutputCtx)); if (unlikely(output_ctx == NULL)) { LogFileFreeCtx(file_ctx); SCFree(flow_ctx); return result; } flow_ctx->file_ctx = file_ctx; output_ctx->data = flow_ctx; output_ctx->DeInit = OutputFlowLogDeinit; result.ctx = output_ctx; result.ok = true; return result; }
OutputCtx *OutputHttpLogInitSub(ConfNode *conf, OutputCtx *parent_ctx) { AlertJsonThread *ajt = parent_ctx->data; LogHttpFileCtx *http_ctx = SCMalloc(sizeof(LogHttpFileCtx)); if (unlikely(http_ctx == NULL)) return NULL; OutputCtx *output_ctx = SCCalloc(1, sizeof(OutputCtx)); if (unlikely(output_ctx == NULL)) { SCFree(http_ctx); return NULL; } http_ctx->file_ctx = ajt->file_ctx; http_ctx->flags = LOG_HTTP_DEFAULT; if (conf) { const char *extended = ConfNodeLookupChildValue(conf, "extended"); if (extended != NULL) { if (ConfValIsTrue(extended)) { http_ctx->flags = LOG_HTTP_EXTENDED; } } } output_ctx->data = http_ctx; output_ctx->DeInit = NULL; /* enable the logger for the app layer */ AppLayerParserRegisterLogger(IPPROTO_TCP, ALPROTO_HTTP); return output_ctx; }
/** * \brief add a key-value pktvar to the pkt * \retval r 0 ok, -1 error */ int PktVarAddKeyValue(Packet *p, uint8_t *key, uint16_t ksize, uint8_t *value, uint16_t size) { PktVar *pv = SCCalloc(1, sizeof(PktVar)); if (unlikely(pv == NULL)) return -1; pv->key = key; pv->key_len = ksize; pv->value = value; pv->value_len = size; PktVar *tpv = p->pktvar; if (p->pktvar == NULL) p->pktvar = pv; else { while(tpv) { if (tpv->next == NULL) { tpv->next = pv; return 0; } tpv = tpv->next; } } return 0; }
/** * \brief Create a new LogFileCtx for "fast" output style. * \param conf The configuration node for this output. * \return A LogFileCtx pointer on success, NULL on failure. */ static OutputCtx *JsonAlertLogInitCtxSub(ConfNode *conf, OutputCtx *parent_ctx) { AlertJsonThread *ajt = parent_ctx->data; OutputCtx *output_ctx = SCCalloc(1, sizeof(OutputCtx)); if (unlikely(output_ctx == NULL)) return NULL; if (conf) { const char *payload = ConfNodeLookupChildValue(conf, "payload"); const char *packet = ConfNodeLookupChildValue(conf, "packet"); const char *payload_printable = ConfNodeLookupChildValue(conf, "payload-printable"); if (payload_printable != NULL) { if (ConfValIsTrue(payload_printable)) { ajt->file_ctx->flags |= LOG_JSON_PAYLOAD; } } if (payload != NULL) { if (ConfValIsTrue(payload)) { ajt->file_ctx->flags |= LOG_JSON_PAYLOAD_BASE64; } } if (packet != NULL) { if (ConfValIsTrue(packet)) { ajt->file_ctx->flags |= LOG_JSON_PACKET; } } } output_ctx->data = ajt->file_ctx; output_ctx->DeInit = JsonAlertLogDeInitCtxSub; return output_ctx; }
OutputCtx *OutputNetFlowLogInit(ConfNode *conf) { SCLogInfo("hi"); LogFileCtx *file_ctx = LogFileNewCtx(); if(file_ctx == NULL) { SCLogError(SC_ERR_NETFLOW_LOG_GENERIC, "couldn't create new file_ctx"); return NULL; } if (SCConfLogOpenGeneric(conf, file_ctx, DEFAULT_LOG_FILENAME, 1) < 0) { LogFileFreeCtx(file_ctx); return NULL; } LogJsonFileCtx *flow_ctx = SCMalloc(sizeof(LogJsonFileCtx)); if (unlikely(flow_ctx == NULL)) { LogFileFreeCtx(file_ctx); return NULL; } OutputCtx *output_ctx = SCCalloc(1, sizeof(OutputCtx)); if (unlikely(output_ctx == NULL)) { LogFileFreeCtx(file_ctx); SCFree(flow_ctx); return NULL; } flow_ctx->file_ctx = file_ctx; output_ctx->data = flow_ctx; output_ctx->DeInit = OutputNetFlowLogDeinit; return output_ctx; }
OutputCtx *OutputSshLogInitSub(ConfNode *conf, OutputCtx *parent_ctx) { AlertJsonThread *ajt = parent_ctx->data; if (OutputSshLoggerEnable() != 0) { SCLogError(SC_ERR_CONF_YAML_ERROR, "only one 'ssh' logger " "can be enabled"); return NULL; } OutputSshCtx *ssh_ctx = SCMalloc(sizeof(OutputSshCtx)); if (unlikely(ssh_ctx == NULL)) return NULL; OutputCtx *output_ctx = SCCalloc(1, sizeof(OutputCtx)); if (unlikely(output_ctx == NULL)) { SCFree(ssh_ctx); return NULL; } ssh_ctx->file_ctx = ajt->file_ctx; output_ctx->data = ssh_ctx; output_ctx->DeInit = OutputSshLogDeinitSub; return output_ctx; }
/** * \brief Create a new LogFileCtx for "fast" output style. * \param conf The configuration node for this output. * \return A LogFileCtx pointer on success, NULL on failure. */ OutputCtx *AlertPcapInfoInitCtx(ConfNode *conf) { LogFileCtx *logfile_ctx = LogFileNewCtx(); if (logfile_ctx == NULL) { SCLogDebug("AlertPcapInfoInitCtx2: Could not create new LogFileCtx"); return NULL; } const char *filename = ConfNodeLookupChildValue(conf, "filename"); if (filename == NULL) filename = DEFAULT_LOG_FILENAME; const char *mode = ConfNodeLookupChildValue(conf, "append"); if (mode == NULL) mode = DEFAULT_PCAPINFO_MODE_APPEND; if (AlertPcapInfoOpenFileCtx(logfile_ctx, filename, mode) < 0) { LogFileFreeCtx(logfile_ctx); return NULL; } OutputCtx *output_ctx = SCCalloc(1, sizeof(OutputCtx)); if (unlikely(output_ctx == NULL)) return NULL; output_ctx->data = logfile_ctx; output_ctx->DeInit = AlertPcapInfoDeInitCtx; SCLogInfo("Fast log output initialized, filename: %s", filename); return output_ctx; }
OutputCtx *OutputTlsLogInitSub(ConfNode *conf, OutputCtx *parent_ctx) { OutputJsonCtx *ojc = parent_ctx->data; OutputTlsCtx *tls_ctx = SCMalloc(sizeof(OutputTlsCtx)); if (unlikely(tls_ctx == NULL)) return NULL; OutputCtx *output_ctx = SCCalloc(1, sizeof(OutputCtx)); if (unlikely(output_ctx == NULL)) { SCFree(tls_ctx); return NULL; } tls_ctx->file_ctx = ojc->file_ctx; tls_ctx->flags = LOG_TLS_DEFAULT; if (conf) { const char *extended = ConfNodeLookupChildValue(conf, "extended"); if (extended != NULL) { if (ConfValIsTrue(extended)) { tls_ctx->flags = LOG_TLS_EXTENDED; } } } output_ctx->data = tls_ctx; output_ctx->DeInit = OutputTlsLogDeinitSub; AppLayerParserRegisterLogger(IPPROTO_TCP, ALPROTO_TLS); return output_ctx; }
/** \brief Create a new LogFileCtx for unified alert logging. * \param conf The ConfNode for this output. * \return NULL if failure, LogFileCtx* to the file_ctx if succesful * */ OutputCtx *AlertUnifiedAlertInitCtx(ConfNode *conf) { int ret = 0; LogFileCtx *file_ctx = NULL; file_ctx = LogFileNewCtx(); if (file_ctx == NULL) { SCLogError(SC_ERR_UNIFIED_ALERT_GENERIC, "Couldn't create new file_ctx"); goto error; } const char *filename = NULL; if (conf != NULL) filename = ConfNodeLookupChildValue(conf, "filename"); if (filename == NULL) filename = DEFAULT_LOG_FILENAME; file_ctx->prefix = SCStrdup(filename); const char *s_limit = NULL; uint32_t limit = DEFAULT_LIMIT; if (conf != NULL) { s_limit = ConfNodeLookupChildValue(conf, "limit"); if (s_limit != NULL) { if (ByteExtractStringUint32(&limit, 10, 0, s_limit) == -1) { SCLogError(SC_ERR_INVALID_ARGUMENT, "Fail to initialize unified alert output, invalid limit: %s", s_limit); exit(EXIT_FAILURE); } if (limit < MIN_LIMIT) { SCLogError(SC_ERR_INVALID_ARGUMENT, "Fail to initialize unified alert output, limit less than " "allowed minimum: %d.", MIN_LIMIT); exit(EXIT_FAILURE); } } } file_ctx->size_limit = limit * 1024 * 1024; ret = AlertUnifiedAlertOpenFileCtx(file_ctx, filename); if (ret < 0) goto error; OutputCtx *output_ctx = SCCalloc(1, sizeof(OutputCtx)); if (output_ctx == NULL) goto error; output_ctx->data = file_ctx; output_ctx->DeInit = AlertUnifiedAlertDeInitCtx; SCLogInfo("Unified-alert initialized: filename %s, limit %"PRIu32" MB", filename, limit); return output_ctx; error: if (file_ctx != NULL) { LogFileFreeCtx(file_ctx); } return NULL; }
/** * \brief Create a new LogFileCtx for "drop" output style. * \param conf The configuration node for this output. * \return A LogFileCtx pointer on success, NULL on failure. */ static OutputCtx *LogDropLogInitCtx(ConfNode *conf) { if (OutputDropLoggerEnable() != 0) { SCLogError(SC_ERR_CONF_YAML_ERROR, "only one 'drop' logger " "can be enabled"); return NULL; } LogFileCtx *logfile_ctx = LogFileNewCtx(); if (logfile_ctx == NULL) { SCLogDebug("LogDropLogInitCtx: Could not create new LogFileCtx"); return NULL; } if (SCConfLogOpenGeneric(conf, logfile_ctx, DEFAULT_LOG_FILENAME, 1) < 0) { LogFileFreeCtx(logfile_ctx); return NULL; } OutputCtx *output_ctx = SCCalloc(1, sizeof(OutputCtx)); if (unlikely(output_ctx == NULL)) { LogFileFreeCtx(logfile_ctx); return NULL; } output_ctx->data = logfile_ctx; output_ctx->DeInit = LogDropLogDeInitCtx; return output_ctx; }
/** \brief Turn byte array into string. * * All non-printables are copied over, except for '\0', which is * turned into literal \0 in the string. * * \param bytes byte array * \param nbytes number of bytes * \return string nul-terminated string or NULL on error */ char *BytesToString(const uint8_t *bytes, size_t nbytes) { size_t n = nbytes + 1; size_t nulls = 0; size_t u; for (u = 0; u < nbytes; u++) { if (bytes[u] == '\0') nulls++; } n += nulls; char *string = SCCalloc(1, n); if (string == NULL) return NULL; if (nulls == 0) { /* no nulls */ memcpy(string, bytes, nbytes); } else { /* nulls present */ char *dst = string; for (u = 0; u < nbytes; u++) { if (bytes[u] == '\0') { *dst++ = '\\'; *dst++ = '0'; } else { *dst++ = bytes[u]; } } } return string; }
/** * \brief Create a new LogFileCtx for "fast" output style. * \param conf The configuration node for this output. * \return A LogFileCtx pointer on success, NULL on failure. */ static OutputCtx *JsonAlertLogInitCtxSub(ConfNode *conf, OutputCtx *parent_ctx) { OutputJsonCtx *ajt = parent_ctx->data; AlertJsonOutputCtx *json_output_ctx = NULL; OutputCtx *output_ctx = SCCalloc(1, sizeof(OutputCtx)); if (unlikely(output_ctx == NULL)) return NULL; json_output_ctx = SCMalloc(sizeof(AlertJsonOutputCtx)); if (unlikely(json_output_ctx == NULL)) { goto error; } memset(json_output_ctx, 0, sizeof(AlertJsonOutputCtx)); json_output_ctx->file_ctx = ajt->file_ctx; XffSetup(json_output_ctx, conf); output_ctx->data = json_output_ctx; output_ctx->DeInit = JsonAlertLogDeInitCtxSub; return output_ctx; error: if (json_output_ctx != NULL) { SCFree(json_output_ctx); } if (output_ctx != NULL) { SCFree(output_ctx); } return NULL; }
static int DecodeMPLSTestPacketTooSmall(void) { ThreadVars tv; DecodeThreadVars dtv; memset(&dtv, 0, sizeof(DecodeThreadVars)); memset(&tv, 0, sizeof(ThreadVars)); Packet *p0 = SCCalloc(1, SIZE_OF_PACKET); memset(p0, 0, SIZE_OF_PACKET); uint8_t pkt0[] = { 0x00, 0x01, 0x51, 0xff }; DecodeMPLS(&tv, &dtv, p0, pkt0, sizeof(pkt0), NULL); FAIL_IF_NOT(ENGINE_ISSET_EVENT(p0, MPLS_PKT_TOO_SMALL)); SCFree(p0); Packet *p1 = SCCalloc(1, SIZE_OF_PACKET); FAIL_IF_NULL(p1); uint8_t pkt1[] = { 0x00, 0x01, 0x51, 0xff, 0x45 }; DecodeMPLS(&tv, &dtv, p1, pkt1, sizeof(pkt1), NULL); FAIL_IF_NOT(ENGINE_ISSET_EVENT(p1, MPLS_PKT_TOO_SMALL)); SCFree(p1); Packet *p2 = SCCalloc(1, SIZE_OF_PACKET); FAIL_IF_NULL(p2); uint8_t pkt2[] = { 0x00, 0x01, 0x51, 0xff, 0x45, 0x01 }; DecodeMPLS(&tv, &dtv, p2, pkt2, sizeof(pkt2), NULL); FAIL_IF_NOT(ENGINE_ISSET_EVENT(p2, MPLS_PKT_TOO_SMALL)); SCFree(p2); Packet *p3 = SCCalloc(1, SIZE_OF_PACKET); FAIL_IF_NULL(p3); uint8_t pkt3[] = { 0x00, 0x01, 0x51, 0xff, 0x45, 0x01, 0x02 }; DecodeMPLS(&tv, &dtv, p3, pkt3, sizeof(pkt3), NULL); FAIL_IF_NOT(ENGINE_ISSET_EVENT(p3, MPLS_PKT_TOO_SMALL)); SCFree(p3); // This should not create a too small event is it has one more byte // than required. Packet *p4 = SCCalloc(1, SIZE_OF_PACKET); FAIL_IF_NULL(p4); uint8_t pkt4[] = { 0x00, 0x01, 0x51, 0xff, 0x45, 0x01, 0x02, 0x03 }; DecodeMPLS(&tv, &dtv, p4, pkt4, sizeof(pkt4), NULL); FAIL_IF(ENGINE_ISSET_EVENT(p4, MPLS_PKT_TOO_SMALL)); SCFree(p4); PASS; }
PktProfiling *SCProfilePacketStart(void) { uint64_t sample = SC_ATOMIC_ADD(samples, 1); if (sample % rate == 0) return SCCalloc(1, sizeof(PktProfiling)); else return NULL; }
/** \brief Create a new http log LogFileCtx. * \param conf Pointer to ConfNode containing this loggers configuration. * \return NULL if failure, LogFileCtx* to the file_ctx if succesful * */ OutputCtx *LogStatsLogInitCtx(ConfNode *conf) { LogFileCtx *file_ctx = LogFileNewCtx(); if (file_ctx == NULL) { SCLogError(SC_ERR_HTTP_LOG_GENERIC, "couldn't create new file_ctx"); return NULL; } if (SCConfLogOpenGeneric(conf, file_ctx, DEFAULT_LOG_FILENAME, 1) < 0) { LogFileFreeCtx(file_ctx); return NULL; } LogStatsFileCtx *statslog_ctx = SCMalloc(sizeof(LogStatsFileCtx)); if (unlikely(statslog_ctx == NULL)) { LogFileFreeCtx(file_ctx); return NULL; } memset(statslog_ctx, 0x00, sizeof(LogStatsFileCtx)); statslog_ctx->flags = LOG_STATS_TOTALS; if (conf != NULL) { const char *totals = ConfNodeLookupChildValue(conf, "totals"); const char *threads = ConfNodeLookupChildValue(conf, "threads"); const char *nulls = ConfNodeLookupChildValue(conf, "null-values"); SCLogDebug("totals %s threads %s", totals, threads); if (totals != NULL && ConfValIsFalse(totals)) { statslog_ctx->flags &= ~LOG_STATS_TOTALS; } if (threads != NULL && ConfValIsTrue(threads)) { statslog_ctx->flags |= LOG_STATS_THREADS; } if (nulls != NULL && ConfValIsTrue(nulls)) { statslog_ctx->flags |= LOG_STATS_NULLS; } SCLogDebug("statslog_ctx->flags %08x", statslog_ctx->flags); } statslog_ctx->file_ctx = file_ctx; OutputCtx *output_ctx = SCCalloc(1, sizeof(OutputCtx)); if (unlikely(output_ctx == NULL)) { LogFileFreeCtx(file_ctx); SCFree(statslog_ctx); return NULL; } output_ctx->data = statslog_ctx; output_ctx->DeInit = LogStatsLogDeInitCtx; SCLogDebug("STATS log output initialized"); return output_ctx; }
static OutputCtx *JsonDropLogInitCtx(ConfNode *conf) { if (OutputDropLoggerEnable() != 0) { SCLogError(SC_ERR_CONF_YAML_ERROR, "only one 'drop' logger " "can be enabled"); return NULL; } JsonDropOutputCtx *drop_ctx = SCCalloc(1, sizeof(*drop_ctx)); if (drop_ctx == NULL) return NULL; drop_ctx->file_ctx = LogFileNewCtx(); if (drop_ctx->file_ctx == NULL) { JsonDropOutputCtxFree(drop_ctx); return NULL; } if (SCConfLogOpenGeneric(conf, drop_ctx->file_ctx, DEFAULT_LOG_FILENAME, 1) < 0) { JsonDropOutputCtxFree(drop_ctx); return NULL; } OutputCtx *output_ctx = SCCalloc(1, sizeof(OutputCtx)); if (unlikely(output_ctx == NULL)) { JsonDropOutputCtxFree(drop_ctx); return NULL; } if (conf) { const char *extended = ConfNodeLookupChildValue(conf, "alerts"); if (extended != NULL) { if (ConfValIsTrue(extended)) { drop_ctx->flags = LOG_DROP_ALERTS; } } } output_ctx->data = drop_ctx; output_ctx->DeInit = JsonDropLogDeInitCtx; return output_ctx; }
inline int PacketCallocExtPkt(Packet *p, int datalen) { if (! p->ext_pkt) { p->ext_pkt = SCCalloc(1, datalen); if (unlikely(p->ext_pkt == NULL)) { SET_PKT_LEN(p, 0); return -1; } } return 0; }
void SCProfilingSghThreadSetup(SCProfileSghDetectCtx *ctx, DetectEngineThreadCtx *det_ctx) { if (ctx == NULL) return; uint32_t array_size = det_ctx->de_ctx->sgh_array_cnt; SCProfileSghData *a = SCCalloc(array_size, sizeof(SCProfileSghData)); if (a != NULL) { det_ctx->sgh_perf_data = a; } }
OutputCtx *OutputStatsLogInit(ConfNode *conf) { LogFileCtx *file_ctx = LogFileNewCtx(); if(file_ctx == NULL) { SCLogError(SC_ERR_STATS_LOG_GENERIC, "couldn't create new file_ctx"); return NULL; } if (SCConfLogOpenGeneric(conf, file_ctx, DEFAULT_LOG_FILENAME, 1) < 0) { LogFileFreeCtx(file_ctx); return NULL; } OutputStatsCtx *stats_ctx = SCMalloc(sizeof(OutputStatsCtx)); if (unlikely(stats_ctx == NULL)) { LogFileFreeCtx(file_ctx); return NULL; } stats_ctx->flags = JSON_STATS_TOTALS; if (conf != NULL) { const char *totals = ConfNodeLookupChildValue(conf, "totals"); const char *threads = ConfNodeLookupChildValue(conf, "threads"); const char *deltas = ConfNodeLookupChildValue(conf, "deltas"); SCLogDebug("totals %s threads %s deltas %s", totals, threads, deltas); if (totals != NULL && ConfValIsFalse(totals)) { stats_ctx->flags &= ~JSON_STATS_TOTALS; } if (threads != NULL && ConfValIsTrue(threads)) { stats_ctx->flags |= JSON_STATS_THREADS; } if (deltas != NULL && ConfValIsTrue(deltas)) { stats_ctx->flags |= JSON_STATS_DELTAS; } SCLogDebug("stats_ctx->flags %08x", stats_ctx->flags); } OutputCtx *output_ctx = SCCalloc(1, sizeof(OutputCtx)); if (unlikely(output_ctx == NULL)) { LogFileFreeCtx(file_ctx); SCFree(stats_ctx); return NULL; } stats_ctx->file_ctx = file_ctx; output_ctx->data = stats_ctx; output_ctx->DeInit = OutputStatsLogDeinit; return output_ctx; }