1/* SPDX-License-Identifier: GPL-2.0-only */ 2 3#include <cpu/intel/post_codes.h> 4#include <cpu/x86/mtrr.h> 5#include <cpu/x86/cache.h> 6#include <cpu/x86/post_code.h> 7#include <cpu/x86/64bit/entry64.inc> 8 9.section .init 10.global bootblock_pre_c_entry 11 12#include <cpu/intel/car/cache_as_ram_symbols.inc> 13 14.code32 15_cache_as_ram_setup: 16 17bootblock_pre_c_entry: 18 19cache_as_ram: 20 post_code(POSTCODE_BOOTBLOCK_CAR) 21 22 /* Send INIT IPI to all excluding ourself. */ 23 movl $0x000C4500, %eax 24 movl $0xFEE00300, %esi 25 movl %eax, (%esi) 26 27 /* All CPUs need to be in Wait for SIPI state */ 28wait_for_sipi: 29 movl (%esi), %eax 30 bt $12, %eax 31 jc wait_for_sipi 32 33 post_code(POSTCODE_SOC_CLEAR_FIXED_MTRRS) 34 35 /* Clear/disable fixed MTRRs */ 36 mov $fixed_mtrr_list, %ebx 37 xor %eax, %eax 38 xor %edx, %edx 39 40clear_fixed_mtrr: 41 movzwl (%ebx), %ecx 42 wrmsr 43 add $2, %ebx 44 cmp $fixed_mtrr_list_end, %ebx 45 jl clear_fixed_mtrr 46 47 /* Figure out how many MTRRs we have, and clear them out */ 48 mov $MTRR_CAP_MSR, %ecx 49 rdmsr 50 movzb %al, %ebx /* Number of variable MTRRs */ 51 mov $MTRR_PHYS_BASE(0), %ecx 52 xor %eax, %eax 53 xor %edx, %edx 54 55clear_var_mtrr: 56 wrmsr 57 inc %ecx 58 wrmsr 59 inc %ecx 60 dec %ebx 61 jnz clear_var_mtrr 62 63 post_code(POSTCODE_SOC_SET_DEF_MTRR_TYPE) 64 /* Configure the default memory type to uncacheable. */ 65 movl $MTRR_DEF_TYPE_MSR, %ecx 66 rdmsr 67 andl $(~0x00000cff), %eax 68 wrmsr 69 70 /* Determine CPU_ADDR_BITS and load PHYSMASK high word to %edx. */ 71 movl $0x80000008, %eax 72 cpuid 73 movb %al, %cl 74 sub $32, %cl 75 movl $1, %edx 76 shl %cl, %edx 77 subl $1, %edx 78 79 /* Preload high word of address mask (in %edx) for Variable 80 MTRRs 0 and 1. */ 81addrsize_set_high: 82 xorl %eax, %eax 83 movl $MTRR_PHYS_MASK(0), %ecx 84 wrmsr 85 movl $MTRR_PHYS_MASK(1), %ecx 86 wrmsr 87 88 post_code(POSTCODE_SOC_SET_MTRR_BASE) 89 /* Set Cache-as-RAM base address. */ 90 movl $(MTRR_PHYS_BASE(0)), %ecx 91 movl $_car_mtrr_start, %eax 92 orl $MTRR_TYPE_WRBACK, %eax 93 xorl %edx, %edx 94 wrmsr 95 96 post_code(POSTCODE_SOC_SET_MTRR_MASK) 97 /* Set Cache-as-RAM mask. */ 98 movl $(MTRR_PHYS_MASK(0)), %ecx 99 rdmsr 100 movl car_mtrr_mask, %eax 101 orl $MTRR_PHYS_MASK_VALID, %eax 102 wrmsr 103 104 post_code(POSTCODE_SOC_ENABLE_MTRRS) 105 106 /* Enable MTRR. */ 107 movl $MTRR_DEF_TYPE_MSR, %ecx 108 rdmsr 109 orl $MTRR_DEF_TYPE_EN, %eax 110 wrmsr 111 112 /* Enable L2 cache. */ 113 movl $0x11e, %ecx 114 rdmsr 115 orl $(1 << 8), %eax 116 wrmsr 117 118 /* Enable cache (CR0.CD = 0, CR0.NW = 0). */ 119 movl %cr0, %eax 120 andl $(~(CR0_CacheDisable | CR0_NoWriteThrough)), %eax 121 invd 122 movl %eax, %cr0 123 124 /* Clear the cache memory region. This will also fill up the cache. */ 125 cld 126 xorl %eax, %eax 127 movl car_mtrr_start, %edi 128 movl car_mtrr_size, %ecx 129 shr $2, %ecx 130 rep stosl 131 132 post_code(POSTCODE_SOC_DISABLE_CACHE) 133 /* Enable Cache-as-RAM mode by disabling cache. */ 134 movl %cr0, %eax 135 orl $CR0_CacheDisable, %eax 136 movl %eax, %cr0 137 138 /* Enable cache for our code in Flash because we do XIP here */ 139 movl $MTRR_PHYS_BASE(1), %ecx 140 xorl %edx, %edx 141 movl $_program, %eax 142 andl xip_mtrr_mask, %eax 143 orl $MTRR_TYPE_WRPROT, %eax 144 wrmsr 145 movl $MTRR_PHYS_MASK(1), %ecx 146 rdmsr 147 movl xip_mtrr_mask, %eax 148 orl $MTRR_PHYS_MASK_VALID, %eax 149 wrmsr 150 151 post_code(POSTCODE_SOC_ENABLE_CACHE) 152 /* Enable cache. */ 153 movl %cr0, %eax 154 andl $(~(CR0_CacheDisable | CR0_NoWriteThrough)), %eax 155 movl %eax, %cr0 156 157 /* Setup the stack. */ 158 mov $_ecar_stack, %esp 159 160 /* Need to align stack to 16 bytes at call instruction. Account for 161 the pushes below. */ 162 andl $0xfffffff0, %esp 163 subl $4, %esp 164 165#if ENV_X86_64 166 setup_longmode $PM4LE 167 168 movd %mm2, %rdi 169 shlq $32, %rdi 170 movd %mm1, %rsi 171 or %rsi, %rdi 172 movd %mm0, %rsi 173#else 174 /* push TSC and BIST to stack */ 175 movd %mm0, %eax 176 pushl %eax /* BIST */ 177 movd %mm2, %eax 178 pushl %eax /* tsc[63:32] */ 179 movd %mm1, %eax 180 pushl %eax /* tsc[31:0] */ 181#endif 182 183 /* Copy .data section content to Cache-As-Ram */ 184#include <cpu/x86/copy_data_section.inc> 185 186before_c_entry: 187 post_code(POSTCODE_BOOTBLOCK_BEFORE_C_ENTRY) 188 call bootblock_c_entry_bist 189 190 /* Should never see this postcode */ 191 post_code(POSTCODE_DEAD_CODE) 192 193.Lhlt: 194 hlt 195 jmp .Lhlt 196 197fixed_mtrr_list: 198 .word MTRR_FIX_64K_00000 199 .word MTRR_FIX_16K_80000 200 .word MTRR_FIX_16K_A0000 201 .word MTRR_FIX_4K_C0000 202 .word MTRR_FIX_4K_C8000 203 .word MTRR_FIX_4K_D0000 204 .word MTRR_FIX_4K_D8000 205 .word MTRR_FIX_4K_E0000 206 .word MTRR_FIX_4K_E8000 207 .word MTRR_FIX_4K_F0000 208 .word MTRR_FIX_4K_F8000 209fixed_mtrr_list_end: 210 211_cache_as_ram_setup_end: 212