Changeset 35f3b8c in mainline


Ignore:
Timestamp:
2006-05-18T23:24:40Z (19 years ago)
Author:
Martin Decky <martin@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
c0bc189
Parents:
8424198
Message:

ppc32 work
update framebuffer
get rid of the BAT memory mapping (not finished yet)

Location:
arch/ppc32
Files:
1 deleted
11 edited

Legend:

Unmodified
Added
Removed
  • arch/ppc32/include/asm.h

    r8424198 r35f3b8c  
    141141void cpu_halt(void);
    142142void asm_delay_loop(__u32 t);
     143void invalidate_bat(void);
    143144
    144145extern void userspace_asm(__address uspace_uarg, __address stack, __address entry);
  • arch/ppc32/include/asm/regname.h

    r8424198 r35f3b8c  
    190190#define sprg3   275
    191191#define prv             287
     192#define ibat0u  528
     193#define ibat0l  529
     194#define ibat1u  530
     195#define ibat1l  531
     196#define ibat2u  532
     197#define ibat2l  533
     198#define ibat3u  534
     199#define ibat3l  535
     200#define dbat0u  536
     201#define dbat0l  537
     202#define dbat1u  538
     203#define dbat1l  539
     204#define dbat2u  540
     205#define dbat2l  541
     206#define dbat3u  542
     207#define dbat3l  543
    192208#define hid0    1008
    193209
  • arch/ppc32/include/mm/frame.h

    r8424198 r35f3b8c  
    3636#ifndef __ASM__
    3737
     38#include <arch/types.h>
     39
     40extern __address last_frame;
     41
    3842extern void frame_arch_init(void);
    3943
  • arch/ppc32/include/mm/page.h

    r8424198 r35f3b8c  
    109109                (1 << PAGE_READ_SHIFT) |
    110110                (1 << PAGE_WRITE_SHIFT) |
    111                 (1 << PAGE_EXEC_SHIFT)
     111                (1 << PAGE_EXEC_SHIFT) |
     112                (p->g << PAGE_GLOBAL_SHIFT)
    112113        );
    113114}
     
    118119       
    119120        p->p = !(flags & PAGE_NOT_PRESENT);
     121        p->g = (flags & PAGE_GLOBAL) != 0;
    120122        p->valid = 1;
    121123}
    122124
    123125extern void page_arch_init(void);
     126
     127#define PHT_BITS        16
     128#define PHT_ORDER       4
     129
     130typedef struct {
     131        unsigned v : 1;          /**< Valid */
     132        unsigned vsid : 24;      /**< Virtual Segment ID */
     133        unsigned h : 1;          /**< Primary/secondary hash */
     134        unsigned api : 6;        /**< Abbreviated Page Index */
     135        unsigned rpn : 20;       /**< Real Page Number */
     136        unsigned reserved0 : 3;
     137        unsigned r : 1;          /**< Reference */
     138        unsigned c : 1;          /**< Change */
     139        unsigned wimg : 4;       /**< Access control */
     140        unsigned reserved1 : 1;
     141        unsigned pp : 2;         /**< Page protection */
     142} phte_t;
     143
     144extern void pht_refill(bool data, istate_t *istate);
     145extern void pht_init(void);
    124146
    125147#endif /* __ASM__ */
  • arch/ppc32/include/mm/tlb.h

    r8424198 r35f3b8c  
    3030#define __ppc32_TLB_H__
    3131
    32 #include <arch/exception.h>
    33 #include <typedefs.h>
    34 
    35 #define PHT_BITS        16
    36 #define PHT_ORDER       4
    37 
    38 typedef struct {
    39         unsigned v : 1;          /**< Valid */
    40         unsigned vsid : 24;      /**< Virtual Segment ID */
    41         unsigned h : 1;          /**< Primary/secondary hash */
    42         unsigned api : 6;        /**< Abbreviated Page Index */
    43         unsigned rpn : 20;       /**< Real Page Number */
    44         unsigned reserved0 : 3;
    45         unsigned r : 1;          /**< Reference */
    46         unsigned c : 1;          /**< Change */
    47         unsigned wimg : 4;       /**< Access control */
    48         unsigned reserved1 : 1;
    49         unsigned pp : 2;         /**< Page protection */
    50 } phte_t;
    51 
    52 extern void pht_refill(bool data, istate_t *istate);
    5332
    5433#endif
  • arch/ppc32/include/types.h

    r8424198 r35f3b8c  
    5353        unsigned p : 1;       /**< Present bit. */
    5454        unsigned a : 1;       /**< Accessed bit. */
     55        unsigned g : 1;       /**< Global bit. */
    5556        unsigned valid : 1;   /**< Valid content even if not present. */
    5657        unsigned pfn : 20;    /**< Physical frame number. */
  • arch/ppc32/src/asm.S

    r8424198 r35f3b8c  
    3434.global iret
    3535.global iret_syscall
     36.global invalidate_bat
    3637.global memsetb
    3738.global memcpy
     
    194195        rfi
    195196       
     197invalidate_bat:
     198       
     199        # invalidate block address translation registers
     200       
     201        li r14, 0
     202       
     203        mtspr ibat0u, r14
     204        mtspr ibat0l, r14
     205       
     206        mtspr ibat1u, r14
     207        mtspr ibat1l, r14
     208       
     209        mtspr ibat2u, r14
     210        mtspr ibat2l, r14
     211       
     212        mtspr ibat3u, r14
     213        mtspr ibat3l, r14
     214       
     215        mtspr dbat0u, r14
     216        mtspr dbat0l, r14
     217       
     218        mtspr dbat1u, r14
     219        mtspr dbat1l, r14
     220       
     221        mtspr dbat2u, r14
     222        mtspr dbat2l, r14
     223       
     224        mtspr dbat3u, r14
     225        mtspr dbat3l, r14
     226       
     227        blr
     228       
    196229memsetb:
    197230        rlwimi r5, r5, 8, 16, 23
  • arch/ppc32/src/mm/page.c

    r8424198 r35f3b8c  
    3030#include <genarch/mm/page_pt.h>
    3131#include <arch/mm/frame.h>
     32#include <arch/asm.h>
    3233#include <mm/frame.h>
    3334#include <mm/page.h>
     35#include <mm/as.h>
     36#include <arch.h>
    3437#include <arch/types.h>
     38#include <arch/exception.h>
     39#include <config.h>
     40#include <print.h>
     41#include <symtab.h>
     42
     43static phte_t *phte;
     44
     45
     46/** Try to find PTE for faulting address
     47 *
     48 * Try to find PTE for faulting address.
     49 * The AS->lock must be held on entry to this function.
     50 *
     51 * @param badvaddr Faulting virtual address.
     52 * @param istate Pointer to interrupted state.
     53 * @param pfrc Pointer to variable where as_page_fault() return code will be stored.
     54 * @return         PTE on success, NULL otherwise.
     55 *
     56 */
     57static pte_t *find_mapping_and_check(__address badvaddr, istate_t *istate, int *pfcr)
     58{
     59        /*
     60         * Check if the mapping exists in page tables.
     61         */     
     62        pte_t *pte = page_mapping_find(AS, badvaddr);
     63        if ((pte) && (pte->p)) {
     64                /*
     65                 * Mapping found in page tables.
     66                 * Immediately succeed.
     67                 */
     68                return pte;
     69        } else {
     70                int rc;
     71       
     72                /*
     73                 * Mapping not found in page tables.
     74                 * Resort to higher-level page fault handler.
     75                 */
     76                page_table_unlock(AS, true);
     77                switch (rc = as_page_fault(badvaddr, istate)) {
     78                        case AS_PF_OK:
     79                                /*
     80                                 * The higher-level page fault handler succeeded,
     81                                 * The mapping ought to be in place.
     82                                 */
     83                                page_table_lock(AS, true);
     84                                pte = page_mapping_find(AS, badvaddr);
     85                                ASSERT((pte) && (pte->p));
     86                                return pte;
     87                        case AS_PF_DEFER:
     88                                page_table_lock(AS, true);
     89                                *pfcr = rc;
     90                                return NULL;
     91                        case AS_PF_FAULT:
     92                                page_table_lock(AS, true);
     93                                printf("Page fault.\n");
     94                                *pfcr = rc;
     95                                return NULL;
     96                        default:
     97                                panic("unexpected rc (%d)\n", rc);
     98                }       
     99        }
     100}
     101
     102
     103static void pht_refill_fail(__address badvaddr, istate_t *istate)
     104{
     105        char *symbol = "";
     106        char *sym2 = "";
     107
     108        char *s = get_symtab_entry(istate->pc);
     109        if (s)
     110                symbol = s;
     111        s = get_symtab_entry(istate->lr);
     112        if (s)
     113                sym2 = s;
     114        panic("%p: PHT Refill Exception at %p (%s<-%s)\n", badvaddr, istate->pc, symbol, sym2);
     115}
     116
     117static void pht_insert(const __address vaddr, const pfn_t pfn)
     118{
     119        __u32 page = (vaddr >> 12) & 0xffff;
     120        __u32 api = (vaddr >> 22) & 0x3f;
     121        __u32 vsid;
     122       
     123        asm volatile (
     124                "mfsrin %0, %1\n"
     125                : "=r" (vsid)
     126                : "r" (vaddr)
     127        );
     128       
     129        /* Primary hash (xor) */
     130        __u32 hash = ((vsid ^ page) & 0x3ff) << 3;
     131       
     132        __u32 i;
     133        /* Find unused PTE in PTEG */
     134        for (i = 0; i < 8; i++) {
     135                if (!phte[hash + i].v)
     136                        break;
     137        }
     138       
     139        // TODO: Check access/change bits, secondary hash
     140       
     141        if (i == 8)
     142                i = page % 8;
     143       
     144        phte[hash + i].v = 1;
     145        phte[hash + i].vsid = vsid;
     146        phte[hash + i].h = 0;
     147        phte[hash + i].api = api;
     148        phte[hash + i].rpn = pfn;
     149        phte[hash + i].r = 0;
     150        phte[hash + i].c = 0;
     151        phte[hash + i].pp = 2; // FIXME
     152}
     153
     154
     155/** Process Instruction/Data Storage Interrupt
     156 *
     157 * @param data   True if Data Storage Interrupt.
     158 * @param istate Interrupted register context.
     159 *
     160 */
     161void pht_refill(bool data, istate_t *istate)
     162{
     163        asid_t asid;
     164        __address badvaddr;
     165        pte_t *pte;
     166       
     167        int pfcr;
     168       
     169        if (data) {
     170                asm volatile (
     171                        "mfdar %0\n"
     172                        : "=r" (badvaddr)
     173                );
     174        } else
     175                badvaddr = istate->pc;
     176               
     177        spinlock_lock(&AS->lock);
     178        asid = AS->asid;
     179        spinlock_unlock(&AS->lock);
     180       
     181        page_table_lock(AS, true);
     182       
     183        pte = find_mapping_and_check(badvaddr, istate, &pfcr);
     184        if (!pte) {
     185                switch (pfcr) {
     186                case AS_PF_FAULT:
     187                        goto fail;
     188                        break;
     189                case AS_PF_DEFER:
     190                        /*
     191                         * The page fault came during copy_from_uspace()
     192                         * or copy_to_uspace().
     193                         */
     194                        page_table_unlock(AS, true);
     195                        return;
     196                default:
     197                        panic("Unexpected pfrc (%d)\n", pfcr);
     198                        break;
     199                }
     200        }
     201       
     202        pte->a = 1; /* Record access to PTE */
     203        pht_insert(badvaddr, pte->pfn);
     204       
     205        page_table_unlock(AS, true);
     206        return;
     207       
     208fail:
     209        page_table_unlock(AS, true);
     210        pht_refill_fail(badvaddr, istate);
     211}
     212
     213
     214void pht_init(void)
     215{
     216        memsetb((__address) phte, 1 << PHT_BITS, 0);
     217       
     218        /* Insert global kernel mapping */
     219       
     220        __address cur;
     221        for (cur = 0; cur < last_frame; cur += FRAME_SIZE) {
     222                pte_t *pte = page_mapping_find(AS_KERNEL, PA2KA(cur));
     223                if ((pte) && (pte->p) && (pte->g))
     224                        pht_insert(PA2KA(cur), pte->pfn);
     225        }
     226}
     227
    35228
    36229void page_arch_init(void)
    37230{
    38         page_mapping_operations = &pt_mapping_operations;
    39 }
     231        if (config.cpu_active == 1) {
     232                page_mapping_operations = &pt_mapping_operations;
     233               
     234                /*
     235                 * PA2KA(identity) mapping for all frames until last_frame.
     236                 */
     237                __address cur;
     238                int flags;
     239               
     240                for (cur = 0; cur < last_frame; cur += FRAME_SIZE) {
     241                        flags = PAGE_CACHEABLE;
     242                        if ((PA2KA(cur) >= config.base) && (PA2KA(cur) < config.base + config.kernel_size))
     243                                flags |= PAGE_GLOBAL;
     244                        page_mapping_insert(AS_KERNEL, PA2KA(cur), cur, flags);
     245                }
     246               
     247                /* Allocate page hash table */
     248                phte_t *physical_phte = (phte_t *) PFN2ADDR(frame_alloc(PHT_ORDER, FRAME_KA | FRAME_PANIC));
     249                phte = (phte_t *) PA2KA((__address) physical_phte);
     250               
     251                ASSERT((__address) physical_phte % (1 << PHT_BITS) == 0);
     252                pht_init();
     253               
     254                asm volatile (
     255                        "mtsdr1 %0\n"
     256                        :
     257                        : "r" ((__address) physical_phte)
     258                );
     259               
     260                /* Invalidate block address translation registers,
     261                   thus remove the temporary mapping */
     262//              invalidate_bat();
     263        }
     264}
  • arch/ppc32/src/mm/tlb.c

    r8424198 r35f3b8c  
    2727 */
    2828
    29 #include <arch/mm/tlb.h>
    30 #include <arch/types.h>
    3129#include <mm/tlb.h>
    32 #include <mm/frame.h>
    33 #include <mm/page.h>
    34 #include <mm/as.h>
    35 #include <arch.h>
    36 #include <print.h>
    37 #include <symtab.h>
    38 
    39 
    40 static phte_t *phte;
    4130
    4231
     
    4837void tlb_arch_init(void)
    4938{
    50         phte_t *physical_phte = (phte_t *) PFN2ADDR(frame_alloc(PHT_ORDER, FRAME_KA | FRAME_PANIC));
    51         phte =(phte_t *) PA2KA((__address) physical_phte);
    52        
    53         ASSERT((__address) physical_phte % (1 << PHT_BITS) == 0);
    54        
    55         memsetb((__address) phte, 1 << PHT_BITS, 0);
    56        
    5739        asm volatile (
    58                 "mtsdr1 %0\n"
    59                 :
    60                 : "r" ((__address) physical_phte)
     40                "tlbia\n"
    6141        );
    62 }
    63 
    64 
    65 /** Try to find PTE for faulting address
    66  *
    67  * Try to find PTE for faulting address.
    68  * The AS->lock must be held on entry to this function.
    69  *
    70  * @param badvaddr Faulting virtual address.
    71  * @param istate Pointer to interrupted state.
    72  * @param pfrc Pointer to variable where as_page_fault() return code will be stored.
    73  * @return         PTE on success, NULL otherwise.
    74  *
    75  */
    76 static pte_t *find_mapping_and_check(__address badvaddr, istate_t *istate, int *pfcr)
    77 {
    78         /*
    79          * Check if the mapping exists in page tables.
    80          */     
    81         pte_t *pte = page_mapping_find(AS, badvaddr);
    82         if ((pte) && (pte->p)) {
    83                 /*
    84                  * Mapping found in page tables.
    85                  * Immediately succeed.
    86                  */
    87                 return pte;
    88         } else {
    89                 int rc;
    90        
    91                 /*
    92                  * Mapping not found in page tables.
    93                  * Resort to higher-level page fault handler.
    94                  */
    95                 page_table_unlock(AS, true);
    96                 switch (rc = as_page_fault(badvaddr, istate)) {
    97                 case AS_PF_OK:
    98                         /*
    99                          * The higher-level page fault handler succeeded,
    100                          * The mapping ought to be in place.
    101                          */
    102                         page_table_lock(AS, true);
    103                         pte = page_mapping_find(AS, badvaddr);
    104                         ASSERT((pte) && (pte->p));
    105                         return pte;
    106                         break;
    107                 case AS_PF_DEFER:
    108                         page_table_lock(AS, true);
    109                         *pfcr = rc;
    110                         return NULL;
    111                         break;
    112                 case AS_PF_FAULT:
    113                         page_table_lock(AS, true);
    114                         printf("Page fault.\n");
    115                         *pfcr = rc;
    116                         return NULL;
    117                         break;
    118                 default:
    119                         panic("unexpected rc (%d)\n", rc);
    120                         break;
    121                 }       
    122         }
    123 }
    124 
    125 
    126 static void pht_refill_fail(__address badvaddr, istate_t *istate)
    127 {
    128         char *symbol = "";
    129         char *sym2 = "";
    130 
    131         char *s = get_symtab_entry(istate->pc);
    132         if (s)
    133                 symbol = s;
    134         s = get_symtab_entry(istate->lr);
    135         if (s)
    136                 sym2 = s;
    137         panic("%p: PHT Refill Exception at %p (%s<-%s)\n", badvaddr, istate->pc, symbol, sym2);
    138 }
    139 
    140 
    141 /** Process Instruction/Data Storage Interrupt
    142  *
    143  * @param data   True if Data Storage Interrupt.
    144  * @param istate Interrupted register context.
    145  *
    146  */
    147 void pht_refill(bool data, istate_t *istate)
    148 {
    149         asid_t asid;
    150         __address badvaddr;
    151         pte_t *pte;
    152         __u32 page;
    153         __u32 api;
    154         __u32 vsid;
    155         __u32 hash;
    156         __u32 i;
    157         int pfcr;
    158        
    159         if (data) {
    160                 asm volatile (
    161                         "mfdar %0\n"
    162                         : "=r" (badvaddr)
    163                 );
    164         } else
    165                 badvaddr = istate->pc;
    166                
    167         spinlock_lock(&AS->lock);
    168         asid = AS->asid;
    169         spinlock_unlock(&AS->lock);
    170        
    171         page_table_lock(AS, true);
    172        
    173         pte = find_mapping_and_check(badvaddr, istate, &pfcr);
    174         if (!pte) {
    175                 switch (pfcr) {
    176                 case AS_PF_FAULT:
    177                         goto fail;
    178                         break;
    179                 case AS_PF_DEFER:
    180                         /*
    181                          * The page fault came during copy_from_uspace()
    182                          * or copy_to_uspace().
    183                          */
    184                         page_table_unlock(AS, true);
    185                         return;
    186                 default:
    187                         panic("Unexpected pfrc (%d)\n", pfcr);
    188                         break;
    189                 }
    190         }
    191 
    192         /* Record access to PTE */
    193         pte->a = 1;
    194        
    195         page = (badvaddr >> 12) & 0xffff;
    196         api = (badvaddr >> 22) & 0x3f;
    197         asm volatile (
    198                 "mfsrin %0, %1\n"
    199                 : "=r" (vsid)
    200                 : "r" (badvaddr)
    201         );
    202        
    203         /* Primary hash (xor) */
    204         hash = ((vsid ^ page) & 0x3ff) << 3;
    205        
    206         /* Find invalid PTE in PTEG */
    207         for (i = 0; i < 8; i++) {
    208                 if (!phte[hash + i].v)
    209                         break;
    210         }
    211        
    212         // TODO: Check access/change bits, secondary hash
    213        
    214         if (i == 8)
    215                 i = page % 8;
    216        
    217         phte[hash + i].v = 1;
    218         phte[hash + i].vsid = vsid;
    219         phte[hash + i].h = 0;
    220         phte[hash + i].api = api;
    221         phte[hash + i].rpn = pte->pfn;
    222         phte[hash + i].r = 0;
    223         phte[hash + i].c = 0;
    224         phte[hash + i].pp = 2; // FIXME
    225        
    226         page_table_unlock(AS, true);
    227         return;
    228        
    229 fail:
    230         page_table_unlock(AS, true);
    231         pht_refill_fail(badvaddr, istate);
    23242}
    23343
     
    23545void tlb_invalidate_all(void)
    23646{
    237         ipl_t ipl;
    238 
    239         ipl = interrupts_disable();
    240         memsetb((__address) phte, 1 << PHT_BITS, 0);
    241         interrupts_restore(ipl);
    24247}
    24348
  • arch/ppc32/src/ppc32.c

    r8424198 r35f3b8c  
    2929#include <arch.h>
    3030#include <arch/boot/boot.h>
    31 #include <arch/console.h>
    3231#include <arch/drivers/cuda.h>
    3332#include <arch/mm/memory_init.h>
    3433#include <arch/interrupt.h>
     34#include <genarch/fb/fb.h>
    3535#include <userspace.h>
    3636#include <proc/uarg.h>
     
    6868                /* Merge all zones to 1 big zone */
    6969                zone_merge_all();
    70                
    71                 ppc32_console_register();
    7270        }
    7371}
  • arch/ppc32/src/proc/scheduler.c

    r8424198 r35f3b8c  
    4141void before_thread_runs_arch(void)
    4242{
    43         tlb_invalidate_all();
     43        pht_init();
    4444        asm volatile (
    4545                "mtsprg0 %0\n"
Note: See TracChangeset for help on using the changeset viewer.