From: Kirill Isakov Date: Fri, 23 Jul 2021 16:37:49 +0000 (+0600) Subject: Fix all UBSAN warnings triggered by tests. X-Git-Url: https://tinc-vpn.org/git/browse?p=tinc;a=commitdiff_plain;h=4214794ce68b9456146a5bf35db9e58da836b728 Fix all UBSAN warnings triggered by tests. --- diff --git a/src/hash.c b/src/hash.c index 63b8f547..39e88c99 100644 --- a/src/hash.c +++ b/src/hash.c @@ -29,11 +29,11 @@ static uint32_t hash_function(const void *p, size_t len) { uint32_t hash = 0; while(true) { - for(int i = len > 4 ? 4 : len; --i;) { + for(size_t i = len > 4 ? 4 : len; --i;) { hash += (uint32_t)q[len - i] << (8 * i); } - hash *= 0x9e370001UL; // Golden ratio prime. + hash = (uint32_t)(hash * 0x9e370001UL); // Golden ratio prime. if(len <= 4) { break; diff --git a/src/net_setup.c b/src/net_setup.c index 12571518..a04f9535 100644 --- a/src/net_setup.c +++ b/src/net_setup.c @@ -231,7 +231,7 @@ static bool read_ecdsa_private_key(void) { return false; } - if(s.st_mode & ~0100700) { + if(s.st_mode & ~0100700u) { logger(DEBUG_ALWAYS, LOG_WARNING, "Warning: insecure file permissions for Ed25519 private key file `%s'!", fname); } @@ -323,7 +323,7 @@ static bool read_rsa_private_key(void) { return false; } - if(s.st_mode & ~0100700) { + if(s.st_mode & ~0100700u) { logger(DEBUG_ALWAYS, LOG_WARNING, "Warning: insecure file permissions for RSA private key file `%s'!", fname); } diff --git a/src/route.c b/src/route.c index d1048e76..3fe6edb2 100644 --- a/src/route.c +++ b/src/route.c @@ -63,7 +63,7 @@ static timeout_t age_subnets_timeout; /* RFC 1071 */ -static uint16_t inet_checksum(void *vdata, int len, uint16_t prevsum) { +static uint16_t inet_checksum(void *vdata, size_t len, uint16_t prevsum) { uint8_t *data = vdata; uint16_t word; uint32_t checksum = prevsum ^ 0xFFFF; @@ -83,7 +83,7 @@ static uint16_t inet_checksum(void *vdata, int len, uint16_t prevsum) { checksum = (checksum & 0xFFFF) + (checksum >> 16); } - return ~checksum; + return (uint16_t) ~checksum; } static bool ratelimit(int frequency) { @@ -199,7 +199,7 @@ static void route_ipv4_unreachable(node_t *source, vpn_packet_t *packet, length_ ip.ip_src = ip_dst; ip.ip_dst = ip_src; - ip.ip_sum = inet_checksum(&ip, ip_size, ~0); + ip.ip_sum = inet_checksum(&ip, ip_size, 0xFFFF); /* Fill in ICMP header */ @@ -207,7 +207,7 @@ static void route_ipv4_unreachable(node_t *source, vpn_packet_t *packet, length_ icmp.icmp_code = code; icmp.icmp_cksum = 0; - icmp.icmp_cksum = inet_checksum(&icmp, icmp_size, ~0); + icmp.icmp_cksum = inet_checksum(&icmp, icmp_size, 0xFFFF); icmp.icmp_cksum = inet_checksum(DATA(packet) + ether_size + ip_size + icmp_size, oldlen, icmp.icmp_cksum); /* Copy structs on stack back to packet */ @@ -312,7 +312,7 @@ static void route_ipv6_unreachable(node_t *source, vpn_packet_t *packet, length_ /* Generate checksum */ - checksum = inet_checksum(&pseudo, sizeof(pseudo), ~0); + checksum = inet_checksum(&pseudo, sizeof(pseudo), 0xFFFF); checksum = inet_checksum(&icmp6, icmp6_size, checksum); checksum = inet_checksum(DATA(packet) + ether_size + ip6_size + icmp6_size, ntohl(pseudo.length) - icmp6_size, checksum); @@ -401,7 +401,7 @@ static void clamp_mss(const node_t *source, const node_t *via, vpn_packet_t *pac } /* Find TCP header */ - int start = ether_size; + size_t start = ether_size; uint16_t type = DATA(packet)[12] << 8 | DATA(packet)[13]; if(type == ETH_P_8021Q) { @@ -573,7 +573,7 @@ static void route_broadcast(node_t *source, vpn_packet_t *packet) { static void fragment_ipv4_packet(node_t *dest, vpn_packet_t *packet, length_t ether_size) { struct ip ip; vpn_packet_t fragment; - int maxlen, todo; + size_t maxlen, todo; uint8_t *offset; uint16_t ip_off, origf; @@ -601,7 +601,7 @@ static void fragment_ipv4_packet(node_t *dest, vpn_packet_t *packet, length_t et ip_off &= IP_OFFMASK; while(todo) { - int len = todo > maxlen ? maxlen : todo; + size_t len = todo > maxlen ? maxlen : todo; memcpy(DATA(&fragment) + ether_size + ip_size, offset, len); todo -= len; offset += len; @@ -609,7 +609,7 @@ static void fragment_ipv4_packet(node_t *dest, vpn_packet_t *packet, length_t et ip.ip_len = htons(ip_size + len); ip.ip_off = htons(ip_off | origf | (todo ? IP_MF : 0)); ip.ip_sum = 0; - ip.ip_sum = inet_checksum(&ip, ip_size, ~0); + ip.ip_sum = inet_checksum(&ip, ip_size, 0xFFFF); memcpy(DATA(&fragment), DATA(packet), ether_size); memcpy(DATA(&fragment) + ether_size, &ip, ip_size); fragment.len = ether_size + ip_size + len; @@ -857,7 +857,7 @@ static void route_neighborsol(node_t *source, vpn_packet_t *packet) { /* Generate checksum */ - checksum = inet_checksum(&pseudo, sizeof(pseudo), ~0); + checksum = inet_checksum(&pseudo, sizeof(pseudo), 0xFFFF); checksum = inet_checksum(&ns, ns_size, checksum); if(has_opt) { @@ -931,7 +931,7 @@ static void route_neighborsol(node_t *source, vpn_packet_t *packet) { /* Generate checksum */ - checksum = inet_checksum(&pseudo, sizeof(pseudo), ~0); + checksum = inet_checksum(&pseudo, sizeof(pseudo), 0xFFFF); checksum = inet_checksum(&ns, ns_size, checksum); if(has_opt) { diff --git a/src/sptps.c b/src/sptps.c index eeaf833e..6ad1c8d6 100644 --- a/src/sptps.c +++ b/src/sptps.c @@ -92,7 +92,7 @@ static void warning(sptps_t *s, const char *format, ...) { // Send a record (datagram version, accepts all record types, handles encryption and authentication). static bool send_record_priv_datagram(sptps_t *s, uint8_t type, const void *data, uint16_t len) { - char buffer[len + 21UL]; + uint8_t buffer[len + 21UL]; // Create header with sequence number, length and record type uint32_t seqno = s->outseqno++; @@ -117,7 +117,7 @@ static bool send_record_priv(sptps_t *s, uint8_t type, const void *data, uint16_ return send_record_priv_datagram(s, type, data, len); } - char buffer[len + 19UL]; + uint8_t buffer[len + 19UL]; // Create header with sequence number, length and record type uint32_t seqno = s->outseqno++; @@ -187,8 +187,8 @@ static bool send_sig(sptps_t *s) { size_t siglen = ecdsa_size(s->mykey); // Concatenate both KEX messages, plus tag indicating if it is from the connection originator, plus label - char msg[(1 + 32 + keylen) * 2 + 1 + s->labellen]; - char sig[siglen]; + uint8_t msg[(1 + 32 + keylen) * 2 + 1 + s->labellen]; + uint8_t sig[siglen]; msg[0] = s->initiator; memcpy(msg + 1, s->mykex, 1 + 32 + keylen); @@ -253,7 +253,7 @@ static bool send_ack(sptps_t *s) { } // Receive an ACKnowledgement record. -static bool receive_ack(sptps_t *s, const char *data, uint16_t len) { +static bool receive_ack(sptps_t *s, const uint8_t *data, uint16_t len) { (void)data; if(len) { @@ -278,7 +278,7 @@ static bool receive_ack(sptps_t *s, const char *data, uint16_t len) { } // Receive a Key EXchange record, respond by sending a SIG record. -static bool receive_kex(sptps_t *s, const char *data, uint16_t len) { +static bool receive_kex(sptps_t *s, const uint8_t *data, uint16_t len) { // Verify length of the HELLO record if(len != 1 + 32 + ECDH_SIZE) { return error(s, EIO, "Invalid KEX record length"); @@ -307,7 +307,7 @@ static bool receive_kex(sptps_t *s, const char *data, uint16_t len) { } // Receive a SIGnature record, verify it, if it passed, compute the shared secret and calculate the session keys. -static bool receive_sig(sptps_t *s, const char *data, uint16_t len) { +static bool receive_sig(sptps_t *s, const uint8_t *data, uint16_t len) { size_t keylen = ECDH_SIZE; size_t siglen = ecdsa_size(s->hiskey); @@ -317,7 +317,7 @@ static bool receive_sig(sptps_t *s, const char *data, uint16_t len) { } // Concatenate both KEX messages, plus tag indicating if it is from the connection originator - char msg[(1 + 32 + keylen) * 2 + 1 + s->labellen]; + uint8_t msg[(1 + 32 + keylen) * 2 + 1 + s->labellen]; msg[0] = !s->initiator; memcpy(msg + 1, s->hiskex, 1 + 32 + keylen); @@ -383,7 +383,7 @@ bool sptps_force_kex(sptps_t *s) { } // Receive a handshake record. -static bool receive_handshake(sptps_t *s, const char *data, uint16_t len) { +static bool receive_handshake(sptps_t *s, const uint8_t *data, uint16_t len) { // Only a few states to deal with handshaking. switch(s->state) { case SPTPS_SECONDARY_KEX: @@ -528,7 +528,7 @@ bool sptps_verify_datagram(sptps_t *s, const void *vdata, size_t len) { } // Receive incoming data, datagram version. -static bool sptps_receive_data_datagram(sptps_t *s, const char *data, size_t len) { +static bool sptps_receive_data_datagram(sptps_t *s, const uint8_t *data, size_t len) { if(len < (s->instate ? 21 : 5)) { return error(s, EIO, "Received short packet"); } @@ -558,7 +558,7 @@ static bool sptps_receive_data_datagram(sptps_t *s, const char *data, size_t len // Decrypt - char buffer[len]; + uint8_t buffer[len]; size_t outlen; if(!chacha_poly1305_decrypt(s->incipher, seqno, data, len, buffer, &outlen)) { @@ -599,7 +599,7 @@ static bool sptps_receive_data_datagram(sptps_t *s, const char *data, size_t len // Receive incoming data. Check if it contains a complete record, if so, handle it. size_t sptps_receive_data(sptps_t *s, const void *vdata, size_t len) { - const char *data = vdata; + const uint8_t *data = vdata; size_t total_read = 0; if(!s->state) { diff --git a/src/sptps.h b/src/sptps.h index f5686f4e..1da0af8a 100644 --- a/src/sptps.h +++ b/src/sptps.h @@ -50,7 +50,7 @@ typedef struct sptps { bool datagram; int state; - char *inbuf; + uint8_t *inbuf; size_t buflen; uint16_t reclen; diff --git a/src/subnet_parse.c b/src/subnet_parse.c index 32b7e0a0..d877c7fd 100644 --- a/src/subnet_parse.c +++ b/src/subnet_parse.c @@ -186,9 +186,7 @@ static int subnet_compare_ipv6(const subnet_t *a, const subnet_t *b) { } int subnet_compare(const subnet_t *a, const subnet_t *b) { - int result; - - result = a->type - b->type; + int result = (int)a->type - (int)b->type; if(result) { return result; diff --git a/src/utils.c b/src/utils.c index c9f3085a..f14094f6 100644 --- a/src/utils.c +++ b/src/utils.c @@ -54,7 +54,7 @@ static int charhex2bin(char c) { } size_t hex2bin(const char *src, void *vdst, size_t length) { - char *dst = vdst; + uint8_t *dst = vdst; size_t i; for(i = 0; i < length && isxdigit(src[i * 2]) && isxdigit(src[i * 2 + 1]); i++) { @@ -67,7 +67,8 @@ size_t hex2bin(const char *src, void *vdst, size_t length) { size_t bin2hex(const void *vsrc, char *dst, size_t length) { const char *src = vsrc; - for(size_t i = length; i-- > 0;) { + for(size_t i = length; i > 0;) { + --i; dst[i * 2 + 1] = hexadecimals[(unsigned char) src[i] & 15]; dst[i * 2] = hexadecimals[(unsigned char) src[i] >> 4]; }