pull/16430/merge
Catena cyber 13 hours ago committed by GitHub
commit b36381f4c1
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194

@ -75,6 +75,7 @@ static void DetectLuaRegisterTests(void);
static void DetectLuaFree(DetectEngineCtx *, void *);
static int g_lua_ja3_list_id = 0;
static int g_lua_ja3s_list_id = 0;
static int g_lua_http_uri_list_id = 0;
/**
* \brief Registration function for keyword: lua
@ -104,6 +105,12 @@ void DetectLuaRegister(void)
DetectAppLayerInspectEngineRegister(
"ja3s.lua", ALPROTO_QUIC, SIG_FLAG_TOCLIENT, 1, DetectEngineInspectGenericList, NULL);
g_lua_http_uri_list_id = DetectBufferTypeRegister("http.uri.lua");
DetectAppLayerInspectEngineRegister("http.uri.lua", ALPROTO_HTTP1, SIG_FLAG_TOSERVER,
HTP_REQUEST_PROGRESS_LINE, DetectEngineInspectGenericList, NULL);
DetectAppLayerInspectEngineRegisterSubState("http.uri.lua", ALPROTO_HTTP2, SIG_FLAG_TOSERVER,
HTTP2TxTypeStream, HTTP2ProgHeaders, DetectEngineInspectGenericList, NULL);
SCLogDebug("registering lua rule option");
}
@ -112,6 +119,7 @@ void DetectLuaRegister(void)
#define FLAG_DATATYPE_PAYLOAD BIT_U32(1)
#define FLAG_LIST_JA3 BIT_U32(3)
#define FLAG_LIST_JA3S BIT_U32(4)
#define FLAG_LIST_HTTP_URI BIT_U32(5)
#define FLAG_ERROR_LOGGED BIT_U32(23)
#define FLAG_BLOCKED_FUNCTION_LOGGED BIT_U32(24)
#define FLAG_INSTRUCTION_LIMIT_LOGGED BIT_U32(25)
@ -659,6 +667,9 @@ static int DetectLuaSetupPrime(DetectEngineCtx *de_ctx, DetectLuaData *ld, const
ld->flags |= FLAG_LIST_JA3;
} else if (strcmp(k, "ja3s") == 0) {
ld->flags |= FLAG_LIST_JA3S;
} else if (strcmp(k, "http.uri") == 0) {
// TODO/DRAFT/decision-required: Should this rather be named http.request_line ?
ld->flags |= FLAG_LIST_HTTP_URI;
} else if (strcmp(k, "packet") == 0) {
ld->flags |= FLAG_DATATYPE_PACKET;
} else if (strcmp(k, "payload") == 0) {
@ -770,6 +781,8 @@ static int DetectLuaSetup (DetectEngineCtx *de_ctx, Signature *s, const char *st
list = g_lua_ja3_list_id;
} else if (lua->flags & FLAG_LIST_JA3S) {
list = g_lua_ja3s_list_id;
} else if (lua->flags & FLAG_LIST_HTTP_URI) {
list = g_lua_http_uri_list_id;
}
}

@ -31,16 +31,13 @@
static const char htp_tx[] = "suricata:http:tx";
struct LuaTx {
htp_tx_t *tx;
void *tx;
AppProto alproto;
};
static int LuaHttpGetTx(lua_State *luastate)
static int LuaHttpGetTxProtoChecked(Flow *flow, lua_State *luastate)
{
if (!LuaStateNeedProto(luastate, ALPROTO_HTTP1)) {
return LuaCallbackError(luastate, "error: protocol not http");
}
htp_tx_t *tx = LuaStateGetTX(luastate);
void *tx = LuaStateGetTX(luastate);
if (tx == NULL) {
return LuaCallbackError(luastate, "error: no tx available");
}
@ -50,6 +47,7 @@ static int LuaHttpGetTx(lua_State *luastate)
}
ltx->tx = tx;
ltx->alproto = flow->alproto;
luaL_getmetatable(luastate, htp_tx);
lua_setmetatable(luastate, -2);
@ -57,6 +55,46 @@ static int LuaHttpGetTx(lua_State *luastate)
return 1;
}
static int LuaHttpGetTx(lua_State *luastate)
{
Flow *flow = LuaStateGetFlow(luastate);
if (flow == NULL)
return LuaCallbackError(luastate, "internal error: no flow");
if (flow->alproto != ALPROTO_HTTP1 && flow->alproto != ALPROTO_HTTP2 &&
flow->alproto != ALPROTO_DOH2) {
return LuaCallbackError(luastate, "error: protocol not http");
}
return LuaHttpGetTxProtoChecked(flow, luastate);
}
static int LuaHttpGetHttp1Tx(lua_State *luastate)
{
Flow *flow = LuaStateGetFlow(luastate);
if (flow == NULL)
return LuaCallbackError(luastate, "internal error: no flow");
if (flow->alproto != ALPROTO_HTTP1) {
return LuaCallbackError(luastate, "error: protocol not http");
}
return LuaHttpGetTxProtoChecked(flow, luastate);
}
static int LuaHttpGetHttp2Tx(lua_State *luastate)
{
Flow *flow = LuaStateGetFlow(luastate);
if (flow == NULL)
return LuaCallbackError(luastate, "internal error: no flow");
if (flow->alproto != ALPROTO_HTTP2 && flow->alproto != ALPROTO_DOH2) {
return LuaCallbackError(luastate, "error: protocol not http");
}
return LuaHttpGetTxProtoChecked(flow, luastate);
}
static int LuaHttpGetRequestHost(lua_State *luastate)
{
struct LuaTx *tx = luaL_testudata(luastate, 1, htp_tx);
@ -64,6 +102,10 @@ static int LuaHttpGetRequestHost(lua_State *luastate)
lua_pushnil(luastate);
return 1;
}
if (tx->alproto != ALPROTO_HTTP1) {
lua_pushnil(luastate);
return 1;
}
const struct bstr *host = htp_tx_request_hostname(tx->tx);
if (host == NULL) {
lua_pushnil(luastate);
@ -80,6 +122,16 @@ static int LuaHttpGetRequestUriRaw(lua_State *luastate)
lua_pushnil(luastate);
return 1;
}
if (tx->alproto == ALPROTO_HTTP2 || tx->alproto == ALPROTO_DOH2) {
uint32_t b_len = 0;
const uint8_t *b = NULL;
if (SCHttp2TxGetUri(tx->tx, &b, &b_len) != 1) {
lua_pushnil(luastate);
return 1;
}
return LuaPushStringBuffer(luastate, b, b_len);
} // else ALPROTO_HTTP1
const struct bstr *uri = htp_tx_request_uri(tx->tx);
if (uri == NULL) {
lua_pushnil(luastate);
@ -96,6 +148,17 @@ static int LuaHttpGetRequestUriNormalized(lua_State *luastate)
lua_pushnil(luastate);
return 1;
}
if (tx->alproto == ALPROTO_HTTP2 || tx->alproto == ALPROTO_DOH2) {
uint32_t b_len = 0;
const uint8_t *b = NULL;
if (SCHttp2TxGetUri(tx->tx, &b, &b_len) != 1) {
lua_pushnil(luastate);
return 1;
}
return LuaPushStringBuffer(luastate, b, b_len);
} // else ALPROTO_HTTP1
bstr *request_uri_normalized = (bstr *)htp_tx_normalized_uri(tx->tx);
if (request_uri_normalized == NULL || bstr_ptr(request_uri_normalized) == NULL ||
@ -113,6 +176,16 @@ static int LuaHttpGetRequestLine(lua_State *luastate)
lua_pushnil(luastate);
return 1;
}
if (tx->alproto == ALPROTO_HTTP2 || tx->alproto == ALPROTO_DOH2) {
uint32_t b_len = 0;
const uint8_t *b = NULL;
if (SCHttp2TxGetRequestLine(tx->tx, &b, &b_len) != 1) {
lua_pushnil(luastate);
return 1;
}
return LuaPushStringBuffer(luastate, b, b_len);
} // else ALPROTO_HTTP1
const struct bstr *line = htp_tx_request_line(tx->tx);
if (line == NULL) {
@ -130,6 +203,10 @@ static int LuaHttpGetResponseLine(lua_State *luastate)
lua_pushnil(luastate);
return 1;
}
if (tx->alproto != ALPROTO_HTTP1) {
lua_pushnil(luastate);
return 1;
}
const struct bstr *line = htp_tx_response_line(tx->tx);
if (line == NULL) {
@ -147,6 +224,10 @@ static int LuaHttpGetHeader(lua_State *luastate, int dir)
lua_pushnil(luastate);
return 1;
}
if (tx->alproto != ALPROTO_HTTP1) {
lua_pushnil(luastate);
return 1;
}
/* since arg was added at last, it must be on top of the stack */
const char *name = LuaGetStringArgument(luastate, lua_gettop(luastate));
@ -185,6 +266,10 @@ static int LuaHttpGetRawHeaders(lua_State *luastate, int dir)
lua_pushnil(luastate);
return 1;
}
if (tx->alproto != ALPROTO_HTTP1) {
lua_pushnil(luastate);
return 1;
}
HtpTxUserData *htud = (HtpTxUserData *)htp_tx_get_user_data(tx->tx);
uint8_t *raw = htud->request_headers_raw;
@ -217,6 +302,10 @@ static int LuaHttpGetHeaders(lua_State *luastate, int dir)
lua_pushnil(luastate);
return 1;
}
if (tx->alproto != ALPROTO_HTTP1) {
lua_pushnil(luastate);
return 1;
}
const htp_headers_t *table = htp_tx_request_headers(tx->tx);
if (dir == 1)
@ -258,6 +347,10 @@ static int LuaHttpGetBody(lua_State *luastate, int dir)
lua_pushnil(luastate);
return 1;
}
if (tx->alproto != ALPROTO_HTTP1) {
lua_pushnil(luastate);
return 1;
}
HtpTxUserData *htud = (HtpTxUserData *)htp_tx_get_user_data(tx->tx);
@ -329,6 +422,8 @@ static const struct luaL_Reg txlib[] = {
static const struct luaL_Reg htplib[] = {
// clang-format off
{"get_tx", LuaHttpGetTx },
{"get_http1_tx", LuaHttpGetHttp1Tx },
{"get_http2_tx", LuaHttpGetHttp2Tx },
{NULL, NULL,},
// clang-format on
};

Loading…
Cancel
Save