Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependents: oldheating gps motorhome heating
Revision 193:47a953ab571b, committed 2021-01-24
- Comitter:
- andrewboyson
- Date:
- Sun Jan 24 15:09:55 2021 +0000
- Parent:
- 192:0dfa138a8e7d
- Child:
- 194:f35c6e218de1
- Commit message:
- Fixed ability of name resolution to use IPv6 - the MAC for the DNS server IP address had to be made available.
Changed in this revision
--- a/ip4/ip4addr.c Fri Jan 22 13:24:08 2021 +0000
+++ b/ip4/ip4addr.c Sun Jan 24 15:09:55 2021 +0000
@@ -34,13 +34,41 @@
return HttpAddF("%d.%d.%d.%d", a3, a2, a1, a0);
}
-uint32_t Ip4AddrParse(const char* text)
+uint32_t Ip4AddrParse(const char* pText) //Returns 0 on error
{
+ const char* p = pText;
int ints[4];
- sscanf(text, "%d.%d.%d.%d", &ints[3], &ints[2], &ints[1], &ints[0]);
- return (ints[0] << 24) + (ints[1] << 16) + (ints[2] << 8) + ints[3];
+ int field = 0;
+ int word = 0;
+ while(true)
+ {
+ switch (*p)
+ {
+ case '.':
+ ints[field] = word;
+ field++;
+ if (field > 3) return 0;
+ word = 0;
+ break;
+ case '0': word *= 10; word += 0; break;
+ case '1': word *= 10; word += 1; break;
+ case '2': word *= 10; word += 2; break;
+ case '3': word *= 10; word += 3; break;
+ case '4': word *= 10; word += 4; break;
+ case '5': word *= 10; word += 5; break;
+ case '6': word *= 10; word += 6; break;
+ case '7': word *= 10; word += 7; break;
+ case '8': word *= 10; word += 8; break;
+ case '9': word *= 10; word += 9; break;
+ case 0:
+ ints[field] = word;
+ uint32_t addr4 = (ints[0] << 0) + (ints[1] << 8) + (ints[2] << 16) + (ints[3] << 24);
+ return addr4;
+ default: return 0;
+ }
+ p++;
+ }
}
-
void Ip4AddrFromDest(const int dest, uint32_t* pDstIp)
{
switch (dest)
--- a/ip6/ip6addr.c Fri Jan 22 13:24:08 2021 +0000
+++ b/ip6/ip6addr.c Sun Jan 24 15:09:55 2021 +0000
@@ -54,6 +54,58 @@
*p = 0;
return p - pText;
}
+void Ip6AddrParse(const char *pText, char *address) //Contains an empty address if invalid
+{
+ int field = 0;
+ int word = 0;
+ while(true)
+ {
+ switch (*pText)
+ {
+ case ':':
+ address[field] = (word >> 8) & 0xFF;
+ field++;
+ if (field > 15) { address[0] = 0; return; }
+ address[field] = word & 0xFF;
+ field++;
+ if (field > 15) { address[0] = 0; return; }
+ word = 0;
+ break;
+ case '0': word <<= 4; word |= 0; break;
+ case '1': word <<= 4; word |= 1; break;
+ case '2': word <<= 4; word |= 2; break;
+ case '3': word <<= 4; word |= 3; break;
+ case '4': word <<= 4; word |= 4; break;
+ case '5': word <<= 4; word |= 5; break;
+ case '6': word <<= 4; word |= 6; break;
+ case '7': word <<= 4; word |= 7; break;
+ case '8': word <<= 4; word |= 8; break;
+ case '9': word <<= 4; word |= 9; break;
+ case 'a':
+ case 'A': word <<= 4; word |= 10; break;
+ case 'b':
+ case 'B': word <<= 4; word |= 11; break;
+ case 'c':
+ case 'C': word <<= 4; word |= 12; break;
+ case 'd':
+ case 'D': word <<= 4; word |= 13; break;
+ case 'e':
+ case 'E': word <<= 4; word |= 14; break;
+ case 'f':
+ case 'F': word <<= 4; word |= 15; break;
+ case 0:
+ address[field] = (word >> 8) & 0xFF;
+ field++;
+ if (field != 15) { address[0] = 0; return; }
+ address[field] = word & 0xFF;
+ return;
+ default:
+ address[0] = 0;
+ return;
+ }
+ pText++;
+ }
+}
static void logHexNibble(bool* pAdded, int number, int index)
{
int nibble = number;
--- a/ip6/ip6addr.h Fri Jan 22 13:24:08 2021 +0000 +++ b/ip6/ip6addr.h Sun Jan 24 15:09:55 2021 +0000 @@ -2,6 +2,7 @@ #include <stdbool.h> extern int Ip6AddrToString(const char* ip, int size, char* text); +extern void Ip6AddrParse (const char *ip, char *address); extern int Ip6AddrLog (const char* ip); extern int Ip6AddrHttp (const char* ip);
--- a/resolve/ar4.c Fri Jan 22 13:24:08 2021 +0000
+++ b/resolve/ar4.c Sun Jan 24 15:09:55 2021 +0000
@@ -152,6 +152,15 @@
}
return false;
}
+bool Ar4CheckHaveMacAndFetchIfNot(uint32_t ip)
+{
+ if (!Ar4HaveMacForIp(ip))
+ {
+ Ar4MakeRequestForMacFromIp(ip); //The request is only repeated if made after a freeze time - call as often as you want.
+ return false;
+ }
+ return true;
+}
uint32_t Ar4IndexToIp(int i)
{
return records[i].ip;
--- a/resolve/ar4.h Fri Jan 22 13:24:08 2021 +0000 +++ b/resolve/ar4.h Sun Jan 24 15:09:55 2021 +0000 @@ -10,6 +10,7 @@ extern void Ar4IpToMac(uint32_t ip, char* pMac); extern uint32_t Ar4IndexToIp(int index); extern bool Ar4HaveMacForIp(uint32_t ip); +extern bool Ar4CheckHaveMacAndFetchIfNot(uint32_t ip); extern void Ar4SendHttp(void); extern void Ar4SendAjax(void);
--- a/resolve/ar6.c Fri Jan 22 13:24:08 2021 +0000
+++ b/resolve/ar6.c Sun Jan 24 15:09:55 2021 +0000
@@ -145,7 +145,7 @@
}
MacClear(mac);
}
-bool Ar6HaveMacForIp(char* ip, char* mac)
+bool Ar6HaveMacForIp(char* ip)
{
for (int i = 0; i < RECORDS_COUNT; i++)
{
@@ -153,6 +153,15 @@
}
return false;
}
+bool Ar6CheckHaveMacAndFetchIfNot(char* ip)
+{
+ if (!Ar6HaveMacForIp(ip))
+ {
+ Ar6MakeRequestForMacFromIp(ip); //The request is only repeated if made after a freeze time - call as often as you want.
+ return false;
+ }
+ return true;
+}
void Ar6IndexToIp(int i, char* ip)
{
Ip6AddrCopy(ip, records[i].ip);
--- a/resolve/ar6.h Fri Jan 22 13:24:08 2021 +0000 +++ b/resolve/ar6.h Sun Jan 24 15:09:55 2021 +0000 @@ -8,7 +8,8 @@ extern void Ar6IpToMac(char* ip, char* pMac); extern void Ar6IndexToIp(int index, char* pIp); -extern bool Ar6HaveMacForIp(char* ip, char* mac); +extern bool Ar6HaveMacForIp(char* ip); +extern bool Ar6CheckHaveMacAndFetchIfNot(char* ip); extern void Ar6SendHttp(void); extern void Ar6SendAjax(void);
--- a/resolve/nr.c Fri Jan 22 13:24:08 2021 +0000
+++ b/resolve/nr.c Sun Jan 24 15:09:55 2021 +0000
@@ -17,6 +17,7 @@
#include "nr.h"
#include "nrtest.h"
#include "ndp.h"
+#include "ar6.h"
bool Nr4Trace = false; //Do not use
bool NrTrace = false;
@@ -540,7 +541,7 @@
static void sendRequest(struct record* pr)
{
- if (DnsQueryIsBusy) return;
+ //if (DnsQueryIsBusy) return;
switch (pr->state)
{
@@ -581,7 +582,7 @@
break;
case STATE_WAIT_FOR_ETH:
if (!DnsQueryIsBusy)
- {
+ {
switch (pr->todo)
{
case TODO_NAME_FROM_ADDRESS: queryNameFromIp(pr); break;
--- a/resolve/nr.h Fri Jan 22 13:24:08 2021 +0000 +++ b/resolve/nr.h Sun Jan 24 15:09:55 2021 +0000 @@ -4,7 +4,7 @@ extern bool Nr4Trace; //Spare extern bool NrTrace; -#define NR_NAME_MAX_LENGTH 32 +#define NR_NAME_MAX_LENGTH 40 extern void NrMakeRequestForNameFromAddress6(char* address6); extern void NrMakeRequestForNameFromAddress4(uint32_t address4);
--- a/resolve/nrtest.c Fri Jan 22 13:24:08 2021 +0000
+++ b/resolve/nrtest.c Sun Jan 24 15:09:55 2021 +0000
@@ -2,34 +2,107 @@
#include <stdint.h>
#include "nr.h"
+#include "ar6.h"
+#include "ndp.h"
#include "dnsquery.h"
#include "dns.h"
#include "eth.h"
#include "ip4addr.h"
+#include "ip6addr.h"
+#include "log.h"
+#include "mac.h"
char NrTest[NR_NAME_MAX_LENGTH];
-static bool _doIt = false;
+static int _ipProtocol = 0;
+static int _dnsProtocol = 0;
+static bool _makeRequestForNameFromAddr4 = false;
+static bool _makeRequestForNameFromAddr6 = false;
+static bool _makeRequestForAddr4FromName = false;
+static bool _makeRequestForAddr6FromName = false;
+
+static uint32_t _addr4;
+static char _addr6[16];
-void NrTestNameFromAddress(void)
+void NrTestSendRequest(int ipProtocol, int dnsProtocol)
{
- _doIt = true;
+ _ipProtocol = ipProtocol;
+ _dnsProtocol = dnsProtocol;
+
+ if (NrTest[0])
+ {
+ _addr4 = Ip4AddrParse(NrTest);
+ if (_addr4)
+ {
+ _makeRequestForNameFromAddr4 = true;
+ }
+ else
+ {
+ Ip6AddrParse(NrTest, _addr6);
+ if (!Ip6AddrIsEmpty(_addr6))
+ {
+ _makeRequestForNameFromAddr6 = true;
+ }
+ else
+ {
+ _makeRequestForAddr4FromName = true;
+ _makeRequestForAddr6FromName = true;
+ }
+ }
+ }
}
-void NrTestAddress4FromName(void)
+
+static bool getMacOfDnsServer6()
{
- NrMakeRequestForAddress4FromName(NrTest);
-}
-void NrTestAddress6FromName(void)
-{
- NrMakeRequestForAddress6FromName(NrTest);
+ //For IPv6 UDNS check if have the MAC for the DNS server and, if not, request it and stop
+ if (_ipProtocol == ETH_IPV6 && _dnsProtocol == DNS_PROTOCOL_UDNS)
+ {
+ char mac[6];
+ Ar6IpToMac(NdpDnsServer, mac);
+ if (MacIsEmpty(mac))
+ {
+ Ar6MakeRequestForMacFromIp(NdpDnsServer); //The request is only repeated if made after a freeze time - call as often as you want.
+ return false;
+ }
+ }
+ return true;
}
void NrTestMain(void)
{
- if (!_doIt) return;
if (DnsQueryIsBusy) return;
- uint32_t addr4 = Ip4AddrParse(NrTest);
- if (!addr4) return;
- DnsQueryNameFromIp4(addr4, DNS_PROTOCOL_MDNS, ETH_IPV4);
- _doIt = false;
+
+
+ if (_makeRequestForNameFromAddr4)
+ {
+ //if (!getMacOfDnsServer6()) return;
+ LogTime("NrTest - making "); DnsProtocolLog(_dnsProtocol); Log(" request over "); EthProtocolLog(_ipProtocol); LogF(" for name from '%s'\r\n", NrTest);
+ DnsQueryNameFromIp4(_addr4, _dnsProtocol, _ipProtocol);
+ _makeRequestForNameFromAddr4 = false;
+ return;
+ }
+ if (_makeRequestForNameFromAddr6)
+ {
+ //if (!getMacOfDnsServer6()) return;
+ LogTime("NrTest - making "); DnsProtocolLog(_dnsProtocol); Log(" request over "); EthProtocolLog(_ipProtocol); LogF(" for name from '%s'\r\n", NrTest);
+ DnsQueryNameFromIp6(_addr6, _dnsProtocol, _ipProtocol);
+ _makeRequestForNameFromAddr6 = false;
+ return;
+ }
+ if (_makeRequestForAddr4FromName)
+ {
+ //if (!getMacOfDnsServer6()) return;
+ LogTime("NrTest - making "); DnsProtocolLog(_dnsProtocol); Log(" request over "); EthProtocolLog(_ipProtocol); LogF(" for A from '%s'\r\n", NrTest);
+ DnsQueryIp4FromName(NrTest, _dnsProtocol, _ipProtocol);
+ _makeRequestForAddr4FromName = false;
+ return;
+ }
+ if (_makeRequestForAddr6FromName)
+ {
+ //if (!getMacOfDnsServer6()) return;
+ LogTime("NrTest - making "); DnsProtocolLog(_dnsProtocol); Log(" request over "); EthProtocolLog(_ipProtocol); LogF(" for AAAA from '%s'\r\n", NrTest);
+ DnsQueryIp6FromName(NrTest, _dnsProtocol, _ipProtocol);
+ _makeRequestForAddr6FromName = false;
+ return;
+ }
}
\ No newline at end of file
--- a/resolve/nrtest.h Fri Jan 22 13:24:08 2021 +0000 +++ b/resolve/nrtest.h Sun Jan 24 15:09:55 2021 +0000 @@ -1,7 +1,5 @@ extern char NrTest[]; -extern void NrTestAddress4FromName(void); -extern void NrTestAddress6FromName(void); -extern void NrTestNameFromAddress(void); +extern void NrTestSendRequest(int ipProtocol, int dnsProtocol); extern void NrTestMain(void); \ No newline at end of file
--- a/udp/dns/dnsquery.c Fri Jan 22 13:24:08 2021 +0000
+++ b/udp/dns/dnsquery.c Sun Jan 24 15:09:55 2021 +0000
@@ -15,6 +15,9 @@
#include "dnshdr.h"
#include "dnsname.h"
#include "dnslabel.h"
+#include "ar6.h"
+#include "ndp.h"
+#include "mac.h"
bool DnsQueryTrace = false;
@@ -159,6 +162,13 @@
if (_RecordType == DNS_RECORD_NONE) return DO_NOTHING;
if (_DnsProtocol == DNS_PROTOCOL_NONE) return DO_NOTHING;
+
+ //For IPv6 UDNS check if have the MAC for the DNS server and, if not, request it and stop
+ if (_IpProtocol == ETH_IPV6 && _DnsProtocol == DNS_PROTOCOL_UDNS)
+ {
+ if (!Ar6CheckHaveMacAndFetchIfNot(NdpDnsServer)) return DO_NOTHING;
+ }
+
NetTraceHostCheckIp6(DnsQueryIp6);
if (DnsQueryTrace || NetTraceHostGetMatched()) logQuery();