mambo
mambo copied to clipboard
Rationale behind "while" in arm_inline_hash_lookup(...)
The arm_inline_hash_lookup routine has a while loop that spins if registers r0 and r1 are set in the register list: scanner_arm.c#L424. What is the rationale here? I assume the ultimate purpose is to ensure the pop does not clobber the values moved to r0 and r1during runtime. But if that was the intention, why not just change line 425 to arm_pop_regs(reglist & 0x7ffc)?
I ask because in some cases, during ARM block scanning, the scanner silently just fails. I tracked it down to that while loop, which spins on the instruction pop {r1, r2, r3, r4, r5, r6, r7, r8, r9, sl, fp, pc} (encoded ase8bd8ffe).
There are a few infinite loops like that in MAMBO. They are basically asserts which stop execution and allow you to attach a debugger and inspect the context instead of exiting. I'll admit that doing that silently is less than ideal.
In this case, the issue is that the values saved at scanner_arm.c#L411 and which would be restored by the dispatcher are stale (because those values would be overwritten by the POP). I think the best solution is to POP (reglist & 3) before inserting the lookup routine, but I'll need to take a closer look. By the way, where have you encountered this instruction? It doesn't look compiler generated, which is why I've never encountered it before.
What you say makes sense. So in that case, technically speaking, shouldn't the assert statement also check if r2 is being POPed? I'm aware that arm_inline_hash_lookup doesn't use r2 but then the values saved in scanner_arm.c#L411 saves r2 as well.
The updated value of R2 (i.e. after the POP) is saved at scanner_arm.c#L428, so it doesn't have to be included in the assert. Now, I've spent a bit of time looking at the file history to try to understand why R2 is also saved by the STM, but as far as I can tell it's always been redundant.