From 2183683bd633818dd031b090b5530951de76f392 Mon Sep 17 00:00:00 2001 From: Werner Koch Date: Wed, 11 Feb 2015 10:27:57 +0100 Subject: [PATCH] Use inline functions to convert buffer data to scalars. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * common/host2net.h (buf16_to_ulong, buf16_to_uint): New. (buf16_to_ushort, buf16_to_u16): New. (buf32_to_size_t, buf32_to_ulong, buf32_to_uint, buf32_to_u32): New. -- Commit 91b826a38880fd8a989318585eb502582636ddd8 was not enough to avoid all sign extension on shift problems. Hanno Böck found a case with an invalid read due to this problem. To fix that once and for all almost all uses of "<< 24" and "<< 8" are changed by this patch to use an inline function from host2net.h. Signed-off-by: Werner Koch --- agent/cvt-openpgp.c | 7 +++-- common/b64enc.c | 2 +- common/dns-cert.c | 20 ++++++------ common/host2net.h | 72 ++++++++++++++++++++++++++++++++++++++++---- common/iobuf.c | 7 +++-- common/pka.c | 14 +++++---- common/srv.c | 28 +++++++++-------- common/tlv.c | 2 +- dirmngr/ldap.c | 5 +-- g10/build-packet.c | 8 ++--- g10/call-agent.c | 3 +- g10/getkey.c | 14 +++++---- g10/keygen.c | 9 +++--- g10/keyid.c | 29 ++++++++---------- g10/misc.c | 10 ------ g10/parse-packet.c | 37 +++++++++++------------ g10/pubkey-enc.c | 4 +-- g10/seckey-cert.c | 2 +- g10/tdbio.c | 20 ++++++------ g10/trust.c | 3 +- g13/mount.c | 7 ++--- kbx/keybox-dump.c | 22 ++------------ kbx/keybox-openpgp.c | 8 ++--- kbx/keybox-search.c | 25 ++------------- kbx/keybox-update.c | 9 +++--- scd/apdu.c | 40 +++++++++++------------- scd/app-nks.c | 3 +- scd/app-openpgp.c | 3 +- scd/ccid-driver.c | 2 +- sm/fingerprint.c | 13 +++----- tools/ccidmon.c | 2 +- 31 files changed, 220 insertions(+), 210 deletions(-) diff --git a/agent/cvt-openpgp.c b/agent/cvt-openpgp.c index 5f944934a..cadc87180 100644 --- a/agent/cvt-openpgp.c +++ b/agent/cvt-openpgp.c @@ -27,6 +27,7 @@ #include "agent.h" #include "i18n.h" #include "cvt-openpgp.h" +#include "host2net.h" /* Helper to pass data via the callback to do_unprotect. */ @@ -487,7 +488,7 @@ do_unprotect (const char *passphrase, ndata = (ndatabits+7)/8; if (ndata > 1) - csum_pgp7 = p[ndata-2] << 8 | p[ndata-1]; + csum_pgp7 = buf16_to_u16 (p+ndata-2); data = xtrymalloc_secure (ndata); if (!data) { @@ -531,7 +532,7 @@ do_unprotect (const char *passphrase, } else { - desired_csum = (data[ndata-2] << 8 | data[ndata-1]); + desired_csum = buf16_to_u16 (data+ndata-2); actual_csum = checksum (data, ndata-2); if (desired_csum != actual_csum) { @@ -586,7 +587,7 @@ do_unprotect (const char *passphrase, p = gcry_mpi_get_opaque (skey[i], &ndatabits); ndata = (ndatabits+7)/8; - if (!(ndata >= 2) || !(ndata == ((p[0] << 8 | p[1]) + 7)/8 + 2)) + if (!(ndata >= 2) || !(ndata == (buf16_to_ushort (p) + 7)/8 + 2)) { gcry_cipher_close (cipher_hd); return gpg_error (GPG_ERR_BAD_SECKEY); diff --git a/common/b64enc.c b/common/b64enc.c index 91ba69d48..087f27c9d 100644 --- a/common/b64enc.c +++ b/common/b64enc.c @@ -253,7 +253,7 @@ b64enc_write (struct b64state *state, const void *buffer, size_t nbytes) u32 crc = state->crc; for (p=buffer, n=nbytes; n; p++, n-- ) - crc = (crc << 8) ^ crc_table[((crc >> 16)&0xff) ^ *p]; + crc = ((u32)crc << 8) ^ crc_table[((crc >> 16)&0xff) ^ *p]; state->crc = (crc & 0x00ffffff); } diff --git a/common/dns-cert.c b/common/dns-cert.c index 4e297bf92..317ebb1d8 100644 --- a/common/dns-cert.c +++ b/common/dns-cert.c @@ -47,6 +47,7 @@ #endif #include "util.h" +#include "host2net.h" #include "dns-cert.h" /* Not every installation has gotten around to supporting CERTs @@ -130,7 +131,7 @@ get_dns_cert (const char *name, estream_t *r_key, if (datalen < 5) continue; /* Truncated CERT record - skip. */ - ctype = ((data[0] << 8) | data[1]); + ctype = buf16_to_uint (data); /* (key tag and algorithm fields are not required.) */ data += 5; datalen -= 5; @@ -262,12 +263,13 @@ get_dns_cert (const char *name, estream_t *r_key, if ((emsg - pt) < 15) break; - type = *pt++ << 8; - type |= *pt++; + type = buf16_to_u16 (pt); + pt += 2; - class = *pt++ << 8; + class = buf16_to_u16 (pt); + pt += 2; class |= *pt++; - /* We asked for IN and got something else !? */ + if (class != C_IN) break; @@ -275,8 +277,8 @@ get_dns_cert (const char *name, estream_t *r_key, pt += 4; /* data length */ - dlen = *pt++ << 8; - dlen |= *pt++; + dlen = buf16_to_u16 (pt); + pt += 2; /* We asked for CERT and got something else - might be a CNAME, so loop around again. */ @@ -287,8 +289,8 @@ get_dns_cert (const char *name, estream_t *r_key, } /* The CERT type */ - ctype = *pt++ << 8; - ctype |= *pt++; + ctype = buf16_to_u16 (pt); + pt += 2; /* Skip the CERT key tag and algo which we don't need. */ pt += 3; diff --git a/common/host2net.h b/common/host2net.h index dd20e36ce..be5e5202a 100644 --- a/common/host2net.h +++ b/common/host2net.h @@ -1,5 +1,5 @@ /* host2net.h - Endian conversion macros - * Copyright (C) 1998, 2014 Werner Koch + * Copyright (C) 1998, 2014, 2015 Werner Koch * * This file is part of GnuPG. * @@ -32,9 +32,6 @@ #include "types.h" -#define buftoulong( p ) ((*(byte*)(p) << 24) | (*((byte*)(p)+1)<< 16) | \ - (*((byte*)(p)+2) << 8) | (*((byte*)(p)+3))) -#define buftoushort( p ) ((*((byte*)(p)) << 8) | (*((byte*)(p)+1))) #define ulongtobuf( p, a ) do { \ ((byte*)p)[0] = a >> 24; \ ((byte*)p)[1] = a >> 16; \ @@ -45,8 +42,71 @@ ((byte*)p)[0] = a >> 8; \ ((byte*)p)[1] = a ; \ } while(0) -#define buftou32( p) buftoulong( (p) ) -#define u32tobuf( p, a) ulongtobuf( (p), (a) ) + + +static inline unsigned long +buf16_to_ulong (const void *buffer) +{ + const unsigned char *p = buffer; + + return (((unsigned long)p[0] << 8) | p[1]); +} + +static inline unsigned int +buf16_to_uint (const void *buffer) +{ + const unsigned char *p = buffer; + + return (((unsigned int)p[0] << 8) | p[1]); +} + +static inline unsigned short +buf16_to_ushort (const void *buffer) +{ + const unsigned char *p = buffer; + + return (((unsigned short)p[0] << 8) | p[1]); +} + +static inline u16 +buf16_to_u16 (const void *buffer) +{ + const unsigned char *p = buffer; + + return (((u16)p[0] << 8) | p[1]); +} + +static inline size_t +buf32_to_size_t (const void *buffer) +{ + const unsigned char *p = buffer; + + return (((size_t)p[0] << 24) | (p[1] << 16) | (p[2] << 8) | p[3]); +} + +static inline unsigned long +buf32_to_ulong (const void *buffer) +{ + const unsigned char *p = buffer; + + return (((unsigned long)p[0] << 24) | (p[1] << 16) | (p[2] << 8) | p[3]); +} + +static inline unsigned int +buf32_to_uint (const void *buffer) +{ + const unsigned char *p = buffer; + + return (((unsigned int)p[0] << 24) | (p[1] << 16) | (p[2] << 8) | p[3]); +} + +static inline u32 +buf32_to_u32 (const void *buffer) +{ + const unsigned char *p = buffer; + + return (((u32)p[0] << 24) | (p[1] << 16) | (p[2] << 8) | p[3]); +} #endif /*GNUPG_COMMON_HOST2NET_H*/ diff --git a/common/iobuf.c b/common/iobuf.c index badbf78da..ca74bd71e 100644 --- a/common/iobuf.c +++ b/common/iobuf.c @@ -871,7 +871,7 @@ block_filter (void *opaque, int control, iobuf_t chain, byte * buffer, } else if (c == 255) { - a->size = iobuf_get (chain) << 24; + a->size = (size_t)iobuf_get (chain) << 24; a->size |= iobuf_get (chain) << 16; a->size |= iobuf_get (chain) << 8; if ((c = iobuf_get (chain)) == -1) @@ -1228,9 +1228,12 @@ iobuf_t iobuf_temp_with_content (const char *buffer, size_t length) { iobuf_t a; + int i; a = iobuf_alloc (3, length); - memcpy (a->d.buf, buffer, length); + /* memcpy (a->d.buf, buffer, length); */ + for (i=0; i < length; i++) + a->d.buf[i] = buffer[i]; a->d.len = length; return a; diff --git a/common/pka.c b/common/pka.c index d47216298..4ead97f63 100644 --- a/common/pka.c +++ b/common/pka.c @@ -51,6 +51,7 @@ #endif #include "util.h" +#include "host2net.h" #include "pka.h" #ifdef USE_DNS_PKA @@ -252,13 +253,14 @@ get_pka_info (const char *address, unsigned char *fpr) if (p >= pend - 10) return NULL; /* RR too short. */ - type = *p++ << 8; - type |= *p++; - class = *p++ << 8; - class |= *p++; + type = buf16_to_uint (p); + p += 2; + class = buf16_to_uint (p); + p += 2; p += 4; - txtlen = *p++ << 8; - txtlen |= *p++; + txtlen = buf16_to_uint (p); + p += 2; + if (type != T_TXT || class != C_IN) return NULL; /* Answer does not match the query. */ diff --git a/common/srv.c b/common/srv.c index 7a0c42d4f..2107aa528 100644 --- a/common/srv.c +++ b/common/srv.c @@ -48,6 +48,7 @@ #endif #include "util.h" +#include "host2net.h" #include "srv.h" /* Not every installation has gotten around to supporting SRVs @@ -184,27 +185,28 @@ getsrv (const char *name,struct srventry **list) if((emsg-pt)<16) goto fail; - type=*pt++ << 8; - type|=*pt++; + type = buf16_to_u16 (pt); + pt += 2; /* We asked for SRV and got something else !? */ if(type!=T_SRV) goto fail; - class=*pt++ << 8; - class|=*pt++; + class = buf16_to_u16 (pt); + pt += 2; /* We asked for IN and got something else !? */ if(class!=C_IN) goto fail; - pt+=4; /* ttl */ - dlen=*pt++ << 8; - dlen|=*pt++; - srv->priority=*pt++ << 8; - srv->priority|=*pt++; - srv->weight=*pt++ << 8; - srv->weight|=*pt++; - srv->port=*pt++ << 8; - srv->port|=*pt++; + pt += 4; /* ttl */ + dlen = buf16_to_u16 (pt); + pt += 2; + + srv->priority = buf16_to_ushort (pt); + pt += 2; + srv->weight = buf16_to_ushort (pt); + pt += 2; + srv->port = buf16_to_ushort (pt); + pt += 2; /* Get the name. 2782 doesn't allow name compression, but dn_expand still works to pull the name out of the diff --git a/common/tlv.c b/common/tlv.c index 51a0907c3..74cb4a744 100644 --- a/common/tlv.c +++ b/common/tlv.c @@ -96,7 +96,7 @@ do_find_tlv (const unsigned char *buffer, size_t length, { /* Two byte length follows. */ if (n < 2) return NULL; /* We expected 2 more bytes with the length. */ - len = (s[0] << 8) | s[1]; + len = ((size_t)s[0] << 8) | s[1]; s += 2; n -= 2; } else diff --git a/dirmngr/ldap.c b/dirmngr/ldap.c index 00df167e2..c59619897 100644 --- a/dirmngr/ldap.c +++ b/dirmngr/ldap.c @@ -36,6 +36,7 @@ #include "ldapserver.h" #include "misc.h" #include "ldap-wrapper.h" +#include "host2net.h" #define UNENCODED_URL_CHARS "abcdefghijklmnopqrstuvwxyz" \ @@ -664,7 +665,7 @@ fetch_next_cert_ldap (cert_fetch_context_t context, gpg_error_t err; unsigned char hdr[5]; char *p, *pend; - int n; + unsigned long n; int okay = 0; /* int is_cms = 0; */ @@ -677,7 +678,7 @@ fetch_next_cert_ldap (cert_fetch_context_t context, err = read_buffer (context->reader, hdr, 5); if (err) break; - n = (hdr[1] << 24)|(hdr[2]<<16)|(hdr[3]<<8)|hdr[4]; + n = buf32_to_ulong (hdr+1); if (*hdr == 'V' && okay) { #if 0 /* That code is not yet ready. */ diff --git a/g10/build-packet.c b/g10/build-packet.c index cda753ca1..e44350e44 100644 --- a/g10/build-packet.c +++ b/g10/build-packet.c @@ -32,6 +32,7 @@ #include "iobuf.h" #include "i18n.h" #include "options.h" +#include "host2net.h" static int do_user_id( IOBUF out, int ctb, PKT_user_id *uid ); static int do_key (iobuf_t out, int ctb, PKT_public_key *pk); @@ -621,10 +622,7 @@ delete_sig_subpkt (subpktarea_t *area, sigsubpkttype_t reqtype ) if( n == 255 ) { if( buflen < 4 ) break; - n = (((size_t)buffer[0] << 24) - | (buffer[1] << 16) - | (buffer[2] << 8) - | buffer[3]); + n = buf32_to_size_t (buffer); buffer += 4; buflen -= 4; } @@ -747,7 +745,7 @@ build_sig_subpkt (PKT_signature *sig, sigsubpkttype_t type, /* This should never happen since we don't currently allow creating such a subpacket, but just in case... */ case SIGSUBPKT_SIG_EXPIRE: - if(buffer_to_u32(buffer)+sig->timestamp<=make_timestamp()) + if(buf32_to_u32(buffer)+sig->timestamp<=make_timestamp()) sig->flags.expired=1; else sig->flags.expired=0; diff --git a/g10/call-agent.c b/g10/call-agent.c index dc9d1575a..4bac8a0ef 100644 --- a/g10/call-agent.c +++ b/g10/call-agent.c @@ -41,6 +41,7 @@ #include "call-agent.h" #include "status.h" #include "../common/shareddefs.h" +#include "host2net.h" #ifndef DBG_ASSUAN # define DBG_ASSUAN 1 @@ -761,7 +762,7 @@ agent_scd_apdu (const char *hexapdu, unsigned int *r_sw) err = gpg_error (GPG_ERR_CARD); else { - *r_sw = (data[datalen-2] << 8) | data[datalen-1]; + *r_sw = buf16_to_uint (data+datalen-2); } xfree (data); } diff --git a/g10/getkey.c b/g10/getkey.c index 62d2d3306..30c454b21 100644 --- a/g10/getkey.c +++ b/g10/getkey.c @@ -36,6 +36,8 @@ #include "i18n.h" #include "keyserver-internal.h" #include "call-agent.h" +#include "host2net.h" + #define MAX_PK_CACHE_ENTRIES PK_UID_CACHE_SIZE #define MAX_UID_CACHE_ENTRIES PK_UID_CACHE_SIZE @@ -1418,8 +1420,8 @@ fixup_uidnode (KBNODE uidnode, KBNODE signode, u32 keycreated) /* Ditto for the key expiration. */ p = parse_sig_subpkt (sig->hashed, SIGSUBPKT_KEY_EXPIRE, NULL); - if (p && buffer_to_u32 (p)) - uid->help_key_expire = keycreated + buffer_to_u32 (p); + if (p && buf32_to_u32 (p)) + uid->help_key_expire = keycreated + buf32_to_u32 (p); else uid->help_key_expire = 0; @@ -1651,9 +1653,9 @@ merge_selfsigs_main (KBNODE keyblock, int *r_revoked, key_usage = parse_key_usage (sig); p = parse_sig_subpkt (sig->hashed, SIGSUBPKT_KEY_EXPIRE, NULL); - if (p && buffer_to_u32 (p)) + if (p && buf32_to_u32 (p)) { - key_expire = keytimestamp + buffer_to_u32 (p); + key_expire = keytimestamp + buf32_to_u32 (p); key_expire_seen = 1; } @@ -2102,8 +2104,8 @@ merge_selfsigs_subkey (KBNODE keyblock, KBNODE subnode) subpk->pubkey_usage = key_usage; p = parse_sig_subpkt (sig->hashed, SIGSUBPKT_KEY_EXPIRE, NULL); - if (p && buffer_to_u32 (p)) - key_expire = keytimestamp + buffer_to_u32 (p); + if (p && buf32_to_u32 (p)) + key_expire = keytimestamp + buf32_to_u32 (p); else key_expire = 0; subpk->has_expired = key_expire >= curtime ? 0 : key_expire; diff --git a/g10/keygen.c b/g10/keygen.c index 078957108..11bfbd436 100644 --- a/g10/keygen.c +++ b/g10/keygen.c @@ -43,6 +43,8 @@ #include "call-agent.h" #include "pkglue.h" #include "../common/shareddefs.h" +#include "host2net.h" + /* The default algorithms. If you change them remember to change them also in gpg.c:gpgconf_list. You should also check that the value @@ -845,10 +847,7 @@ make_backsig (PKT_signature *sig, PKT_public_key *pk, } else if (buf[1] == 255) { - pktlen = buf[2] << 24; - pktlen |= buf[3] << 16; - pktlen |= buf[4] << 8; - pktlen |= buf[5]; + pktlen = buf32_to_size_t (buf+2); buf += 6; } else @@ -865,7 +864,7 @@ make_backsig (PKT_signature *sig, PKT_public_key *pk, break; case 2: - pktlen = buf[mark++] << 24; + pktlen = (size_t)buf[mark++] << 24; pktlen |= buf[mark++] << 16; case 1: diff --git a/g10/keyid.c b/g10/keyid.c index 662806b3e..9f7b70fca 100644 --- a/g10/keyid.c +++ b/g10/keyid.c @@ -35,6 +35,8 @@ #include "keydb.h" #include "i18n.h" #include "rmd160.h" +#include "host2net.h" + #define KEYID_STR_SIZE 19 @@ -256,9 +258,9 @@ v3_keyid (gcry_mpi_t a, u32 *ki) else { p = buffer + nbytes - 8; - ki[0] = (p[0] << 24) | (p[1] <<16) | (p[2] << 8) | p[3]; + ki[0] = buf32_to_u32 (p); p += 4; - ki[1] = (p[0] << 24) | (p[1] <<16) | (p[2] << 8) | p[3]; + ki[1] = buf32_to_u32 (p); } xfree (buffer); return ki[1]; @@ -378,15 +380,8 @@ keystr_from_desc(KEYDB_SEARCH_DESC *desc) { u32 keyid[2]; - keyid[0] = ((unsigned char)desc->u.fpr[12] << 24 - | (unsigned char)desc->u.fpr[13] << 16 - | (unsigned char)desc->u.fpr[14] << 8 - | (unsigned char)desc->u.fpr[15]); - keyid[1] = ((unsigned char)desc->u.fpr[16] << 24 - | (unsigned char)desc->u.fpr[17] << 16 - | (unsigned char)desc->u.fpr[18] << 8 - | (unsigned char)desc->u.fpr[19]); - + keyid[0] = buf32_to_u32 (desc->u.fpr+12); + keyid[1] = buf32_to_u32 (desc->u.fpr+16); return keystr(keyid); } @@ -427,8 +422,8 @@ keyid_from_pk (PKT_public_key *pk, u32 *keyid) if(md) { dp = gcry_md_read ( md, 0 ); - keyid[0] = dp[12] << 24 | dp[13] << 16 | dp[14] << 8 | dp[15] ; - keyid[1] = dp[16] << 24 | dp[17] << 16 | dp[18] << 8 | dp[19] ; + keyid[0] = buf32_to_u32 (dp+12); + keyid[1] = buf32_to_u32 (dp+16); lowbits = keyid[1]; gcry_md_close (md); pk->keyid[0] = keyid[0]; @@ -474,8 +469,8 @@ keyid_from_fingerprint( const byte *fprint, size_t fprint_len, u32 *keyid ) else { const byte *dp = fprint; - keyid[0] = dp[12] << 24 | dp[13] << 16 | dp[14] << 8 | dp[15] ; - keyid[1] = dp[16] << 24 | dp[17] << 16 | dp[18] << 8 | dp[19] ; + keyid[0] = buf32_to_u32 (dp+12); + keyid[1] = buf32_to_u32 (dp+16); } return keyid[1]; @@ -691,8 +686,8 @@ fingerprint_from_pk (PKT_public_key *pk, byte *array, size_t *ret_len) if (!array) array = xmalloc ( len ); memcpy (array, dp, len ); - pk->keyid[0] = dp[12] << 24 | dp[13] << 16 | dp[14] << 8 | dp[15] ; - pk->keyid[1] = dp[16] << 24 | dp[17] << 16 | dp[18] << 8 | dp[19] ; + pk->keyid[0] = buf32_to_u32 (dp+12); + pk->keyid[1] = buf32_to_u32 (dp+16); gcry_md_close( md); if (ret_len) diff --git a/g10/misc.c b/g10/misc.c index a2b5075ed..37582afa3 100644 --- a/g10/misc.c +++ b/g10/misc.c @@ -278,16 +278,6 @@ checksum_mpi (gcry_mpi_t a) return csum; } -u32 -buffer_to_u32( const byte *buffer ) -{ - unsigned long a; - a = *buffer << 24; - a |= buffer[1] << 16; - a |= buffer[2] << 8; - a |= buffer[3]; - return a; -} void print_pubkey_algo_note (pubkey_algo_t algo) diff --git a/g10/parse-packet.c b/g10/parse-packet.c index 012d37368..62320865c 100644 --- a/g10/parse-packet.c +++ b/g10/parse-packet.c @@ -34,6 +34,7 @@ #include "options.h" #include "main.h" #include "i18n.h" +#include "host2net.h" /* Maximum length of packets to avoid excessive memory allocation. */ @@ -90,7 +91,7 @@ static unsigned short read_16 (IOBUF inp) { unsigned short a; - a = iobuf_get_noeof (inp) << 8; + a = (unsigned short)iobuf_get_noeof (inp) << 8; a |= iobuf_get_noeof (inp); return a; } @@ -100,7 +101,7 @@ static unsigned long read_32 (IOBUF inp) { unsigned long a; - a = iobuf_get_noeof (inp) << 24; + a = (unsigned long)iobuf_get_noeof (inp) << 24; a |= iobuf_get_noeof (inp) << 16; a |= iobuf_get_noeof (inp) << 8; a |= iobuf_get_noeof (inp); @@ -486,7 +487,7 @@ parse (IOBUF inp, PACKET * pkt, int onlykeypkts, off_t * retpos, } else if (c == 255) { - pktlen = (hdr[hdrlen++] = iobuf_get_noeof (inp)) << 24; + pktlen = (unsigned long)(hdr[hdrlen++] = iobuf_get_noeof (inp)) << 24; pktlen |= (hdr[hdrlen++] = iobuf_get_noeof (inp)) << 16; pktlen |= (hdr[hdrlen++] = iobuf_get_noeof (inp)) << 8; if ((c = iobuf_get (inp)) == -1) @@ -1132,14 +1133,14 @@ dump_sig_subpkt (int hashed, int type, int critical, case SIGSUBPKT_SIG_CREATED: if (length >= 4) es_fprintf (listfp, "sig created %s", - strtimestamp (buffer_to_u32 (buffer))); + strtimestamp (buf32_to_u32 (buffer))); break; case SIGSUBPKT_SIG_EXPIRE: if (length >= 4) { - if (buffer_to_u32 (buffer)) + if (buf32_to_u32 (buffer)) es_fprintf (listfp, "sig expires after %s", - strtimevalue (buffer_to_u32 (buffer))); + strtimevalue (buf32_to_u32 (buffer))); else es_fprintf (listfp, "sig does not expire"); } @@ -1172,9 +1173,9 @@ dump_sig_subpkt (int hashed, int type, int critical, case SIGSUBPKT_KEY_EXPIRE: if (length >= 4) { - if (buffer_to_u32 (buffer)) + if (buf32_to_u32 (buffer)) es_fprintf (listfp, "key expires after %s", - strtimevalue (buffer_to_u32 (buffer))); + strtimevalue (buf32_to_u32 (buffer))); else es_fprintf (listfp, "key does not expire"); } @@ -1198,8 +1199,8 @@ dump_sig_subpkt (int hashed, int type, int critical, case SIGSUBPKT_ISSUER: if (length >= 8) es_fprintf (listfp, "issuer key ID %08lX%08lX", - (ulong) buffer_to_u32 (buffer), - (ulong) buffer_to_u32 (buffer + 4)); + (ulong) buf32_to_u32 (buffer), + (ulong) buf32_to_u32 (buffer + 4)); break; case SIGSUBPKT_NOTATION: { @@ -1461,8 +1462,7 @@ enum_sig_subpkt (const subpktarea_t * pktbuf, sigsubpkttype_t reqtype, { if (buflen < 4) goto too_short; - n = (buffer[0] << 24) | (buffer[1] << 16) - | (buffer[2] << 8) | buffer[3]; + n = buf32_to_size_t (buffer); buffer += 4; buflen -= 4; } @@ -1735,7 +1735,7 @@ parse_signature (IOBUF inp, int pkttype, unsigned long pktlen, p = parse_sig_subpkt (sig->hashed, SIGSUBPKT_SIG_CREATED, NULL); if (p) - sig->timestamp = buffer_to_u32 (p); + sig->timestamp = buf32_to_u32 (p); else if (!(sig->pubkey_algo >= 100 && sig->pubkey_algo <= 110) && opt.verbose) log_info ("signature packet without timestamp\n"); @@ -1743,16 +1743,16 @@ parse_signature (IOBUF inp, int pkttype, unsigned long pktlen, p = parse_sig_subpkt2 (sig, SIGSUBPKT_ISSUER, NULL); if (p) { - sig->keyid[0] = buffer_to_u32 (p); - sig->keyid[1] = buffer_to_u32 (p + 4); + sig->keyid[0] = buf32_to_u32 (p); + sig->keyid[1] = buf32_to_u32 (p + 4); } else if (!(sig->pubkey_algo >= 100 && sig->pubkey_algo <= 110) && opt.verbose) log_info ("signature packet without keyid\n"); p = parse_sig_subpkt (sig->hashed, SIGSUBPKT_SIG_EXPIRE, NULL); - if (p && buffer_to_u32 (p)) - sig->expiredate = sig->timestamp + buffer_to_u32 (p); + if (p && buf32_to_u32 (p)) + sig->expiredate = sig->timestamp + buf32_to_u32 (p); if (sig->expiredate && sig->expiredate <= make_timestamp ()) sig->flags.expired = 1; @@ -2365,8 +2365,7 @@ parse_attribute_subpkts (PKT_user_id * uid) { if (buflen < 4) goto too_short; - n = (buffer[0] << 24) | (buffer[1] << 16) - | (buffer[2] << 8) | buffer[3]; + n = buf32_to_size_t (buffer); buffer += 4; buflen -= 4; } diff --git a/g10/pubkey-enc.c b/g10/pubkey-enc.c index fcd24f86e..957476984 100644 --- a/g10/pubkey-enc.c +++ b/g10/pubkey-enc.c @@ -35,6 +35,7 @@ #include "i18n.h" #include "pkglue.h" #include "call-agent.h" +#include "host2net.h" static gpg_error_t get_it (PKT_pubkey_enc *k, @@ -321,8 +322,7 @@ get_it (PKT_pubkey_enc *enc, DEK *dek, PKT_public_key *sk, u32 *keyid) } /* Copy the key to DEK and compare the checksum. */ - csum = frame[nframe - 2] << 8; - csum |= frame[nframe - 1]; + csum = buf16_to_u16 (frame+nframe-2); memcpy (dek->key, frame + n, dek->keylen); for (csum2 = 0, n = 0; n < dek->keylen; n++) csum2 += dek->key[n]; diff --git a/g10/seckey-cert.c b/g10/seckey-cert.c index 10037567c..02dbb4859 100644 --- a/g10/seckey-cert.c +++ b/g10/seckey-cert.c @@ -115,7 +115,7 @@ xxxx_do_check( PKT_secret_key *sk, const char *tryagain_text, int mode, ndata = (ndatabits+7)/8; if ( ndata > 1 ) - csumc = p[ndata-2] << 8 | p[ndata-1]; + csumc = buf16_to_u16 (p+ndata-2); data = xmalloc_secure ( ndata ); gcry_cipher_decrypt ( cipher_hd, data, ndata, p, ndata ); gcry_mpi_release (sk->skey[i]); sk->skey[i] = NULL ; diff --git a/g10/tdbio.c b/g10/tdbio.c index 9bb8a04e0..91ee3ab78 100644 --- a/g10/tdbio.c +++ b/g10/tdbio.c @@ -1257,13 +1257,13 @@ tdbio_read_record( ulong recnum, TRUSTREC *rec, int expected ) rec->r.ver.trust_model = *p++; rec->r.ver.min_cert_level = *p++; p += 2; - rec->r.ver.created = buftoulong(p); p += 4; - rec->r.ver.nextcheck = buftoulong(p); p += 4; + rec->r.ver.created = buf32_to_ulong(p); p += 4; + rec->r.ver.nextcheck = buf32_to_ulong(p); p += 4; p += 4; p += 4; - rec->r.ver.firstfree =buftoulong(p); p += 4; + rec->r.ver.firstfree =buf32_to_ulong(p); p += 4; p += 4; - rec->r.ver.trusthashtbl =buftoulong(p); p += 4; + rec->r.ver.trusthashtbl =buf32_to_ulong(p); p += 4; if( recnum ) { log_error( _("%s: version record with recnum %lu\n"), db_name, (ulong)recnum ); @@ -1276,17 +1276,17 @@ tdbio_read_record( ulong recnum, TRUSTREC *rec, int expected ) } break; case RECTYPE_FREE: - rec->r.free.next = buftoulong(p); p += 4; + rec->r.free.next = buf32_to_ulong(p); p += 4; break; case RECTYPE_HTBL: for(i=0; i < ITEMS_PER_HTBL_RECORD; i++ ) { - rec->r.htbl.item[i] = buftoulong(p); p += 4; + rec->r.htbl.item[i] = buf32_to_ulong(p); p += 4; } break; case RECTYPE_HLST: - rec->r.hlst.next = buftoulong(p); p += 4; + rec->r.hlst.next = buf32_to_ulong(p); p += 4; for(i=0; i < ITEMS_PER_HLST_RECORD; i++ ) { - rec->r.hlst.rnum[i] = buftoulong(p); p += 4; + rec->r.hlst.rnum[i] = buf32_to_ulong(p); p += 4; } break; case RECTYPE_TRUST: @@ -1295,12 +1295,12 @@ tdbio_read_record( ulong recnum, TRUSTREC *rec, int expected ) rec->r.trust.depth = *p++; rec->r.trust.min_ownertrust = *p++; p++; - rec->r.trust.validlist = buftoulong(p); p += 4; + rec->r.trust.validlist = buf32_to_ulong(p); p += 4; break; case RECTYPE_VALID: memcpy( rec->r.valid.namehash, p, 20); p+=20; rec->r.valid.validity = *p++; - rec->r.valid.next = buftoulong(p); p += 4; + rec->r.valid.next = buf32_to_ulong(p); p += 4; rec->r.valid.full_count = *p++; rec->r.valid.marginal_count = *p++; break; diff --git a/g10/trust.c b/g10/trust.c index 796694d59..316fe2fe1 100644 --- a/g10/trust.c +++ b/g10/trust.c @@ -33,6 +33,7 @@ #include "main.h" #include "i18n.h" #include "trustdb.h" +#include "host2net.h" /* Return true if key is disabled. Note that this is usually used via @@ -536,7 +537,7 @@ mark_usable_uid_certs (kbnode_t keyblock, kbnode_t uidnode, u32 expire; p = parse_sig_subpkt (sig->hashed, SIGSUBPKT_SIG_EXPIRE, NULL ); - expire = p? sig->timestamp + buffer_to_u32(p) : 0; + expire = p? sig->timestamp + buf32_to_u32(p) : 0; if (expire==0 || expire > curtime ) { diff --git a/g13/mount.c b/g13/mount.c index a9203d11f..8d1c0150f 100644 --- a/g13/mount.c +++ b/g13/mount.c @@ -37,6 +37,7 @@ #include "call-gpg.h" #include "mountinfo.h" #include "runner.h" +#include "host2net.h" /* Parse the header prefix and return the length of the entire header. */ @@ -50,8 +51,7 @@ parse_header (const char *filename, if (packetlen != 32) return gpg_error (GPG_ERR_BUG); - len = ((packet[2] << 24) | (packet[3] << 16) - | (packet[4] << 8) | packet[5]); + len = buf32_to_uint (packet+2); if (packet[0] != (0xc0|61) || len < 26 || memcmp (packet+6, "GnuPG/G13", 10)) { @@ -76,8 +76,7 @@ parse_header (const char *filename, return gpg_error (GPG_ERR_NOT_IMPLEMENTED); } - len = ((packet[20] << 24) | (packet[21] << 16) - | (packet[22] << 8) | packet[23]); + len = buf32_to_uint (packet+20); /* Do a basic sanity check on the length. */ if (len < 32 || len > 1024*1024) diff --git a/kbx/keybox-dump.c b/kbx/keybox-dump.c index 5315e8444..8815a6f7f 100644 --- a/kbx/keybox-dump.c +++ b/kbx/keybox-dump.c @@ -25,30 +25,14 @@ #include "keybox-defs.h" #include +#include "host2net.h" /* Argg, we can't include ../common/util.h */ char *bin2hexcolon (const void *buffer, size_t length, char *stringbuf); +#define get32(a) buf32_to_ulong ((a)) +#define get16(a) buf16_to_ulong ((a)) -static ulong -get32 (const byte *buffer) -{ - ulong a; - a = *buffer << 24; - a |= buffer[1] << 16; - a |= buffer[2] << 8; - a |= buffer[3]; - return a; -} - -static ulong -get16 (const byte *buffer) -{ - ulong a; - a = *buffer << 8; - a |= buffer[1]; - return a; -} void print_string (FILE *fp, const byte *p, size_t n, int delim) diff --git a/kbx/keybox-openpgp.c b/kbx/keybox-openpgp.c index 6ae6c44ce..2cac242e9 100644 --- a/kbx/keybox-openpgp.c +++ b/kbx/keybox-openpgp.c @@ -36,7 +36,7 @@ #include #include "../common/openpgpdefs.h" - +#include "host2net.h" /* Assume a valid OpenPGP packet at the address pointed to by BUFBTR which has a maximum length as stored at BUFLEN. Return the header @@ -94,10 +94,8 @@ next_packet (unsigned char const **bufptr, size_t *buflen, { if (len <4 ) return gpg_error (GPG_ERR_INV_PACKET); /* No length bytes. */ - pktlen = (*buf++) << 24; - pktlen |= (*buf++) << 16; - pktlen |= (*buf++) << 8; - pktlen |= (*buf++); + pktlen = buf32_to_ulong (buf); + buf += 4; len -= 4; } else /* Partial length encoding is not allowed for key packets. */ diff --git a/kbx/keybox-search.c b/kbx/keybox-search.c index 0a3ed43d0..d22ef1921 100644 --- a/kbx/keybox-search.c +++ b/kbx/keybox-search.c @@ -29,7 +29,7 @@ #include "keybox-defs.h" #include - +#include "host2net.h" #define xtoi_1(p) (*(p) <= '9'? (*(p)- '0'): \ *(p) <= 'F'? (*(p)-'A'+10):(*(p)-'a'+10)) @@ -42,27 +42,8 @@ struct sn_array_s { }; - -static inline ulong -get32 (const byte *buffer) -{ - ulong a; - a = *buffer << 24; - a |= buffer[1] << 16; - a |= buffer[2] << 8; - a |= buffer[3]; - return a; -} - -static inline ulong -get16 (const byte *buffer) -{ - ulong a; - a = *buffer << 8; - a |= buffer[1]; - return a; -} - +#define get32(a) buf32_to_ulong ((a)) +#define get16(a) buf16_to_ulong ((a)) static inline unsigned int diff --git a/kbx/keybox-update.c b/kbx/keybox-update.c index 7b207a520..4b14b2f23 100644 --- a/kbx/keybox-update.c +++ b/kbx/keybox-update.c @@ -28,6 +28,7 @@ #include "keybox-defs.h" #include "../common/sysutils.h" +#include "../common/host2net.h" #define EXTSEP_S "." @@ -734,8 +735,7 @@ keybox_compress (KEYBOX_HANDLE hd) buffer = _keybox_get_blob_image (blob, &length); if (length > 4 && buffer[4] == KEYBOX_BLOBTYPE_HEADER) { - u32 last_maint = ((buffer[20] << 24) | (buffer[20+1] << 16) - | (buffer[20+2] << 8) | (buffer[20+3])); + u32 last_maint = buf32_to_u32 (buffer+20); if ( (last_maint + 3*3600) > time (NULL) ) { @@ -811,7 +811,7 @@ keybox_compress (KEYBOX_HANDLE hd) rc = gpg_error (GPG_ERR_BUG); break; } - blobflags = ((buffer[pos] << 8) | (buffer[pos+1])); + blobflags = buf16_to_uint (buffer+pos); if ((blobflags & KEYBOX_FLAG_BLOB_EPHEMERAL)) { /* This is an ephemeral blob. */ @@ -820,8 +820,7 @@ keybox_compress (KEYBOX_HANDLE hd) || size != 4) created_at = 0; /* oops. */ else - created_at = ((buffer[pos] << 24) | (buffer[pos+1] << 16) - | (buffer[pos+2] << 8) | (buffer[pos+3])); + created_at = buf32_to_u32 (buffer+pos); if (created_at && created_at < cut_time) { diff --git a/scd/apdu.c b/scd/apdu.c index 4ec6b4d00..e5db4f096 100644 --- a/scd/apdu.c +++ b/scd/apdu.c @@ -59,6 +59,7 @@ #include "scdaemon.h" #include "exechelp.h" #endif /* GNUPG_MAJOR_VERSION != 1 */ +#include "host2net.h" #include "iso7816.h" #include "apdu.h" @@ -1047,15 +1048,14 @@ pcsc_get_status_wrapped (int slot, unsigned int *status) i? strerror (errno) : "premature EOF"); goto command_failed; } - len = (msgbuf[1] << 24) | (msgbuf[2] << 16) | (msgbuf[3] << 8 ) | msgbuf[4]; + len = buf_to_size_t (msgbuf+1); if (msgbuf[0] != 0x81 || len < 4) { log_error ("invalid response header from PC/SC received\n"); goto command_failed; } len -= 4; /* Already read the error code. */ - err = PCSC_ERR_MASK ((msgbuf[5] << 24) | (msgbuf[6] << 16) - | (msgbuf[7] << 8 ) | msgbuf[8]); + err = PCSC_ERR_MASK (buf32_to_ulong (msgbuf+5)); if (err) { log_error ("pcsc_status failed: %s (0x%lx)\n", @@ -1218,15 +1218,14 @@ pcsc_send_apdu_wrapped (int slot, unsigned char *apdu, size_t apdulen, i? strerror (errno) : "premature EOF"); goto command_failed; } - len = (msgbuf[1] << 24) | (msgbuf[2] << 16) | (msgbuf[3] << 8 ) | msgbuf[4]; + len = buf_to_size_t (msgbuf+1); if (msgbuf[0] != 0x81 || len < 4) { log_error ("invalid response header from PC/SC received\n"); goto command_failed; } len -= 4; /* Already read the error code. */ - err = PCSC_ERR_MASK ((msgbuf[5] << 24) | (msgbuf[6] << 16) - | (msgbuf[7] << 8 ) | msgbuf[8]); + err = PCSC_ERR_MASK (buf32_to_ulong (msgbuf+5)); if (err) { log_error ("pcsc_transmit failed: %s (0x%lx)\n", @@ -1359,15 +1358,14 @@ control_pcsc_wrapped (int slot, pcsc_dword_t ioctl_code, i? strerror (errno) : "premature EOF"); goto command_failed; } - len = (msgbuf[1] << 24) | (msgbuf[2] << 16) | (msgbuf[3] << 8 ) | msgbuf[4]; + len = buf32_to_size_t (msgbuf+1); if (msgbuf[0] != 0x81 || len < 4) { log_error ("invalid response header from PC/SC received\n"); goto command_failed; } len -= 4; /* Already read the error code. */ - err = PCSC_ERR_MASK ((msgbuf[5] << 24) | (msgbuf[6] << 16) - | (msgbuf[7] << 8 ) | msgbuf[8]); + err = PCSC_ERR_MASK (buf32_to_ulong (msgbuf+5)); if (err) { log_error ("pcsc_control failed: %s (0x%lx)\n", @@ -1497,15 +1495,14 @@ close_pcsc_reader_wrapped (int slot) i? strerror (errno) : "premature EOF"); goto command_failed; } - len = (msgbuf[1] << 24) | (msgbuf[2] << 16) | (msgbuf[3] << 8 ) | msgbuf[4]; + len = buf32_to_size_t (msgbuf+1); if (msgbuf[0] != 0x81 || len < 4) { log_error ("invalid response header from PC/SC received\n"); goto command_failed; } len -= 4; /* Already read the error code. */ - err = PCSC_ERR_MASK ((msgbuf[5] << 24) | (msgbuf[6] << 16) - | (msgbuf[7] << 8 ) | msgbuf[8]); + err = PCSC_ERR_MASK (buf32_to_ulong (msgbuf+5)); if (err) log_error ("pcsc_close failed: %s (0x%lx)\n", pcsc_error_string (err), err); @@ -1687,7 +1684,7 @@ reset_pcsc_reader_wrapped (int slot) i? strerror (errno) : "premature EOF"); goto command_failed; } - len = (msgbuf[1] << 24) | (msgbuf[2] << 16) | (msgbuf[3] << 8 ) | msgbuf[4]; + len = buf32_to_size_t (msgbuf+1); if (msgbuf[0] != 0x81 || len < 4) { log_error ("invalid response header from PC/SC received\n"); @@ -1701,8 +1698,7 @@ reset_pcsc_reader_wrapped (int slot) sw = SW_HOST_GENERAL_ERROR; goto command_failed; } - err = PCSC_ERR_MASK ((msgbuf[5] << 24) | (msgbuf[6] << 16) - | (msgbuf[7] << 8 ) | msgbuf[8]); + err = PCSC_ERR_MASK (buf32_to_ulong (msgbuf+5)); if (err) { log_error ("PC/SC RESET failed: %s (0x%lx)\n", @@ -1794,9 +1790,9 @@ pcsc_vendor_specific_init (int slot) if (l == 1) v = p[0]; else if (l == 2) - v = ((p[0] << 8) | p[1]); + v = buf16_to_uint (p); else if (l == 4) - v = ((p[0] << 24) | (p[1] << 16) | (p[2] << 8) | p[3]); + v = buf32_to_uint (p); if (code == FEATURE_VERIFY_PIN_DIRECT) reader_table[slot].pcsc.verify_ioctl = v; @@ -1855,9 +1851,9 @@ pcsc_vendor_specific_init (int slot) if (l == 1) v = p[0]; else if (l == 2) - v = ((p[1] << 8) | p[0]); + v = buf16_to_uint (p); else if (l == 4) - v = ((p[3] << 24) | (p[2] << 16) | (p[1] << 8) | p[0]); + v = buf32_to_uint (p); if (tag == PCSCv2_PART10_PROPERTY_bMinPINSize) reader_table[slot].pcsc.pinmin = v; @@ -2151,7 +2147,7 @@ open_pcsc_reader_wrapped (const char *portstr) i? strerror (errno) : "premature EOF"); goto command_failed; } - len = (msgbuf[1] << 24) | (msgbuf[2] << 16) | (msgbuf[3] << 8 ) | msgbuf[4]; + len = buf32_to_size_t (msgbuf+1); if (msgbuf[0] != 0x81 || len < 4) { log_error ("invalid response header from PC/SC received\n"); @@ -2164,9 +2160,7 @@ open_pcsc_reader_wrapped (const char *portstr) (unsigned long)len); goto command_failed; } - err = PCSC_ERR_MASK ((msgbuf[5] << 24) | (msgbuf[6] << 16) - | (msgbuf[7] << 8 ) | msgbuf[8]); - + err = PCSC_ERR_MASK (buf32_to_ulong (msgbuf+5)); if (err) { log_error ("PC/SC OPEN failed: %s\n", pcsc_error_string (err)); diff --git a/scd/app-nks.c b/scd/app-nks.c index 19a33ed12..d0b96a906 100644 --- a/scd/app-nks.c +++ b/scd/app-nks.c @@ -56,6 +56,7 @@ #include "app-common.h" #include "tlv.h" #include "apdu.h" +#include "host2net.h" static char const aid_nks[] = { 0xD2, 0x76, 0x00, 0x00, 0x03, 0x01, 0x02 }; static char const aid_sigg[] = { 0xD2, 0x76, 0x00, 0x00, 0x66, 0x01 }; @@ -278,7 +279,7 @@ get_chv_status (app_t app, int sigg, int pwid) rc = -1; /* Error. */ else { - unsigned int sw = ((result[resultlen-2] << 8) | result[resultlen-1]); + unsigned int sw = buf16_to_uint (result+resultlen-2); if (sw == 0x6a88) rc = -2; /* No such PIN. */ diff --git a/scd/app-openpgp.c b/scd/app-openpgp.c index f68813bfd..6583fb278 100644 --- a/scd/app-openpgp.c +++ b/scd/app-openpgp.c @@ -67,6 +67,7 @@ #include "iso7816.h" #include "app-common.h" #include "tlv.h" +#include "host2net.h" /* A table describing the DOs of the card. */ @@ -876,7 +877,7 @@ send_fprtime_if_not_null (ctrl_t ctrl, const char *keyword, char numbuf1[50], numbuf2[50]; unsigned long value; - value = (stamp[0] << 24) | (stamp[1]<<16) | (stamp[2]<<8) | stamp[3]; + value = buf32_to_ulong (stamp); if (!value) return; sprintf (numbuf1, "%d", number); diff --git a/scd/ccid-driver.c b/scd/ccid-driver.c index fdfe1f510..1926f7115 100644 --- a/scd/ccid-driver.c +++ b/scd/ccid-driver.c @@ -290,7 +290,7 @@ static int send_escape_cmd (ccid_driver_t handle, const unsigned char *data, static unsigned int convert_le_u32 (const unsigned char *buf) { - return buf[0] | (buf[1] << 8) | (buf[2] << 16) | (buf[3] << 24); + return buf[0] | (buf[1] << 8) | (buf[2] << 16) | ((unsigned int)buf[3] << 24); } diff --git a/sm/fingerprint.c b/sm/fingerprint.c index b849afb4e..a82945eb2 100644 --- a/sm/fingerprint.c +++ b/sm/fingerprint.c @@ -31,6 +31,9 @@ #include #include +#include "host2net.h" + + /* Return the fingerprint of the certificate (we can't put this into libksba because we need libgcrypt support). The caller must provide an array of sufficient length or NULL so that the function @@ -149,14 +152,8 @@ gpgsm_get_short_fingerprint (ksba_cert_t cert, unsigned long *r_high) gpgsm_get_fingerprint (cert, GCRY_MD_SHA1, digest, NULL); if (r_high) - *r_high = (((unsigned long)digest[12]<<24) - |(digest[13]<<16) - |(digest[14]<< 8) - |digest[15]); - return (((unsigned long)digest[16]<<24) - |(digest[17]<<16) - |(digest[18]<<8) - |digest[19]); + *r_high = buf32_to_ulong (digest+12); + return buf32_to_ulong (digest + 16); } diff --git a/tools/ccidmon.c b/tools/ccidmon.c index 1137bab00..4e39b5c1d 100644 --- a/tools/ccidmon.c +++ b/tools/ccidmon.c @@ -145,7 +145,7 @@ err (const char *format, ...) static unsigned int convert_le_u32 (const unsigned char *buf) { - return buf[0] | (buf[1] << 8) | (buf[2] << 16) | (buf[3] << 24); + return buf[0] | (buf[1] << 8) | (buf[2] << 16) | ((unsigned int)buf[3] << 24); }