diff options
author | ian <ian@138bc75d-0d04-0410-961f-82ee72b054a4> | 2012-02-11 00:03:10 +0000 |
---|---|---|
committer | ian <ian@138bc75d-0d04-0410-961f-82ee72b054a4> | 2012-02-11 00:03:10 +0000 |
commit | aba5c3d2c4d92d4d3c3218719ed10d3dd7b3b9ec (patch) | |
tree | 9b9c08f320214694fa37fdd972b1d515e73dc55f | |
parent | 6c4f0f01fedee7b4952d0a21f60fa70984124ffb (diff) | |
download | gcc-aba5c3d2c4d92d4d3c3218719ed10d3dd7b3b9ec.tar.gz |
runtime: Fix chan code for big-endian strict-alignment systems
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@184115 138bc75d-0d04-0410-961f-82ee72b054a4
-rw-r--r-- | libgo/runtime/chan.c | 31 |
1 files changed, 23 insertions, 8 deletions
diff --git a/libgo/runtime/chan.c b/libgo/runtime/chan.c index 4fc2d603659..24be9500a8b 100644 --- a/libgo/runtime/chan.c +++ b/libgo/runtime/chan.c @@ -409,11 +409,20 @@ closed: void __go_send_small(ChanType *t, Hchan* c, uint64 val) { - byte b[sizeof(uint64)]; - - runtime_memclr(b, sizeof(uint64)); - __builtin_memcpy(b, &val, t->__element_type->__size); - runtime_chansend(t, c, b, nil); + union + { + byte b[sizeof(uint64)]; + uint64 v; + } u; + byte *p; + + u.v = val; +#ifndef WORDS_BIGENDIAN + p = u.b; +#else + p = u.b + sizeof(uint64) - t->__element_type->__size; +#endif + runtime_chansend(t, c, p, nil); } // The compiler generates a call to __go_send_big to send a value @@ -433,9 +442,15 @@ __go_receive_small(ChanType *t, Hchan* c) byte b[sizeof(uint64)]; uint64 v; } u; + byte *p; u.v = 0; - runtime_chanrecv(t, c, u.b, nil, nil); +#ifndef WORDS_BIGENDIAN + p = u.b; +#else + p = u.b + sizeof(uint64) - t->__element_type->__size; +#endif + runtime_chanrecv(t, c, p, nil, nil); return u.v; } @@ -654,8 +669,8 @@ newselect(int32 size, Select **selp) sel->tcase = size; sel->ncase = 0; - sel->pollorder = (void*)(sel->scase + size); - sel->lockorder = (void*)(sel->pollorder + size); + sel->lockorder = (void*)(sel->scase + size); + sel->pollorder = (void*)(sel->lockorder + size); *selp = sel; if(debug) |