lua: document new suricata.dns lua library

Ticket: #7602
pull/12799/head
Jason Ish 8 months ago committed by Victor Julien
parent 1206c1c5af
commit a6b116bcbe

@ -0,0 +1,164 @@
DNS
---
DNS transaction details are exposes to Lua scripts with the
``suricata.dns`` library, For example::
local dns = require("suricata.dns")
Setup
^^^^^
If your purpose is to create a logging script, initialize the buffer as:
::
function init (args)
local needs = {}
needs["protocol"] = "dns"
return needs
end
If you are going to use the script for rule matching, choose one of
the available DNS buffers listed in :ref:`lua-detection` and follow
the pattern:
::
function init (args)
local needs = {}
needs["dns.rrname"] = tostring(true)
return needs
end
Transaction
~~~~~~~~~~~
DNS is transaction based, and the current transaction must be obtained before use::
local tx, err = dns.get_tx()
if tx == err then
print(err)
end
All other functions are methods on the transaction table.
Transaction Methods
~~~~~~~~~~~~~~~~~~~
``answers()``
^^^^^^^^^^^^^
Get the ``answers`` response section as a table of tables.
Example::
local tx = dns.get_tx()
local answers = tx:answers()
if answers ~= nil then
for n, t in pairs(answers) do
rrname = t["rrname"]
rrtype = t["type"]
ttl = t["ttl"]
print ("ANSWER: " .. ts .. " " .. rrname .. " [**] " .. rrtype .. " [**] " ..
ttl .. " [**] " .. srcip .. ":" .. sp .. " -> " ..
dstip .. ":" .. dp)
end
end
``authorities()``
^^^^^^^^^^^^^^^^^
Get the ``authorities`` response section as a table of tables.
Example::
local tx = dns.get_tx()
local authorities = tx:authorities();
if authorities ~= nil then
for n, t in pairs(authorities) do
rrname = t["rrname"]
rrtype = t["type"]
ttl = t["ttl"]
print ("AUTHORITY: " .. ts .. " " .. rrname .. " [**] " .. rrtype .. " [**] " ..
ttl .. " [**] " .. srcip .. ":" .. sp .. " -> " ..
dstip .. ":" .. dp)
end
end
``queries()``
^^^^^^^^^^^^^
Get the ``queries`` request or response section as a table of tables.
Example::
local tx = dns.get_tx()
local queries = tx:queries();
if queries ~= nil then
for n, t in pairs(queries) do
rrname = t["rrname"]
rrtype = t["type"]
print ("QUERY: " .. ts .. " " .. rrname .. " [**] " .. rrtype .. " [**] " ..
"TODO" .. " [**] " .. srcip .. ":" .. sp .. " -> " ..
dstip .. ":" .. dp)
end
end
``rcode()``
^^^^^^^^^^^
Get the ``rcode`` value as an integer.
Example::
local tx = dns.get_tx()
local rcode = tx:rcode()
print (rcode)
``rcode_string()``
^^^^^^^^^^^^^^^^^^
Get the ``rcode`` value as a string.
Example::
local tx = dns.get_tx()
local rcode_string = tx:rcode_string();
print (rcode_string)
``recursion_desired()``
^^^^^^^^^^^^^^^^^^^^^^^
Return the value of the recursion desired (RD) flag as a boolean.
Example::
local tx = dns.get_tx()
if tx:recursion_desired() == true then
print ("RECURSION DESIRED")
end
``rrname()``
^^^^^^^^^^^^
Return the resource name from the first query object.
Example::
local tx = dns.get_tx()
local rrname = tx:rrname()
print(rrname)
``txid()``
^^^^^^^^^^
Return the DNS transaction ID found in the DNS message.
Example::
local tx = dns.get_tx()
local txid = tx:txid()
print(txid)

@ -9,5 +9,6 @@ environment without access to additional modules.
.. toctree::
base64
dns
hashlib
packetlib

@ -297,113 +297,6 @@ HttpGetResponseHeaders
print(n,v)
end
DNS
---
If your purpose is to create a logging script, initialize the buffer as:
::
function init (args)
local needs = {}
needs["protocol"] = "dns"
return needs
end
If you are going to use the script for rule matching, choose one of the available DNS buffers listed in
:ref:`lua-detection` and follow the pattern:
::
function init (args)
local needs = {}
needs["dns.rrname"] = tostring(true)
return needs
end
DnsGetQueries
~~~~~~~~~~~~~
::
dns_query = DnsGetQueries();
if dns_query ~= nil then
for n, t in pairs(dns_query) do
rrname = t["rrname"]
rrtype = t["type"]
print ("QUERY: " .. ts .. " " .. rrname .. " [**] " .. rrtype .. " [**] " ..
"TODO" .. " [**] " .. srcip .. ":" .. sp .. " -> " ..
dstip .. ":" .. dp)
end
end
returns a table of tables
DnsGetAnswers
~~~~~~~~~~~~~
::
dns_answers = DnsGetAnswers();
if dns_answers ~= nil then
for n, t in pairs(dns_answers) do
rrname = t["rrname"]
rrtype = t["type"]
ttl = t["ttl"]
print ("ANSWER: " .. ts .. " " .. rrname .. " [**] " .. rrtype .. " [**] " ..
ttl .. " [**] " .. srcip .. ":" .. sp .. " -> " ..
dstip .. ":" .. dp)
end
end
returns a table of tables
DnsGetAuthorities
~~~~~~~~~~~~~~~~~
::
dns_auth = DnsGetAuthorities();
if dns_auth ~= nil then
for n, t in pairs(dns_auth) do
rrname = t["rrname"]
rrtype = t["type"]
ttl = t["ttl"]
print ("AUTHORITY: " .. ts .. " " .. rrname .. " [**] " .. rrtype .. " [**] " ..
ttl .. " [**] " .. srcip .. ":" .. sp .. " -> " ..
dstip .. ":" .. dp)
end
end
returns a table of tables
DnsGetRcode
~~~~~~~~~~~
::
rcode = DnsGetRcode();
if rcode == nil then
return 0
end
print (rcode)
returns a lua string with the error message, or nil
DnsGetRecursionDesired
~~~~~~~~~~~~~~~~~~~~~~
::
if DnsGetRecursionDesired() == true then
print ("RECURSION DESIRED")
end
returns a bool
TLS
---

@ -39,15 +39,15 @@ static int LuaDnsGetTx(lua_State *L)
{
if (!(LuaStateNeedProto(L, ALPROTO_DNS))) {
return LuaCallbackError(L, "error: protocol not dns");
}
}
RSDNSTransaction *tx = LuaStateGetTX(L);
if (tx == NULL) {
return LuaCallbackError(L, "error: no tx available");
}
}
struct LuaTx *ltx = (struct LuaTx *)lua_newuserdata(L, sizeof(*ltx));
if (ltx == NULL) {
return LuaCallbackError(L, "error: fail to allocate user data");
}
}
ltx->tx = tx;
luaL_getmetatable(L, dns_tx);
@ -62,9 +62,9 @@ static int LuaDnsTxGetRrname(lua_State *L)
if (tx == NULL) {
lua_pushnil(L);
return 1;
}
}
return SCDnsLuaGetRrname(L, tx->tx);
}
}
static int LuaDnsTxGetTxid(lua_State *L)
{
@ -72,7 +72,7 @@ static int LuaDnsTxGetTxid(lua_State *L)
if (tx == NULL) {
lua_pushnil(L);
return 1;
}
}
return SCDnsLuaGetTxId(L, tx->tx);
}
@ -82,7 +82,7 @@ static int LuaDnsTxGetRcode(lua_State *L)
if (tx == NULL) {
lua_pushnil(L);
return 1;
}
}
return SCDnsLuaGetRcode(L, tx->tx);
}
@ -92,7 +92,7 @@ static int LuaDnsTxGetRcodeString(lua_State *L)
if (tx == NULL) {
lua_pushnil(L);
return 1;
}
}
return SCDnsLuaGetRcodeString(L, tx->tx);
}
@ -102,7 +102,7 @@ static int LuaDnsTxGetRecursionDesired(lua_State *L)
if (tx == NULL) {
lua_pushnil(L);
return 1;
}
}
uint16_t flags = SCDnsTxGetResponseFlags(tx->tx);
int recursion_desired = flags & 0x0080 ? 1 : 0;
lua_pushboolean(L, recursion_desired);
@ -115,7 +115,7 @@ static int LuaDnsTxGetQueries(lua_State *L)
if (tx == NULL) {
lua_pushnil(L);
return 1;
}
}
return SCDnsLuaGetQueryTable(L, tx->tx);
}
@ -125,7 +125,7 @@ static int LuaDnsTxGetAnswers(lua_State *L)
if (tx == NULL) {
lua_pushnil(L);
return 1;
}
}
return SCDnsLuaGetAnswerTable(L, tx->tx);
}
@ -135,7 +135,7 @@ static int LuaDnsTxGetAuthorities(lua_State *L)
if (tx == NULL) {
lua_pushnil(L);
return 1;
}
}
return SCDnsLuaGetAuthorityTable(L, tx->tx);
}
@ -151,7 +151,7 @@ static const struct luaL_Reg txlib[] = {
{ "txid", LuaDnsTxGetTxid },
{ NULL, NULL, }
// clang-format on
};
};
static const struct luaL_Reg dnslib[] = {
// clang-format off

Loading…
Cancel
Save