x86-64: Fix CFI data for interrupt frames
The patch titled "x86: Don't use frame pointer to save old stack on irq entry" did not properly adjust CFI directives, so this patch is a follow-up to that one. With the old stack pointer no longer stored in a callee-saved register (plus some offset), we now have to use a CFA expression to describe the memory location where it is being found. This requires the use of .cfi_escape (allowing arbitrary byte streams to be emitted into .eh_frame), as there is no .cfi_def_cfa_expression (which also cannot reasonably be expected, as it would require a full expression parser). Signed-off-by: Jan Beulich <jbeulich@suse.com> Cc: Frederic Weisbecker <fweisbec@gmail.com> Link: http://lkml.kernel.org/r/4E8360200200007800058467@nat28.tlf.novell.com Signed-off-by: Ingo Molnar <mingo@elte.hu>
This commit is contained in:
		
					parent
					
						
							
								e05139f256
							
						
					
				
			
			
				commit
				
					
						eab9e6137f
					
				
			
		
					 2 changed files with 11 additions and 5 deletions
				
			
		| 
						 | 
				
			
			@ -27,6 +27,7 @@
 | 
			
		|||
#define CFI_REMEMBER_STATE	.cfi_remember_state
 | 
			
		||||
#define CFI_RESTORE_STATE	.cfi_restore_state
 | 
			
		||||
#define CFI_UNDEFINED		.cfi_undefined
 | 
			
		||||
#define CFI_ESCAPE		.cfi_escape
 | 
			
		||||
 | 
			
		||||
#ifdef CONFIG_AS_CFI_SIGNAL_FRAME
 | 
			
		||||
#define CFI_SIGNAL_FRAME	.cfi_signal_frame
 | 
			
		||||
| 
						 | 
				
			
			@ -68,6 +69,7 @@
 | 
			
		|||
#define CFI_REMEMBER_STATE	cfi_ignore
 | 
			
		||||
#define CFI_RESTORE_STATE	cfi_ignore
 | 
			
		||||
#define CFI_UNDEFINED		cfi_ignore
 | 
			
		||||
#define CFI_ESCAPE		cfi_ignore
 | 
			
		||||
#define CFI_SIGNAL_FRAME	cfi_ignore
 | 
			
		||||
 | 
			
		||||
#endif
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -331,10 +331,15 @@ ENDPROC(native_usergs_sysret64)
 | 
			
		|||
1:	incl PER_CPU_VAR(irq_count)
 | 
			
		||||
	jne 2f
 | 
			
		||||
	mov PER_CPU_VAR(irq_stack_ptr),%rsp
 | 
			
		||||
	EMPTY_FRAME 0
 | 
			
		||||
	CFI_DEF_CFA_REGISTER	rsi
 | 
			
		||||
 | 
			
		||||
2:	/* Store previous stack value */
 | 
			
		||||
	pushq %rsi
 | 
			
		||||
	CFI_ESCAPE	0x0f /* DW_CFA_def_cfa_expression */, 6, \
 | 
			
		||||
			0x77 /* DW_OP_breg7 */, 0, \
 | 
			
		||||
			0x06 /* DW_OP_deref */, \
 | 
			
		||||
			0x08 /* DW_OP_const1u */, SS+8-RBP, \
 | 
			
		||||
			0x22 /* DW_OP_plus */
 | 
			
		||||
	/* We entered an interrupt context - irqs are off: */
 | 
			
		||||
	TRACE_IRQS_OFF
 | 
			
		||||
	.endm
 | 
			
		||||
| 
						 | 
				
			
			@ -788,7 +793,6 @@ END(interrupt)
 | 
			
		|||
	subq $ORIG_RAX-RBP, %rsp
 | 
			
		||||
	CFI_ADJUST_CFA_OFFSET ORIG_RAX-RBP
 | 
			
		||||
	SAVE_ARGS_IRQ
 | 
			
		||||
	PARTIAL_FRAME 0
 | 
			
		||||
	call \func
 | 
			
		||||
	.endm
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -813,10 +817,10 @@ ret_from_intr:
 | 
			
		|||
 | 
			
		||||
	/* Restore saved previous stack */
 | 
			
		||||
	popq %rsi
 | 
			
		||||
	leaq 16(%rsi), %rsp
 | 
			
		||||
 | 
			
		||||
	CFI_DEF_CFA_REGISTER	rsi
 | 
			
		||||
	leaq ARGOFFSET-RBP(%rsi), %rsp
 | 
			
		||||
	CFI_DEF_CFA_REGISTER	rsp
 | 
			
		||||
	CFI_ADJUST_CFA_OFFSET	-16
 | 
			
		||||
	CFI_ADJUST_CFA_OFFSET	RBP-ARGOFFSET
 | 
			
		||||
 | 
			
		||||
exit_intr:
 | 
			
		||||
	GET_THREAD_INFO(%rcx)
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue