Migrate from @unaligned_load to mem::load

This commit is contained in:
Christoffer Lerno
2026-01-17 19:12:32 +01:00
parent a326e31e57
commit d3ebd4a130
9 changed files with 41 additions and 41 deletions

View File

@@ -101,7 +101,7 @@ macro read(bytes, $Type)
$default: $default:
ptr = bytes[..].ptr; ptr = bytes[..].ptr;
$endswitch $endswitch
return bitcast(@unaligned_load(*(char[$Type.sizeof]*)ptr, 1), $Type).val; return bitcast(mem::load((char[$Type.sizeof]*)ptr, $align: 1), $Type).val;
} }
<* <*
@@ -118,7 +118,7 @@ macro write(x, bytes, $Type)
$default: $default:
ptr = bytes[..].ptr; ptr = bytes[..].ptr;
$endswitch $endswitch
@unaligned_store(*($typeof(x)*)ptr, bitcast(x, $Type).val, 1); mem::store(($typeof(x)*)ptr, bitcast(x, $Type).val, 1);
} }
macro bool is_bitorder($Type) macro bool is_bitorder($Type)

View File

@@ -142,7 +142,7 @@ fn void ChaCha20.transform(&self, char[] data)
char[] aligned_data = data[offset..]; char[] aligned_data = data[offset..];
for (; x <= (BLOCK_SIZE - usz.sizeof); x += usz.sizeof) for (; x <= (BLOCK_SIZE - usz.sizeof); x += usz.sizeof)
{ {
((usz*)aligned_data.ptr)[x / usz.sizeof] ^= @unaligned_load(*(usz*)(&key_stream[x]), 1); ((usz*)aligned_data.ptr)[x / usz.sizeof] ^= mem::load((usz*)(&key_stream[x]), $align: 1);
} }
for (; x < BLOCK_SIZE; x++) data[x] ^= key_stream[x]; for (; x < BLOCK_SIZE; x++) data[x] ^= key_stream[x];
} }

View File

@@ -62,8 +62,8 @@ fn ulong hash(char[] data, ulong seed = 0)
for (; data.len > 16; data = data[16..]) for (; data.len > 16; data = data[16..])
{ {
@a5mul( @a5mul(
@unaligned_load(((ulong*)data.ptr)[0], 1) ^ seed1, mem::load((ulong*)data.ptr, 1) ^ seed1,
@unaligned_load(((ulong*)data.ptr)[1], 1) ^ seed2, mem::load((ulong*)data.ptr + 1, 1) ^ seed2,
seed1, seed2 seed1, seed2
); );
@@ -71,16 +71,16 @@ fn ulong hash(char[] data, ulong seed = 0)
seed2 += val10; seed2 += val10;
} }
a = @unaligned_load(*(ulong*)(data.ptr + (uptr)data.len - 16), 1); a = mem::load((ulong*)(data.ptr + (uptr)data.len - 16), 1);
b = @unaligned_load(*(ulong*)(data.ptr + (uptr)data.len - 8), 1); b = mem::load((ulong*)(data.ptr + (uptr)data.len - 8), 1);
} }
else else
{ {
a = ((ulong)@unaligned_load(*(uint*)&data[0], 1) << 32) a = ((ulong)mem::load((uint*)&data[0], 1) << 32)
| @unaligned_load(*(uint*)&data[^4], 1); | mem::load((uint*)&data[^4], 1);
b = ((ulong)@unaligned_load(*(uint*)&data[(data.len >> 3) * 4], 1) << 32) b = ((ulong)mem::load((uint*)&data[(data.len >> 3) * 4], 1) << 32)
| @unaligned_load(*(uint*)(data.ptr + data.len - 4 - (data.len >> 3) * 4), 1); | mem::load((uint*)(data.ptr + data.len - 4 - (data.len >> 3) * 4), 1);
} }
} }
else else

View File

@@ -229,7 +229,7 @@ fn void Blake3.init(&self, char[] key = {}, char explicit_flags = 0)
if (key.len) if (key.len)
{ {
foreach (i, &w : self.key) *w = @unaligned_load(*(uint*)&key[i * $sizeof(self.key[0])], 1); foreach (i, &w : self.key) *w = mem::load((uint*)&key[i * $sizeof(self.key[0])], 1);
if (!explicit_flags) explicit_flags = Blake3Flags.KEYED_HASH; if (!explicit_flags) explicit_flags = Blake3Flags.KEYED_HASH;
} }
else else
@@ -599,7 +599,7 @@ macro @round(uint[] state, uint* msg, usz round) @local
fn void compress_pre(uint[] state, uint[] cv, char[BLOCK_SIZE] block, usz block_len, ulong counter, char flags) @local @noinline fn void compress_pre(uint[] state, uint[] cv, char[BLOCK_SIZE] block, usz block_len, ulong counter, char flags) @local @noinline
{ {
uint[16] block_words @noinit; uint[16] block_words @noinit;
foreach (i, &b : block_words) *b = @unaligned_load(*(uint*)&block[i * 4], 1); foreach (i, &b : block_words) *b = mem::load((uint*)&block[i * 4], 1);
state[0:8] = cv[0:8]; state[0:8] = cv[0:8];
state[8:4] = IV[0:4]; state[8:4] = IV[0:4];
state[12] = (uint)counter; state[12] = (uint)counter;
@@ -626,8 +626,8 @@ macro compress_xof(uint[] cv, char[BLOCK_SIZE] block, usz block_len, ulong count
{ {
uint[16] state @noinit; uint[16] state @noinit;
compress_pre(state[..], cv, block, block_len, counter, flags); compress_pre(state[..], cv, block, block_len, counter, flags);
$for usz $i = 0; $i < 8; $i++: @unaligned_store(*(uint*)&out[4 * $i], state[$i] ^ state[$i + 8], 1); $endfor $for usz $i = 0; $i < 8; $i++: mem::store((uint*)&out[4 * $i], state[$i] ^ state[$i + 8], 1); $endfor
$for usz $i = 0; $i < 8; $i++: @unaligned_store(*(uint*)&out[4 * (8 + $i)], state[$i + 8] ^ cv[$i], 1); $endfor $for usz $i = 0; $i < 8; $i++: mem::store((uint*)&out[4 * (8 + $i)], state[$i + 8] ^ cv[$i], 1); $endfor
} }
macro @xof_many(uint[] cv, char[BLOCK_SIZE] block, usz block_len, ulong counter, char flags, char[] out, usz out_blocks) @local macro @xof_many(uint[] cv, char[BLOCK_SIZE] block, usz block_len, ulong counter, char flags, char[] out, usz out_blocks) @local
@@ -645,7 +645,7 @@ macro hash_one(char* input, usz blocks, uint[] key, ulong counter, char flags, c
if (blocks == 1) block_flags |= flags_end; if (blocks == 1) block_flags |= flags_end;
compress_in_place(cv[..], input[:BLOCK_SIZE], BLOCK_SIZE, counter, block_flags); compress_in_place(cv[..], input[:BLOCK_SIZE], BLOCK_SIZE, counter, block_flags);
} }
foreach (i, c : cv) @unaligned_store(*(uint*)&out[i * 4], c, 1); foreach (i, c : cv) mem::store((uint*)&out[i * 4], c, 1);
} }
macro hash_many(char*[] inputs, usz num_inputs, usz blocks, uint[] key, ulong counter, bool $increment_counter, char flags, char flags_start, char flags_end, char* out) @local macro hash_many(char*[] inputs, usz num_inputs, usz blocks, uint[] key, ulong counter, bool $increment_counter, char flags, char flags_start, char flags_end, char* out) @local

View File

@@ -58,38 +58,38 @@ fn ulong hash(char[] data, ulong seed = 0)
if (@likely(data.len >= 8)) if (@likely(data.len >= 8))
{ {
r1h ^= @unaligned_load(*(ulong*)data.ptr, 1); r1h ^= mem::load((ulong*)data.ptr, 1);
r2h ^= (data.len < 12) r2h ^= (data.len < 12)
? ((data[data.len - 3] | ((ulong)data[data.len - 2] << 8) | ((ulong)data[data.len - 1] << 16) | ((ulong)1 << 24)) >> ((data.len * 8) ^ 88)) ? ((data[data.len - 3] | ((ulong)data[data.len - 2] << 8) | ((ulong)data[data.len - 1] << 16) | ((ulong)1 << 24)) >> ((data.len * 8) ^ 88))
: (((@unaligned_load(*(uint*)&data[^4], 1) | ((ulong)1 << 32)) >> (128 - data.len * 8)) << 32 | @unaligned_load(*(uint*)&data[8], 1)); : (((mem::load((uint*)&data[^4], 1) | ((ulong)1 << 32)) >> (128 - data.len * 8)) << 32 | mem::load((uint*)&data[8], 1));
} }
else if (data.len != 0) else if (data.len != 0)
{ {
r1h ^= (data.len < 4) r1h ^= (data.len < 4)
? (((ulong)1 << (data.len * 8)) ^ data[0] ^ (data.len > 1 ? (ulong)data[1] << 8 : 0) ^ (data.len > 2 ? (ulong)data[2] << 16 : 0)) ? (((ulong)1 << (data.len * 8)) ^ data[0] ^ (data.len > 1 ? (ulong)data[1] << 8 : 0) ^ (data.len > 2 ? (ulong)data[2] << 16 : 0))
: (((@unaligned_load(*(uint*)&data[^4], 1) | ((ulong)1 << 32)) >> (64 - data.len * 8)) << 32 | @unaligned_load(*(uint*)&data[0], 1)); : (((mem::load((uint*)&data[^4], 1) | ((ulong)1 << 32)) >> (64 - data.len * 8)) << 32 | mem::load((uint*)&data[0], 1));
} }
} }
else if (data.len < 32) else if (data.len < 32)
{ {
// HASH16 // HASH16
@komimul( @komimul(
@unaligned_load(*(ulong*)&data[0], 1) ^ seed1, mem::load((ulong*)&data[0], 1) ^ seed1,
@unaligned_load(*(ulong*)&data[8], 1) ^ seed5, mem::load((ulong*)&data[8], 1) ^ seed5,
seed1, seed5 seed1, seed5
); );
seed1 ^= seed5; seed1 ^= seed5;
if (data.len < 24) if (data.len < 24)
{ {
r1h = (((@unaligned_load(*(ulong*)&data[^8], 1) >> 8) | ((ulong)1 << 56)) >> (((int)(data.len * 8) ^ 184))) ^ seed1; r1h = (((mem::load((ulong*)&data[^8], 1) >> 8) | ((ulong)1 << 56)) >> (((int)(data.len * 8) ^ 184))) ^ seed1;
r2h = seed5; r2h = seed5;
} }
else else
{ {
r1h = @unaligned_load(*(ulong*)&data[16], 1) ^ seed1; r1h = mem::load((ulong*)&data[16], 1) ^ seed1;
r2h = (((@unaligned_load(*(ulong*)&data[^8], 1) >> 8) | ((ulong)1 << 56)) >> (((int)(data.len * 8) ^ 248))) ^ seed5; r2h = (((mem::load((ulong*)&data[^8], 1) >> 8) | ((ulong)1 << 56)) >> (((int)(data.len * 8) ^ 248))) ^ seed5;
} }
} }
else else
@@ -106,8 +106,8 @@ fn ulong hash(char[] data, ulong seed = 0)
{ {
$for var $x = 0; $x < 4; ++$x : $for var $x = 0; $x < 4; ++$x :
@komimul( @komimul(
@unaligned_load(*(ulong*)&data[0 + ($x * 8)], 1) ^ seeds[$x], mem::load((ulong*)&data[0 + ($x * 8)], 1) ^ seeds[$x],
@unaligned_load(*(ulong*)&data[32 + ($x * 8)], 1) ^ seeds[4 + $x], mem::load((ulong*)&data[32 + ($x * 8)], 1) ^ seeds[4 + $x],
seeds[$x], seeds[4 + $x] seeds[$x], seeds[4 + $x]
); );
$endfor $endfor
@@ -125,8 +125,8 @@ fn ulong hash(char[] data, ulong seed = 0)
for (; data.len >= 16; data = data[16:^16]) for (; data.len >= 16; data = data[16:^16])
{ {
@komimul( @komimul(
@unaligned_load(*(ulong*)&data[0], 1) ^ seed1, mem::load((ulong*)&data[0], 1) ^ seed1,
@unaligned_load(*(ulong*)&data[8], 1) ^ seed5, mem::load((ulong*)&data[8], 1) ^ seed5,
seed1, seed5 seed1, seed5
); );
seed1 ^= seed5; seed1 ^= seed5;
@@ -137,13 +137,13 @@ fn ulong hash(char[] data, ulong seed = 0)
// NOTE: This is translated from the original code. It grabs the last ulong off the buffer even though the // NOTE: This is translated from the original code. It grabs the last ulong off the buffer even though the
// data slice is less than 8 bytes. This is possible because this branch only occurs in a loop where // data slice is less than 8 bytes. This is possible because this branch only occurs in a loop where
// the original data slice length is >= 32. // the original data slice length is >= 32.
r1h = (((@unaligned_load(*(ulong*)(data.ptr + data.len - 8), 1) >> 8) | ((ulong)1 << 56)) >> ((data.len * 8) ^ 0x38)) ^ seed1; r1h = (((mem::load((ulong*)(data.ptr + data.len - 8), 1) >> 8) | ((ulong)1 << 56)) >> ((data.len * 8) ^ 0x38)) ^ seed1;
r2h = seed5; r2h = seed5;
} }
else else
{ {
r1h = @unaligned_load(*(ulong*)data.ptr, 1) ^ seed1; r1h = mem::load((ulong*)data.ptr, 1) ^ seed1;
r2h = (((@unaligned_load(*(ulong*)&data[^8], 1) >> 8) | ((ulong)1 << 56)) >> ((data.len * 8) ^ 0x78)) ^ seed5; r2h = (((mem::load((ulong*)&data[^8], 1) >> 8) | ((ulong)1 << 56)) >> ((data.len * 8) ^ 0x78)) ^ seed5;
} }
} }

View File

@@ -108,7 +108,7 @@ macro @i(x, y, z) => y ^ (x | ~z);
macro void @step(#f, a, b, c, d, ptr, n, t, s) macro void @step(#f, a, b, c, d, ptr, n, t, s)
{ {
*a += #f(b, c, d) + @unaligned_load(*(uint *)&ptr[n * 4], 2) + t; *a += #f(b, c, d) + mem::load((uint *)&ptr[n * 4], 2) + t;
*a = (*a << s) | ((*a & 0xffffffff) >> (32 - s)); *a = (*a << s) | ((*a & 0xffffffff) >> (32 - s));
*a += b; *a += b;
} }

View File

@@ -62,8 +62,8 @@ alias tag = hash;
fn void Poly1305.init(&self, char[KEY_SIZE] key) fn void Poly1305.init(&self, char[KEY_SIZE] key)
{ {
*self = { // implicitly clears state as well *self = { // implicitly clears state as well
.r = @unaligned_load(*(uint128*)&key[ 0], 1) & 0x0ffffffc_0ffffffc_0ffffffc_0fffffff, // clamped per spec .r = mem::load((uint128*)&key[ 0], 1) & 0x0ffffffc_0ffffffc_0ffffffc_0fffffff, // clamped per spec
.nonce = @unaligned_load(*(uint128*)&key[16], 1) .nonce = mem::load((uint128*)&key[16], 1)
}; };
self.r0 = @unaligned_load(((ulong*)&self.r)[0], 1); self.r0 = @unaligned_load(((ulong*)&self.r)[0], 1);
@@ -139,8 +139,8 @@ fn void Poly1305.blocks(&self, char[] input, ulong pad_bit = 1) @local
{ {
for (; input.len >= BLOCK_SIZE; input = input[BLOCK_SIZE..]) for (; input.len >= BLOCK_SIZE; input = input[BLOCK_SIZE..])
{ {
ulong i0 = @unaligned_load(*(ulong*)&input[0], 1); ulong i0 = mem::load((ulong*)&input[0], 1);
ulong i1 = @unaligned_load(*(ulong*)&input[8], 1); ulong i1 = mem::load((ulong*)&input[8], 1);
uint128 d0 = (uint128)self.h[0] + i0; uint128 d0 = (uint128)self.h[0] + i0;
self.h[0] = (ulong)d0; self.h[0] = (ulong)d0;

View File

@@ -161,7 +161,7 @@ fn void Whirlpool.process_block(&self, char* block) @local
// NOTE: These loops are unrolled with C3's Chad-tier compile-time evaluation. // NOTE: These loops are unrolled with C3's Chad-tier compile-time evaluation.
$for var $round = 0; $round < 8; $round++: $for var $round = 0; $round < 8; $round++:
k[$round] = self.hash[$round]; k[$round] = self.hash[$round];
state[$round] = $$bswap(@unaligned_load(((ulong*)block)[$round], 1)) ^ self.hash[$round]; state[$round] = $$bswap(mem::load((ulong*)block + $round, 1)) ^ self.hash[$round];
self.hash[$round] = state[$round]; self.hash[$round] = state[$round];
$endfor $endfor

View File

@@ -34,8 +34,8 @@ fn ulong hash(char[] input, ulong seed = 0)
{ {
if (@likely(input.len >= 4)) if (@likely(input.len >= 4))
{ {
a = (ulong)@unaligned_load(*(uint*)input.ptr, 1); // first 4 bytes widened to a u64 a = (ulong)mem::load((uint*)input.ptr, 1); // first 4 bytes widened to a u64
b = (ulong)@unaligned_load(*(uint*)&input[^4], 1); // a walking 4-byte window based on input.len b = (ulong)mem::load((uint*)&input[^4], 1); // a walking 4-byte window based on input.len
} }
else if (input.len > 0) else if (input.len > 0)
{ {
@@ -44,8 +44,8 @@ fn ulong hash(char[] input, ulong seed = 0)
} }
else else
{ {
a = @unaligned_load(*(ulong*)input.ptr, 1); // first 8 bytes a = mem::load((ulong*)input.ptr, 1); // first 8 bytes
b = @unaligned_load(*(ulong*)&input[^8], 1); // a walking 8-byte window based on input.len b = mem::load((ulong*)&input[^8], 1); // a walking 8-byte window based on input.len
} }
uint128 r = ((uint128)a ^ 0xe703_7ed1_a0b4_28db) * ((uint128)b ^ seed); uint128 r = ((uint128)a ^ 0xe703_7ed1_a0b4_28db) * ((uint128)b ^ seed);