Date: Thu, 09 Jan 2014 23:37:21 +0200 From: Guy Yur <guyyur@gmail.com> To: FreeBSD-gnats-submit@freebsd.org Subject: arm/185617: 10.0-RC1, armv6: "pfctl -s state" crashes on BeagleBone Black due to unaligned access Message-ID: <52cf16b1.45b00e0a.3aa5.ffff8053@mx.google.com> Resent-Message-ID: <201401092140.s09Le2Iu037915@freefall.freebsd.org>
next in thread | raw e-mail | index | archive | help
>Number: 185617 >Category: arm >Synopsis: 10.0-RC1, armv6: "pfctl -s state" crashes on BeagleBone Black due to unaligned access >Confidential: no >Severity: serious >Priority: medium >Responsible: freebsd-arm >State: open >Quarter: >Keywords: >Date-Required: >Class: sw-bug >Submitter-Id: current-users >Arrival-Date: Thu Jan 09 21:40:02 UTC 2014 >Closed-Date: >Last-Modified: >Originator: Guy Yur >Release: FreeBSD 10.0-RC1 arm >Organization: >Environment: System: FreeBSD bbb.localdomain 10.0-RC1 FreeBSD 10.0-RC1 #1 r259250M: Thu Dec 12 22:54:08 IST 2013 root@vm8.localdomain:/usr/obj/arm.armv6/usr/src/sys/BBB arm >Description: I am running 10.0-RC1 arm.armv6 on the BeagleBone Black. The "pfctl -s state" command is crashing when trying to print the second entry. struct pfsync_state has a size that is not divisiable by 4 leading to the second entry in the returned state array not being aligned. This is fine when accessing the entry as a struct pfsync_state pointer since the struct has the __packed attribute and on arm unaligned access will be used. When print_host is called it receives a pf_addr struct pointer &nk->addr[1] which is not aligned on 4 bytes for the second entry and since the struct is not __packed it will be accessed using word load instructions which will trigger an unaligned access fault and pfctl will exit with bus error. (gdb) bt #0 print_host (addr=0x2085a11a, port=7660, af=2 '\002', opts=1024) at /usr/src/sbin/pfctl/pf_print_state.c:178 #1 0x00021c4c in print_state (s=0x2085a0f2, opts=1024) at /usr/src/sbin/pfctl/pf_print_state.c:236 #2 0x0000c664 in pfctl_show_states (dev=<value optimized out>, iface=0x0, opts=1024) at /usr/src/sbin/pfctl/pfctl.c:1095 sizeof(struct pfsync_state_key) is 36 sizeof(struct pfsync_state_peer) is 32 sizeof(struct pf_addr) is 16 sizeof(struct pfsync_state) is 242 >How-To-Repeat: pf running on an arm host, make sure there is more than one active connection. Run: pfctl -s state >Fix: A quick workaround is for print_state to copy the pf_addr in pfsync_state_key to a pf_addr struct on the stack and pass it to print_host. Another possibility is to make sure pfsync_state is aligned on at least 4 bytes (8 preferred for the u_int64_t id) or create a new aligned struct for the DIOCGETSTATE and DIOCGETSTATES ioctls to separate between the pfsync_state as protocol data and the info returned by the ioctls. Changing pfsync_state size will break KBI and the pfsync protocol. >Release-Note: >Audit-Trail: >Unformatted:
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?52cf16b1.45b00e0a.3aa5.ffff8053>