Bug 210028 - Unhandled instruction 0x13CB032 on ppc32
Summary: Unhandled instruction 0x13CB032 on ppc32
Status: RESOLVED FIXED
Alias: None
Product: valgrind
Classification: Developer tools
Component: memcheck (show other bugs)
Version: 3.6 SVN
Platform: Compiled Sources Linux
: NOR normal
Target Milestone: ---
Assignee: Julian Seward
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2009-10-09 22:56 UTC by Brandon Rioja
Modified: 2015-04-27 20:37 UTC (History)
2 users (show)

See Also:
Latest Commit:
Version Fixed In:


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Brandon Rioja 2009-10-09 22:56:24 UTC
When running valgrind's memcheck on a ppc32, I see an invalid instruction error.


# ./valgrind echo hi
==1012== Memcheck, a memory error detector
==1012== Copyright (C) 2002-2009, and GNU GPL'd, by Julian Seward et al.
==1012== Using Valgrind-3.6.0.SVN and LibVEX; rerun with -h for copyright info
==1012== Command: echo hi
==1012==
disInstr(ppc): declined to decode an AltiVec insn.
disInstr(ppc): unhandled instruction: 0x13CB0321
                 primary 4(0x4), secondary 801(0x321)
==1012== valgrind: Unrecognised instruction at address 0x400ec70.
==1012== Your program just tried to execute an instruction that Valgrind
==1012== did not recognise.  There are two possible reasons for this.
==1012== 1. Your program has a bug and erroneously jumped to a non-code
==1012==    location.  If you are running Memcheck and you just saw a
==1012==    warning about a bad jump, it's probably your program's fault.
==1012== 2. The instruction is legitimate but Valgrind doesn't handle it,
==1012==    i.e. it's Valgrind's fault.  If you think this is the case or
==1012==    you are not sure, please let us know and we'll try to fix it.
==1012== Either way, Valgrind will now raise a SIGILL signal which will
==1012== probably kill your program.
==1012==
==1012== Process terminating with default action of signal 4 (SIGILL)
==1012==  Illegal opcode at address 0x400EC70
==1012==    at 0x400EC70: _dl_catch_error (dl-error.c:160)
==1012==    by 0x4002CE7: do_preload (rtld.c:804)
==1012==    by 0x4005A93: dl_main (rtld.c:1727)
==1012==    by 0x401595B: _dl_sysdep_start (dl-sysdep.c:239)
==1012==    by 0x4002517: _dl_start_final (rtld.c:323)
==1012==    by 0x4002A43: _dl_start (rtld.c:551)
==1012==    by 0x40164CF: _start (in /lib/ld-2.5.90.so)
==1012==
==1012== HEAP SUMMARY:
==1012==     in use at exit: 0 bytes in 0 blocks
==1012==   total heap usage: 0 allocs, 0 frees, 0 bytes allocated
==1012==
==1012== All heap blocks were freed -- no leaks are possible
==1012==
==1012== For counts of detected and suppressed errors, rerun with: -v
==1012== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 4 from 2)
Illegal instruction


I compiled valgrind with these commands:

export TARGET_TOOL_BASE=/opt/montavista/cge50/montavista/cge/devkit/ppc/85xx/bin/ppc_85xx- 

export CC=${TARGET_TOOL_BASE}gcc 
export CXX=${TARGET_TOOL_BASE}g++ 
export LD=${TARGET_TOOL_BASE}ld 

#svn co svn://svn.valgrind.org/valgrind/trunk valgrind 

cd valgrind 
./autogen.sh 
./configure --prefix=/home/rootfs/local --enable-shared --host=ppc-linux --target=ppc-linux --enable-debug --disable-tls || exit 1 
make clean
make -j8 || exit 1 
make install  || exit 1
Comment 1 Brandon Rioja 2009-10-09 23:17:41 UTC
I tried compiling a simple program with no altivec support.

ppc_85xx-g++ -mno-altivec test.cpp

“””
int main() {
  return 0;
}
“””

But I get an error on startup. The altivec instruction seems to still exist.

./valgrind ../../a.out
==1026== Memcheck, a memory error detector
==1026== Copyright (C) 2002-2009, and GNU GPL'd, by Julian Seward et al.
==1026== Using Valgrind-3.6.0.SVN and LibVEX; rerun with -h for copyright info
==1026== Command: ../../a.out
==1026==
disInstr(ppc): declined to decode an AltiVec insn.
disInstr(ppc): unhandled instruction: 0x13CB0321
                 primary 4(0x4), secondary 801(0x321)
Comment 2 Florian Krohm 2015-04-26 10:44:44 UTC
objdump says:
13 cb 03 21     vmhraddshs v30,v11,v0,v12

It appears that we have fixed this sometime in the past...
Comment 3 Arseny Solokha 2015-04-27 07:37:09 UTC
It wasn't fixed in the past.

# ./valgrind echo   
==692== Memcheck, a memory error detector
==692== Copyright (C) 2002-2013, and GNU GPL'd, by Julian Seward et al.
==692== Using Valgrind-3.10.1 and LibVEX; rerun with -h for copyright info
==692== Command: echo
==692== 
disInstr(ppc): declined to decode an AltiVec insn.
disInstr(ppc): unhandled instruction: 0x13CB0321
                 primary 4(0x4), secondary 801(0x321)
==692== valgrind: Unrecognised instruction at address 0x400fb08.
==692==    at 0x400FB08: _dl_catch_error (in /lib/ld-2.20.so)
==692==    by 0x4002203: do_preload (in /lib/ld-2.20.so)
==692==    by 0x40055A3: dl_main (in /lib/ld-2.20.so)
==692==    by 0x401717F: _dl_sysdep_start (in /lib/ld-2.20.so)
==692==    by 0x4005A4B: _dl_start_final (in /lib/ld-2.20.so)
==692==    by 0x4005E0B: _dl_start (in /lib/ld-2.20.so)
==692==    by 0x4018BA7: _start (in /lib/ld-2.20.so)
==692== Your program just tried to execute an instruction that Valgrind
==692== did not recognise.  There are two possible reasons for this.
==692== 1. Your program has a bug and erroneously jumped to a non-code
==692==    location.  If you are running Memcheck and you just saw a
==692==    warning about a bad jump, it's probably your program's fault.
==692== 2. The instruction is legitimate but Valgrind doesn't handle it,
==692==    i.e. it's Valgrind's fault.  If you think this is the case or
==692==    you are not sure, please let us know and we'll try to fix it.
==692== Either way, Valgrind will now raise a SIGILL signal which will
==692== probably kill your program.
==692== 
==692== Process terminating with default action of signal 4 (SIGILL)
==692==  Illegal opcode at address 0x400FB08
==692==    at 0x400FB08: _dl_catch_error (in /lib/ld-2.20.so)
==692==    by 0x4002203: do_preload (in /lib/ld-2.20.so)
==692==    by 0x40055A3: dl_main (in /lib/ld-2.20.so)
==692==    by 0x401717F: _dl_sysdep_start (in /lib/ld-2.20.so)
==692==    by 0x4005A4B: _dl_start_final (in /lib/ld-2.20.so)
==692==    by 0x4005E0B: _dl_start (in /lib/ld-2.20.so)
==692==    by 0x4018BA7: _start (in /lib/ld-2.20.so)
==692== 
==692== HEAP SUMMARY:
==692==     in use at exit: 0 bytes in 0 blocks
==692==   total heap usage: 0 allocs, 0 frees, 0 bytes allocated
==692== 
==692== All heap blocks were freed -- no leaks are possible
==692== 
==692== For counts of detected and suppressed errors, rerun with: -v
==692== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 0 from 0)
Illegal instruction


MPC85xx supports SPE and isel, but not AltiVec. So, "-M e500x2" should be added to objdump's command line parameters (at least for 2.24). AltiVec and SPE both use the same opcode space, so "13 cb" seems to be common prefix for them. SPE mnemonics start w/ "ev", for example:

# /usr/powerpc-e500v2-linux-gnuspe/binutils-bin/2.24/objdump -M e500x2 -Cd /bin/echo | grep "13 cb"
10015a34:       13 cb 6b 01     evldd   r30,104(r11)
10016a58:       13 cb 73 01     evldd   r30,112(r11)
10028504:       13 cb 83 01     evldd   r30,128(r11)
1002855c:       13 cb 83 21     evstdd  r30,128(r11)
Comment 4 Florian Krohm 2015-04-27 20:37:20 UTC
(In reply to Arseny Solokha from comment #3)
> It wasn't fixed in the past.
> 
> # ./valgrind echo   
> ==692== Memcheck, a memory error detector
> ==692== Copyright (C) 2002-2013, and GNU GPL'd, by Julian Seward et al.
> ==692== Using Valgrind-3.10.1 and LibVEX; rerun with -h for copyright info
> ==692== Command: echo
> ==692== 
> disInstr(ppc): declined to decode an AltiVec insn.
> disInstr(ppc): unhandled instruction: 0x13CB0321
>                  primary 4(0x4), secondary 801(0x321)

So valgrind thinks this is an altivec instruction because it has no support for SPE and e500 instructions. The thing is that valgrind can only process altivec insns on a host that has altivec capabilities. The machine I tested this on has altivec, so everything looked good on my end, leading me to believe the insn was implemented. As you say, your box does not support altivec which explains the error message..
Now, if this is an e500 insn, then there is no support for those insns whatsoever right now. See also bug #268106. 

> ==692== valgrind: Unrecognised instruction at address 0x400fb08.
> ==692==    at 0x400FB08: _dl_catch_error (in /lib/ld-2.20.so)
> ==692==    by 0x4002203: do_preload (in /lib/ld-2.20.so)
> ==692==    by 0x40055A3: dl_main (in /lib/ld-2.20.so)
> ==692==    by 0x401717F: _dl_sysdep_start (in /lib/ld-2.20.so)
> ==692==    by 0x4005A4B: _dl_start_final (in /lib/ld-2.20.so)
> ==692==    by 0x4005E0B: _dl_start (in /lib/ld-2.20.so)
> ==692==    by 0x4018BA7: _start (in /lib/ld-2.20.so)
> ==692== Your program just tried to execute an instruction that Valgrind
> ==692== did not recognise.  There are two possible reasons for this.
> ==692== 1. Your program has a bug and erroneously jumped to a non-code
> ==692==    location.  If you are running Memcheck and you just saw a
> ==692==    warning about a bad jump, it's probably your program's fault.
> ==692== 2. The instruction is legitimate but Valgrind doesn't handle it,
> ==692==    i.e. it's Valgrind's fault.  If you think this is the case or
> ==692==    you are not sure, please let us know and we'll try to fix it.
> ==692== Either way, Valgrind will now raise a SIGILL signal which will
> ==692== probably kill your program.
> ==692== 
> ==692== Process terminating with default action of signal 4 (SIGILL)
> ==692==  Illegal opcode at address 0x400FB08
> ==692==    at 0x400FB08: _dl_catch_error (in /lib/ld-2.20.so)
> ==692==    by 0x4002203: do_preload (in /lib/ld-2.20.so)
> ==692==    by 0x40055A3: dl_main (in /lib/ld-2.20.so)
> ==692==    by 0x401717F: _dl_sysdep_start (in /lib/ld-2.20.so)
> ==692==    by 0x4005A4B: _dl_start_final (in /lib/ld-2.20.so)
> ==692==    by 0x4005E0B: _dl_start (in /lib/ld-2.20.so)
> ==692==    by 0x4018BA7: _start (in /lib/ld-2.20.so)
> ==692== 
> ==692== HEAP SUMMARY:
> ==692==     in use at exit: 0 bytes in 0 blocks
> ==692==   total heap usage: 0 allocs, 0 frees, 0 bytes allocated
> ==692== 
> ==692== All heap blocks were freed -- no leaks are possible
> ==692== 
> ==692== For counts of detected and suppressed errors, rerun with: -v
> ==692== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 0 from 0)
> Illegal instruction
> 
> 
> MPC85xx supports SPE and isel, but not AltiVec. So, "-M e500x2" should be
> added to objdump's command line parameters (at least for 2.24). AltiVec and
> SPE both use the same opcode space, so "13 cb" seems to be common prefix for
> them. SPE mnemonics start w/ "ev", for example:
> 
> # /usr/powerpc-e500v2-linux-gnuspe/binutils-bin/2.24/objdump -M e500x2 -Cd
> /bin/echo | grep "13 cb"
> 10015a34:       13 cb 6b 01     evldd   r30,104(r11)
> 10016a58:       13 cb 73 01     evldd   r30,112(r11)
> 10028504:       13 cb 83 01     evldd   r30,128(r11)
> 1002855c:       13 cb 83 21     evstdd  r30,128(r11)