Ignore:
Timestamp:
Aug 16, 2017, 3:27:05 PM (7 years ago)
Author:
alain
Message:

Simplify the hal_mmu_exception() function.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/hal/tsar_mips32/core/hal_exception.c

    r381 r391  
    172172                     __FUNCTION__, this->trdid , process->pid , bad_vaddr , excp_code );
    173173
    174     // a kernel thread should not rise an MMU exception
    175         if( this->type != THREAD_USER )
    176         {
    177                 printk("\n[PANIC] in %s : thread %x is a kernel thread / vaddr = %x\n",
    178                        __FUNCTION__ , this->trdid , bad_vaddr );
    179                 return EXCP_KERNEL_PANIC;
    180         }
    181  
    182     // enable IRQs
    183         hal_enable_irq( NULL );
    184 
     174    // on TSAR, a kernel thread should not rise an MMU exception
     175        assert( (this->type != THREAD_USER) , __FUNCTION__ ,
     176    "thread %x is a kernel thread / vaddr = %x\n", this->trdid , bad_vaddr );
     177 
    185178    // vaddr must be contained in a registered vseg
    186     vseg = vmm_get_vseg( process , bad_vaddr );
    187 
    188     if( vseg == NULL )   // vseg not found in local cluster
    189         {
    190         // get extended pointer on reference process
    191         xptr_t ref_xp = process->ref_xp;
    192 
    193         // get cluster and local pointer on reference process
    194         cxy_t       ref_cxy = GET_CXY( ref_xp );
    195         process_t * ref_ptr = (process_t *)GET_PTR( ref_xp );
    196 
    197         if( local_cxy != ref_cxy )   // reference process is remote
    198         {
    199             // get extended pointer on reference vseg
    200             xptr_t vseg_xp;
    201             rpc_vmm_get_ref_vseg_client( ref_cxy , ref_ptr , bad_vaddr , &vseg_xp );
    202            
    203        
    204             if( vseg == NULL )          // vseg not found => illegal user vaddr
    205             {
    206                 printk("\n[ERROR] in %s for thread %x : illegal vaddr = %x\n",
    207                        __FUNCTION__ , this->trdid , bad_vaddr );
    208 
    209                 hal_disable_irq( NULL );
    210                         return EXCP_USER_ERROR;
    211             }
    212             else                        // vseg found => make a local copy
    213             {
    214                 // allocate a vseg in local cluster
    215                 vseg = vseg_alloc();
    216 
    217                 if( vseg == NULL )
    218                 {
    219                             printk("\n[PANIC] in %s : no memory for vseg / thread = %x\n",
    220                                    __FUNCTION__ , this->trdid );
    221                     hal_disable_irq( NULL );
    222                             return EXCP_KERNEL_PANIC;
    223                 }
    224 
    225                 // initialise local vseg from reference
    226                 vseg_init_from_ref( vseg , ref_xp );
    227 
    228                 // register local vseg in local VMM
    229                 error = vseg_attach( &process->vmm , vseg );
    230             }
    231         }
    232         else                   // reference is local => illegal user vaddr
    233         {
    234             printk("\n[ERROR] in %s for thread %x : illegal vaddr = %x\n",
    235                    __FUNCTION__ , this->trdid , bad_vaddr );
    236 
    237             hal_disable_irq( NULL );
    238                     return EXCP_USER_ERROR;
    239         }
    240     }
     179    error = vmm_get_vseg( process , bad_vaddr , &vseg );
    241180
    242181        vmm_dmsg("\n[INFO] %s : found vseg for thread %x / vseg_min = %x / vseg_max = %x\n",
     
    246185    if( excp_code & MMU_EXCP_PAGE_UNMAPPED )
    247186    {
     187        // enable IRQs before handling page fault
     188        hal_enable_irq( NULL );
     189
    248190        // try to map the unmapped PTE
    249191        error = vmm_handle_page_fault( process,
    250192                                       vseg,
    251193                                       bad_vaddr >> CONFIG_PPM_PAGE_SHIFT );  // vpn
    252 
    253         if( error )
    254         {
    255             printk("\n[PANIC] in %s for thread %x : cannot map legal vaddr = %x\n",
     194        // disable IRQs
     195        hal_disable_irq( NULL );
     196
     197        if( error )     // not enough memory
     198        {
     199            printk("\n[ERROR] in %s for thread %x : cannot map legal vaddr = %x\n",
    256200               __FUNCTION__ , this->trdid , bad_vaddr );
    257201
    258             hal_disable_irq( NULL );
    259                     return EXCP_KERNEL_PANIC;
    260         }
    261         else
     202                    return EXCP_USER_ERROR;
     203        }
     204        else            // page fault successfully handled
    262205        {
    263206            vmm_dmsg("\n[INFO] %s : page fault handled for vaddr = %x in thread %x\n",
    264207                             __FUNCTION__ , bad_vaddr , this->trdid );
    265208 
    266             // page fault successfully handled
    267             hal_disable_irq( NULL );
    268209            return EXCP_NON_FATAL;
    269210        }
     
    274215               __FUNCTION__ , this->trdid , bad_vaddr );
    275216
    276         hal_disable_irq( NULL );
    277217        return EXCP_USER_ERROR;
    278218    }
     
    282222               __FUNCTION__ , this->trdid , bad_vaddr );
    283223
    284         hal_disable_irq( NULL );
    285224        return EXCP_USER_ERROR;
    286225    }
     
    290229               __FUNCTION__ , this->trdid , bad_vaddr );
    291230
    292         hal_disable_irq( NULL );
    293231        return EXCP_USER_ERROR;
    294232    }
     
    299237               __FUNCTION__ , this->trdid , excp_code , bad_vaddr );
    300238
    301         hal_disable_irq( NULL );
    302239        return EXCP_KERNEL_PANIC;
    303240    }
Note: See TracChangeset for help on using the changeset viewer.