mirror of
https://codeberg.org/libreboot/lbmk.git
synced 2026-07-18 14:12:44 +02:00
libreboot-utils: safe memcmp
Signed-off-by: Leah Rowe <leah@libreboot.org>
This commit is contained in:
@@ -378,6 +378,7 @@ char *smalloc(char **buf, size_t size);
|
|||||||
void *vmalloc(void **buf, size_t size);
|
void *vmalloc(void **buf, size_t size);
|
||||||
int slen(const char *scmp, size_t maxlen,
|
int slen(const char *scmp, size_t maxlen,
|
||||||
size_t *rval);
|
size_t *rval);
|
||||||
|
int vcmp(const void *s1, const void *s2, size_t n);
|
||||||
int scmp(const char *a, const char *b,
|
int scmp(const char *a, const char *b,
|
||||||
size_t maxlen, int *rval);
|
size_t maxlen, int *rval);
|
||||||
int sdup(const char *s,
|
int sdup(const char *s,
|
||||||
|
|||||||
@@ -143,7 +143,7 @@ read_file(void)
|
|||||||
if (_r < 0)
|
if (_r < 0)
|
||||||
err_exit(errno, "%s: read failed (cmp)", f->tname);
|
err_exit(errno, "%s: read failed (cmp)", f->tname);
|
||||||
|
|
||||||
if (memcmp(f->buf, f->bufcmp, f->gbe_file_size) != 0)
|
if (vcmp(f->buf, f->bufcmp, f->gbe_file_size) != 0)
|
||||||
err_exit(errno, "%s: %s: read contents differ (pre-test)",
|
err_exit(errno, "%s: %s: read contents differ (pre-test)",
|
||||||
f->fname, f->tname);
|
f->fname, f->tname);
|
||||||
}
|
}
|
||||||
@@ -329,7 +329,7 @@ check_written_part(size_t p)
|
|||||||
f->rw_check_err_read[p] = f->io_err_gbe = 1;
|
f->rw_check_err_read[p] = f->io_err_gbe = 1;
|
||||||
else if ((size_t)rval != gbe_rw_size)
|
else if ((size_t)rval != gbe_rw_size)
|
||||||
f->rw_check_partial_read[p] = f->io_err_gbe = 1;
|
f->rw_check_partial_read[p] = f->io_err_gbe = 1;
|
||||||
else if (memcmp(mem_offset, f->pad, gbe_rw_size) != 0)
|
else if (vcmp(mem_offset, f->pad, gbe_rw_size) != 0)
|
||||||
f->rw_check_bad_part[p] = f->io_err_gbe = 1;
|
f->rw_check_bad_part[p] = f->io_err_gbe = 1;
|
||||||
|
|
||||||
if (f->rw_check_err_read[p] ||
|
if (f->rw_check_err_read[p] ||
|
||||||
|
|||||||
@@ -567,7 +567,7 @@ mkhtemp(int *fd,
|
|||||||
if_err(fname_len > template_len, EOVERFLOW))
|
if_err(fname_len > template_len, EOVERFLOW))
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
if (if_err(memcmp(fname, template + template_len - fname_len,
|
if (if_err(vcmp(fname, template + template_len - fname_len,
|
||||||
fname_len) != 0, EINVAL))
|
fname_len) != 0, EINVAL))
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
|
|||||||
@@ -292,6 +292,39 @@ err:
|
|||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* because no libc reimagination is complete
|
||||||
|
* without a reimplementation of memcmp. and
|
||||||
|
* no safe one is complete without null checks.
|
||||||
|
*/
|
||||||
|
int
|
||||||
|
vcmp(const void *s1, const void *s2, size_t n)
|
||||||
|
{
|
||||||
|
size_t i = 0;
|
||||||
|
size_t a;
|
||||||
|
size_t b;
|
||||||
|
|
||||||
|
if (if_err(s1 == NULL || s2 == NULL, EFAULT))
|
||||||
|
err_exit(EFAULT, "vcmp: null input");
|
||||||
|
|
||||||
|
const unsigned char *x = s1;
|
||||||
|
const unsigned char *y = s2;
|
||||||
|
|
||||||
|
for ( ; i + sizeof(size_t) <= n; i += sizeof(size_t)) {
|
||||||
|
|
||||||
|
memcpy(&a, x + i, sizeof(size_t));
|
||||||
|
memcpy(&b, y + i, sizeof(size_t));
|
||||||
|
|
||||||
|
if (a != b)
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
for ( ; i < n; i++)
|
||||||
|
if (x[i] != y[i])
|
||||||
|
return (int)x[i] - (int)y[i];
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
/* on functions that return with errno,
|
/* on functions that return with errno,
|
||||||
* i sometimes have a default fallback,
|
* i sometimes have a default fallback,
|
||||||
* which is set if errno wasn't changed,
|
* which is set if errno wasn't changed,
|
||||||
|
|||||||
@@ -28,7 +28,7 @@ main(int argc, char **argv)
|
|||||||
xpledgex("stdio", NULL);
|
xpledgex("stdio", NULL);
|
||||||
|
|
||||||
buf = rmalloc(size);
|
buf = rmalloc(size);
|
||||||
if (!memcmp(buf, buf + (size >> 1), size >> 1))
|
if (!vcmp(buf, buf + (size >> 1), size >> 1))
|
||||||
same = 1;
|
same = 1;
|
||||||
|
|
||||||
if (argc < 2) /* no spew */
|
if (argc < 2) /* no spew */
|
||||||
|
|||||||
Reference in New Issue
Block a user