aboutsummaryrefslogtreecommitdiff
path: root/libsframe/sframe.c
diff options
context:
space:
mode:
Diffstat (limited to 'libsframe/sframe.c')
-rw-r--r--libsframe/sframe.c18
1 files changed, 16 insertions, 2 deletions
diff --git a/libsframe/sframe.c b/libsframe/sframe.c
index d4eaaee..b17d323 100644
--- a/libsframe/sframe.c
+++ b/libsframe/sframe.c
@@ -652,6 +652,11 @@ sframe_frame_row_entry_copy (sframe_frame_row_entry *dst, sframe_frame_row_entry
return 0;
}
+/* Decode the SFrame FRE start address offset value from FRE_BUF in on-disk
+ binary format, given the FRE_TYPE. Updates the FRE_START_ADDR.
+
+ Returns 0 on success, SFRAME_ERR otherwise. */
+
static int
sframe_decode_fre_start_address (const char *fre_buf,
uint32_t *fre_start_addr,
@@ -659,6 +664,9 @@ sframe_decode_fre_start_address (const char *fre_buf,
{
uint32_t saddr = 0;
int err = 0;
+ size_t addr_size = 0;
+
+ addr_size = sframe_fre_start_addr_size (fre_type);
if (fre_type == SFRAME_FRE_TYPE_ADDR1)
{
@@ -668,12 +676,18 @@ sframe_decode_fre_start_address (const char *fre_buf,
else if (fre_type == SFRAME_FRE_TYPE_ADDR2)
{
uint16_t *ust = (uint16_t *)fre_buf;
- saddr = (uint32_t)*ust;
+ /* SFrame is an unaligned on-disk format. Using memcpy helps avoid the
+ use of undesirable unaligned loads. See PR libsframe/29856. */
+ uint16_t tmp = 0;
+ memcpy (&tmp, ust, addr_size);
+ saddr = (uint32_t)tmp;
}
else if (fre_type == SFRAME_FRE_TYPE_ADDR4)
{
uint32_t *uit = (uint32_t *)fre_buf;
- saddr = (uint32_t)*uit;
+ int32_t tmp = 0;
+ memcpy (&tmp, uit, addr_size);
+ saddr = (uint32_t)tmp;
}
else
return sframe_set_errno (&err, SFRAME_ERR_INVAL);