diff options
author | Ilya Maximets <i.maximets@ovn.org> | 2022-06-24 14:55:56 +0200 |
---|---|---|
committer | Ilya Maximets <i.maximets@ovn.org> | 2022-06-24 23:52:29 +0200 |
commit | e4f75b330fe99e3680c65223d0223a389babddc1 (patch) | |
tree | bf3b0f6627b57d834a692ea8abbc74178b9cc480 | |
parent | f5a714b30edb3dedd8723e494a7815cf69a9e4af (diff) | |
download | openvswitch-e4f75b330fe99e3680c65223d0223a389babddc1.tar.gz |
odp-util: Fix unaligned access to tunnel id.
SUMMARY: UndefinedBehaviorSanitizer:
lib/odp-util.c:3436:32: runtime error:
load of misaligned address 0x624000489424 for type 'const ovs_be64'
(aka 'const unsigned long'), which requires 8 byte alignment 0x624000489424:
note: pointer points here
0c 00 00 00 ff ff ff ff ff ff ff ff 08 00 01 00 ...
^
0 0x9b13a2 in format_be64 lib/odp-util.c:3436:32
1 0x9b13a2 in format_odp_tun_attr lib/odp-util.c:3942:13
2 0x9b13a2 in format_odp_key_attr__ lib/odp-util.c:4221:9
3 0x9ae7a2 in odp_flow_format lib/odp-util.c:4606:17
4 0xee5037 in format_dpif_flow lib/dpctl.c:862:5
5 0xed69ed in dpctl_dump_flows lib/dpctl.c:1142:13
6 0xed32b3 in dpctl_unixctl_handler lib/dpctl.c:3035:17
7 0xc7c80b in process_command lib/unixctl.c:310:13
8 0xc7c80b in run_connection lib/unixctl.c:344:17
9 0xc7c80b in unixctl_server_run lib/unixctl.c:395:21
10 0x59a9a4 in main vswitchd/ovs-vswitchd.c:130:9
11 0x7fee2803acf2 in __libc_start_main (/lib64/libc.so.6+0x3acf2)
12 0x47e60d in _start (vswitchd/ovs-vswitchd+0x47e60d)
Tunnel id mask in the flow key is only 4 bytes aligned, so has to be
accessed with appropriate unaligned read function.
Acked-by: Dumitru Ceara <dceara@redhat.com>
Acked-by: Aaron Conole <aconole@redhat.com>
Signed-off-by: Ilya Maximets <i.maximets@ovn.org>
-rw-r--r-- | lib/odp-util.c | 10 |
1 files changed, 5 insertions, 5 deletions
diff --git a/lib/odp-util.c b/lib/odp-util.c index 0df892132..fa6287f6d 100644 --- a/lib/odp-util.c +++ b/lib/odp-util.c @@ -3341,16 +3341,16 @@ format_eth(struct ds *ds, const char *name, const struct eth_addr key, static void format_be64(struct ds *ds, const char *name, ovs_be64 key, - const ovs_be64 *mask, bool verbose) + const ovs_32aligned_be64 *mask_, bool verbose) { - bool mask_empty = mask && !*mask; + ovs_be64 mask = mask_ ? get_32aligned_be64(mask_) : htonll(0); - if (verbose || !mask_empty) { - bool mask_full = !mask || *mask == OVS_BE64_MAX; + if (verbose || mask) { + bool mask_full = !mask_ || mask == OVS_BE64_MAX; ds_put_format(ds, "%s=0x%"PRIx64, name, ntohll(key)); if (!mask_full) { /* Partially masked. */ - ds_put_format(ds, "/%#"PRIx64, ntohll(*mask)); + ds_put_format(ds, "/%#"PRIx64, ntohll(mask)); } ds_put_char(ds, ','); } |