tree: drop last paragraph of GPL copyright header
[coreboot.git] / src / cpu / intel / car / cache_as_ram.inc
blobe28d033837706982c6ebb6ef4d663479dee48076
1 /*
2  * This file is part of the coreboot project.
3  *
4  * Copyright (C) 2000, 2007 Ronald G. Minnich <rminnich@gmail.com>
5  * Copyright (C) 2005 Eswar Nallusamy, LANL
6  * Copyright (C) 2005 Tyan (written by Yinghai Lu for Tyan)
7  * Copyright (C) 2007-2010 coresystems GmbH
8  * Copyright (C) 2007 Carl-Daniel Hailfinger
9  *
10  * This program is free software; you can redistribute it and/or modify
11  * it under the terms of the GNU General Public License as published by
12  * the Free Software Foundation; version 2 of the License.
13  *
14  * This program is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17  * GNU General Public License for more details.
18  */
20 #include <cpu/x86/mtrr.h>
21 #include <cpu/x86/cache.h>
22 #include <cpu/x86/lapic_def.h>
23 #include <cpu/x86/post_code.h>
25 #define CacheSize               CONFIG_DCACHE_RAM_SIZE
26 #define CacheBase               (0xd0000 - CacheSize)
28         /* Save the BIST result. */
29         movl    %eax, %ebp
31 CacheAsRam:
32         /* Check whether the processor has HT capability. */
33         movl    $01, %eax
34         cpuid
35         btl     $28, %edx
36         jnc     NotHtProcessor
37         bswapl  %ebx
38         cmpb    $01, %bh
39         jbe     NotHtProcessor
41         /*
42          * It is a HT processor. Send SIPI to the other logical processor
43          * within this processor so that the CAR related common system
44          * registers are programmed accordingly.
45          */
47         /*
48          * Use some register that is common to both logical processors
49          * as semaphore. Refer Appendix B, Vol.3.
50          */
51         xorl    %eax, %eax
52         xorl    %edx, %edx
53         movl    $MTRR_FIX_64K_00000, %ecx
54         wrmsr
56         /*
57          * Figure out the logical AP's APIC ID; the following logic will
58          * work only for processors with 2 threads.
59          * Refer to Vol 3. Table 7-1 for details about this logic.
60          */
61         movl    $0xFEE00020, %esi
62         movl    (%esi), %ebx
63         andl    $0xFF000000, %ebx
64         bswapl  %ebx
65         btl     $0, %ebx
66         jnc     LogicalAP0
67         andb    $0xFE, %bl
68         jmp     Send_SIPI
69 LogicalAP0:
70         orb     $0x01, %bl
71 Send_SIPI:
72         bswapl  %ebx    /* EBX - logical AP's APIC ID. */
74         /*
75          * Fill up the IPI command registers in the Local APIC mapped to
76          * default address and issue SIPI to the other logical processor
77          * within this processor die.
78          */
79 Retry_SIPI:
80         movl    %ebx, %eax
81         movl    $0xFEE00310, %esi
82         movl    %eax, (%esi)
84         /* SIPI vector - F900:0000 */
85         movl    $0x000006F9, %eax
86         movl    $0xFEE00300, %esi
87         movl    %eax, (%esi)
89         movl    $0x30, %ecx
90 SIPI_Delay:
91         pause
92         decl    %ecx
93         jnz     SIPI_Delay
95         movl    (%esi), %eax
96         andl    $0x00001000, %eax
97         jnz     Retry_SIPI
99         /* Wait for the Logical AP to complete initialization. */
100 LogicalAP_SIPINotdone:
101         movl    $MTRR_FIX_64K_00000, %ecx
102         rdmsr
103         orl     %eax, %eax
104         jz      LogicalAP_SIPINotdone
106 NotHtProcessor:
107         /* Set the default memory type and enable fixed and variable MTRRs. */
108         movl    $MTRR_DEF_TYPE_MSR, %ecx
109         xorl    %edx, %edx
110         movl    $(MTRR_DEF_TYPE_EN | MTRR_DEF_TYPE_FIX_EN), %eax
111         wrmsr
113         /* Clear all MTRRs. */
114         xorl    %edx, %edx
115         movl    $all_mtrr_msrs, %esi
117 clear_fixed_var_mtrr:
118         lodsl   (%esi), %eax
119         testl   %eax, %eax
120         jz      clear_fixed_var_mtrr_out
122         movl    %eax, %ecx
123         xorl    %eax, %eax
124         wrmsr
126         jmp     clear_fixed_var_mtrr
128 all_mtrr_msrs:
129         /* fixed MTRR MSRs */
130         .long   MTRR_FIX_64K_00000
131         .long   MTRR_FIX_16K_80000
132         .long   MTRR_FIX_16K_A0000
133         .long   MTRR_FIX_4K_C0000
134         .long   MTRR_FIX_4K_C8000
135         .long   MTRR_FIX_4K_D0000
136         .long   MTRR_FIX_4K_D8000
137         .long   MTRR_FIX_4K_E0000
138         .long   MTRR_FIX_4K_E8000
139         .long   MTRR_FIX_4K_F0000
140         .long   MTRR_FIX_4K_F8000
142         /* var MTRR MSRs */
143         .long   MTRR_PHYS_BASE(0)
144         .long   MTRR_PHYS_MASK(0)
145         .long   MTRR_PHYS_BASE(1)
146         .long   MTRR_PHYS_MASK(1)
147         .long   MTRR_PHYS_BASE(2)
148         .long   MTRR_PHYS_MASK(2)
149         .long   MTRR_PHYS_BASE(3)
150         .long   MTRR_PHYS_MASK(3)
151         .long   MTRR_PHYS_BASE(4)
152         .long   MTRR_PHYS_MASK(4)
153         .long   MTRR_PHYS_BASE(5)
154         .long   MTRR_PHYS_MASK(5)
155         .long   MTRR_PHYS_BASE(6)
156         .long   MTRR_PHYS_MASK(6)
157         .long   MTRR_PHYS_BASE(7)
158         .long   MTRR_PHYS_MASK(7)
160         .long   0x000 /* NULL, end of table */
162 clear_fixed_var_mtrr_out:
165  * 0x06 is the WB IO type for a given 4k segment.
166  * segs is the number of 4k segments in the area of the particular
167  *      register we want to use for CAR.
168  * reg  is the register where the IO type should be stored.
169  */
170 .macro extractmask segs, reg
171 .if \segs <= 0
172         /*
173          * The xorl here is superfluous because at the point of first execution
174          * of this macro, %eax and %edx are cleared. Later invocations of this
175          * macro will have a monotonically increasing segs parameter.
176          */
177         xorl \reg, \reg
178 .elseif \segs == 1
179         movl    $0x06000000, \reg /* WB IO type */
180 .elseif \segs == 2
181         movl    $0x06060000, \reg /* WB IO type */
182 .elseif \segs == 3
183         movl    $0x06060600, \reg /* WB IO type */
184 .elseif \segs >= 4
185         movl    $0x06060606, \reg /* WB IO type */
186 .endif
187 .endm
190  * carsize is the cache size in bytes we want to use for CAR.
191  * windowoffset is the 32k-aligned window into CAR size.
192  */
193 .macro simplemask carsize, windowoffset
194         .set gas_bug_workaround,(((\carsize - \windowoffset) >> 12) - 4)
195         extractmask gas_bug_workaround, %eax
196         .set gas_bug_workaround,(((\carsize - \windowoffset) >> 12))
197         extractmask gas_bug_workaround, %edx
198         /*
199          * Without the gas bug workaround, the entire macro would consist
200          * only of the two lines below:
201          *   extractmask (((\carsize - \windowoffset) >> 12) - 4), %eax
202          *   extractmask (((\carsize - \windowoffset) >> 12)), %edx
203          */
204 .endm
206 #if CacheSize > 0x10000
207 #error Invalid CAR size, must be at most 64k.
208 #endif
209 #if CacheSize < 0x1000
210 #error Invalid CAR size, must be at least 4k. This is a processor limitation.
211 #endif
212 #if (CacheSize & (0x1000 - 1))
213 #error Invalid CAR size, is not a multiple of 4k. This is a processor limitation.
214 #endif
216 #if CacheSize > 0x8000
217         /* Enable caching for 32K-64K using fixed MTRR. */
218         movl    $MTRR_FIX_4K_C0000, %ecx
219         simplemask CacheSize, 0x8000
220         wrmsr
221 #endif
223         /* Enable caching for 0-32K using fixed MTRR. */
224         movl    $MTRR_FIX_4K_C8000, %ecx
225         simplemask CacheSize, 0
226         wrmsr
228 #if CONFIG_XIP_ROM_SIZE
230         /*
231          * Enable write base caching so we can do execute in place (XIP)
232          * on the flash ROM.
233          */
234         movl    $MTRR_PHYS_BASE(1), %ecx
235         xorl    %edx, %edx
236         /*
237          * IMPORTANT: The following calculation _must_ be done at runtime. See
238          * http://www.coreboot.org/pipermail/coreboot/2010-October/060855.html
239          */
240         movl    $copy_and_run, %eax
241         andl    $(~(CONFIG_XIP_ROM_SIZE - 1)), %eax
242         orl     $MTRR_TYPE_WRBACK, %eax
243         wrmsr
245         movl    $MTRR_PHYS_MASK(1), %ecx
246         movl    $0x0000000f, %edx
247         movl    $(~(CONFIG_XIP_ROM_SIZE - 1) | MTRR_PHYS_MASK_VALID), %eax
248         wrmsr
249 #endif /* CONFIG_XIP_ROM_SIZE */
251         /* Enable cache. */
252         movl    %cr0, %eax
253         andl    $(~(CR0_CacheDisable | CR0_NoWriteThrough)), %eax
254         movl    %eax, %cr0
256         /* Read the range with lodsl. */
257         movl    $CacheBase, %esi
258         cld
259         movl    $(CacheSize >> 2), %ecx
260         rep     lodsl
262         /* Clear the range. */
263         movl    $CacheBase, %edi
264         movl    $(CacheSize >> 2), %ecx
265         xorl    %eax, %eax
266         rep     stosl
268 #if 0
269         /* Check the cache as ram. */
270         movl    $CacheBase, %esi
271         movl    $(CacheSize >> 2), %ecx
272 .xin1:
273         movl    %esi, %eax
274         movl    %eax, (%esi)
275         decl    %ecx
276         je      .xout1
277         add     $4, %esi
278         jmp     .xin1
279 .xout1:
281         movl    $CacheBase, %esi
282         // movl $(CacheSize >> 2), %ecx
283         movl    $4, %ecx
284 .xin1x:
285         movl    %esi, %eax
287         movl    $0x4000, %edx
288         movb    %ah, %al
289 .testx1:
290         outb    %al, $0x80
291         decl    %edx
292         jnz     .testx1
294         movl    (%esi), %eax
295         cmpb    0xff, %al
296         je      .xin2   /* Don't show. */
298         movl    $0x4000, %edx
299 .testx2:
300         outb    %al, $0x80
301         decl    %edx
302         jnz     .testx2
304 .xin2:
305         decl    %ecx
306         je      .xout1x
307         add     $4, %esi
308         jmp     .xin1x
309 .xout1x:
310 #endif
312         movl    $(CacheBase + CacheSize - 4), %eax
313         movl    %eax, %esp
314 lout:
315         /* Restore the BIST result. */
316         movl    %ebp, %eax
318         /* We need to set EBP? No need. */
319         movl    %esp, %ebp
320         pushl   %eax  /* BIST */
321         call    main
323         /* We don't need CAR from now on. */
325         /* Disable cache. */
326         movl    %cr0, %eax
327         orl     $CR0_CacheDisable, %eax
328         movl    %eax, %cr0
330         /* Clear sth. */
331         movl    $MTRR_FIX_4K_C8000, %ecx
332         xorl    %edx, %edx
333         xorl    %eax, %eax
334         wrmsr
336 #if CONFIG_DCACHE_RAM_SIZE > 0x8000
337         movl    $MTRR_FIX_4K_C0000, %ecx
338         wrmsr
339 #endif
341         /*
342          * Set the default memory type and disable fixed
343          * and enable variable MTRRs.
344          */
345         movl    $MTRR_DEF_TYPE_MSR, %ecx
346         xorl    %edx, %edx
347         movl    $MTRR_DEF_TYPE_EN, %eax /* Enable variable and disable fixed MTRRs. */
348         wrmsr
350         /* Enable cache. */
351         movl    %cr0, %eax
352         andl    $(~(CR0_CacheDisable | CR0_NoWriteThrough)), %eax
353         movl    %eax, %cr0
355 __main:
356         post_code(POST_PREPARE_RAMSTAGE)
357         cld                     /* Clear direction flag. */
359         movl    $CONFIG_RAMTOP, %esp
360         movl    %esp, %ebp
361         call    copy_and_run
363 .Lhlt:
364         post_code(POST_DEAD_CODE)
365         hlt
366         jmp     .Lhlt