#include "encode.hpp"
#include <stdlib.h>
#include <sys/time.h>
void to_hex(const unsigned char* from, unsigned char* to, size_t len) {
while (len) {
sprintf((char*)to, "%02x", (unsigned char)*from);
len--;
from++;
to += 2;
}
}
bool from_hex(const unsigned char* from, unsigned char* to, size_t len) {
if (len % 2 != 0) {
return false;
}
while (len) {
unsigned h;
if (sscanf((const char*)from, "%02x", &h) != 1) {
return false;
}
*to = (unsigned char)h;
len -= 2;
from += 2;
to++;
}
return true;
}
static uint64_t htonll(uint64_t v) {
uint32_t hi = htonl((uint32_t)(v >> 32));
uint32_t lo = htonl((uint32_t)(v & 0xffffffffllu));
return (((uint64_t)lo) << 32) | hi;
}
uint64_t get_nonce() {
struct timeval tv;
gettimeofday(&tv, NULL);
srand(tv.tv_usec);
union {
uint64_t a;
uint16_t b[4];
} rv;
rv.b[0] = (uint16_t)rand(); // TODO: this is not sound
rv.b[1] = (uint16_t)rand();
rv.b[2] = (uint16_t)rand();
rv.b[3] = (uint16_t)rand();
return rv.a;
}
uint64_t obfuscate_dst(uint64_t nonce, const sockaddr_in& dst) {
static const uint64_t secret = htonll(0xabcdefabcdefabcdllu);
static const uint16_t sentinel = htons(0xb3e4);
union {
uint64_t v;
struct {
uint16_t sentinel;
uint16_t port;
uint32_t addr;
};
} d;
d.sentinel = sentinel;
d.port = dst.sin_port;
d.addr = dst.sin_addr.s_addr;
return (d.v ^ secret) ^ nonce;
}