xref: /minix3/common/lib/libc/string/consttime_memequal.c (revision 84d9c625bfea59e274550651111ae9edfdc40fbd)
1*84d9c625SLionel Sambuc /* $NetBSD: consttime_memequal.c,v 1.4 2013/08/28 19:31:14 riastradh Exp $ */
2*84d9c625SLionel Sambuc 
3*84d9c625SLionel Sambuc #if !defined(_KERNEL) && !defined(_STANDALONE)
4*84d9c625SLionel Sambuc #include "namespace.h"
5*84d9c625SLionel Sambuc #include <string.h>
6*84d9c625SLionel Sambuc #ifdef __weak_alias
7*84d9c625SLionel Sambuc __weak_alias(consttime_memequal,_consttime_memequal)
8*84d9c625SLionel Sambuc #endif
9*84d9c625SLionel Sambuc #else
10*84d9c625SLionel Sambuc #include <lib/libkern/libkern.h>
11*84d9c625SLionel Sambuc #endif
12*84d9c625SLionel Sambuc 
13*84d9c625SLionel Sambuc int
14*84d9c625SLionel Sambuc consttime_memequal(const void *b1, const void *b2, size_t len)
15*84d9c625SLionel Sambuc {
16*84d9c625SLionel Sambuc 	const char *c1 = b1, *c2 = b2;
17*84d9c625SLionel Sambuc 	int res = 0;
18*84d9c625SLionel Sambuc 
19*84d9c625SLionel Sambuc 	while (len --)
20*84d9c625SLionel Sambuc 		res |= *c1++ ^ *c2++;
21*84d9c625SLionel Sambuc 
22*84d9c625SLionel Sambuc 	/*
23*84d9c625SLionel Sambuc 	 * If the compiler for your favourite architecture generates a
24*84d9c625SLionel Sambuc 	 * conditional branch for `!res', it will be a data-dependent
25*84d9c625SLionel Sambuc 	 * branch, in which case this should be replaced by
26*84d9c625SLionel Sambuc 	 *
27*84d9c625SLionel Sambuc 	 *	return (1 - (1 & ((res - 1) >> 8)));
28*84d9c625SLionel Sambuc 	 *
29*84d9c625SLionel Sambuc 	 * or rewritten in assembly.
30*84d9c625SLionel Sambuc 	 */
31*84d9c625SLionel Sambuc 	return !res;
32*84d9c625SLionel Sambuc }
33