diff options
author | Volker Lendecke <vl@samba.org> | 2018-10-02 13:16:23 +0200 |
---|---|---|
committer | Jeremy Allison <jra@samba.org> | 2018-10-08 22:17:09 +0200 |
commit | a9ed0e93bbd6cd32ed1d35b1279b401d1755d1e5 (patch) | |
tree | a8801ccb8a383894886a01aa495abf07dc574dba /source3 | |
parent | 2a35cbb02f09e490f2b533849a08100881f12230 (diff) | |
download | samba-a9ed0e93bbd6cd32ed1d35b1279b401d1755d1e5.tar.gz |
registry: Add error checks to regdb_unpack_values
This makes "regdb_unpack_values" take a size_t as buflen. The only
caller calls it with TDB_DATA.dsize, which *is* size_t. Convert the
internal "len" variable to the unsigned size_t as well and add overflow
checks. This depends on tdb_unpack to either return -1 or a positive
value less than or equal to the passed-in "size_t" buflen;
Signed-off-by: Volker Lendecke <vl@samba.org>
Reviewed-by: Jeremy Allison <jra@samba.org>
Diffstat (limited to 'source3')
-rw-r--r-- | source3/registry/reg_backend_db.c | 36 |
1 files changed, 28 insertions, 8 deletions
diff --git a/source3/registry/reg_backend_db.c b/source3/registry/reg_backend_db.c index a0db5eab9ce..32189101e31 100644 --- a/source3/registry/reg_backend_db.c +++ b/source3/registry/reg_backend_db.c @@ -1833,9 +1833,12 @@ static int regdb_fetch_keys(const char *key, struct regsubkey_ctr *ctr) Unpack a list of registry values frem the TDB ***************************************************************************/ -static int regdb_unpack_values(struct regval_ctr *values, uint8_t *buf, int buflen) +static int regdb_unpack_values(struct regval_ctr *values, + uint8_t *buf, + size_t buflen) { - int len = 0; + int this_len; + size_t len = 0; uint32_t type; fstring valuename; uint32_t size; @@ -1845,7 +1848,13 @@ static int regdb_unpack_values(struct regval_ctr *values, uint8_t *buf, int bufl /* loop and unpack the rest of the registry values */ - len += tdb_unpack(buf+len, buflen-len, "d", &num_values); + this_len = tdb_unpack(buf, buflen, "d", &num_values); + if (this_len == -1) { + DBG_WARNING("Invalid registry data, " + "tdb_unpack failed\n"); + return -1; + } + len = this_len; for ( i=0; i<num_values; i++ ) { /* unpack the next regval */ @@ -1854,11 +1863,22 @@ static int regdb_unpack_values(struct regval_ctr *values, uint8_t *buf, int bufl size = 0; data_p = NULL; valuename[0] = '\0'; - len += tdb_unpack(buf+len, buflen-len, "fdB", - valuename, - &type, - &size, - &data_p); + this_len = tdb_unpack(buf+len, buflen-len, "fdB", + valuename, + &type, + &size, + &data_p); + if (this_len == -1) { + DBG_WARNING("Invalid registry data, " + "tdb_unpack failed\n"); + return -1; + } + len += this_len; + if (len < (size_t)this_len) { + DBG_WARNING("Invalid registry data, " + "integer overflow\n"); + return -1; + } regval_ctr_addvalue(values, valuename, type, (uint8_t *)data_p, size); |