From ee71110afa0e6f0dce3044956dd9e222baa764de Mon Sep 17 00:00:00 2001 From: Anoop Saldanha Date: Fri, 6 Apr 2012 00:37:16 +0530 Subject: [PATCH] update handling negative offsets in byte_extract. Also improve validation in byte_extract to not extract values out of the buffer range --- src/detect-byte-extract.c | 31 +++++++++++++++++++- src/detect-engine-payload.c | 66 +++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 95 insertions(+), 2 deletions(-) diff --git a/src/detect-byte-extract.c b/src/detect-byte-extract.c index 9ccbf3f..0d6e71c 100644 --- a/src/detect-byte-extract.c +++ b/src/detect-byte-extract.c @@ -77,7 +77,7 @@ #define PARSE_REGEX "^" \ "\\s*([0-9]+)\\s*" \ - ",\\s*([0-9]+)\\s*" \ + ",\\s*(-?[0-9]+)\\s*" \ ",\\s*([^\\s,]+)\\s*" \ "(?:(?:,\\s*([^\\s,]+)\\s*)|(?:,\\s*([^\\s,]+)\\s+([^\\s,]+)\\s*))?" \ "(?:(?:,\\s*([^\\s,]+)\\s*)|(?:,\\s*([^\\s,]+)\\s+([^\\s,]+)\\s*))?" \ @@ -175,7 +175,7 @@ int DetectByteExtractDoMatch(DetectEngineThreadCtx *det_ctx, SigMatch *sm, } /* Validate that the to-be-extracted is within the packet */ - if (data->nbytes > len) { + if (ptr < payload || data->nbytes > len) { SCLogDebug("Data not within payload pkt=%p, ptr=%p, len=%"PRIu32", nbytes=%d", payload, ptr, len, data->nbytes); return 0; @@ -4757,6 +4757,32 @@ static int DetectByteExtractTest62(void) return result; } +int DetectByteExtractTest63(void) +{ + int result = 0; + + DetectByteExtractData *bed = DetectByteExtractParse("4, -2, one"); + if (bed == NULL) + goto end; + + if (bed->nbytes != 4 || + bed->offset != -2 || + strcmp(bed->name, "one") != 0 || + bed->flags != 0 || + bed->endian != DETECT_BYTE_EXTRACT_ENDIAN_DEFAULT || + bed->base != DETECT_BYTE_EXTRACT_BASE_NONE || + bed->align_value != 0 || + bed->multiplier_value != DETECT_BYTE_EXTRACT_MULTIPLIER_DEFAULT) { + goto end; + } + + result = 1; + end: + if (bed != NULL) + DetectByteExtractFree(bed); + return result; +} + #endif /* UNITTESTS */ void DetectByteExtractRegisterTests(void) @@ -4832,6 +4858,7 @@ void DetectByteExtractRegisterTests(void) UtRegisterTest("DetectByteExtractTest60", DetectByteExtractTest60, 1); UtRegisterTest("DetectByteExtractTest61", DetectByteExtractTest61, 1); UtRegisterTest("DetectByteExtractTest62", DetectByteExtractTest62, 1); + UtRegisterTest("DetectByteExtractTest63", DetectByteExtractTest63, 1); #endif /* UNITTESTS */ return; diff --git a/src/detect-engine-payload.c b/src/detect-engine-payload.c index d1774c2..388f4ad 100644 --- a/src/detect-engine-payload.c +++ b/src/detect-engine-payload.c @@ -815,6 +815,70 @@ end: return result; } +/* + * \test Test negative byte extract. + */ +static int PayloadTestSig25(void) +{ + uint8_t buf[] = { + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x35, /* the last byte is 2 */ + 0x07, 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, + 0x0E, 0x0F, + }; + uint16_t buflen = sizeof(buf); + Packet *p = UTHBuildPacket( buf, buflen, IPPROTO_TCP); + int result = 0; + + char sig[] = "alert tcp any any -> any any (msg:\"dummy\"; " + "content:\"|35 07 08 09|\"; " + "byte_extract:1,-4,one,string,dec,relative; " + "content:\"|0C 0D 0E 0F|\"; distance:one; sid:1;)"; + + if (UTHPacketMatchSigMpm(p, sig, MPM_AC) == 0) { + result = 0; + goto end; + } + + result = 1; + +end: + if (p != NULL) + UTHFreePacket(p); + return result; +} + +/* + * \test Test negative byte extract. + */ +static int PayloadTestSig26(void) +{ + uint8_t buf[] = { + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x35, /* the last byte is 2 */ + 0x07, 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, + 0x0E, 0x0F, + }; + uint16_t buflen = sizeof(buf); + Packet *p = UTHBuildPacket( buf, buflen, IPPROTO_TCP); + int result = 0; + + char sig[] = "alert tcp any any -> any any (msg:\"dummy\"; " + "content:\"|35 07 08 09|\"; " + "byte_extract:1,-3000,one,string,dec,relative; " + "content:\"|0C 0D 0E 0F|\"; distance:one; sid:1;)"; + + if (UTHPacketMatchSigMpm(p, sig, MPM_AC) != 0) { + result = 0; + goto end; + } + + result = 1; + +end: + if (p != NULL) + UTHFreePacket(p); + return result; +} + #endif /* UNITTESTS */ void PayloadRegisterTests(void) { @@ -844,6 +908,8 @@ void PayloadRegisterTests(void) { UtRegisterTest("PayloadTestSig22", PayloadTestSig22, 1); UtRegisterTest("PayloadTestSig23", PayloadTestSig23, 1); UtRegisterTest("PayloadTestSig24", PayloadTestSig24, 1); + UtRegisterTest("PayloadTestSig25", PayloadTestSig25, 1); + UtRegisterTest("PayloadTestSig26", PayloadTestSig26, 1); #endif /* UNITTESTS */ return; -- 1.7.1