Thursday, November 28, 2019

Re: SIGBUS on octeon for my program

Half the cpu platforms fault on unaligned access.

There are strategies for handling this. Your code must use them.

It is kind of boring, actually.


Peter J. Philipp <pjp@centroid.eu> wrote:

> On Wed, Nov 27, 2019 at 03:30:23PM +0100, Peter J. Philipp wrote:
> > Hi David,
> >
> > I'm going to upgrade to -current and then report back.. it'll take me a few
> > days to do that (I'm super slow).
> >
> > ...
> > I'll see if this sort of issue repeats after I upgrade the octeon router
> > to -current.
> >
> > Thanks!
> > -peter
>
> Hi David and Misc@,
>
> OK this is weird. For people who are just reading this thread it's about
> OpenBSD/octeon SIGBUS'ing my program with an unalignment error.
>
> I upgraded to -current (very pleased that pppoe0 works now, as an aside),
> and got the debug right after the fork. Here is the output of gdb
>
> debug.1--->
> Continuing.
>
> Program received signal SIGBUS, Bus error.
> lookup_axfr (f=0x2c6274db78, so=6, zonename=0x2c6b3d2130 "words.",
> mysoa=0xfffffe7920, format=20, tsigkey=0x2c37b083d0 "pass",
> tsigpass=0xfffffe7b60 "*censored*=",
> segment=0xfffffe7b40, answers=0xfffffe7b3c, additionalcount=0xfffffe7b38)
> at util.c:1842
> 1842 *type = htons(DNS_TYPE_AXFR);
> (gdb) list
> 1837
> 1838 memcpy(p, name, len);
> 1839 totallen += len;
> 1840
> 1841 type = (u_int16_t *)&query[totallen];
> 1842 *type = htons(DNS_TYPE_AXFR);
> 1843 totallen += sizeof(u_int16_t);
> 1844
> 1845 class = (u_int16_t *)&query[totallen];
> 1846 *class = htons(DNS_CLASS_IN);
> (gdb) print type
> $1 = (u_int16_t *) 0xfffffe763d
> <-----
>
> So I point a pointer of type u_int16_t to a memory address (which may be
> unaligned) and then load it with a value. I've always done it this way
> throughout my program, but just to be sure that it isn't caused by the stack
> somehow I moved query variable to the heap (or it's equivalent) and tried
> again.
>
> debug.2--->
> Loaded symbols for /usr/libexec/ld.so
> pull_remote_zone (lrz=0x216549d000) at parse.y:3605
> 3605 while (debugger == 1)
> (gdb) set debugger=0
> Current language: auto; currently minimal
> (gdb) cont
> Continuing.
>
> Program received signal SIGBUS, Bus error.
> lookup_axfr (f=0x21b8dfdb78, so=6, zonename=0x22041a4a10 "words.",
> mysoa=0xffffff9050, format=20, tsigkey=0x22052c35b0 "pass",
> tsigpass=0xffffff9290 "*censored*=",
> segment=0xffffff9270, answers=0xffffff926c, additionalcount=0xffffff9268)
> at util.c:1849
> 1849 *type = htons(DNS_TYPE_AXFR);
> (gdb) print type
> $1 = (u_int16_t *) 0x21d57f1015
> (gdb) print query
> $2 = 0x21d57f1000 ""
> (gdb) print (char*)type - query
> $3 = 21
> <-------
>
> So now I have a true offset of variable type it's not aligned. What can I
> do here? Does this need fixing in OpenBSD/octeon or do I have to fix my
> code for this? I don't really know what to use instead of this other than
> memcpy'ing this value instead of (overloading?) the 16 bit integer.
>
> Any help is welcomed!
>
> Best regards,
> -peter
>

No comments:

Post a Comment