Skip to content

Commit

Permalink
[PATCH] swsusp: clean assembly parts
Browse files Browse the repository at this point in the history
This patch fixes register saving so that each register is only saved once,
and adds missing saving of %cr8 on x86-64.  Some reordering so that
save/restore is more logical/safer (segment registers should be restored
after gdt).

Signed-off-by: Pavel Machek <pavel@suse.cz>
Signed-off-by: Andrew Morton <akpm@osdl.org>
Signed-off-by: Linus Torvalds <torvalds@osdl.org>
  • Loading branch information
Pavel Machek authored and Linus Torvalds committed Jun 25, 2005
1 parent c61978b commit 8d783b3
Show file tree
Hide file tree
Showing 3 changed files with 17 additions and 20 deletions.
17 changes: 7 additions & 10 deletions arch/i386/power/cpu.c
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,6 @@ void __save_processor_state(struct saved_context *ctxt)
*/
asm volatile ("sgdt %0" : "=m" (ctxt->gdt_limit));
asm volatile ("sidt %0" : "=m" (ctxt->idt_limit));
asm volatile ("sldt %0" : "=m" (ctxt->ldt));
asm volatile ("str %0" : "=m" (ctxt->tr));

/*
Expand Down Expand Up @@ -107,7 +106,6 @@ static void fix_processor_context(void)

void __restore_processor_state(struct saved_context *ctxt)
{

/*
* control registers
*/
Expand All @@ -116,6 +114,13 @@ void __restore_processor_state(struct saved_context *ctxt)
asm volatile ("movl %0, %%cr2" :: "r" (ctxt->cr2));
asm volatile ("movl %0, %%cr0" :: "r" (ctxt->cr0));

/*
* now restore the descriptor tables to their proper values
* ltr is done i fix_processor_context().
*/
asm volatile ("lgdt %0" :: "m" (ctxt->gdt_limit));
asm volatile ("lidt %0" :: "m" (ctxt->idt_limit));

/*
* segment registers
*/
Expand All @@ -124,14 +129,6 @@ void __restore_processor_state(struct saved_context *ctxt)
asm volatile ("movw %0, %%gs" :: "r" (ctxt->gs));
asm volatile ("movw %0, %%ss" :: "r" (ctxt->ss));

/*
* now restore the descriptor tables to their proper values
* ltr is done i fix_processor_context().
*/
asm volatile ("lgdt %0" :: "m" (ctxt->gdt_limit));
asm volatile ("lidt %0" :: "m" (ctxt->idt_limit));
asm volatile ("lldt %0" :: "m" (ctxt->ldt));

/*
* sysenter MSRs
*/
Expand Down
18 changes: 9 additions & 9 deletions arch/x86_64/kernel/suspend.c
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,6 @@ void __save_processor_state(struct saved_context *ctxt)
*/
asm volatile ("sgdt %0" : "=m" (ctxt->gdt_limit));
asm volatile ("sidt %0" : "=m" (ctxt->idt_limit));
asm volatile ("sldt %0" : "=m" (ctxt->ldt));
asm volatile ("str %0" : "=m" (ctxt->tr));

/* XMM0..XMM15 should be handled by kernel_fpu_begin(). */
Expand All @@ -69,6 +68,7 @@ void __save_processor_state(struct saved_context *ctxt)
asm volatile ("movq %%cr2, %0" : "=r" (ctxt->cr2));
asm volatile ("movq %%cr3, %0" : "=r" (ctxt->cr3));
asm volatile ("movq %%cr4, %0" : "=r" (ctxt->cr4));
asm volatile ("movq %%cr8, %0" : "=r" (ctxt->cr8));
}

void save_processor_state(void)
Expand All @@ -90,11 +90,19 @@ void __restore_processor_state(struct saved_context *ctxt)
/*
* control registers
*/
asm volatile ("movq %0, %%cr8" :: "r" (ctxt->cr8));
asm volatile ("movq %0, %%cr4" :: "r" (ctxt->cr4));
asm volatile ("movq %0, %%cr3" :: "r" (ctxt->cr3));
asm volatile ("movq %0, %%cr2" :: "r" (ctxt->cr2));
asm volatile ("movq %0, %%cr0" :: "r" (ctxt->cr0));

/*
* now restore the descriptor tables to their proper values
* ltr is done i fix_processor_context().
*/
asm volatile ("lgdt %0" :: "m" (ctxt->gdt_limit));
asm volatile ("lidt %0" :: "m" (ctxt->idt_limit));

/*
* segment registers
*/
Expand All @@ -108,14 +116,6 @@ void __restore_processor_state(struct saved_context *ctxt)
wrmsrl(MSR_GS_BASE, ctxt->gs_base);
wrmsrl(MSR_KERNEL_GS_BASE, ctxt->gs_kernel_base);

/*
* now restore the descriptor tables to their proper values
* ltr is done i fix_processor_context().
*/
asm volatile ("lgdt %0" :: "m" (ctxt->gdt_limit));
asm volatile ("lidt %0" :: "m" (ctxt->idt_limit));
asm volatile ("lldt %0" :: "m" (ctxt->ldt));

fix_processor_context();

do_fpu_end();
Expand Down
2 changes: 1 addition & 1 deletion include/asm-x86_64/suspend.h
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ arch_prepare_suspend(void)
struct saved_context {
u16 ds, es, fs, gs, ss;
unsigned long gs_base, gs_kernel_base, fs_base;
unsigned long cr0, cr2, cr3, cr4;
unsigned long cr0, cr2, cr3, cr4, cr8;
u16 gdt_pad;
u16 gdt_limit;
unsigned long gdt_base;
Expand Down

0 comments on commit 8d783b3

Please sign in to comment.