why is mips different (erik's version)? supermic% ./8.out 78780000 mikro% ./v.out 7878 rpi% ./5.out 78780000 On Wed, Nov 27, 2013 at 8:31 AM, erik quanstrom wrote: > On Wed Nov 27 11:04:46 EST 2013, steve@quintile.net wrote: > > > Whilst porting some code from the net I came across > > the attached, rather obscure, code. > > > > run as: > > > > larch% 8c -D 'STATIC=static' t.c && 8l t.8 && 8.out > > 78780000 > > larch% 8c -D 'STATIC=' t.c && 8l t.8 && 8.out > > 0 > > > > I think it is tickling a bug in 8c, though > > I may be just showing my lack of knowledge of > > the C standard... > > > > anyone any thoughts? > > this code is not correct. it breaks the anti-aliasing rules. the > compiler is allowed to assume that tmp is not modified. > recently had trouble with floating point in stdio for the same > reasons. > > to work around this, use a union, or better yet getle(buf, 3) > (or be as the case may be), > > since there's not enough context to sort out if the original is > supposed to be big or little endian, here's a union version: > > - erik > ------ > #include > #include > > static uint > getdword_n(void *vmem, int n) > { > uchar *mem; > union { > uint i; > uchar u[sizeof(uint)]; > } tmp; > > mem = vmem; > tmp.i = 0; > switch (n){ > case 3: > tmp.u[1] = mem[2]; > case 2: > tmp.u[2] = mem[1]; > case 1: > tmp.u[3] = mem[0]; > } > return tmp.i; > } > > void > main(void) > { > uint x; > > char buf[] = "xxxx"; > > x = getdword_n(buf, 2); > print("%x\n", x); > } > >