Memory corruption debug with android ndk - memory

I am getting a segfault in the native part of my android app, in the moment a void function returns to its caller. To visualize better, I put a log statement at the end of the callee function, and one in the caller function, right after the call to the callee (sorry for the pun).
In the logcat, the first message is printed, and the second not (the app crashes).
Thinking about a possible memory corruption I decided to activate malloc debug (giving "setprop libc.debug.malloc 10" in adb shell). Then, i get this in the logcat right after the log message from the end of the callee function:
D/MyApp - NativeSide(12778): I am the callee function and I am about to return!
E/libc (12778): *** FREE CHECK: buffer 0x82869900 corrupted 16 bytes before allocation
E/libc (12778): call stack:
E/libc (12778): 0: 8000e3ea
E/libc (12778): 1: 8000e49c
E/libc (12778): 2: 8000e4e2
E/libc (12778): 3: 8000e540
E/libc (12778): 4: afd14ccc
E/libc (12778): 5: 81258188
E/libc (12778): 6: 81258188
E/libc (12778): 7: 81258188
E/libc (12778): 8: 81258188
E/libc (12778): 9: 81258188
E/libc (12778): 10: 81258188
E/libc (12778): 11: 81258188
E/libc (12778): 12: 81258188
E/libc (12778): 13: 81258188
E/libc (12778): 14: 81258188
E/libc (12778): 15: 81258188
E/libc (12778): 16: 81258188
E/libc (12778): 17: 81258188
E/libc (12778): 18: 81258188
E/libc (12778): 19: 81258188
I couldn't find any information on how to decipher this output. The numbers shown at each line are changing at every app launch. I hope there's a way to use this information as a clue on where the corruption happens, as I can't find it from the code. I also tried building the native libraries with the "-fstack-check flag, but I couldn't say if I got more informations in the log (it seems not but I might have missed them), or whether I need to do other things to get them.
Also, here's the stack dump, coming after the "FREE CHECK:" message.
I/DEBUG (12311): *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** ***
I/DEBUG (12311): Build fingerprint: 'google/soju/crespo:2.3/GRH55/79397:user/release-keys'
I/DEBUG (12311): pid: 12778, tid: 12907 >>> com.ntrack.tuner <<<
I/DEBUG (12311): signal 11 (SIGSEGV), code 1 (SEGV_MAPERR), fault addr deadbaad
I/DEBUG (12311): r0 deadbaad r1 45ea374c r2 00000027 r3 00000000
I/DEBUG (12311): r4 00000080 r5 45ea374c r6 8003422e r7 45ea37b4
I/DEBUG (12311): r8 45da4000 r9 a811eca5 10 00100000 fp 00000001
I/DEBUG (12311): ip ffffffff sp 45ea3738 lr 8000f623 pc 8000f650 cpsr 20000030
I/DEBUG (12311): d0 3f9664f48406d639 d1 3f8226e3e96e8495
I/DEBUG (12311): d2 3faba1ba1bb34201 d3 0000000000000000
I/DEBUG (12311): d4 3d7943379e56fd24 d5 3d8f940585cd5f95
I/DEBUG (12311): d6 3f2cf2145b888497 d7 3f2cf214636d85f8
I/DEBUG (12311): d8 0000000000000000 d9 0000000000000000
I/DEBUG (12311): d10 0000000000000000 d11 0000000000000000
I/DEBUG (12311): d12 0000000000000000 d13 0000000000000000
I/DEBUG (12311): d14 0000000000000000 d15 0000000000000000
I/DEBUG (12311): scr 20000010
I/DEBUG (12311):
Anything, a suggestion on the typical things to check or just the way to make use of the malloc debug informations would be of great help, thanks!

The malloc debug property is probably setting some magic numbers before and after the area you allocate. Then, when freeing, it would check those areas to make sure the magic number is still there.
For example, if you allocate 1024 bytes:
char * p = malloc(1024);
The malloc debug code would actually allocate 1024 bytes that you requested, plus some extra around it:
[ 32 bytes ---- | -------- 1024 bytes ------| ---- 32 bytes ]
^ 0xc0000000 ^ 0xc0000020
The library would then write a magic value into those 32 bytes:
[ 32 bytes ---- | -------- 1024 bytes ------| ---- 32 bytes ]
[ 0xdeadd00d | | 0xdeadd00d ]
^ 0xc0000000 ^ 0xc0000020
The library would return 0xc0000020 into p and internally it would save 0xc0000000, the size, etc.
Your function then uses the allocated area somehow:
memset(p, 0, 1025);
Notice this line copied more than 1024 bytes. That would write a 0 into the last 32 byte magic area (notice the 0 in the last 32 bytes, which should be 0xdeadd00d):
[ 32 bytes ---- | -------- 1024 bytes ------| ---- 32 bytes ]
[ 0xdeadd00d | 000... ...00 | 0x0eadd00d ]
^ 0xc0000000 ^ 0xc0000020 (address)
When your function calls free:
free(p);
The library would then check to make sure the first and last 32 bytes are still 0xdeadd00d. Since your function overwrote the last 32 bytes, it would print an error like you posted.
This is only an example of how a malloc debug checking would work. If you would like to see exactly what the malloc debug checks and how it works, go to the bionic directory of Android source and search for the property you set, libc.debug.malloc.
Check your code for how you use allocated memory in the called function. You are probably writing to an area outside of the area you allocated.

To me, this:
a segfault in the native part of my android app, in the moment a void function returns to its caller.
means stack corruption (more than heap corruption). What state is stored on the stack of this function you're returning from (and from every function it calls ..)?
The call stack output you're seeing should be the address of each function on the stack at the time the corruption was detected. You'll need to know what address your library was loaded at to map those back to a symbol in your .so. (I think this question will help: How to use addr2line in Android)
The fact that 81258188 repeats off the top of the stack dump also suggest that you might've blown out the bottom of the stack (by recursing too many times). If you're not aware of any intentional recursion in your code, then figuring out where your library was loaded and mapping that back to your code could be useful.

Related

Windbg load symbol at address which is a reload module, symbol name can not be displayed

I've wrote some pieces of code which is used to reload a PE module into arbitrary address, and below is the memory that the code reload ntoskrnl.exe of windows kernel:
kd> lm
start end module name
83c14000 84018000 nt (pdb symbols) \\vboxsvr\symbols\ntkrnlmp.pdb\00625D7D36754CBEBA4533BA9A0F3FE22\ntkrnlmp.pdb
899e1000 899e1000 nt_ffffffff899e1000 T (pdb symbols) \\vboxsvr\sharedfolder\nt.pdb
......
Address 0x83c14000 is the original ntoskrnl.exe and 0x899e1000 is the new loaded one, 2 addresses contains same binary data:
kd> dc 83c14000 L20
83c14000 00905a4d 00000003 00000004 0000ffff MZ..............
83c14010 000000b8 00000000 00000040 00000000 ........#.......
83c14020 00000000 00000000 00000000 00000000 ................
83c14030 00000000 00000000 00000000 00000278 ............x...
83c14040 0eba1f0e cd09b400 4c01b821 685421cd ........!..L.!Th
83c14050 70207369 72676f72 63206d61 6f6e6e61 is program canno
83c14060 65622074 6e757220 206e6920 20534f44 t be run in DOS
83c14070 65646f6d 0a0d0d2e 00000024 00000000 mode....$.......
kd> dc 899e1000 L20
899e1000 00905a4d 00000003 00000004 0000ffff MZ..............
899e1010 000000b8 00000000 00000040 00000000 ........#.......
899e1020 00000000 00000000 00000000 00000000 ................
899e1030 00000000 00000000 00000000 00000278 ............x...
899e1040 0eba1f0e cd09b400 4c01b821 685421cd ........!..L.!Th
899e1050 70207369 72676f72 63206d61 6f6e6e61 is program canno
899e1060 65622074 6e757220 206e6920 20534f44 t be run in DOS
899e1070 65646f6d 0a0d0d2e 00000024 00000000 mode....$.......
The \\vboxsvr\symbols\ntkrnlmp.pdb\00625D7D36754CBEBA4533BA9A0F3FE22\ntkrnlmp.pdb and \\vboxsvr\sharedfolder\nt.pdb are same file, I just copied it into two difference places in order to use it.
The prolbem is: the reload kernel can not display correct symbol names.
Here is the evidence.
Show original ZwCreateFile codes:
kd> u ZwCreateFile L5
nt!ZwCreateFile:
83c47300 b842000000 mov eax,42h
83c47305 8d542404 lea edx,[esp+4]
83c47309 9c pushfd
83c4730a 6a08 push 8
83c4730c e86d230000 call nt!KiSystemService (83c4967e)
Which seems all good, then I caculated the offset of this function:
kd> ?83c47300-83c14000 // original function offset in ntoskrnl.exe
Evaluate expression: 209664 = 00033300
kd> ?899e1000+00033300 // function address in reloaded ntoskrnl.exe (0x899e1000 is new base address, see above)
Evaluate expression: -1985920256 = 89a14300
Check the "new" function at 0x89a14300:
kd> u 89a14300 L5
ReadVirtual: 89a14300 not properly sign extended
89a14300 b842000000 mov eax,42h
89a14305 8d542404 lea edx,[esp+4]
89a14309 9c pushfd
89a1430a 6a08 push 8
89a1430c e86d230000 call 89a1667e
They have same OP code, except the call instruction. Original displayed with correct symbolic name nt!KiSystemService but the new reloaded one is not (just displayed a raw adress).
I caculated the offset again:
kd> ?83c4967e-83c14000
Evaluate expression: 218750 = 0003567e
kd> ?89a1667e-899e1000
Evaluate expression: 218750 = 0003567e
The call instruction's offset is equal.
What am I wrong ? I want the reloaded module displays with correct symbolic name ...
The magic is hidden here:
kd> lm
start end module name
83c14000 84018000 nt (pdb symbols) \\vboxsvr\symbols\ntkrnlmp.pdb\00625D7D36754CBEBA4533BA9A0F3FE22\ntkrnlmp.pdb
899e1000 899e1000 nt_ffffffff899e1000 T (pdb symbols) \\vboxsvr\sharedfolder\nt.pdb
......
Original nt module end address is 84018000, but the new loaded module's end address qeuals its start address, so we need reload new module with this command:
.reload /i nt=899e1000,404000
After we indicated the correct size of new loaded module, all symbols worked:
kd> lmol
start end module name
83c14000 84018000 nt (pdb symbols) \\vboxsvr\sharedfolder\ntkrnlmp.pdb
899e1000 89de5000 ntkrnlmp (pdb symbols) \\vboxsvr\sharedfolder\ntkrnlmp.pdb
92cb8000 92cfb000 petool (private pdb symbols) x:\test\petool\build\objchk_win7_x86\i386\petool.pdb
kd> u nt!ZwCreateFile L5
nt!ZwCreateFile:
83c47300 b842000000 mov eax,42h
83c47305 8d542404 lea edx,[esp+4]
83c47309 9c pushfd
83c4730a 6a08 push 8
83c4730c e86d230000 call nt!KiSystemService (83c4967e)
kd> ?83c47300-83c14000+899e1000
Evaluate expression: -1985920256 = 89a14300
kd> u 89a14300 L5
89a14300 b842000000 mov eax,42h
89a14305 8d542404 lea edx,[esp+4]
89a14309 9c pushfd
89a1430a 6a08 push 8
89a1430c e86d230000 call ntkrnlmp!KiSystemService (89a1667e)
kd> u ntkrnlmp!ZwCreateFile L5
ntkrnlmp!ZwCreateFile:
89a14300 b842000000 mov eax,42h
89a14305 8d542404 lea edx,[esp+4]
89a14309 9c pushfd
89a1430a 6a08 push 8
89a1430c e86d230000 call ntkrnlmp!KiSystemService (89a1667e)

"dyld`__abort_with_payload" error and exit code 45 on attempted reverse engineering of iOS app

I am attempting to reverse engineer an iOS app to remove jailbreak detection. When using lldb, I got this output:
* thread #1: tid = 0xe26e, 0x00000001012322f8 dyld`__abort_with_payload + 8, queue = 'com.apple.main-thread', stop reason = signal SIGABRT
I looked it up and __abort_with_payload has to do with embedded binaries or code signing or something, which gives me reason to believe it has something to do with how mobilesubstrate injects dylibs into apps.
I tried disabling mobilesubstrate, and running lldb again. This time, it gave a different issue:
Process 16662 resuming
Process 16662 exited with status = 45 (0x0000002d)
What is exit code 45? Google searching didn't help very much, but according to osstatus.com, it can mean ENOTSUP or "Operation not supported". What does "Operation not supported" mean?
It's PT_DENY_ATTACH.
Many SO answers already cover it to some extent to give you an idea: here & here . Even in more details covered in Alexander O'mara 's blog post here
To counter it in lldb before your executable runs type:
b ptrace
You should see something like this:
Breakpoint 5: where = libsystem_kernel.dylib`__ptrace, address = 0x00000001c2b17140
Giving you indication where it's actually handled.
When you hit the ptrace breakpoint type:
th r
i.e. shortened syntax for thread return
It will force exiting the ptrace function without actually doing the denying part.
After the th r you may see something like this
-> 0x100daa548 <+140>: str w0, [sp, #392]
0x100daa54c <+144>: bl 0x100b01cb8 ; ___lldb_unnamed_function1756$$prodx
0x100daa550 <+148>: bl 0x100b02538 ; ___lldb_unnamed_function1760$$prodx
0x100daa554 <+152>: bl 0x100daa470 ; ___lldb_unnamed_function29542$$prodx
The code snippet is from OP and is irrelevant. What is important is ip(i.e. instruction pointer register) is pointing to the next assembly instruction after the ptrace call. Hence to see what's going on we must disassemble preceding assembly code. Every single arm64 assembly instruction is 4 bytes hence we type:
di -s 0x100daa544
That will most likely yield:
0x100daa544 bl <some address> ; aka ptrace(PT_DENY_ATTACH, ...)
So now you can just inspect the actual bytes of the opcodes^:
x 0x100daa544 -c 4
These are the bytes to replace with the nop mentioned below.
However it may happen the ptrace is made directly instead through a syscall like this (that's what libsystem_kernel.dylib`__ptrace: actually does internally) :
mov x0, #0x1f ; this is PT_DENY_ATTACH 31 syscall argument
mov x16, #0x1a ; x0,x16 can be set in numerous ways so I skip the opcodes
01 10 00 D4 svc #0x80
This is AARCH64 (aka arm64) assembly so I'm assuming your device is iPhone5s or newer. To further obfuscate it, the instructions might be separated by some nonrelevant instructions. If you need to follow this path check the SO question here.
So replacing 01 10 00 D4 in your favourite hex editor with
1f 20 03 d5 nop
should get you going.
One could go crazy with not using 0x80 in svc for the syscall
01 00 00 d4 svc #0
21 00 00 d4 svc #1
01 02 00 d4 svc #0x10
e1 1f 00 d4 svc #0xff
Each of them would happen to work, but it might break at any point (still it hasn’t since iOS7 up to present iOS 13).
Final remarks:
If you actually modify the binary some extra protection mechanism might exist like checksum and other self integrity checks. That's definitely beyond the scope of this question.

Awk filtering out paragraphs

I have a plain txt file which contains paragraphs which contain about 15-40 lines and each paragraph is separated from the previous/next one with 3 empty lines, I'd like to print out all the paragraphs which contain the string "sasi89".
Example:
PokerStars Hand #61919020230: Tournament #393199063, $0.10+$0.01 USD Hold'em No Limit - Level IV (50/100) - 2011/05/10 12:11:58 ET
Table '393199063 1' 9-max Seat #9 is the button
Seat 1: bebe2829 (1529 in chips)
Seat 3: zng 111 (4374 in chips)
Seat 4: mal4o (11100 in chips)
Seat 6: gysomi (6118 in chips)
Seat 7: DEEAMAYA (2590 in chips)
Seat 9: sasi89 (235 in chips)
bebe2829: posts small blind 50
zng 111: posts big blind 100
*** HOLE CARDS ***
Dealt to sasi89 [Kc Th]
mal4o: folds
gysomi: folds
DEEAMAYA: folds
sasi89: raises 135 to 235 and is all-in
bebe2829: folds
zng 111: calls 135
*** FLOP *** [7h 9s Tc]
*** TURN *** [7h 9s Tc] [Qd]
*** RIVER *** [7h 9s Tc Qd] [9d]
*** SHOW DOWN ***
zng 111: shows [Jh Kh] (a straight, Nine to King)
sasi89: shows [Kc Th] (two pair, Tens and Nines)
zng 111 collected 520 from pot
sasi89 finished the tournament in 11th place
*** SUMMARY ***
Total pot 520 | Rake 0
Board [7h 9s Tc Qd 9d]
Seat 1: bebe2829 (small blind) folded before Flop
Seat 3: zng 111 (big blind) showed [Jh Kh] and won (520) with a straight, Nine to King
Seat 4: mal4o folded before Flop (didn't bet)
Seat 6: gysomi folded before Flop (didn't bet)
Seat 7: DEEAMAYA folded before Flop (didn't bet)
Seat 9: sasi89 (button) showed [Kc Th] and lost with two pair, Tens and Nines
PokerStars Hand #61918994165: Tournament #393199063, $0.10+$0.01 USD Hold'em No Limit - Level IV (50/100) - 2011/05/10 12:11:19 ET
Table '393199063 1' 9-max Seat #7 is the button
Seat 1: bebe2829 (1079 in chips)
Seat 3: zng 111 (4374 in chips)
Seat 4: mal4o (11500 in chips)
Seat 6: gysomi (6118 in chips)
Seat 7: DEEAMAYA (2590 in chips)
Seat 9: sasi89 (285 in chips)
sasi89: posts small blind 50
bebe2829: posts big blind 100
*** HOLE CARDS ***
Dealt to sasi89 [2d 7h]
zng 111: folds
mal4o: calls 100
gysomi: folds
DEEAMAYA: folds
sasi89: folds
bebe2829: checks
*** FLOP *** [8c Js 2h]
bebe2829: checks
mal4o: checks
*** TURN *** [8c Js 2h] [8h]
bebe2829: checks
mal4o: checks
*** RIVER *** [8c Js 2h 8h] [6h]
bebe2829: bets 300
mal4o: calls 300
*** SHOW DOWN ***
bebe2829: shows [Jc 3c] (two pair, Jacks and Eights)
mal4o: mucks hand
bebe2829 collected 850 from pot
*** SUMMARY ***
Total pot 850 | Rake 0
Board [8c Js 2h 8h 6h]
Seat 1: bebe2829 (big blind) showed [Jc 3c] and won (850) with two pair, Jacks and Eights
Seat 3: zng 111 folded before Flop (didn't bet)
Seat 4: mal4o mucked [6d Ac]
Seat 6: gysomi folded before Flop (didn't bet)
Seat 7: DEEAMAYA (button) folded before Flop (didn't bet)
Seat 9: sasi89 (small blind) folded before Flop
You can use awk in "paragraph mode" (see https://www.gnu.org/software/gawk/manual/html_node/Multiple-Line.html) by setting RS to the empty string:
awk -v RS= '/sasi89/' file
The above assumes there's no other blank lines in your file except those between paragraphs.
awk to the rescue
awk 'BEGIN{ORS=RS="\n\n\n"} /sasi89/'
this will keep the 3 empty lines between paragraphs. If you want to normalize to single empty line remove ORS= or simply
awk -v RS="\n\n\n" '/sasi89/'

Assembly-segmentation fault [duplicate]

This question already has an answer here:
What happens if there is no exit system call in an assembly program?
(1 answer)
Closed last month.
I am new to assembly. I am trying to do this:
SECTION .data
SECTION .bss
SECTION .text
global _start
_start:
nop
mov rax, 067FEh
mov bx, ax
mov cl, bh
mov ch, bl
nop
Everytime I run this , I get a segmentation fault. I used gdb to test where it went wrong. It appeared that every time after mov rax, 067FEh, it said the program received SIGSEGV. I tried replacing rax with eax or ax, but it still gave the fault. When I tried to look up the value in rax, it was 067FEh. I can't figure out what happened there. Can anybody help?
The SIGSEGV is coming from that fact that you are dropping out of the .text section. You need to add:
mov eax, 1
int 0x80
to properly exit the program. If you do not do that, the code with continue to execute past your program (usually into a bunch of 00 00 bytes). Also, you do not need the section .data and section .bss declarations because you are not using them.

iOS iPad panic crash log interpret

can anyone help me out in interpreting this panic crash log?
this happens during rotation with many images ... it involves javascript if that is of any help.
Incident Identifier: AD3EB83A-2379-4876-BCB3-6C9A4B5DC862
CrashReporter Key: e580be25a4b36b96f0d033b88c3cfebf6232e309
Hardware Model: iPad2,1
Date/Time: 2012-06-27 14:26:41.182 +0200
OS Version: iPhone OS 5.1.1 (9B206)
panic(cpu 1 caller 0x801c6fdb): mbuf_watchdog: 4 waiters stuck for 12 secs
13872/13872 mbufs in use:
13868 mbufs allocated to data
4 mbufs allocated to packet headers
13748/13748 mbuf 2KB clusters in use
0/122 mbuf 4KB clusters in use
31452 KB allocated to network (approx. 98% in use)
mbuf leak detection table:
total captured: 31701 (one per 500)
total allocs outstanding: 42
new hash recorded: 27032 allocs, 26944 traces
hash collisions: 18 allocs, 4669 traces
overwrites: 26449 allocs, 0 traces
lock conflicts: 0
top 5 outstanding traces:
[1] 29 outstanding alloc(s), 30 hit(s), 1 collision(s)
[2] 5 outstanding alloc(s), 26 hit(s), 0 collision(s)
[3] 3 outstanding alloc(s), 2546 hit(s), 0 collision(s)
[4] 3 outstanding alloc(s), 1844 hit(s), 0 collision(s)
[5] 1 outstanding alloc(s), 4662 hit(s), 4661 collision(s)
trace [1] trace [2] trace [3] trace [4] trace [5]
---------- ---------- ---------- ---------- ----------
1: 0x801bff71 0x801bff71 0x801bff71 0x801bff71 0x801bff71
2: 0x801b0df3 0x801b0df3 0x801b0e2b 0x801b0df3 0x801b0df3
3: 0x801bf8b5 0x801c12db 0x801c12db 0x801bf871 0x801b0f39
4: 0x801b0c67 0x801c9517 0x801c9517 0x801b0c67 0x801c08bb
5: 0x801c12db 0x801cece3 0x801cece3 0x801c12db 0x802b7855
6: 0x801c9517 0x801ceb05 0x801ceb05 0x801c9517 0x801be739
7: 0x801cece3 0x801e1bd8 0x801e1bd8 0x801cece3 0x8010e8d5
8: 0x801ceb05 0x801ceb05 0x802b91f5
9: 0x801e1bd8 0x801e1bd8 0x802b937f
10: 0x802b8591
11: 0x8002425b
12:
13:
14:
15:
16:
Debugger message: panic
OS version: 9B206
Kernel version: Darwin Kernel Version 11.0.0: S
Thanks for any insight.
You should use instruments to check memory allocations and memory leaks. It could also be that the app was too long unresponsive and was killed, the text 4 waiters stuck for 12 secs could indicate that. The crash report content and format is pretty unique, haven't seen that one yet. So these are just guesses.

Resources