• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

PowerDNS / pdns / 12595591960

03 Jan 2025 09:27AM UTC coverage: 62.774% (+2.5%) from 60.245%
12595591960

Pull #15008

github

web-flow
Merge c2a2749d3 into 788f396a7
Pull Request #15008: Do not follow CNAME records for ANY or CNAME queries

30393 of 78644 branches covered (38.65%)

Branch coverage included in aggregate %.

105822 of 138350 relevant lines covered (76.49%)

4613078.44 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

31.94
/pdns/dnsdistdist/dnsdist-lua-bindings-dnscrypt.cc
1
/*
2
 * This file is part of PowerDNS or dnsdist.
3
 * Copyright -- PowerDNS.COM B.V. and its contributors
4
 *
5
 * This program is free software; you can redistribute it and/or modify
6
 * it under the terms of version 2 of the GNU General Public License as
7
 * published by the Free Software Foundation.
8
 *
9
 * In addition, for the avoidance of any doubt, permission is granted to
10
 * link this program with OpenSSL and to (re)distribute the binaries
11
 * produced as the result of such linking.
12
 *
13
 * This program is distributed in the hope that it will be useful,
14
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16
 * GNU General Public License for more details.
17
 *
18
 * You should have received a copy of the GNU General Public License
19
 * along with this program; if not, write to the Free Software
20
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
21
 */
22

23
#include "config.h"
24
#include "dnsdist.hh"
25
#include "dnsdist-lua.hh"
26

27
#include "dolog.hh"
28

29
void setupLuaBindingsDNSCrypt(LuaContext& luaCtx, bool client)
30
{
649✔
31
#ifdef HAVE_DNSCRYPT
649✔
32
  /* DNSCryptContext bindings */
33
  luaCtx.registerFunction<std::string (DNSCryptContext::*)() const>("getProviderName", [](const DNSCryptContext& ctx) { return ctx.getProviderName().toStringNoDot(); });
649✔
34
  luaCtx.registerFunction("markActive", &DNSCryptContext::markActive);
649✔
35
  luaCtx.registerFunction("markInactive", &DNSCryptContext::markInactive);
649✔
36
  luaCtx.registerFunction("reloadCertificates", &DNSCryptContext::reloadCertificates);
649✔
37
  luaCtx.registerFunction("removeInactiveCertificate", &DNSCryptContext::removeInactiveCertificate);
649✔
38
  luaCtx.registerFunction<void (std::shared_ptr<DNSCryptContext>::*)(const std::string& certFile, const std::string& keyFile, boost::optional<bool> active)>("loadNewCertificate", [](std::shared_ptr<DNSCryptContext>& ctx, const std::string& certFile, const std::string& keyFile, boost::optional<bool> active) {
649✔
39
    if (ctx == nullptr) {
1!
40
      throw std::runtime_error("DNSCryptContext::loadNewCertificate() called on a nil value");
×
41
    }
×
42

43
    ctx->loadNewCertificate(certFile, keyFile, active ? *active : true);
1!
44
  });
1✔
45
  luaCtx.registerFunction<void (std::shared_ptr<DNSCryptContext>::*)(const DNSCryptCert& newCert, const DNSCryptPrivateKey& newKey, boost::optional<bool> active)>("addNewCertificate", [](std::shared_ptr<DNSCryptContext>& ctx, const DNSCryptCert& newCert, const DNSCryptPrivateKey& newKey, boost::optional<bool> active) {
649✔
46
    if (ctx == nullptr) {
×
47
      throw std::runtime_error("DNSCryptContext::addNewCertificate() called on a nil value");
×
48
    }
×
49

50
    ctx->addNewCertificate(newCert, newKey, active ? *active : true);
×
51
  });
×
52
  luaCtx.registerFunction<LuaArray<std::shared_ptr<DNSCryptCertificatePair>> (std::shared_ptr<DNSCryptContext>::*)()>("getCertificatePairs", [](std::shared_ptr<DNSCryptContext>& ctx) {
649✔
53
    LuaArray<std::shared_ptr<DNSCryptCertificatePair>> result;
×
54

55
    if (ctx != nullptr) {
×
56
      size_t idx = 1;
×
57
      for (const auto& pair : ctx->getCertificates()) {
×
58
        result.emplace_back(idx++, pair);
×
59
      }
×
60
    }
×
61

62
    return result;
×
63
  });
×
64

65
  luaCtx.registerFunction<std::shared_ptr<DNSCryptCertificatePair> (std::shared_ptr<DNSCryptContext>::*)(size_t idx)>("getCertificatePair", [](std::shared_ptr<DNSCryptContext>& ctx, size_t idx) {
649✔
66
    if (ctx == nullptr) {
×
67
      throw std::runtime_error("DNSCryptContext::getCertificatePair() called on a nil value");
×
68
    }
×
69

70
    std::shared_ptr<DNSCryptCertificatePair> result = nullptr;
×
71
    auto pairs = ctx->getCertificates();
×
72
    if (idx < pairs.size()) {
×
73
      result = pairs.at(idx);
×
74
    }
×
75

76
    return result;
×
77
  });
×
78

79
  luaCtx.registerFunction<const DNSCryptCert (std::shared_ptr<DNSCryptContext>::*)(size_t idx)>("getCertificate", [](std::shared_ptr<DNSCryptContext>& ctx, size_t idx) {
649✔
80
    if (ctx == nullptr) {
4!
81
      throw std::runtime_error("DNSCryptContext::getCertificate() called on a nil value");
×
82
    }
×
83

84
    auto pairs = ctx->getCertificates();
4✔
85
    if (idx < pairs.size()) {
4!
86
      return pairs.at(idx)->cert;
4✔
87
    }
4✔
88

89
    throw std::runtime_error("This DNSCrypt context has no certificate at index " + std::to_string(idx));
×
90
  });
4✔
91

92
  luaCtx.registerFunction<std::string (std::shared_ptr<DNSCryptContext>::*)() const>("printCertificates", [](const std::shared_ptr<DNSCryptContext>& ctx) {
649✔
93
    ostringstream ret;
×
94

95
    if (ctx != nullptr) {
×
96
      size_t idx = 1;
×
97
      boost::format fmt("%1$-3d %|5t|%2$-8d %|10t|%3$-7d %|20t|%4$-21.21s %|41t|%5$-21.21s");
×
98
      ret << (fmt % "#" % "Serial" % "Version" % "From" % "To") << endl;
×
99

100
      for (const auto& pair : ctx->getCertificates()) {
×
101
        const auto& cert = pair->cert;
×
102
        const DNSCryptExchangeVersion version = DNSCryptContext::getExchangeVersion(cert);
×
103

104
        ret << (fmt % idx % cert.getSerial() % (version == DNSCryptExchangeVersion::VERSION1 ? 1 : 2) % DNSCryptContext::certificateDateToStr(cert.getTSStart()) % DNSCryptContext::certificateDateToStr(cert.getTSEnd())) << endl;
×
105
      }
×
106
    }
×
107

108
    return ret.str();
×
109
  });
×
110

111
  luaCtx.registerFunction<void (DNSCryptContext::*)(const std::string& providerPrivateKeyFile, uint32_t serial, time_t begin, time_t end, boost::optional<DNSCryptExchangeVersion> version)>("generateAndLoadInMemoryCertificate", [](DNSCryptContext& ctx, const std::string& providerPrivateKeyFile, uint32_t serial, time_t begin, time_t end, boost::optional<DNSCryptExchangeVersion> version) {
649✔
112
    DNSCryptPrivateKey privateKey;
3✔
113
    DNSCryptCert cert;
3✔
114

115
    try {
3✔
116
      if (generateDNSCryptCertificate(providerPrivateKeyFile, serial, begin, end, version ? *version : DNSCryptExchangeVersion::VERSION1, cert, privateKey)) {
3!
117
        ctx.addNewCertificate(cert, privateKey);
3✔
118
      }
3✔
119
    }
3✔
120
    catch (const std::exception& e) {
3✔
121
      errlog("Error generating a DNSCrypt certificate: %s", e.what());
×
122
      g_outputBuffer = "Error generating a DNSCrypt certificate: " + string(e.what()) + "\n";
×
123
    }
×
124
  });
3✔
125

126
  /* DNSCryptCertificatePair */
127
  luaCtx.registerFunction<const DNSCryptCert (std::shared_ptr<DNSCryptCertificatePair>::*)() const>("getCertificate", [](const std::shared_ptr<DNSCryptCertificatePair>& pair) {
649✔
128
    if (pair == nullptr) {
×
129
      throw std::runtime_error("DNSCryptCertificatePair::getCertificate() called on a nil value");
×
130
    }
×
131
    return pair->cert;
×
132
  });
×
133
  luaCtx.registerFunction<bool (std::shared_ptr<DNSCryptCertificatePair>::*)() const>("isActive", [](const std::shared_ptr<DNSCryptCertificatePair>& pair) {
649✔
134
    if (pair == nullptr) {
×
135
      throw std::runtime_error("DNSCryptCertificatePair::isActive() called on a nil value");
×
136
    }
×
137
    return pair->active;
×
138
  });
×
139

140
  /* DNSCryptCert */
141
  luaCtx.registerFunction<std::string (DNSCryptCert::*)() const>("getMagic", [](const DNSCryptCert& cert) {
649✔
142
    // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast): std::string's API
143
    return std::string(reinterpret_cast<const char*>(cert.magic.data()), cert.magic.size());
×
144
  });
×
145
  luaCtx.registerFunction<std::string (DNSCryptCert::*)() const>("getEsVersion", [](const DNSCryptCert& cert) {
649✔
146
    // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast): std::string's API
147
    return std::string(reinterpret_cast<const char*>(cert.esVersion.data()), cert.esVersion.size());
×
148
  });
×
149
  luaCtx.registerFunction<std::string (DNSCryptCert::*)() const>("getProtocolMinorVersion", [](const DNSCryptCert& cert) {
649✔
150
    // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast): std::string's API
151
    return std::string(reinterpret_cast<const char*>(cert.protocolMinorVersion.data()), cert.protocolMinorVersion.size());
×
152
  });
×
153
  luaCtx.registerFunction<std::string (DNSCryptCert::*)() const>("getSignature", [](const DNSCryptCert& cert) {
649✔
154
    // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast): std::string's API
155
    return std::string(reinterpret_cast<const char*>(cert.signature.data()), cert.signature.size());
×
156
  });
×
157
  luaCtx.registerFunction<std::string (DNSCryptCert::*)() const>("getResolverPublicKey", [](const DNSCryptCert& cert) {
649✔
158
    // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast): std::string's API
159
    return std::string(reinterpret_cast<const char*>(cert.signedData.resolverPK.data()), cert.signedData.resolverPK.size());
×
160
  });
×
161
  luaCtx.registerFunction<std::string (DNSCryptCert::*)() const>("getClientMagic", [](const DNSCryptCert& cert) {
649✔
162
    // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast): std::string's API
163
    return std::string(reinterpret_cast<const char*>(cert.signedData.clientMagic.data()), cert.signedData.clientMagic.size());
×
164
  });
×
165
  luaCtx.registerFunction<uint32_t (DNSCryptCert::*)() const>("getSerial", [](const DNSCryptCert& cert) { return cert.getSerial(); });
649✔
166
  luaCtx.registerFunction<uint32_t (DNSCryptCert::*)() const>("getTSStart", [](const DNSCryptCert& cert) { return ntohl(cert.getTSStart()); });
649✔
167
  luaCtx.registerFunction<uint32_t (DNSCryptCert::*)() const>("getTSEnd", [](const DNSCryptCert& cert) { return ntohl(cert.getTSEnd()); });
649✔
168

169
  luaCtx.writeFunction("generateDNSCryptCertificate", [client](const std::string& providerPrivateKeyFile, const std::string& certificateFile, const std::string& privateKeyFile, uint32_t serial, time_t begin, time_t end, boost::optional<DNSCryptExchangeVersion> version) {
649✔
170
    setLuaNoSideEffect();
7✔
171
    if (client) {
7!
172
      return;
×
173
    }
×
174
    DNSCryptPrivateKey privateKey;
7✔
175
    DNSCryptCert cert;
7✔
176

177
    try {
7✔
178
      if (generateDNSCryptCertificate(providerPrivateKeyFile, serial, begin, end, version ? *version : DNSCryptExchangeVersion::VERSION1, cert, privateKey)) {
7!
179
        privateKey.saveToFile(privateKeyFile);
7✔
180
        DNSCryptContext::saveCertFromFile(cert, certificateFile);
7✔
181
      }
7✔
182
    }
7✔
183
    catch (const std::exception& e) {
7✔
184
      errlog("Error generating a DNSCrypt certificate: %s", e.what());
×
185
      g_outputBuffer = "Error generating a DNSCrypt certificate: " + string(e.what()) + "\n";
×
186
    }
×
187
  });
7✔
188

189
  luaCtx.writeFunction("generateDNSCryptProviderKeys", [client](const std::string& publicKeyFile, const std::string& privateKeyFile) {
649✔
190
    setLuaNoSideEffect();
×
191
    if (client) {
×
192
      return;
×
193
    }
×
194
    DNSCryptCertSignedData::ResolverPublicKeyType publicKey;
×
195
    DNSCryptCertSignedData::ResolverPrivateKeyType privateKey;
×
196
    sodium_mlock(privateKey.data(), privateKey.size());
×
197

198
    try {
×
199
      DNSCryptContext::generateProviderKeys(publicKey, privateKey);
×
200

201
      ofstream pubKStream(publicKeyFile);
×
202
      // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast): ofstream's API
203
      pubKStream.write(reinterpret_cast<char*>(publicKey.data()), publicKey.size());
×
204
      pubKStream.close();
×
205

206
      ofstream privKStream(privateKeyFile);
×
207
      // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast): ofstream's API
208
      privKStream.write(reinterpret_cast<char*>(privateKey.data()), privateKey.size());
×
209
      privKStream.close();
×
210

211
      g_outputBuffer = "Provider fingerprint is: " + DNSCryptContext::getProviderFingerprint(publicKey) + "\n";
×
212
    }
×
213
    catch (const std::exception& e) {
×
214
      errlog("Error generating a DNSCrypt provider key: %s", e.what());
×
215
      g_outputBuffer = "Error generating a DNSCrypt provider key: " + string(e.what()) + "\n";
×
216
    }
×
217

218
    sodium_memzero(privateKey.data(), privateKey.size());
×
219
    sodium_munlock(privateKey.data(), privateKey.size());
×
220
  });
×
221

222
  luaCtx.writeFunction("printDNSCryptProviderFingerprint", [](const std::string& publicKeyFile) {
649✔
223
    setLuaNoSideEffect();
×
224
    DNSCryptCertSignedData::ResolverPublicKeyType publicKey;
×
225

226
    try {
×
227
      ifstream file(publicKeyFile);
×
228
      // NOLINTNEXTLINE(cppcoreguidelines-pro-type-reinterpret-cast): ifstream's API
229
      file.read(reinterpret_cast<char*>(publicKey.data()), publicKey.size());
×
230

231
      if (file.fail()) {
×
232
        throw std::runtime_error("Invalid dnscrypt provider public key file " + publicKeyFile);
×
233
      }
×
234

235
      file.close();
×
236
      g_outputBuffer = "Provider fingerprint is: " + DNSCryptContext::getProviderFingerprint(publicKey) + "\n";
×
237
    }
×
238
    catch (const std::exception& e) {
×
239
      errlog("Error getting a DNSCrypt provider fingerprint: %s", e.what());
×
240
      g_outputBuffer = "Error getting a DNSCrypt provider fingerprint: " + string(e.what()) + "\n";
×
241
    }
×
242
  });
×
243
#endif
649✔
244
}
649✔
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2025 Coveralls, Inc