#include "pqp.h" #include #include typedef _layout pq_array { int32_t nonempty, nullable, ty, nelts, resv; char body []; } pq_array; typedef _layout pq_array_elt { uint32_t sz; /* -1 for null */ char body []; } pq_array_elt; #include struct pqp_array* pqp_array_read(const void* pqary) { const pq_array* pqa = pqary; pqp_array* r = calloc(1, sizeof(pqp_array) + (sizeof(pqp_array_elt) * pqa -> nelts)); *r = (pqp_array) { .ty = ntohl(pqa -> ty), .nullable = ntohl(pqa -> nullable), .sz = ntohl(pqa -> nelts), }; const char* p = pqa -> body; for(size_t i = 0; i < r -> sz; ++ i) { const pq_array_elt* e = (void*)p; r -> elts[i] = (pqp_array_elt) { .sz = ntohl(e -> sz), .data = (e -> sz == pq_null ? null : e -> body), }; if (e -> sz == pq_null) p += 4; /* null */ else p += 4 + r->elts[i].sz; } return r; } bool pqp_inet_read(const void* pqinet, struct sockaddr* d) { if(memcmp(pqinet,"\x02\x20\x00\x04",4) == 0) { uint32_t ip = 0; for(uint8_t i = 0; i<4; ++i) { ip |= (uint32_t)(((uint8_t*)pqinet)[4 + i]) << 8*i; } struct sockaddr_in* dd = (void*)d; _zero(*dd); dd -> sin_family = AF_INET; dd -> sin_port = 0; dd -> sin_addr = (struct in_addr){ip}; } else if(memcmp(pqinet,"\x03\x80\x00\x10",4) == 0) { struct sockaddr_in6* dd = (void*)d; _zero(*dd); dd -> sin6_family = AF_INET6; dd -> sin6_port = 0; memcpy(&(dd->sin6_addr), pqinet+4, 16); } else return false; return true; }