diff options
Diffstat (limited to 'src/arch/x86')
-rw-r--r-- | src/arch/x86/Makefile.inc | 5 | ||||
-rw-r--r-- | src/arch/x86/assembly_entry.S | 10 | ||||
-rw-r--r-- | src/arch/x86/car.ld | 44 | ||||
-rw-r--r-- | src/arch/x86/include/arch/header.ld | 3 | ||||
-rw-r--r-- | src/arch/x86/memlayout.ld | 14 |
5 files changed, 51 insertions, 25 deletions
diff --git a/src/arch/x86/Makefile.inc b/src/arch/x86/Makefile.inc index e0e8a3b7b9..accb022a81 100644 --- a/src/arch/x86/Makefile.inc +++ b/src/arch/x86/Makefile.inc @@ -64,11 +64,6 @@ $(1)-S-ccopts += -I. $$(objcbfs)/$(1).debug: $$$$($(1)-libs) $$$$($(1)-objs) @printf " LINK $$(subst $$(obj)/,,$$(@))\n" $$(LD_$(1)) $$(LDFLAGS_$(1)) -o $$@ -L$$(obj) $$(COMPILER_RT_FLAGS_$(1)) --whole-archive --start-group $$(filter-out %.ld,$$($(1)-objs)) $$($(1)-libs) --no-whole-archive $$(COMPILER_RT_$(1)) --end-group -T $(call src-to-obj,$(1),$(CONFIG_MEMLAYOUT_LD_FILE)) --oformat $(2) - -LANG=C LC_ALL= $$(OBJCOPY_$(1)) --only-section .illegal_globals $$(@) $$(objcbfs)/$(1)_null.offenders >/dev/null 2>&1 - if [ -z "$$$$($$(NM_$(1)) $$(objcbfs)/$(1)_null.offenders 2>&1 | grep 'no symbols')" ];then \ - echo "Forbidden global variables in $(1):"; \ - $$(NM_$(1)) $$(objcbfs)/$(1)_null.offenders; false; \ - fi endef ############################################################################### diff --git a/src/arch/x86/assembly_entry.S b/src/arch/x86/assembly_entry.S index 869acc84e2..9a9a0465dc 100644 --- a/src/arch/x86/assembly_entry.S +++ b/src/arch/x86/assembly_entry.S @@ -33,8 +33,8 @@ _start: /* reset stack pointer to CAR/EARLYRAM stack */ mov $_STACK_TOP, %esp +#if ENV_SEPARATE_DATA_AND_BSS /* clear .bss section as it is not shared */ -#if ENV_SEPARATE_BSS cld xor %eax, %eax movl $(_ebss), %ecx @@ -42,6 +42,14 @@ _start: sub %edi, %ecx shrl $2, %ecx rep stosl + + /* Copy .data section content to Cache-As-Ram */ + movl $(_edata), %ecx + movl $(_data), %edi + sub %edi, %ecx + shrl $2, %ecx + movl $(_data_load),%esi + rep movsl #endif #if ((ENV_SEPARATE_VERSTAGE && CONFIG(VERSTAGE_DEBUG_SPINLOOP)) \ diff --git a/src/arch/x86/car.ld b/src/arch/x86/car.ld index ab6c3b0df8..a1a782ffe0 100644 --- a/src/arch/x86/car.ld +++ b/src/arch/x86/car.ld @@ -59,7 +59,7 @@ * cbmem console. This is useful for clearing this area on a per-stage * basis when more than one stage uses cache-as-ram. */ -#if ENV_SEPARATE_BSS +#if ENV_SEPARATE_DATA_AND_BSS . = ALIGN(ARCH_POINTER_ALIGN_SIZE); _bss = .; /* Allow global uninitialized variables for stages without CAR teardown. */ @@ -89,11 +89,32 @@ _shadow_size = (_ebss - _car_region_start) >> 3; REGION(asan_shadow, ., _shadow_size, ARCH_POINTER_ALIGN_SIZE) #endif - _car_unallocated_start = .; - _car_region_end = . + CONFIG_DCACHE_RAM_SIZE - (. - _car_region_start) - - CONFIG_FSP_T_RESERVED_SIZE; } +#if ENV_SEPARATE_DATA_AND_BSS +/* This symbol defines the load address of the Cache-As-RAM .data + * section. It should be right at the end of the .text section (_etext) + * and ARCH_POINTER_ALIGN_SIZE aligned. */ +_data_load = _etext; + +_bogus = ASSERT(_etext == ALIGN(_etext, ARCH_POINTER_ALIGN_SIZE), "Cache-As-RAM load address is improperly defined."); + +.data ALIGN(ARCH_POINTER_ALIGN_SIZE) : AT (_data_load) { + _data = .; + *(.data); + *(.data.*); + *(.sdata); + *(.sdata.*); + . = ALIGN(ARCH_POINTER_ALIGN_SIZE); + _edata = .; + RECORD_SIZE(data) +} : data_segment +#endif + +_car_unallocated_start = .; +_car_region_end = . + CONFIG_DCACHE_RAM_SIZE - (. - _car_region_start) + - CONFIG_FSP_T_RESERVED_SIZE; + . = _car_region_start; .car.fspm_rc_heap . (NOLOAD) : { . += CONFIG_FSP_M_RC_HEAP_SIZE; @@ -124,18 +145,11 @@ _rom_mtrr_mask = ~(CACHE_ROM_SIZE - 1); _rom_mtrr_base = _rom_mtrr_mask; #endif -/* Global variables are not allowed in romstage - * This section is checked during stage creation to ensure - * that there are no global variables present - */ - -. = 0xffffff00; -.illegal_globals . : { - *(.data) - *(.data.*) -} - +#if ENV_SEPARATE_DATA_AND_BSS +_bogus = ASSERT((CONFIG_DCACHE_RAM_SIZE == 0) || (SIZEOF(.car.data) + SIZEOF(.data) <= CONFIG_DCACHE_RAM_SIZE), "Cache as RAM area is too full"); +#else _bogus = ASSERT((CONFIG_DCACHE_RAM_SIZE == 0) || (SIZEOF(.car.data) <= CONFIG_DCACHE_RAM_SIZE), "Cache as RAM area is too full"); +#endif #if CONFIG(PAGING_IN_CACHE_AS_RAM) _bogus2 = ASSERT(_pagetables == ALIGN(_pagetables, 4096), "_pagetables aren't 4KiB aligned"); #endif diff --git a/src/arch/x86/include/arch/header.ld b/src/arch/x86/include/arch/header.ld index 5b380faad5..2ee021226c 100644 --- a/src/arch/x86/include/arch/header.ld +++ b/src/arch/x86/include/arch/header.ld @@ -3,6 +3,9 @@ PHDRS { to_load PT_LOAD; +#if ENV_SEPARATE_DATA_AND_BSS + data_segment PT_LOAD; +#endif } ENTRY(_start) diff --git a/src/arch/x86/memlayout.ld b/src/arch/x86/memlayout.ld index 549c2f9041..f448bf89de 100644 --- a/src/arch/x86/memlayout.ld +++ b/src/arch/x86/memlayout.ld @@ -3,6 +3,16 @@ #include <memlayout.h> #include <arch/header.ld> +/* + * The bootblock linker script should be included before the Cache-As-RAM linker + * script. Indeed, if it is included after and Cache-As-RAM .data section + * support is enabled, the definition order of the sections makes the linker + * create an image with an almost 4 GB hole. + */ +#if ENV_BOOTBLOCK +INCLUDE "bootblock/arch/x86/bootblock.ld" +#endif /* ENV_BOOTBLOCK */ + SECTIONS { /* @@ -36,7 +46,3 @@ SECTIONS POSTCAR(32M, 1M) #endif } - -#if ENV_BOOTBLOCK - INCLUDE "bootblock/arch/x86/bootblock.ld" -#endif /* ENV_BOOTBLOCK */ |