Print this page
unix: enable caches in locore
The loader should really be as simple as possible to be as small as
possible.  It should configure the machine so that unix can make certain
assumptions but it should leave more complex initialization to unix.

Split Close
Expand all
Collapse all
          --- old/usr/src/uts/armv6/ml/glocore.s
          +++ new/usr/src/uts/armv6/ml/glocore.s
↓ open down ↓ 34 lines elided ↑ open up ↑
  35   35   * boot us at _start. As we've started the world, we also need to set up a
  36   36   * few things about us, for example our stack pointer. To help us out, it's
  37   37   * useful to remember what the loader set up for us:
  38   38   *
  39   39   * - unaligned access are allowed (A = 0, U = 1)
  40   40   * - virtual memory is enabled
  41   41   *   - we (unix) are mapped right were we want to be
  42   42   *   - a UART has been enabled & any memory mapped registers have been 1:1
  43   43   *     mapped
  44   44   *   - ATAGs have been updated to tell us what the mappings are
  45      - * - I/D L1 caches have been enabled
       45 + * - I/D L1 caches have may be disabled
  46   46   */
  47   47  
  48   48          /*
  49   49           * External globals
  50   50           */
  51   51          .globl  _locore_start
  52   52          .globl  mlsetup
  53   53          .globl  sysp
  54   54          .globl  bootops
  55   55          .globl  bootopsp
↓ open down ↓ 26 lines elided ↑ open up ↑
  82   82          mov     sp, #-1
  83   83          cps     #(CPU_MODE_IRQ)
  84   84          mov     sp, #-1
  85   85          cps     #(CPU_MODE_SVC)
  86   86  
  87   87          /* Enable highvecs (moves the base of the exception vector) */
  88   88          mrc     p15, 0, r3, c1, c0, 0
  89   89          orr     r3, r3, #(1 << 13)
  90   90          mcr     p15, 0, r3, c1, c0, 0
  91   91  
       92 +        /*
       93 +         * Go ahead now and enable the L1 I/D caches.  (Involves
       94 +         * invalidating the caches and the TLB.)
       95 +         */
       96 +        mov     r4, #0
       97 +        mov     r5, #0
       98 +        mcr     p15, 0, r4, c7, c7, 0   /* invalidate caches */
       99 +        mcr     p15, 0, r4, c8, c7, 0   /* invalidate tlb */
      100 +        mcr     p15, 0, r5, c7, c10, 4  /* DSB */
      101 +        mrc     p15, 0, r4, c1, c0, 0
      102 +        orr     r4, #0x04       /* D-cache */
      103 +        orr     r4, #0x1000     /* I-cache */
      104 +        mcr     p15, 0, r4, c1, c0, 0
      105 +
  92  106          /* invoke machine specific setup */
  93  107          bl      _mach_start
  94  108  
  95  109          bl      _fakebop_start
  96  110          SET_SIZE(_start)
  97  111  
  98  112  
  99  113  #if defined(__lint)
 100  114  
 101  115  /* ARGSUSED */
↓ open down ↓ 2 lines elided ↑ open up ↑
 104  118  {}
 105  119  
 106  120  #else   /* __lint */
 107  121  
 108  122          /*
 109  123           * We got here from _kobj_init() via exitto().  We have a few different
 110  124           * tasks that we need to take care of before we hop into mlsetup and
 111  125           * then main. We're never going back so we shouldn't feel compelled to
 112  126           * preserve any registers.
 113  127           *
 114      -         *  o Enable our I/D-caches
 115  128           *  o Save the boot syscalls and bootops for later
 116  129           *  o Set up our stack to be the real stack of t0stack.
 117  130           *  o Save t0 as curthread
 118  131           *  o Set up a struct REGS for mlsetup
 119  132           *  o Make sure that we're 8 byte aligned for the call
 120  133           */
 121  134  
 122  135          ENTRY(_locore_start)
 123  136  
 124  137  
↓ open down ↓ 28 lines elided ↑ open up ↑
 153  166          str     r1, [r2]
 154  167          ldr     r2, =bootopsp
 155  168          ldr     r2, [r2]
 156  169          str     r1, [r2]
 157  170  
 158  171          /*
 159  172           * Set up our curthread pointer
 160  173           */
 161  174          ldr     r0, =t0
 162  175          mcr     p15, 0, r0, c13, c0, 4
 163      -
 164      -        /*
 165      -         * Go ahead now and enable the L1 I/D caches.  
 166      -         */
 167      -        mrc     p15, 0, r0, c1, c0, 0
 168      -        orr     r0, #0x04       /* D-cache */
 169      -        orr     r0, #0x1000     /* I-cache */
 170      -        mcr     p15, 0, r0, c1, c0, 0
 171  176  
 172  177          /*
 173  178           * mlsetup() takes the struct regs as an argument. main doesn't take
 174  179           * any and should never return. Currently, we have an 8-byte aligned
 175  180           * stack.  We want to push a zero frame pointer to terminate any
 176  181           * stack walking, but that would cause us to end up with only a
 177  182           * 4-byte aligned stack.  So, to keep things nice and correct, we
 178  183           * push a zero value twice - it's similar to a typical function
 179  184           * entry:
 180  185           *      push { r9, lr }
↓ open down ↓ 26 lines elided ↑ open up ↑
XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX