Author: jmolenda Date: Thu Jan 22 19:02:32 2015 New Revision: 226889 URL: http://llvm.org/viewvc/llvm-project?rev=226889&view=rev Log: Two fixes for compact unwind decoding for frameless large-stack-size i386/x86_64 functions. The stack size was being multiplied by the pointer size incorrectly. The register permutation placeholders (UNWIND_X86_REG_NONE) were decrementing the stack offset of the saved registers when it should not have been.
<rdar://problem/19570035> Modified: lldb/trunk/source/Symbol/CompactUnwindInfo.cpp lldb/trunk/tools/compact-unwind/compact-unwind-dumper.c Modified: lldb/trunk/source/Symbol/CompactUnwindInfo.cpp URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/CompactUnwindInfo.cpp?rev=226889&r1=226888&r2=226889&view=diff ============================================================================== --- lldb/trunk/source/Symbol/CompactUnwindInfo.cpp (original) +++ lldb/trunk/source/Symbol/CompactUnwindInfo.cpp Thu Jan 22 19:02:32 2015 @@ -809,8 +809,16 @@ CompactUnwindInfo::CreateUnwindPlan_x86_ } } + if (mode == UNWIND_X86_64_MODE_STACK_IND) + { + row->SetCFAOffset (stack_size); + } + else + { + row->SetCFAOffset (stack_size * wordsize); + } + row->SetCFARegister (x86_64_eh_regnum::rsp); - row->SetCFAOffset (stack_size * wordsize); row->SetOffset (0); row->SetRegisterLocationToAtCFAPlusOffset (x86_64_eh_regnum::rip, wordsize * -1, true); row->SetRegisterLocationToIsCFAPlusOffset (x86_64_eh_regnum::rsp, 0, true); @@ -919,10 +927,10 @@ CompactUnwindInfo::CreateUnwindPlan_x86_ case UNWIND_X86_64_REG_R14: case UNWIND_X86_64_REG_R15: case UNWIND_X86_64_REG_RBP: - row->SetRegisterLocationToAtCFAPlusOffset (translate_to_eh_frame_regnum_x86_64 (registers[i]), wordsize * -saved_registers_offset, true); + row->SetRegisterLocationToAtCFAPlusOffset (translate_to_eh_frame_regnum_x86_64 (registers[i]), wordsize * -saved_registers_offset, true); + saved_registers_offset++; break; } - saved_registers_offset++; } } unwind_plan.AppendRow (row); @@ -1047,9 +1055,11 @@ CompactUnwindInfo::CreateUnwindPlan_i386 if (mode == UNWIND_X86_MODE_STACK_IND && function_info.valid_range_offset_start != 0) { uint32_t stack_adjust = EXTRACT_BITS (function_info.encoding, UNWIND_X86_FRAMELESS_STACK_ADJUST); +printf("JSMDEBUG got stack_adjust %d from encoding 0x%x\n", stack_adjust, function_info.encoding); // offset into the function instructions; 0 == beginning of first instruction uint32_t offset_to_subl_insn = EXTRACT_BITS (function_info.encoding, UNWIND_X86_FRAMELESS_STACK_SIZE); +printf("JSMDEBUG got offset to sub instruction %d\n", offset_to_subl_insn); SectionList *sl = m_objfile.GetSectionList (); if (sl) @@ -1084,7 +1094,16 @@ CompactUnwindInfo::CreateUnwindPlan_i386 } row->SetCFARegister (i386_eh_regnum::esp); - row->SetCFAOffset (stack_size * wordsize); + + if (mode == UNWIND_X86_MODE_STACK_IND) + { + row->SetCFAOffset (stack_size); + } + else + { + row->SetCFAOffset (stack_size * wordsize); + } + row->SetOffset (0); row->SetRegisterLocationToAtCFAPlusOffset (i386_eh_regnum::eip, wordsize * -1, true); row->SetRegisterLocationToIsCFAPlusOffset (i386_eh_regnum::esp, 0, true); @@ -1193,10 +1212,10 @@ CompactUnwindInfo::CreateUnwindPlan_i386 case UNWIND_X86_REG_EDI: case UNWIND_X86_REG_ESI: case UNWIND_X86_REG_EBP: - row->SetRegisterLocationToAtCFAPlusOffset (translate_to_eh_frame_regnum_i386 (registers[i]), wordsize * -saved_registers_offset, true); + row->SetRegisterLocationToAtCFAPlusOffset (translate_to_eh_frame_regnum_i386 (registers[i]), wordsize * -saved_registers_offset, true); + saved_registers_offset++; break; } - saved_registers_offset++; } } Modified: lldb/trunk/tools/compact-unwind/compact-unwind-dumper.c URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/tools/compact-unwind/compact-unwind-dumper.c?rev=226889&r1=226888&r2=226889&view=diff ============================================================================== --- lldb/trunk/tools/compact-unwind/compact-unwind-dumper.c (original) +++ lldb/trunk/tools/compact-unwind/compact-unwind-dumper.c Thu Jan 22 19:02:32 2015 @@ -495,7 +495,14 @@ print_encoding_x86_64 (struct baton bato printf ("large stack "); } - printf ("frameless function: stack size %d, register count %d ", stack_size * 8, register_count); + if (mode == UNWIND_X86_64_MODE_STACK_IND) + { + printf ("frameless function: stack size %d, register count %d ", stack_size * 8, register_count); + } + else + { + printf ("frameless function: stack size %d, register count %d ", stack_size, register_count); + } if (register_count == 0) { @@ -591,7 +598,14 @@ print_encoding_x86_64 (struct baton bato } - printf (" CFA is rsp+%d ", stack_size * 8); + if (mode == UNWIND_X86_64_MODE_STACK_IND) + { + printf (" CFA is rsp+%d ", stack_size); + } + else + { + printf (" CFA is rsp+%d ", stack_size * 8); + } uint32_t saved_registers_offset = 1; printf (" rip=[CFA-%d]", saved_registers_offset * 8); @@ -605,24 +619,29 @@ print_encoding_x86_64 (struct baton bato break; case UNWIND_X86_64_REG_RBX: printf (" rbx=[CFA-%d]", saved_registers_offset * 8); + saved_registers_offset++; break; case UNWIND_X86_64_REG_R12: printf (" r12=[CFA-%d]", saved_registers_offset * 8); + saved_registers_offset++; break; case UNWIND_X86_64_REG_R13: printf (" r13=[CFA-%d]", saved_registers_offset * 8); + saved_registers_offset++; break; case UNWIND_X86_64_REG_R14: printf (" r14=[CFA-%d]", saved_registers_offset * 8); + saved_registers_offset++; break; case UNWIND_X86_64_REG_R15: printf (" r15=[CFA-%d]", saved_registers_offset * 8); + saved_registers_offset++; break; case UNWIND_X86_64_REG_RBP: printf (" rbp=[CFA-%d]", saved_registers_offset * 8); + saved_registers_offset++; break; } - saved_registers_offset++; } } @@ -712,7 +731,14 @@ print_encoding_i386 (struct baton baton, printf ("large stack "); } - printf ("frameless function: stack size %d, register count %d ", stack_size * 4, register_count); + if (mode == UNWIND_X86_MODE_STACK_IND) + { + printf ("frameless function: stack size %d, register count %d ", stack_size, register_count); + } + else + { + printf ("frameless function: stack size %d, register count %d ", stack_size * 4, register_count); + } if (register_count == 0) { @@ -808,7 +834,14 @@ print_encoding_i386 (struct baton baton, } - printf (" CFA is esp+%d ", stack_size * 4); + if (mode == UNWIND_X86_MODE_STACK_IND) + { + printf (" CFA is esp+%d ", stack_size); + } + else + { + printf (" CFA is esp+%d ", stack_size * 4); + } uint32_t saved_registers_offset = 1; printf (" eip=[CFA-%d]", saved_registers_offset * 4); @@ -822,24 +855,29 @@ print_encoding_i386 (struct baton baton, break; case UNWIND_X86_REG_EBX: printf (" ebx=[CFA-%d]", saved_registers_offset * 4); + saved_registers_offset++; break; case UNWIND_X86_REG_ECX: printf (" ecx=[CFA-%d]", saved_registers_offset * 4); + saved_registers_offset++; break; case UNWIND_X86_REG_EDX: printf (" edx=[CFA-%d]", saved_registers_offset * 4); + saved_registers_offset++; break; case UNWIND_X86_REG_EDI: printf (" edi=[CFA-%d]", saved_registers_offset * 4); + saved_registers_offset++; break; case UNWIND_X86_REG_ESI: printf (" esi=[CFA-%d]", saved_registers_offset * 4); + saved_registers_offset++; break; case UNWIND_X86_REG_EBP: printf (" ebp=[CFA-%d]", saved_registers_offset * 4); + saved_registers_offset++; break; } - saved_registers_offset++; } } _______________________________________________ lldb-commits mailing list lldb-commits@cs.uiuc.edu http://lists.cs.uiuc.edu/mailman/listinfo/lldb-commits