diff options
author | attilamolnar <attilamolnar@hush.com> | 2013-03-20 23:43:51 +0100 |
---|---|---|
committer | attilamolnar <attilamolnar@hush.com> | 2013-03-20 23:43:51 +0100 |
commit | 21f7e4a8cdad2f29fda2768215c3a5352a9fa632 (patch) | |
tree | 7b7c0234cd0acaa3d4feebd8d9e0b941ce0924ba /src | |
parent | fd6a8e93920553e2e6655b0f396be61a6e6b832c (diff) |
Fix infinite loop when all DNS request slots are in use
This is not the best way to detect this scenario, a better detection mechanism will replace this in the future
Diffstat (limited to 'src')
-rw-r--r-- | src/dns.cpp | 20 |
1 files changed, 20 insertions, 0 deletions
diff --git a/src/dns.cpp b/src/dns.cpp index bede73a6f..63bde0ecc 100644 --- a/src/dns.cpp +++ b/src/dns.cpp @@ -258,8 +258,28 @@ DNSRequest* DNS::AddQuery(DNSHeader *header, int &id, const char* original) return NULL; /* Create an id */ + unsigned int tries = 0; do { id = ServerInstance->GenRandomInt(DNS::MAX_REQUEST_ID); + if (++tries == DNS::MAX_REQUEST_ID*5) + { + // If we couldn't find an empty slot this many times, do a sequential scan as a last + // resort. If an empty slot is found that way, go on, otherwise throw an exception + id = -1; + for (int i = 0; i < DNS::MAX_REQUEST_ID; i++) + { + if (!requests[i]) + { + id = i; + break; + } + } + + if (id == -1) + throw ModuleException("DNS: All ids are in use"); + + break; + } } while (requests[id]); DNSRequest* req = new DNSRequest(this, id, original); |