arguments.o lwres.o pdns_recursor.o recursor_cache.o dnsparser.o \
dnswriter.o dnsrecords.o rcpgenerator.o base64.o zoneparser-tng.o \
rec_channel.o rec_channel_rec.o selectmplexer.o sillyrecords.o \
-dns_random.o aescrypt.o aeskey.o aes_modes.o aestab.o lua-pdns-recursor.o \
-randomhelper.o recpacketcache.o dns.o reczones.o base32.o nsecrecords.o \
-dnslabeltext.o
+dns_random.o aescrypt.o aeskey.o aes_modes.o aestab.o dnslabeltext.o \
+lua-pdns.o lua-recursor.o randomhelper.o recpacketcache.o dns.o \
+reczones.o base32.o nsecrecords.o
REC_CONTROL_OBJECTS=rec_channel.o rec_control.o arguments.o misc.o \
unix_utility.o logger.o qtype.o
aes/aestab.c aes/aestab.h aes/brg_endian.h aes/brg_types.h aes/dns_random.cc \
randomhelper.cc namespaces.hh nsecrecords.cc base32.cc dbdnsseckeeper.cc dnssecinfra.cc \
dnsseckeeper.hh dnssecinfra.hh base32.hh dns.cc dnssecsigner.cc polarrsakeyinfra.cc md5.cc \
-md5.hh signingpipe.cc signingpipe.hh dnslabeltext.cc lua-pdns-recursor.cc serialtweaker.cc \
+md5.hh signingpipe.cc signingpipe.hh dnslabeltext.cc lua-pdns.cc lua-auth.cc serialtweaker.cc \
ednssubnet.cc ednssubnet.hh cachecleaner.hh dnslabel.hh dnslabel.cc
#
base64.cc base64.hh zoneparser-tng.cc zoneparser-tng.hh rec_channel.cc rec_channel.hh \
rec_channel_rec.cc selectmplexer.cc epollmplexer.cc sillyrecords.cc htimer.cc htimer.hh \
aes/dns_random.cc aes/aescrypt.c aes/aeskey.c aes/aestab.c aes/aes_modes.c \
-lua-pdns-recursor.cc lua-pdns-recursor.hh randomhelper.cc \
+lua-pdns.cc lua-pdns.hh lua-recursor.cc lua-recursor.hh randomhelper.cc \
recpacketcache.cc recpacketcache.hh dns.cc nsecrecords.cc base32.cc cachecleaner.hh
pdns_recursor_LDFLAGS= $(LUA_LIBS)
::arg().set("max-cache-entries", "Maximum number of cache entries")="1000000";
::arg().set("entropy-source", "If set, read entropy from this file")="/dev/urandom";
+
+ ::arg().set("lua-prequery-script", "Lua script with prequery handler")="";
}
void declareStats(void)
recursor_cache.hh rec_channel.hh qtype.hh misc.hh dns.hh syncres.hh \
sstuff.hh mtasker.hh mtasker.cc lwres.hh logger.hh ahuexception.hh \
mplexer.hh win32_mtasker.hh win32_utility.cc ntservice.hh singleton.hh \
-recursorservice.hh dns_random.hh lua-pdns-recursor.hh namespaces.hh \
+recursorservice.hh dns_random.hh lua-pdns.hh lua-recursor.hh namespaces.hh \
recpacketcache.hh base32.hh cachecleaner.hh"
CFILES="syncres.cc misc.cc unix_utility.cc qtype.cc \
base64.cc zoneparser-tng.cc rec_channel.cc rec_channel_rec.cc rec_control.cc \
selectmplexer.cc epollmplexer.cc kqueuemplexer.cc portsmplexer.cc pdns_hw.cc \
win32_mtasker.cc win32_rec_channel.cc win32_logger.cc ntservice.cc \
-recursorservice.cc sillyrecords.cc lua-pdns-recursor.cc randomhelper.cc \
+recursorservice.cc sillyrecords.cc lua-pdns.cc lua-recursor.cc randomhelper.cc \
devpollmplexer.cc recpacketcache.cc dns.cc reczones.cc base32.cc nsecrecords.cc \
dnslabeltext.cc"
--- /dev/null
+#include "lua-auth.hh"
+
+#if !defined(PDNS_ENABLE_LUA)
+
+AuthLua::AuthLua(const std::string &fname)
+ : PowerDNSLua(fname)
+{
+ // empty
+}
+
+bool AuthLua::prequery(DNSPacket *p)
+{
+ return false;
+}
+
+bool AuthLua::axfrfilter(const ComboAddress& remote, const string& zone, const DNSResourceRecord& in, vector<DNSResourceRecord>& out)
+{
+ return false;
+}
+
+#else
+
+
+extern "C" {
+#undef L
+/* Include the Lua API header files. */
+#include <lua.h>
+#include <lauxlib.h>
+#include <lualib.h>
+}
+
+#include <stdlib.h>
+#include <stdio.h>
+#include <string>
+#include <vector>
+#include <stdexcept>
+#include <boost/foreach.hpp>
+#include "logger.hh"
+#include "namespaces.hh"
+
+AuthLua::AuthLua(const std::string &fname)
+ : PowerDNSLua(fname)
+{
+ registerLuaDNSPacket();
+}
+
+bool AuthLua::axfrfilter(const ComboAddress& remote, const string& zone, const DNSResourceRecord& in, vector<DNSResourceRecord>& out)
+{
+ lua_getglobal(d_lua, "axfrfilter");
+ if(!lua_isfunction(d_lua, -1)) {
+ cerr<<"No such function 'axfrfilter'\n";
+ lua_pop(d_lua, 1);
+ return false;
+ }
+
+ lua_pushstring(d_lua, remote.toString().c_str() );
+ lua_pushstring(d_lua, zone.c_str() );
+ lua_pushstring(d_lua, in.qname.c_str() );
+ lua_pushnumber(d_lua, in.qtype.getCode() );
+ lua_pushnumber(d_lua, in.ttl );
+ lua_pushnumber(d_lua, in.priority );
+ lua_pushstring(d_lua, in.content.c_str() );
+
+ if(lua_pcall(d_lua, 7, 2, 0)) { // error
+ string error=string("lua error in axfrfilter: ")+lua_tostring(d_lua, -1);
+ lua_pop(d_lua, 1);
+ throw runtime_error(error);
+ return false;
+ }
+
+ int newres = (int)lua_tonumber(d_lua, 1); // did we handle it?
+ if(newres < 0) {
+ //cerr << "handler did not handle"<<endl;
+ lua_pop(d_lua, 2);
+ return false;
+ }
+
+ /* get the result */
+ DNSResourceRecord rr;
+ rr.d_place = DNSResourceRecord::ANSWER;
+ rr.ttl = 3600;
+ rr.domain_id = in.domain_id;
+
+ out.clear();
+
+ /* 1 2 3 4 */
+ /* stack: boolean table key row */
+
+#ifndef LUA_VERSION_NUM
+ int tableLen = luaL_getn(d_lua, 2);
+#else
+ int tableLen = lua_objlen(d_lua, 2);
+#endif
+ cerr<<"Returned "<<tableLen<<" rows"<<endl;
+ for(int n=1; n < tableLen + 1; ++n) {
+ lua_pushnumber(d_lua, n);
+ lua_gettable(d_lua, 2);
+
+ uint32_t tmpnum=0;
+ if(!getFromTable("qtype", tmpnum))
+ rr.qtype=QType::A;
+ else
+ rr.qtype=tmpnum;
+
+ getFromTable("content", rr.content);
+ if(!getFromTable("ttl", rr.ttl))
+ rr.ttl=3600;
+
+ if(!getFromTable("qname", rr.qname))
+ rr.qname = zone;
+
+ if(!getFromTable("place", tmpnum))
+ rr.d_place = DNSResourceRecord::ANSWER;
+ else
+ rr.d_place = (DNSResourceRecord::Place) tmpnum;
+
+ /* removes 'value'; keeps 'key' for next iteration */
+ lua_pop(d_lua, 1); // table
+
+ // cerr<<"Adding content '"<<rr.content<<"' with place "<<(int)rr.d_place<<" \n";
+ out.push_back(rr);
+ }
+ lua_pop(d_lua, 2); // c
+ return true;
+}
+
+struct LuaDNSPacket
+{
+ DNSPacket *d_p;
+};
+
+static DNSPacket* ldp_checkDNSPacket(lua_State *L) {
+ void *ud = luaL_checkudata(L, 1, "LuaDNSPacket");
+ luaL_argcheck(L, ud != NULL, 1, "`LuaDNSPacket' expected");
+ return ((LuaDNSPacket *)ud)->d_p;
+}
+
+static int ldp_setRcode(lua_State *L) {
+ DNSPacket *p=ldp_checkDNSPacket(L);
+ int rcode = luaL_checkint(L, 2);
+ p->setRcode(rcode);
+ return 0;
+}
+
+static int ldp_getQuestion(lua_State *L) {
+ DNSPacket *p=ldp_checkDNSPacket(L);
+ lua_pushstring(L, p->qdomain.c_str());
+ lua_pushnumber(L, p->qtype.getCode());
+ return 2;
+}
+
+static int ldp_addRecords(lua_State *L) {
+ DNSPacket *p=ldp_checkDNSPacket(L);
+ vector<DNSResourceRecord> rrs;
+ popResourceRecordsTable(L, "BOGUS", rrs);
+ BOOST_FOREACH(DNSResourceRecord rr, rrs) {
+ p->addRecord(rr);
+ }
+ return 0;
+}
+
+static const struct luaL_reg ldp_methods [] = {
+ {"setRcode", ldp_setRcode},
+ {"getQuestion", ldp_getQuestion},
+ {"addRecords", ldp_addRecords},
+ {NULL, NULL}
+ };
+
+void AuthLua::registerLuaDNSPacket(void) {
+
+ luaL_newmetatable(d_lua, "LuaDNSPacket");
+
+ lua_pushstring(d_lua, "__index");
+ lua_pushvalue(d_lua, -2); /* pushes the metatable */
+ lua_settable(d_lua, -3); /* metatable.__index = metatable */
+
+ luaL_openlib(d_lua, NULL, ldp_methods, 0);
+
+ lua_pop(d_lua, 1);
+}
+
+DNSPacket* AuthLua::prequery(DNSPacket *p)
+{
+ lua_getglobal(d_lua,"prequery");
+ if(!lua_isfunction(d_lua, -1)) {
+ cerr<<"No such function 'prequery'\n";
+ lua_pop(d_lua, 1);
+ return 0;
+ }
+
+ DNSPacket *r=0;
+ // allocate a fresh packet and prefill the question
+ r=p->replyPacket();
+
+ // wrap it
+ LuaDNSPacket* lua_dp = (LuaDNSPacket *)lua_newuserdata(d_lua, sizeof(LuaDNSPacket));
+ lua_dp->d_p=r;
+
+ // make it of the right type
+ luaL_getmetatable(d_lua, "LuaDNSPacket");
+ lua_setmetatable(d_lua, -2);
+
+ if(lua_pcall(d_lua, 1, 1, 0)) { // error
+ string error=string("lua error in prequery: ")+lua_tostring(d_lua, -1);
+ theL()<<Logger::Error<<error<<endl;
+
+ lua_pop(d_lua, 1);
+ throw runtime_error(error);
+ return 0;
+ }
+ bool res=lua_toboolean(d_lua, 1);
+ lua_pop(d_lua, 1);
+ if(res) {
+ // prequery created our response, use it
+ theL()<<Logger::Info<<"overriding query from lua prequery result"<<endl;
+ return r;
+ }
+ else
+ {
+ // prequery wanted nothing to do with this question
+ delete r;
+ return 0;
+ }
+}
+
+
+#endif
\ No newline at end of file
--- /dev/null
+#ifndef PDNS_LUA_AUTH_HH
+#define PDNS_LUA_AUTH_HH
+#include "dns.hh"
+#include "iputils.hh"
+#include "dnspacket.hh"
+#include "lua-pdns.hh"
+
+class AuthLua : public PowerDNSLua
+{
+public:
+ explicit AuthLua(const std::string& fname);
+ // ~AuthLua();
+ bool axfrfilter(const ComboAddress& remote, const string& zone, const DNSResourceRecord& in, vector<DNSResourceRecord>& out);
+ DNSPacket* prequery(DNSPacket *p);
+
+private:
+ void registerLuaDNSPacket(void);
+};
+
+#endif
+++ /dev/null
-#include "lua-pdns-recursor.hh"
-// #include "syncres.hh"
-#include <boost/foreach.hpp>
-
-// to avoid including all of syncres.hh
-int directResolve(const std::string& qname, const QType& qtype, int qclass, vector<DNSResourceRecord>& ret);
-
-#if !defined(PDNS_ENABLE_LUA)
-
-// stub implementation
-
-PowerDNSLua::PowerDNSLua(const std::string& fname)
-{
- throw runtime_error("Lua support disabled");
-}
-
-bool PowerDNSLua::nxdomain(const ComboAddress& remote,const ComboAddress& local, const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable)
-{
- return false;
-}
-
-bool PowerDNSLua::nodata(const ComboAddress& remote,const ComboAddress& local, const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable)
-{
- return false;
-}
-
-bool PowerDNSLua::postresolve(const ComboAddress& remote,const ComboAddress& local, const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable)
-{
- return false;
-}
-
-
-bool PowerDNSLua::preresolve(const ComboAddress& remote, const ComboAddress& local, const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable)
-{
- return false;
-}
-
-bool PowerDNSLua::axfrfilter(const ComboAddress& remote, const string& zone, const DNSResourceRecord& in, vector<DNSResourceRecord>& out)
-{
- return false;
-}
-
-
-PowerDNSLua::~PowerDNSLua()
-{
-
-}
-
-#else
-
-extern "C" {
-#undef L
-/* Include the Lua API header files. */
-#include <lua.h>
-#include <lauxlib.h>
-#include <lualib.h>
-}
-
-#include <stdlib.h>
-#include <stdio.h>
-#include <string>
-#include <vector>
-#include <stdexcept>
-#include "logger.hh"
-#include "namespaces.hh"
-
-bool netmaskMatchTable(lua_State* lua, const std::string& ip)
-{
- lua_pushnil(lua); /* first key */
- while (lua_next(lua, 2) != 0) {
- string netmask=lua_tostring(lua, -1);
- Netmask nm(netmask);
- ComboAddress ca(ip);
- lua_pop(lua, 1);
-
- if(nm.match(ip))
- return true;
- }
- return false;
-}
-
-
-
-void pushResourceRecordsTable(lua_State* lua, const vector<DNSResourceRecord>& records)
-{
- // make a table of tables
- lua_newtable(lua);
-
- int pos=0;
- BOOST_FOREACH(const DNSResourceRecord& rr, records)
- {
- // row number, used by 'lua_settable' below
- lua_pushnumber(lua, ++pos);
- // "row" table
- lua_newtable(lua);
-
- lua_pushstring(lua, rr.qname.c_str());
- lua_setfield(lua, -2, "qname"); // pushes value at the top of the stack to the table immediately below that (-1 = top, -2 is below)
-
- lua_pushstring(lua, rr.content.c_str());
- lua_setfield(lua, -2, "content");
-
- lua_pushnumber(lua, rr.qtype.getCode());
- lua_setfield(lua, -2, "qtype");
-
- lua_pushnumber(lua, rr.ttl);
- lua_setfield(lua, -2, "ttl");
-
- lua_pushnumber(lua, rr.d_place);
- lua_setfield(lua, -2, "place");
-
- lua_settable(lua, -3); // pushes the table we just built into the master table at position pushed above
- }
-}
-
-extern "C" {
-
-int netmaskMatchLua(lua_State *lua)
-{
- bool result=false;
- if(lua_gettop(lua) >= 2) {
- string ip=lua_tostring(lua, 1);
- if(lua_istable(lua, 2)) {
- result = netmaskMatchTable(lua, ip);
- }
- else {
- for(int n=2 ; n <= lua_gettop(lua); ++n) {
- string netmask=lua_tostring(lua, n);
- Netmask nm(netmask);
- ComboAddress ca(ip);
-
- result = nm.match(ip);
- if(result)
- break;
- }
- }
- }
-
- lua_pushboolean(lua, result);
- return 1;
-}
-
-int getLocalAddressLua(lua_State* lua)
-{
- lua_getfield(lua, LUA_REGISTRYINDEX, "__PowerDNSLua");
- PowerDNSLua* pl = (PowerDNSLua*)lua_touserdata(lua, -1);
-
- lua_pushstring(lua, pl->getLocal().toString().c_str());
- return 1;
-}
-
-// called by lua to indicate that this answer is 'variable' and should not be cached
-int setVariableLua(lua_State* lua)
-{
- lua_getfield(lua, LUA_REGISTRYINDEX, "__PowerDNSLua");
- PowerDNSLua* pl = (PowerDNSLua*)lua_touserdata(lua, -1);
- pl->setVariable();
- return 0;
-}
-
-int logLua(lua_State *lua)
-{
- if(lua_gettop(lua) >= 1) {
- string message=lua_tostring(lua, 1);
- theL()<<Logger::Error<<"From Lua script: "<<message<<endl;
- }
- return 0;
-}
-}
-
-int getFakeAAAARecords(const std::string& qname, const std::string& prefix, vector<DNSResourceRecord>& ret)
-{
- int rcode=directResolve(qname, QType(QType::A), 1, ret);
-
- ComboAddress prefixAddress(prefix);
-
- BOOST_FOREACH(DNSResourceRecord& rr, ret)
- {
- if(rr.qtype.getCode() == QType::A && rr.d_place==DNSResourceRecord::ANSWER) {
- ComboAddress ipv4(rr.content);
- uint32_t tmp;
- memcpy((void*)&tmp, &ipv4.sin4.sin_addr.s_addr, 4);
- // tmp=htonl(tmp);
- memcpy(((char*)&prefixAddress.sin6.sin6_addr.s6_addr)+12, &tmp, 4);
- rr.content = prefixAddress.toString();
- rr.qtype = QType(QType::AAAA);
- }
- }
- return rcode;
-}
-
-
-
-PowerDNSLua::PowerDNSLua(const std::string& fname)
-{
- d_lua = lua_open();
-
-#ifndef LUA_VERSION_NUM
- luaopen_base(d_lua);
- luaopen_string(d_lua);
-
- if(lua_dofile(d_lua, fname.c_str()))
-#else
- luaL_openlibs(d_lua);
- if(luaL_dofile(d_lua, fname.c_str()))
-#endif
- throw runtime_error(string("Error loading Lua file '")+fname+"': "+ string(lua_isstring(d_lua, -1) ? lua_tostring(d_lua, -1) : "unknown error"));
-
- lua_settop(d_lua, 0);
-
- lua_pushcfunction(d_lua, netmaskMatchLua);
- lua_setglobal(d_lua, "matchnetmask");
-
- lua_pushcfunction(d_lua, logLua);
- lua_setglobal(d_lua, "pdnslog");
-
- lua_pushcfunction(d_lua, setVariableLua);
- lua_setglobal(d_lua, "setvariable");
-
- lua_pushcfunction(d_lua, getLocalAddressLua);
- lua_setglobal(d_lua, "getlocaladdress");
-
- lua_newtable(d_lua);
-
- for(vector<QType::namenum>::const_iterator iter = QType::names.begin(); iter != QType::names.end(); ++iter) {
- lua_pushnumber(d_lua, iter->second);
- lua_setfield(d_lua, -2, iter->first.c_str());
- }
- lua_pushnumber(d_lua, 3);
- lua_setfield(d_lua, -2, "NXDOMAIN");
- lua_setglobal(d_lua, "pdns");
-
- lua_pushlightuserdata(d_lua, (void*)this);
- lua_setfield(d_lua, LUA_REGISTRYINDEX, "__PowerDNSLua");
-}
-
-bool PowerDNSLua::nxdomain(const ComboAddress& remote, const ComboAddress& local,const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable)
-{
- return passthrough("nxdomain", remote, local, query, qtype, ret, res, variable);
-}
-
-bool PowerDNSLua::preresolve(const ComboAddress& remote, const ComboAddress& local,const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable)
-{
- return passthrough("preresolve", remote, local, query, qtype, ret, res, variable);
-}
-
-bool PowerDNSLua::axfrfilter(const ComboAddress& remote, const string& zone, const DNSResourceRecord& in, vector<DNSResourceRecord>& out)
-{
- lua_getglobal(d_lua, "axfrfilter");
- if(!lua_isfunction(d_lua, -1)) {
- cerr<<"No such function 'axfrfilter'\n";
- lua_pop(d_lua, 1);
- return false;
- }
-
- lua_pushstring(d_lua, remote.toString().c_str() );
- lua_pushstring(d_lua, zone.c_str() );
- lua_pushstring(d_lua, in.qname.c_str() );
- lua_pushnumber(d_lua, in.qtype.getCode() );
- lua_pushnumber(d_lua, in.ttl );
- lua_pushnumber(d_lua, in.priority );
- lua_pushstring(d_lua, in.content.c_str() );
-
- if(lua_pcall(d_lua, 7, 2, 0)) { // error
- string error=string("lua error in axfrfilter: ")+lua_tostring(d_lua, -1);
- lua_pop(d_lua, 1);
- throw runtime_error(error);
- return false;
- }
-
- int newres = (int)lua_tonumber(d_lua, 1); // did we handle it?
- if(newres < 0) {
- //cerr << "handler did not handle"<<endl;
- lua_pop(d_lua, 2);
- return false;
- }
-
- /* get the result */
- DNSResourceRecord rr;
- rr.d_place = DNSResourceRecord::ANSWER;
- rr.ttl = 3600;
- rr.domain_id = in.domain_id;
-
- out.clear();
-
- /* 1 2 3 4 */
- /* stack: boolean table key row */
-
-#ifndef LUA_VERSION_NUM
- int tableLen = luaL_getn(d_lua, 2);
-#else
- int tableLen = lua_objlen(d_lua, 2);
-#endif
- cerr<<"Returned "<<tableLen<<" rows"<<endl;
- for(int n=1; n < tableLen + 1; ++n) {
- lua_pushnumber(d_lua, n);
- lua_gettable(d_lua, 2);
-
- uint32_t tmpnum=0;
- if(!getFromTable("qtype", tmpnum))
- rr.qtype=QType::A;
- else
- rr.qtype=tmpnum;
-
- getFromTable("content", rr.content);
- if(!getFromTable("ttl", rr.ttl))
- rr.ttl=3600;
-
- if(!getFromTable("qname", rr.qname))
- rr.qname = zone;
-
- if(!getFromTable("place", tmpnum))
- rr.d_place = DNSResourceRecord::ANSWER;
- else
- rr.d_place = (DNSResourceRecord::Place) tmpnum;
-
- /* removes 'value'; keeps 'key' for next iteration */
- lua_pop(d_lua, 1); // table
-
- // cerr<<"Adding content '"<<rr.content<<"' with place "<<(int)rr.d_place<<" \n";
- out.push_back(rr);
- }
- lua_pop(d_lua, 2); // c
- return true;
-}
-
-bool PowerDNSLua::nodata(const ComboAddress& remote, const ComboAddress& local,const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable)
-{
- return passthrough("nodata", remote, local, query, qtype, ret, res, variable);
-}
-
-bool PowerDNSLua::postresolve(const ComboAddress& remote, const ComboAddress& local,const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable)
-{
- return passthrough("postresolve", remote, local, query, qtype, ret, res, variable);
-}
-
-bool PowerDNSLua::getFromTable(const std::string& key, std::string& value)
-{
- lua_pushstring(d_lua, key.c_str()); // 4 is now '1'
- lua_gettable(d_lua, -2); // replace by the first entry of our table we hope
-
- bool ret=false;
- if(!lua_isnil(d_lua, -1)) {
- value = lua_tostring(d_lua, -1);
- ret=true;
- }
- lua_pop(d_lua, 1);
- return ret;
-}
-
-
-bool PowerDNSLua::getFromTable(const std::string& key, uint32_t& value)
-{
- lua_pushstring(d_lua, key.c_str()); // 4 is now '1'
- lua_gettable(d_lua, -2); // replace by the first entry of our table we hope
-
- bool ret=false;
- if(!lua_isnil(d_lua, -1)) {
- value = (uint32_t)lua_tonumber(d_lua, -1);
- ret=true;
- }
- lua_pop(d_lua, 1);
- return ret;
-}
-
-bool PowerDNSLua::passthrough(const string& func, const ComboAddress& remote, const ComboAddress& local, const string& query, const QType& qtype, vector<DNSResourceRecord>& ret,
- int& res, bool* variable)
-{
- d_variable = false;
- lua_getglobal(d_lua, func.c_str());
- if(!lua_isfunction(d_lua, -1)) {
- // cerr<<"No such function '"<<func<<"'\n";
- lua_pop(d_lua, 1);
- return false;
- }
-
- d_local = local;
- /* the first argument */
- lua_pushstring(d_lua, remote.toString().c_str() );
- lua_pushstring(d_lua, query.c_str() );
- lua_pushnumber(d_lua, qtype.getCode() );
-
- int extraParameter = 0;
- if(!strcmp(func.c_str(),"nodata")) {
- pushResourceRecordsTable(d_lua, ret);
- extraParameter++;
- }
- else if(!strcmp(func.c_str(),"postresolve")) {
- pushResourceRecordsTable(d_lua, ret);
- lua_pushnumber(d_lua, res);
- extraParameter+=2;
- }
-
- if(lua_pcall(d_lua, 3 + extraParameter, 3, 0)) {
- string error=string("lua error in '"+func+"' while processing query for '"+query+"|"+qtype.getName()+": ")+lua_tostring(d_lua, -1);
- lua_pop(d_lua, 1);
- throw runtime_error(error);
- return false;
- }
-
- *variable |= d_variable;
-
-
- if(!lua_isnumber(d_lua, 1)) {
- string tocall = lua_tostring(d_lua,1);
- string luaqname = lua_tostring(d_lua,2);
- string luaprefix = lua_tostring(d_lua, 3);
- lua_pop(d_lua, 3);
- // cerr<<"should call '"<<tocall<<"' to finish off"<<endl;
- ret.clear();
- res=getFakeAAAARecords(luaqname, luaprefix, ret);
- return true;
- // returned a followup
- }
-
- int newres = (int)lua_tonumber(d_lua, 1); // new rcode
- if(newres < 0) {
- // cerr << "handler did not handle"<<endl;
- lua_pop(d_lua, 3);
- return false;
- }
- res=newres;
-
- /* get the result */
- DNSResourceRecord rr;
- rr.qname = query;
- rr.d_place = DNSResourceRecord::ANSWER;
- rr.ttl = 3600;
-
- ret.clear();
-
- /* 1 2 3 4 */
- /* stack: boolean table key row */
-
-#ifndef LUA_VERSION_NUM
- int tableLen = luaL_getn(d_lua, 2);
-#else
- int tableLen = lua_objlen(d_lua, 2);
-#endif
- // cerr<<"Got back "<<tableLen<< " answers from Lua"<<endl;
-
- for(int n=1; n < tableLen + 1; ++n) {
- lua_pushnumber(d_lua, n);
- lua_gettable(d_lua, 2);
-
- uint32_t tmpnum=0;
- if(!getFromTable("qtype", tmpnum))
- rr.qtype=QType::A;
- else
- rr.qtype=tmpnum;
-
- getFromTable("content", rr.content);
- if(!getFromTable("ttl", rr.ttl))
- rr.ttl=3600;
-
- if(!getFromTable("qname", rr.qname))
- rr.qname = query;
-
- if(!getFromTable("place", tmpnum))
- rr.d_place = DNSResourceRecord::ANSWER;
- else
- rr.d_place = (DNSResourceRecord::Place) tmpnum;
-
- /* removes 'value'; keeps 'key' for next iteration */
- lua_pop(d_lua, 1); // table
-
- // cerr<<"Adding content '"<<rr.content<<"' with place "<<(int)rr.d_place<<" \n";
- ret.push_back(rr);
- }
-
- lua_pop(d_lua, 3);
-
- return true;
-}
-
-PowerDNSLua::~PowerDNSLua()
-{
- lua_close(d_lua);
-}
-#endif
--- /dev/null
+#include "lua-pdns.hh"
+// #include "syncres.hh"
+#include <boost/foreach.hpp>
+
+#if !defined(PDNS_ENABLE_LUA)
+
+// stub implementation
+
+PowerDNSLua::PowerDNSLua(const std::string& fname)
+{
+ throw runtime_error("Lua support disabled");
+}
+
+
+PowerDNSLua::~PowerDNSLua()
+{
+
+}
+
+#else
+
+extern "C" {
+#undef L
+/* Include the Lua API header files. */
+#include <lua.h>
+#include <lauxlib.h>
+#include <lualib.h>
+}
+
+#include <stdlib.h>
+#include <stdio.h>
+#include <string>
+#include <vector>
+#include <stdexcept>
+#include "logger.hh"
+#include "namespaces.hh"
+
+bool netmaskMatchTable(lua_State* lua, const std::string& ip)
+{
+ lua_pushnil(lua); /* first key */
+ while (lua_next(lua, 2) != 0) {
+ string netmask=lua_tostring(lua, -1);
+ Netmask nm(netmask);
+ ComboAddress ca(ip);
+ lua_pop(lua, 1);
+
+ if(nm.match(ip))
+ return true;
+ }
+ return false;
+}
+
+static bool getFromTable(lua_State *lua, const std::string &key, std::string& value)
+{
+ lua_pushstring(lua, key.c_str()); // 4 is now '1'
+ lua_gettable(lua, -2); // replace by the first entry of our table we hope
+
+ bool ret=false;
+ if(!lua_isnil(lua, -1)) {
+ value = lua_tostring(lua, -1);
+ ret=true;
+ }
+ lua_pop(lua, 1);
+ return ret;
+}
+
+static bool getFromTable(lua_State *lua, const std::string &key, uint32_t& value)
+{
+ lua_pushstring(lua, key.c_str()); // 4 is now '1'
+ lua_gettable(lua, -2); // replace by the first entry of our table we hope
+
+ bool ret=false;
+ if(!lua_isnil(lua, -1)) {
+ value = (uint32_t)lua_tonumber(lua, -1);
+ ret=true;
+ }
+ lua_pop(lua, 1);
+ return ret;
+}
+
+void pushResourceRecordsTable(lua_State* lua, const vector<DNSResourceRecord>& records)
+{
+ // make a table of tables
+ lua_newtable(lua);
+
+ int pos=0;
+ BOOST_FOREACH(const DNSResourceRecord& rr, records)
+ {
+ // row number, used by 'lua_settable' below
+ lua_pushnumber(lua, ++pos);
+ // "row" table
+ lua_newtable(lua);
+
+ lua_pushstring(lua, rr.qname.c_str());
+ lua_setfield(lua, -2, "qname"); // pushes value at the top of the stack to the table immediately below that (-1 = top, -2 is below)
+
+ lua_pushstring(lua, rr.content.c_str());
+ lua_setfield(lua, -2, "content");
+
+ lua_pushnumber(lua, rr.qtype.getCode());
+ lua_setfield(lua, -2, "qtype");
+
+ lua_pushnumber(lua, rr.ttl);
+ lua_setfield(lua, -2, "ttl");
+
+ lua_pushnumber(lua, rr.d_place);
+ lua_setfield(lua, -2, "place");
+
+ lua_settable(lua, -3); // pushes the table we just built into the master table at position pushed above
+ }
+}
+
+void popResourceRecordsTable(lua_State *lua, const string &query, vector<DNSResourceRecord>& ret)
+{
+ /* get the result */
+ DNSResourceRecord rr;
+ rr.qname = query;
+ rr.d_place = DNSResourceRecord::ANSWER;
+ rr.ttl = 3600;
+
+ cerr<<"Lua stacksize "<<lua_gettop(lua)<<endl;
+#ifndef LUA_VERSION_NUM
+ int tableLen = luaL_getn(lua, 2);
+#else
+ int tableLen = lua_objlen(lua, 2);
+#endif
+ cerr<<"Got back "<<tableLen<< " answers from Lua"<<endl;
+
+ for(int n=1; n < tableLen + 1; ++n) {
+ lua_pushnumber(lua, n);
+ lua_gettable(lua, 2);
+
+ uint32_t tmpnum=0;
+ if(!getFromTable(lua, "qtype", tmpnum))
+ rr.qtype=QType::A;
+ else
+ rr.qtype=tmpnum;
+
+ getFromTable(lua, "content", rr.content);
+ if(!getFromTable(lua, "ttl", rr.ttl))
+ rr.ttl=3600;
+
+ if(!getFromTable(lua, "qname", rr.qname))
+ rr.qname = query;
+
+ if(!getFromTable(lua, "place", tmpnum))
+ rr.d_place = DNSResourceRecord::ANSWER;
+ else
+ rr.d_place = (DNSResourceRecord::Place) tmpnum;
+
+ /* removes 'value'; keeps 'key' for next iteration */
+ lua_pop(lua, 1); // table
+
+ // cerr<<"Adding content '"<<rr.content<<"' with place "<<(int)rr.d_place<<" \n";
+ ret.push_back(rr);
+ }
+}
+
+extern "C" {
+
+int netmaskMatchLua(lua_State *lua)
+{
+ bool result=false;
+ if(lua_gettop(lua) >= 2) {
+ string ip=lua_tostring(lua, 1);
+ if(lua_istable(lua, 2)) {
+ result = netmaskMatchTable(lua, ip);
+ }
+ else {
+ for(int n=2 ; n <= lua_gettop(lua); ++n) {
+ string netmask=lua_tostring(lua, n);
+ Netmask nm(netmask);
+ ComboAddress ca(ip);
+
+ result = nm.match(ip);
+ if(result)
+ break;
+ }
+ }
+ }
+
+ lua_pushboolean(lua, result);
+ return 1;
+}
+
+int getLocalAddressLua(lua_State* lua)
+{
+ lua_getfield(lua, LUA_REGISTRYINDEX, "__PowerDNSLua");
+ PowerDNSLua* pl = (PowerDNSLua*)lua_touserdata(lua, -1);
+
+ lua_pushstring(lua, pl->getLocal().toString().c_str());
+ return 1;
+}
+
+// called by lua to indicate that this answer is 'variable' and should not be cached
+int setVariableLua(lua_State* lua)
+{
+ lua_getfield(lua, LUA_REGISTRYINDEX, "__PowerDNSLua");
+ PowerDNSLua* pl = (PowerDNSLua*)lua_touserdata(lua, -1);
+ pl->setVariable();
+ return 0;
+}
+
+int logLua(lua_State *lua)
+{
+ if(lua_gettop(lua) >= 1) {
+ string message=lua_tostring(lua, 1);
+ theL()<<Logger::Error<<"From Lua script: "<<message<<endl;
+ }
+ return 0;
+}
+}
+
+PowerDNSLua::PowerDNSLua(const std::string& fname)
+{
+ d_lua = lua_open();
+
+#ifndef LUA_VERSION_NUM
+ luaopen_base(d_lua);
+ luaopen_string(d_lua);
+
+ if(lua_dofile(d_lua, fname.c_str()))
+#else
+ luaL_openlibs(d_lua);
+ if(luaL_dofile(d_lua, fname.c_str()))
+#endif
+ throw runtime_error(string("Error loading Lua file '")+fname+"': "+ string(lua_isstring(d_lua, -1) ? lua_tostring(d_lua, -1) : "unknown error"));
+
+ lua_settop(d_lua, 0);
+
+ lua_pushcfunction(d_lua, netmaskMatchLua);
+ lua_setglobal(d_lua, "matchnetmask");
+
+ lua_pushcfunction(d_lua, logLua);
+ lua_setglobal(d_lua, "pdnslog");
+
+ lua_pushcfunction(d_lua, setVariableLua);
+ lua_setglobal(d_lua, "setvariable");
+
+ lua_pushcfunction(d_lua, getLocalAddressLua);
+ lua_setglobal(d_lua, "getlocaladdress");
+
+ lua_newtable(d_lua);
+
+ for(vector<QType::namenum>::const_iterator iter = QType::names.begin(); iter != QType::names.end(); ++iter) {
+ lua_pushnumber(d_lua, iter->second);
+ lua_setfield(d_lua, -2, iter->first.c_str());
+ }
+ lua_pushnumber(d_lua, 3);
+ lua_setfield(d_lua, -2, "NXDOMAIN");
+ lua_setglobal(d_lua, "pdns");
+
+ lua_pushlightuserdata(d_lua, (void*)this);
+ lua_setfield(d_lua, LUA_REGISTRYINDEX, "__PowerDNSLua");
+}
+
+bool PowerDNSLua::getFromTable(const std::string& key, std::string& value)
+{
+ return ::getFromTable(d_lua, key, value);
+}
+
+bool PowerDNSLua::getFromTable(const std::string& key, uint32_t& value)
+{
+ return ::getFromTable(d_lua, key, value);
+}
+
+
+PowerDNSLua::~PowerDNSLua()
+{
+ lua_close(d_lua);
+}
+#endif
--- /dev/null
+#ifndef PDNS_LUA_PDNS_HH
+#define PDNS_LUA_PDNS_HH
+#include "dns.hh"
+#include "iputils.hh"
+
+struct lua_State;
+
+class PowerDNSLua
+{
+public:
+ explicit PowerDNSLua(const std::string& fname);
+ ~PowerDNSLua();
+ void reload();
+ ComboAddress getLocal()
+ {
+ return d_local;
+ }
+
+ void setVariable()
+ {
+ d_variable=true;
+ }
+
+protected: // FIXME?
+ lua_State* d_lua;
+ bool passthrough(const string& func, const ComboAddress& remote,const ComboAddress& local, const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable);
+ bool getFromTable(const std::string& key, std::string& value);
+ bool getFromTable(const std::string& key, uint32_t& value);
+ bool d_failed;
+ bool d_variable;
+ ComboAddress d_local;
+};
+
+void pushResourceRecordsTable(lua_State* lua, const vector<DNSResourceRecord>& records);
+void popResourceRecordsTable(lua_State *lua, const string &query, vector<DNSResourceRecord>& ret);
+
+#endif
--- /dev/null
+#include "lua-recursor.hh"
+
+// to avoid including all of syncres.hh
+int directResolve(const std::string& qname, const QType& qtype, int qclass, vector<DNSResourceRecord>& ret);
+
+#if !defined(PDNS_ENABLE_LUA)
+
+RecursorLua::RecursorLua(const std::string &fname)
+ : PowerDNSLua(fname)
+{
+ // empty
+}
+
+bool RecursorLua::nxdomain(const ComboAddress& remote,const ComboAddress& local, const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable)
+{
+ return false;
+}
+
+bool RecursorLua::nodata(const ComboAddress& remote,const ComboAddress& local, const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable)
+{
+ return false;
+}
+
+bool RecursorLua::postresolve(const ComboAddress& remote,const ComboAddress& local, const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable)
+{
+ return false;
+}
+
+
+bool RecursorLua::preresolve(const ComboAddress& remote, const ComboAddress& local, const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable)
+{
+ return false;
+}
+
+
+#else
+
+extern "C" {
+#undef L
+/* Include the Lua API header files. */
+#include <lua.h>
+#include <lauxlib.h>
+#include <lualib.h>
+}
+
+#include <stdlib.h>
+#include <stdio.h>
+#include <string>
+#include <vector>
+#include <stdexcept>
+#include <boost/foreach.hpp>
+#include "logger.hh"
+#include "namespaces.hh"
+
+RecursorLua::RecursorLua(const std::string &fname)
+ : PowerDNSLua(fname)
+{
+ // empty
+}
+
+int getFakeAAAARecords(const std::string& qname, const std::string& prefix, vector<DNSResourceRecord>& ret)
+{
+ int rcode=directResolve(qname, QType(QType::A), 1, ret);
+
+ ComboAddress prefixAddress(prefix);
+
+ BOOST_FOREACH(DNSResourceRecord& rr, ret)
+ {
+ if(rr.qtype.getCode() == QType::A && rr.d_place==DNSResourceRecord::ANSWER) {
+ ComboAddress ipv4(rr.content);
+ uint32_t tmp;
+ memcpy((void*)&tmp, &ipv4.sin4.sin_addr.s_addr, 4);
+ // tmp=htonl(tmp);
+ memcpy(((char*)&prefixAddress.sin6.sin6_addr.s6_addr)+12, &tmp, 4);
+ rr.content = prefixAddress.toString();
+ rr.qtype = QType(QType::AAAA);
+ }
+ }
+ return rcode;
+}
+
+bool RecursorLua::nxdomain(const ComboAddress& remote, const ComboAddress& local,const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable)
+{
+ return passthrough("nxdomain", remote, local, query, qtype, ret, res, variable);
+}
+
+bool RecursorLua::preresolve(const ComboAddress& remote, const ComboAddress& local,const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable)
+{
+ return passthrough("preresolve", remote, local, query, qtype, ret, res, variable);
+}
+
+bool RecursorLua::nodata(const ComboAddress& remote, const ComboAddress& local,const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable)
+{
+ return passthrough("nodata", remote, local, query, qtype, ret, res, variable);
+}
+
+bool RecursorLua::postresolve(const ComboAddress& remote, const ComboAddress& local,const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable)
+{
+ return passthrough("postresolve", remote, local, query, qtype, ret, res, variable);
+}
+
+
+bool RecursorLua::passthrough(const string& func, const ComboAddress& remote, const ComboAddress& local, const string& query, const QType& qtype, vector<DNSResourceRecord>& ret,
+ int& res, bool* variable)
+{
+ d_variable = false;
+ lua_getglobal(d_lua, func.c_str());
+ if(!lua_isfunction(d_lua, -1)) {
+ // cerr<<"No such function '"<<func<<"'\n";
+ lua_pop(d_lua, 1);
+ return false;
+ }
+
+ d_local = local;
+ /* the first argument */
+ lua_pushstring(d_lua, remote.toString().c_str() );
+ lua_pushstring(d_lua, query.c_str() );
+ lua_pushnumber(d_lua, qtype.getCode() );
+
+ int extraParameter = 0;
+ if(!strcmp(func.c_str(),"nodata")) {
+ pushResourceRecordsTable(d_lua, ret);
+ extraParameter++;
+ }
+ else if(!strcmp(func.c_str(),"postresolve")) {
+ pushResourceRecordsTable(d_lua, ret);
+ lua_pushnumber(d_lua, res);
+ extraParameter+=2;
+ }
+
+ if(lua_pcall(d_lua, 3 + extraParameter, 3, 0)) {
+ string error=string("lua error in '"+func+"' while processing query for '"+query+"|"+qtype.getName()+": ")+lua_tostring(d_lua, -1);
+ lua_pop(d_lua, 1);
+ throw runtime_error(error);
+ return false;
+ }
+
+ *variable |= d_variable;
+
+
+ if(!lua_isnumber(d_lua, 1)) {
+ string tocall = lua_tostring(d_lua,1);
+ string luaqname = lua_tostring(d_lua,2);
+ string luaprefix = lua_tostring(d_lua, 3);
+ lua_pop(d_lua, 3);
+ // cerr<<"should call '"<<tocall<<"' to finish off"<<endl;
+ ret.clear();
+ res=getFakeAAAARecords(luaqname, luaprefix, ret);
+ return true;
+ // returned a followup
+ }
+
+ int newres = (int)lua_tonumber(d_lua, 1); // new rcode
+ if(newres < 0) {
+ // cerr << "handler did not handle"<<endl;
+ lua_pop(d_lua, 3);
+ return false;
+ }
+ res=newres;
+
+ ret.clear();
+
+ /* 1 2 3 4 */
+ /* stack: boolean table key row */
+
+ popResourceRecordsTable(d_lua, query, ret);
+
+ lua_pop(d_lua, 3);
+
+ return true;
+}
+
+#endif
\ No newline at end of file
-#ifndef PDNS_LUA_PDNS_RECURSOR_HH
-#define PDNS_LUA_PDNS_RECURSOR_HH
+#ifndef PDNS_LUA_RECURSOR_HH
+#define PDNS_LUA_RECURSOR_HH
#include "dns.hh"
#include "iputils.hh"
+#include "lua-pdns.hh"
-struct lua_State;
-
-class PowerDNSLua
+class RecursorLua : public PowerDNSLua
{
public:
- explicit PowerDNSLua(const std::string& fname);
- ~PowerDNSLua();
- void reload();
+ explicit RecursorLua(const std::string& fname);
+ // ~RecursorLua();
bool preresolve(const ComboAddress& remote,const ComboAddress& local, const string& query, const QType& qtype, vector<DNSResourceRecord>& res, int& ret, bool* variable);
bool nxdomain(const ComboAddress& remote, const ComboAddress& local, const string& query, const QType& qtype, vector<DNSResourceRecord>& res, int& ret, bool* variable);
- bool axfrfilter(const ComboAddress& remote, const string& zone, const DNSResourceRecord& in, vector<DNSResourceRecord>& out);
bool nodata(const ComboAddress& remote, const ComboAddress& local, const string& query, const QType& qtype, vector<DNSResourceRecord>& res, int& ret, bool* variable);
bool postresolve(const ComboAddress& remote, const ComboAddress& local, const string& query, const QType& qtype, vector<DNSResourceRecord>& res, int& ret, bool* variable);
- ComboAddress getLocal()
- {
- return d_local;
- }
-
- void setVariable()
- {
- d_variable=true;
- }
private:
- lua_State* d_lua;
bool passthrough(const string& func, const ComboAddress& remote,const ComboAddress& local, const string& query, const QType& qtype, vector<DNSResourceRecord>& ret, int& res, bool* variable);
- bool getFromTable(const std::string& key, std::string& value);
- bool getFromTable(const std::string& key, uint32_t& value);
- bool d_failed;
- bool d_variable;
- ComboAddress d_local;
};
#endif
d_doRecursion= ::arg().mustDo("recursor");
d_logDNSDetails= ::arg().mustDo("log-dns-details");
d_doIPv6AdditionalProcessing = ::arg().mustDo("do-ipv6-additional-processing");
+ string fname= ::arg()["lua-prequery-script"];
+ if(fname.empty())
+ {
+ d_pdl = NULL;
+ }
+ else
+ {
+ d_pdl = new AuthLua(fname);
+ }
+
}
DNSBackend *PacketHandler::getBackend()
DNSPacket *PacketHandler::question(DNSPacket *p)
{
+ DNSPacket *ret;
+
+ if(d_pdl)
+ {
+ ret=d_pdl->prequery(p);
+ if(ret)
+ return ret;
+ }
+
bool shouldRecurse=false;
- DNSPacket *ret=questionOrRecurse(p, &shouldRecurse);
+ ret=questionOrRecurse(p, &shouldRecurse);
if(shouldRecurse) {
DP->sendPacket(p);
}
#include "dnspacket.hh"
#include "packetcache.hh"
#include "dnsseckeeper.hh"
+#include "lua-auth.hh"
#include "namespaces.hh"
bool d_doCNAME;
bool d_logDNSDetails;
bool d_doIPv6AdditionalProcessing;
+ AuthLua* d_pdl;
UeberBackend B; // every thread an own instance
DNSSECKeeper d_dk; // same, might even share B?
#include "iputils.hh"
#include "mplexer.hh"
#include "config.h"
-#include "lua-pdns-recursor.hh"
+#include "lua-recursor.hh"
#ifndef RECURSOR
#include "statbag.hh"
unsigned int g_maxTCPPerClient;
unsigned int g_networkTimeoutMsec;
bool g_logCommonErrors;
-__thread shared_ptr<PowerDNSLua>* t_pdl;
+__thread shared_ptr<RecursorLua>* t_pdl;
__thread RemoteKeeper* t_remotes;
RecursorControlChannel s_rcc; // only active in thread 0
int res;
bool variableAnswer = false;
- // if there is a PowerDNSLua active, and it 'took' the query in preResolve, we don't launch beginResolve
+ // if there is a RecursorLua active, and it 'took' the query in preResolve, we don't launch beginResolve
if(!t_pdl->get() || !(*t_pdl)->preresolve(dc->d_remote, g_listenSocketsAddresses[dc->d_socket], dc->d_mdp.d_qname, QType(dc->d_mdp.d_qtype), ret, res, &variableAnswer)) {
res = sr.beginResolve(dc->d_mdp.d_qname, QType(dc->d_mdp.d_qtype), dc->d_mdp.d_qclass, ret);
return new string("unloaded\n");
}
else {
- *t_pdl = shared_ptr<PowerDNSLua>(new PowerDNSLua(fname));
+ *t_pdl = shared_ptr<RecursorLua>(new RecursorLua(fname));
}
}
catch(std::exception& e) {
L<<Logger::Warning<<"Done priming cache with root hints"<<endl;
t_RC->d_followRFC2181=::arg().mustDo("auth-can-lower-ttl");
- t_pdl = new shared_ptr<PowerDNSLua>();
+ t_pdl = new shared_ptr<RecursorLua>();
try {
if(!::arg()["lua-dns-script"].empty()) {
- *t_pdl = shared_ptr<PowerDNSLua>(new PowerDNSLua(::arg()["lua-dns-script"]));
+ *t_pdl = shared_ptr<RecursorLua>(new RecursorLua(::arg()["lua-dns-script"]));
L<<Logger::Warning<<"Loaded 'lua' script from '"<<::arg()["lua-dns-script"]<<"'"<<endl;
}
-- print(val.content)
end
return origrcode, records
-end
\ No newline at end of file
+end
+
+function prequery ( dnspacket )
+ -- pdnslog ("prequery called for ".. tostring(dnspacket) )
+ qname, qtype = dnspacket:getQuestion()
+ pdnslog ("q: ".. qname.." "..qtype)
+ if qtype == pdns.A and qname == "www.domain.com"
+ then
+ pdnslog ("calling dnspacket:setRcode")
+ dnspacket:setRcode(pdns.NXDOMAIN)
+ pdnslog ("called dnspacket:setRcode")
+ pdnslog ("adding records")
+ ret = {}
+ ret[1] = {qname=qname, qtype=qtype, content="1.2.3.4", place=2}
+ ret[2] = {qname=qname, qtype=pdns.TXT, content=os.date("Retrieved at %Y-%m-%d %H:%M"), ttl=ttl}
+ dnspacket:addRecords(ret)
+ pdnslog ("returning true")
+ return true
+ end
+ pdnslog ("returning false")
+ return false
+end
#include <boost/lexical_cast.hpp>
#include "base64.hh"
#include "inflighter.cc"
-#include "lua-pdns-recursor.hh"
+#include "lua-auth.hh"
#include "namespaces.hh"
#include "common_startup.hh"
#include <boost/scoped_ptr.hpp>
}
}
- scoped_ptr<PowerDNSLua> pdl;
+ scoped_ptr<AuthLua> pdl;
vector<string> scripts;
if(B->getDomainMetadata(domain, "LUA-AXFR-SCRIPT", scripts) && !scripts.empty()) {
try {
- pdl.reset(new PowerDNSLua(scripts[0]));
+ pdl.reset(new AuthLua(scripts[0]));
L<<Logger::Info<<"Loaded Lua script '"<<scripts[0]<<"' to edit the incoming AXFR of '"<<domain<<"'"<<endl;
}
catch(std::exception& e) {