Skip to content

Commit ecc301c

Browse files
davidbenAdam Langley
authored and
Adam Langley
committed
Add a pointer alignment helper function.
Also use a slightly more conservative pattern. Instead of aligning the pointer as a uintptr_t and casting back, compute the offset and advance in pointer space. C guarantees that casting from pointer to uintptr_t and back gives the same pointer, but general integer-to-pointer conversions are generally implementation-defined. GCC does define it in the useful way, but this makes fewer dependencies. Change-Id: I70c7af735e892fe7a8333b78b39d7b1f3f1cdbef Reviewed-on: https://boringssl-review.googlesource.com/c/boringssl/+/48405 Reviewed-by: Adam Langley <[email protected]>
1 parent 268a4a6 commit ecc301c

File tree

4 files changed

+31
-17
lines changed

4 files changed

+31
-17
lines changed

crypto/hrss/hrss.c

+2-6
Original file line numberDiff line numberDiff line change
@@ -1871,9 +1871,7 @@ static struct public_key *public_key_from_external(
18711871
sizeof(struct HRSS_public_key) >= sizeof(struct public_key) + 15,
18721872
"HRSS public key too small");
18731873

1874-
uintptr_t p = (uintptr_t)ext;
1875-
p = (p + 15) & ~15;
1876-
return (struct public_key *)p;
1874+
return align_pointer(ext->opaque, 16);
18771875
}
18781876

18791877
// private_key_from_external does the same thing as |public_key_from_external|,
@@ -1885,9 +1883,7 @@ static struct private_key *private_key_from_external(
18851883
sizeof(struct HRSS_private_key) >= sizeof(struct private_key) + 15,
18861884
"HRSS private key too small");
18871885

1888-
uintptr_t p = (uintptr_t)ext;
1889-
p = (p + 15) & ~15;
1890-
return (struct private_key *)p;
1886+
return align_pointer(ext->opaque, 16);
18911887
}
18921888

18931889
void HRSS_generate_key(

crypto/internal.h

+20
Original file line numberDiff line numberDiff line change
@@ -209,6 +209,9 @@ typedef __uint128_t uint128_t;
209209
#define OPENSSL_SSE2
210210
#endif
211211

212+
213+
// Pointer utility functions.
214+
212215
// buffers_alias returns one if |a| and |b| alias and zero otherwise.
213216
static inline int buffers_alias(const uint8_t *a, size_t a_len,
214217
const uint8_t *b, size_t b_len) {
@@ -221,6 +224,23 @@ static inline int buffers_alias(const uint8_t *a, size_t a_len,
221224
return a_u + a_len > b_u && b_u + b_len > a_u;
222225
}
223226

227+
// align_pointer returns |ptr|, advanced to |alignment|. |alignment| must be a
228+
// power of two, and |ptr| must have at least |alignment - 1| bytes of scratch
229+
// space.
230+
static inline void *align_pointer(void *ptr, size_t alignment) {
231+
// |alignment| must be a power of two.
232+
assert(alignment != 0 && (alignment & (alignment - 1)) == 0);
233+
// Instead of aligning |ptr| as a |uintptr_t| and casting back, compute the
234+
// offset and advance in pointer space. C guarantees that casting from pointer
235+
// to |uintptr_t| and back gives the same pointer, but general
236+
// integer-to-pointer conversions are implementation-defined. GCC does define
237+
// it in the useful way, but this makes fewer assumptions.
238+
uintptr_t offset = (0u - (uintptr_t)ptr) & (alignment - 1);
239+
ptr = (char *)ptr + offset;
240+
assert(((uintptr_t)ptr & (alignment - 1)) == 0);
241+
return ptr;
242+
}
243+
224244

225245
// Constant-time utility functions.
226246
//

crypto/poly1305/poly1305.c

+1-1
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,7 @@ OPENSSL_STATIC_ASSERT(
5656

5757
static inline struct poly1305_state_st *poly1305_aligned_state(
5858
poly1305_state *state) {
59-
return (struct poly1305_state_st *)(((uintptr_t)state + 63) & ~63);
59+
return align_pointer(state, 64);
6060
}
6161

6262
// poly1305_blocks updates |state| given some amount of input data. This

tool/speed.cc

+8-10
Original file line numberDiff line numberDiff line change
@@ -342,12 +342,6 @@ static bool SpeedRSAKeyGen(const std::string &selected) {
342342
return true;
343343
}
344344

345-
static uint8_t *align(uint8_t *in, unsigned alignment) {
346-
return reinterpret_cast<uint8_t *>(
347-
(reinterpret_cast<uintptr_t>(in) + alignment) &
348-
~static_cast<size_t>(alignment - 1));
349-
}
350-
351345
static std::string ChunkLenSuffix(size_t chunk_len) {
352346
char buf[32];
353347
snprintf(buf, sizeof(buf), " (%zu byte%s)", chunk_len,
@@ -384,13 +378,17 @@ static bool SpeedAEADChunk(const EVP_AEAD *aead, std::string name,
384378
new uint8_t[overhead_len + kAlignment]);
385379

386380

387-
uint8_t *const in = align(in_storage.get(), kAlignment);
381+
uint8_t *const in =
382+
static_cast<uint8_t *>(align_pointer(in_storage.get(), kAlignment));
388383
OPENSSL_memset(in, 0, chunk_len);
389-
uint8_t *const out = align(out_storage.get(), kAlignment);
384+
uint8_t *const out =
385+
static_cast<uint8_t *>(align_pointer(out_storage.get(), kAlignment));
390386
OPENSSL_memset(out, 0, chunk_len + overhead_len);
391-
uint8_t *const tag = align(tag_storage.get(), kAlignment);
387+
uint8_t *const tag =
388+
static_cast<uint8_t *>(align_pointer(tag_storage.get(), kAlignment));
392389
OPENSSL_memset(tag, 0, overhead_len);
393-
uint8_t *const in2 = align(in2_storage.get(), kAlignment);
390+
uint8_t *const in2 =
391+
static_cast<uint8_t *>(align_pointer(in2_storage.get(), kAlignment));
394392

395393
if (!EVP_AEAD_CTX_init_with_direction(ctx.get(), aead, key.get(), key_len,
396394
EVP_AEAD_DEFAULT_TAG_LENGTH,

0 commit comments

Comments
 (0)