71 ct_cmovw(ct_sltuw(launderw(byte_idx), byte_len), srcp, decoy1));
73 ct_cmovw(ct_sltuw(launderw(byte_idx), byte_len), destp, decoy2));
82void hardened_memshred(uint32_t *dest,
size_t word_len) {
84 random_order_init(&order, word_len);
87 size_t expected_count = random_order_len(&order);
89 uintptr_t data_addr = (uintptr_t)dest;
92 uintptr_t decoy_addr = (uintptr_t)&decoys;
94 size_t byte_len = word_len *
sizeof(uint32_t);
95 for (; count < expected_count; count = launderw(count) + 1) {
96 size_t byte_idx = launderw(random_order_advance(&order)) *
sizeof(uint32_t);
99 uintptr_t datap = data_addr + byte_idx;
100 uintptr_t decoy = decoy_addr + (byte_idx %
sizeof(decoys));
102 void *data = (
void *)launderw(
103 ct_cmovw(ct_sltuw(launderw(byte_idx), byte_len), datap, decoy));
116 random_order_init(&order, word_len);
119 size_t expected_count = random_order_len(&order);
121 uintptr_t lhs_addr = (uintptr_t)lhs;
122 uintptr_t rhs_addr = (uintptr_t)rhs;
127 uint32_t decoys[8] = {
128 0xaaaaaaaa, 0xaaaaaaaa, 0xaaaaaaaa, 0xaaaaaaaa,
129 0xaaaaaaaa, 0xaaaaaaaa, 0xaaaaaaaa, 0xaaaaaaaa,
131 uintptr_t decoy_addr = (uintptr_t)&decoys;
134 uint32_t ones = UINT32_MAX;
138 size_t byte_len = word_len *
sizeof(uint32_t);
139 for (; count < expected_count; count = launderw(count) + 1) {
140 size_t byte_idx = launderw(random_order_advance(&order)) *
sizeof(uint32_t);
143 uintptr_t ap = lhs_addr + byte_idx;
144 uintptr_t bp = rhs_addr + byte_idx;
145 uintptr_t decoy1 = decoy_addr + (byte_idx %
sizeof(decoys));
148 ((byte_idx + (
sizeof(decoys) / 2) +
sizeof(uint32_t)) %
sizeof(decoys));
150 void *av = (
void *)launderw(
151 ct_cmovw(ct_sltuw(launderw(byte_idx), byte_len), ap, decoy1));
152 void *bv = (
void *)launderw(
153 ct_cmovw(ct_sltuw(launderw(byte_idx), byte_len), bp, decoy2));
155 uint32_t a = read_32(av);
156 uint32_t b = read_32(bv);
163 zeros = launder32(zeros) | (launder32(a) ^ b);
167 ones = launder32(ones) & (launder32(a) ^ ~b);
172 if (launder32(zeros) == 0) {
177 HARDENED_CHECK_NE(ones, UINT32_MAX);