diff options
Diffstat (limited to 'apt-pkg/contrib/srvrec.cc')
-rw-r--r-- | apt-pkg/contrib/srvrec.cc | 32 |
1 files changed, 10 insertions, 22 deletions
diff --git a/apt-pkg/contrib/srvrec.cc b/apt-pkg/contrib/srvrec.cc index b4a3d97d2..174668274 100644 --- a/apt-pkg/contrib/srvrec.cc +++ b/apt-pkg/contrib/srvrec.cc @@ -13,7 +13,7 @@ #include <netinet/in.h> #include <arpa/nameser.h> #include <resolv.h> -#include <chrono> +#include <time.h> #include <algorithm> @@ -68,7 +68,6 @@ bool GetSrvRecords(std::string name, std::vector<SrvRec> &Result) unsigned char *pt = answer+sizeof(HEADER)+compressed_name_len+QFIXEDSZ; while ((int)Result.size() < answer_count && pt < answer+answer_len) { - SrvRec rec; u_int16_t type, klass, priority, weight, port, dlen; char buf[MAXDNAME]; @@ -105,11 +104,7 @@ bool GetSrvRecords(std::string name, std::vector<SrvRec> &Result) pt += compressed_name_len; // add it to our class - rec.priority = priority; - rec.weight = weight; - rec.port = port; - rec.target = buf; - Result.push_back(rec); + Result.emplace_back(buf, priority, weight, port); } // implement load balancing as specified in RFC-2782 @@ -173,21 +168,14 @@ SrvRec PopFromSrvRecs(std::vector<SrvRec> &Recs) #endif // shuffle in a very simplistic way for now (equal weights) - std::vector<SrvRec>::iterator I, J; - I = J = Recs.begin(); - for(;I != Recs.end(); ++I) - { - if(I->priority != J->priority) - break; - } - - // FIXME: meeeeh, where to init this properly - unsigned seed = std::chrono::system_clock::now().time_since_epoch().count(); - std::shuffle(J, I, std::default_random_engine(seed)); - - // meh, no pop_front() in std::vector? - SrvRec selected = *Recs.begin(); - Recs.erase(Recs.begin()); + std::vector<SrvRec>::const_iterator I = Recs.begin(); + std::vector<SrvRec>::const_iterator const J = std::find_if(Recs.cbegin(), Recs.cend(), + [&I](SrvRec const &J) { return I->priority != J.priority; }); + + // clock seems random enough. + I += clock() % std::distance(I, J); + SrvRec const selected = std::move(*I); + Recs.erase(I); if (_config->FindB("Debug::Acquire::SrvRecs", false) == true) std::cerr << "PopFromSrvRecs: selecting " << selected.target << std::endl; |