coreboot-kgpe-d16/src/arch/x86/wakeup.S
Patrick Georgi a73b93157f tree: drop last paragraph of GPL copyright header
It encourages users from writing to the FSF without giving an address.
Linux also prefers to drop that and their checkpatch.pl (that we
imported) looks out for that.

This is the result of util/scripts/no-fsf-addresses.sh with no further
editing.

Change-Id: Ie96faea295fe001911d77dbc51e9a6789558fbd6
Signed-off-by: Patrick Georgi <pgeorgi@chromium.org>
Reviewed-on: http://review.coreboot.org/11888
Tested-by: build bot (Jenkins)
Reviewed-by: Alexandru Gagniuc <mr.nuke.me@gmail.com>
Reviewed-by: Ronald G. Minnich <rminnich@gmail.com>
2015-10-31 21:37:39 +01:00

123 lines
2.5 KiB
ArmAsm

/*
* This file is part of the coreboot project.
*
* Copyright (C) 2009 Rudolf Marek <r.marek@assembler.cz>
* Copyright (C) 2009 coresystems GmbH
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; version 2 of the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#define WAKEUP_BASE 0x600
#define RELOCATED(x) (x - __wakeup + WAKEUP_BASE)
/* CR0 bits */
#define PE (1 << 0)
#ifdef __x86_64__
.code64
#else
.code32
#endif
.globl __wakeup
__wakeup:
#ifdef __x86_64__
.intel_syntax noprefix
xor rax,rax
mov ax, ss
push rax
mov rax, rsp
add rax, 8
push rax
pushfq
push 0x10
lea rax,[rip+3]
push rax
iretq
.code32
/* disable paging */
mov eax, cr0
btc eax, 31
mov cr0, eax
/* disable long mode */
mov ecx, 0xC0000080
rdmsr
btc eax, 8
wrmsr
.att_syntax prefix
#endif
/* First prepare the jmp to the resume vector */
mov 0x4(%esp), %eax /* vector */
/* last 4 bits of linear addr are taken as offset */
andw $0x0f, %ax
movw %ax, (__wakeup_offset)
mov 0x4(%esp), %eax
/* the rest is taken as segment */
shr $4, %eax
movw %ax, (__wakeup_segment)
/* Then overwrite coreboot with our backed up memory */
cld
movl 8(%esp), %esi
movl 12(%esp), %edi
movl 16(%esp), %ecx
shrl $2, %ecx
rep movsl
/* Activate the right segment descriptor real mode. */
ljmp $0x28, $RELOCATED(1f)
1:
.code16
/* 16 bit code from here on... */
/* Load the segment registers w/ properly configured
* segment descriptors. They will retain these
* configurations (limits, writability, etc.) once
* protected mode is turned off.
*/
mov $0x30, %ax
mov %ax, %ds
mov %ax, %es
mov %ax, %fs
mov %ax, %gs
mov %ax, %ss
/* Turn off protection */
movl %cr0, %eax
andl $~PE, %eax
movl %eax, %cr0
/* Now really going into real mode */
ljmp $0, $RELOCATED(1f)
1:
movw $0x0, %ax
movw %ax, %ds
movw %ax, %es
movw %ax, %ss
movw %ax, %fs
movw %ax, %gs
/* This is a FAR JMP to the OS waking vector. The C code changed
* the address to be correct.
*/
.byte 0xea
__wakeup_offset = RELOCATED(.)
.word 0x0000
__wakeup_segment = RELOCATED(.)
.word 0x0000
.globl __wakeup_size
__wakeup_size:
.long . - __wakeup