static int Norm_IP6 (NormalizerContext* c, Packet * p, uint8_t layer, int changes) { IP6RawHdr* h = (IP6RawHdr*)(p->layers[layer].start); NormMode mode = getNormMode(c); if ( Norm_IsEnabled(c, NORM_IP6_TTL) ) { if ( h->ip6hops < ScMinTTL() ) { if ( mode == NORM_MODE_ON ) { h->ip6hops = ScNewTTL(); p->error_flags &= ~PKT_ERR_BAD_TTL; changes++; } normStats[PC_IP6_TTL][mode]++; sfBase.iPegs[PERF_COUNT_IP6_TTL][mode]++; } } return changes; }
static int Norm_IP4 (NormalizerContext* c, Packet * p, uint8_t layer, int changes) { IPHdr* h = (IPHdr*)(p->layers[layer].start); uint16_t fragbits = ntohs(h->ip_off); uint16_t origbits = fragbits; NormMode mode = getNormMode(c); if ( Norm_IsEnabled(c, NORM_IP4_TRIM) && (layer == 1) ) { uint32_t len = p->layers[0].length + ntohs(h->ip_len); if ( (len < p->pkth->pktlen) && ( (len >= ETH_MIN_LEN) || (p->pkth->pktlen > ETH_MIN_LEN) ) ) { if ( mode == NORM_MODE_ON ) { ((DAQ_PktHdr_t*)p->pkth)->pktlen = (len < ETH_MIN_LEN) ? ETH_MIN_LEN : len; p->packet_flags |= PKT_RESIZED; changes++; } normStats[PC_IP4_TRIM][mode]++; sfBase.iPegs[PERF_COUNT_IP4_TRIM][mode]++; } } if ( Norm_IsEnabled(c, NORM_IP4_TOS) ) { if ( h->ip_tos ) { if ( mode == NORM_MODE_ON ) { h->ip_tos = 0; changes++; } normStats[PC_IP4_TOS][mode]++; sfBase.iPegs[PERF_COUNT_IP4_TOS][mode]++; } } #if 0 if ( Norm_IsEnabled(c, NORM_IP4_ID) ) { // TBD implement IP ID normalization / randomization } #endif if ( Norm_IsEnabled(c, NORM_IP4_DF) ) { if ( fragbits & IP4_FLAG_DF ) { if ( mode == NORM_MODE_ON ) { fragbits &= ~IP4_FLAG_DF; changes++; } normStats[PC_IP4_DF][mode]++; sfBase.iPegs[PERF_COUNT_IP4_DF][mode]++; } } if ( Norm_IsEnabled(c, NORM_IP4_RF) ) { if ( fragbits & IP4_FLAG_RF ) { if ( mode == NORM_MODE_ON ) { fragbits &= ~IP4_FLAG_RF; changes++; } normStats[PC_IP4_RF][mode]++; sfBase.iPegs[PERF_COUNT_IP4_RF][mode]++; } } if ( fragbits != origbits ) { h->ip_off = htons(fragbits); } if ( Norm_IsEnabled(c, NORM_IP4_TTL) ) { if ( h->ip_ttl < ScMinTTL() ) { if ( mode == NORM_MODE_ON ) { h->ip_ttl = ScNewTTL(); p->error_flags &= ~PKT_ERR_BAD_TTL; changes++; } normStats[PC_IP4_TTL][mode]++; sfBase.iPegs[PERF_COUNT_IP4_TTL][mode]++; } } if ( p->layers[layer].length > IP_HEADER_LEN ) { if ( mode == NORM_MODE_ON ) { uint8_t* opts = p->layers[layer].start + IP_HEADER_LEN; uint8_t len = p->layers[layer].length - IP_HEADER_LEN; // expect len > 0 because IHL yields a multiple of 4 memset(opts, IPOPT_NOP, len); changes++; } normStats[PC_IP4_OPTS][mode]++; sfBase.iPegs[PERF_COUNT_IP4_OPTS][mode]++; } return changes; }
static ENC_STATUS IP4_Encode (EncState* enc, Buffer* in, Buffer* out) { int len; uint32_t start = out->end; IPHdr* hi = (IPHdr*)enc->p->layers[enc->layer-1].start; IPHdr* ho = (IPHdr*)(out->base + out->end); PROTO_ID next = NextEncoder(enc); UPDATE_BOUND(out, sizeof(*ho)); len = GET_IP_HDR_LEN(hi) - sizeof(*hi); ho->ip_verhl = 0x45; ho->ip_off = 0; ho->ip_id = IpId_Next(); ho->ip_tos = hi->ip_tos; ho->ip_proto = hi->ip_proto; if ( FORWARD(enc) ) { uint8_t ttl = AdjTTL(hi->ip_ttl); ho->ip_src.s_addr = hi->ip_src.s_addr; ho->ip_dst.s_addr = hi->ip_dst.s_addr; if ( enc->p->ssnptr ) ttl = GetTTL(enc); #ifdef NORMALIZER if ( ttl < ScMinTTL() && ScNewTTL() ) ttl = ScNewTTL(); #endif ho->ip_ttl = ttl; } else { uint8_t ttl = MAX_TTL; ho->ip_src.s_addr = hi->ip_dst.s_addr; ho->ip_dst.s_addr = hi->ip_src.s_addr; if ( enc->p->ssnptr ) ttl = GetTTL(enc); #ifdef NORMALIZER if ( ttl < ScMinTTL() && ScNewTTL() ) ttl = ScNewTTL(); #endif ho->ip_ttl = ttl; } enc->ip_hdr = (uint8_t*)hi; enc->ip_len = IP_HLEN(hi) << 2; if ( next < PROTO_MAX ) { int err = encoders[next].fencode(enc, in, out); if ( err ) return err; } if ( enc->proto ) { ho->ip_proto = enc->proto; enc->proto = 0; } len = out->end - start; ho->ip_len = htons((u_int16_t)len); ip_checksum(ho, len); return ENC_OK; }