Changeset 760


Ignore:
Timestamp:
Jan 19, 2016, 11:23:02 AM (9 years ago)
Author:
alain
Message:
 
Location:
soft/giet_vm/giet_kernel
Files:
4 edited

Legend:

Unmodified
Added
Removed
  • soft/giet_vm/giet_kernel/ctx_handler.h

    r714 r760  
    3434// ctx[35]<- BVAR  |ctx[43]<- CMA_TX |ctx[51]<- COPROC |ctx[59]<- ***
    3535// ctx[36]<- PTAB  |ctx[44]<- NIC_RX |ctx[52]<- ENTRY  |ctx[60]<- ***
    36 // ctx[37]<- ***   |ctx[45]<- NIC_TX |ctx[53]<- SIGS   |ctx[61]<- ***
     36// ctx[37]<- NPT2  |ctx[45]<- NIC_TX |ctx[53]<- SIGS   |ctx[61]<- ***
    3737// ctx[38]<- ***   |ctx[46]<- TIM    |ctx[54]<- VSID   |ctx[62]<- ***
    3838// ctx[39]<- PTPR  |ctx[47]<- HBA    |ctx[55]<- LOCKS  |ctx[63]<- ***
     
    6161#define CTX_BVAR_ID      35        // Bad Virtual Address Register (CP0)
    6262#define CTX_PTAB_ID      36    // Page Table Virtual address
    63 //                       37
     63#define CTX_NPT2_ID      37    // Next free PT2 index
    6464//                       38
    6565#define CTX_PTPR_ID      39    // Page Table Pointer Register (PADDR>>13)
  • soft/giet_vm/giet_kernel/kernel_init.c

    r742 r760  
    9595////////////////////////////////////////////////////////////////////////////////
    9696
    97 // array of page tables virtual addresses
    98 __attribute__((section(".kdata")))
    99 volatile unsigned int _ptabs_vaddr[GIET_NB_VSPACE_MAX][X_SIZE][Y_SIZE];
    100 
    101 // array of page tables PTPR values (physical addresses >> 13)
    102 __attribute__((section(".kdata")))
    103 volatile unsigned int _ptabs_ptprs[GIET_NB_VSPACE_MAX][X_SIZE][Y_SIZE];
     97// Array of page tables virtual addresses (one per vspace and per cluster)
     98__attribute__((section(".kdata")))
     99unsigned int        _ptabs_vaddr[GIET_NB_VSPACE_MAX][X_SIZE][Y_SIZE];
     100
     101// Array of page tables physical addresses (one per vspace and per cluster)
     102__attribute__((section(".kdata")))
     103unsigned long long  _ptabs_paddr[GIET_NB_VSPACE_MAX][X_SIZE][Y_SIZE];
     104
     105// Array of pt2 allocators (one per vspace and per cluster)
     106__attribute__((section(".kdata")))
     107unsigned int        _ptabs_next_pt2[GIET_NB_VSPACE_MAX][X_SIZE][Y_SIZE];
     108
     109// Page tables max_pt2  (same value for all page tables)
     110__attribute__((section(".kdata")))
     111unsigned int        _ptabs_max_pt2;
    104112
    105113// Array of pointers on the schedulers
     
    122130__attribute__((section(".kdata")))
    123131sqt_barrier_t  _all_procs_barrier  __attribute__((aligned(64)));
     132
     133// required for concurrent PTAB building
     134__attribute__((section(".kdata")))
     135spin_lock_t    _ptabs_spin_lock[GIET_NB_VSPACE_MAX][X_SIZE][Y_SIZE];
     136
    124137
    125138////////////////////////////////////////////////////////////////////////////////
     
    191204#endif
    192205
     206        ////// get max_pt2 value stored in mapping header
     207        mapping_header_t*  header = (mapping_header_t*)SEG_BOOT_MAPPING_BASE;
     208        _ptabs_max_pt2 = header->max_pt2;
     209
    193210        //////  TTY fifos initialisation
    194211        unsigned int tty_id;
     
    277294    // step 2 : each processor that is allocated at least one thread loops
    278295    //          on its allocated threads:
    279     //          - contributes to _ptabs_vaddr & _ptabs_ptprs arrays
     296    //          - contributes to _ptabs_vaddr & _ptabs_paddr arrays
    280297    //            initialisation, from values stored in the threads contexts.
    281298    //          - set CTX_RA slot  with the kernel _ctx_eret() virtual address.
     
    292309        unsigned int ptab = _get_thread_slot( x, y, p, ltid , CTX_PTAB_ID );
    293310        unsigned int ptpr = _get_thread_slot( x, y, p, ltid , CTX_PTPR_ID );
     311        unsigned int npt2 = _get_thread_slot( x, y, p, ltid , CTX_NPT2_ID );
    294312
    295313        // initialize PTABS arrays
    296         _ptabs_vaddr[vsid][x][y] = ptab;
    297         _ptabs_ptprs[vsid][x][y] = ptpr;
     314        _ptabs_vaddr[vsid][x][y]    = ptab;
     315        _ptabs_paddr[vsid][x][y]    = ((unsigned long long)ptpr) << 13;
     316        _ptabs_next_pt2[vsid][x][y] = npt2;
    298317
    299318        // set the PTPR to use the local page table
     
    319338        " - ctx_ra               = %x\n",
    320339        x , y , p , ltid , 
    321         vsid , x , y , ptab ,
    322         vsid , x , y , ((unsigned long long)ptpr)<<13 ,
     340        vsid , x , y , _ptabs_vaddr[vsid][x][y] ,
     341        vsid , x , y , _ptabs_paddr[vsid][x][y] ,
    323342        ctx_entry, ctx_ra );
    324343#endif
  • soft/giet_vm/giet_kernel/sys_handler.c

    r754 r760  
    9595extern static_scheduler_t* _schedulers[X_SIZE][Y_SIZE][NB_PROCS_MAX];
    9696
    97 // allocated in bdv_driver.c file
    98 spin_lock_t  _bdv_lock;
     97// allocated in kernel_init.c file
     98extern unsigned long long  _ptabs_paddr[GIET_NB_VSPACE_MAX][X_SIZE][Y_SIZE];
    9999
    100100////////////////////////////////////////////////////////////////////////////////
     
    229229
    230230    &_fat_open,                      /* 0x20 */
    231     &_fat_read,                      /* 0x21 */
    232     &_fat_write,                     /* 0x22 */
     231    &_sys_fat_read,                  /* 0x21 */
     232    &_sys_fat_write,                 /* 0x22 */
    233233    &_fat_lseek,                     /* 0x23 */
    234234    &_fat_file_info,                 /* 0x24 */
     
    240240    &_fat_closedir,                  /* 0x2A */
    241241    &_fat_readdir,                   /* 0x2B */
    242     &_sys_ukn,                       /* 0x2C */
    243     &_sys_ukn,                       /* 0x2D */
    244     &_sys_ukn,                       /* 0x2E */
     242    &_sys_fat_pread,                 /* 0x2C */
     243    &_sys_fat_mmap,                  /* 0x2D */
     244    &_sys_fat_munmap,                /* 0x2E */
    245245    &_sys_ukn,                       /* 0x2F */
    246246
     
    274274
    275275
     276
     277///////////////////////////////////////////////////////////////////////////////////
     278//           File system related syscall handlers
     279///////////////////////////////////////////////////////////////////////////////////
     280
     281///////////////////////////////////////////////////////////////////////////////////
     282// This function is called by the _sys_fat_mmap() function.
     283// It implements a simplistic pages allocator from the MMAP vseg of the vspace
     284// identified by the <vspace_id> argument. The number of pages is defined by
     285// the <count> argument.
     286// Allocated pages are never released, and the allocator is the "psegid" field
     287// in the vseg mapping, that is initialised to 0 by the boot code.
     288// In order to support concurrent system calls, the allocator must be
     289// atomically incremented.
     290///////////////////////////////////////////////////////////////////////////////////
     291// Returns the buffer vbase address in case of success.
     292// Returns 0 in case of error (no MMAP vseg or not enough space).
     293///////////////////////////////////////////////////////////////////////////////////
     294static unsigned int _mmap_pages_alloc( unsigned int  vspace_id,
     295                                       unsigned int  count )
     296{
     297    mapping_header_t*   header  = (mapping_header_t *)SEG_BOOT_MAPPING_BASE;
     298    mapping_vspace_t*   vspace  = _get_vspace_base( header );
     299    mapping_vseg_t*     vseg    = _get_vseg_base( header );
     300
     301    // loop on the vsegs to find the MMAP vseg vbase, length, and offset
     302    unsigned int  vseg_id;
     303    unsigned int  vbase;   
     304    unsigned int  offset;   
     305    unsigned int  length;
     306    unsigned int  found = 0;
     307    for (vseg_id = vspace[vspace_id].vseg_offset;
     308         vseg_id < (vspace[vspace_id].vseg_offset + vspace[vspace_id].vsegs);
     309         vseg_id++)
     310    {
     311        if ( vseg[vseg_id].type == VSEG_TYPE_MMAP )
     312        {
     313            offset = _atomic_increment( &vseg[vseg_id].psegid , count );
     314            vbase  = vseg[vseg_id].vbase;
     315            length = vseg[vseg_id].length;
     316            found  = 1;
     317            break;
     318        }
     319    }
     320
     321    if ( (found == 0) || (((offset + count)<<12) > length) )
     322    {
     323        return 0;
     324    }
     325    else
     326    {
     327        return vbase + (offset<<12);
     328    }
     329}  // end _mmap_pages_alloc()
     330
     331
     332///////////////////////////////////////////////////////////////////////////////////
     333// This function implements the giet_fat_read() system call.
     334///////////////////////////////////////////////////////////////////////////////////
     335int _sys_fat_read( unsigned int fd_id,
     336                   unsigned int vaddr,
     337                   unsigned int count )
     338{
     339    return _fat_read( fd_id,
     340                      vaddr,
     341                      count,
     342                      0,                       // no paddr extension
     343                      0,                       // no forced offset
     344                      0 );                     // no special mode
     345}
     346
     347////////////////////////////////////////////////////////////////
     348// This function implements the giet_fat_pread() system call.
     349////////////////////////////////////////////////////////////////
     350int _sys_fat_pread( unsigned int fd_id,
     351                    unsigned int vaddr,
     352                    unsigned int count,
     353                    unsigned int offset )
     354{
     355    return _fat_read( fd_id,
     356                      vaddr,
     357                      count,
     358                      0,                        // no paddr extension
     359                      offset,
     360                      FAT_FORCED_OFFSET );     
     361}
     362
     363////////////////////////////////////////////////////////////////
     364// This function implements the giet_fat_write() system call.
     365////////////////////////////////////////////////////////////////
     366int _sys_fat_write( unsigned int fd_id,
     367                    unsigned int vaddr,
     368                    unsigned int count )
     369{
     370    return _fat_write( fd_id,
     371                       vaddr,
     372                       count,
     373                       0,                       // no paddr extension
     374                       0 );                     // no special mode
     375}
     376
     377///////////////////////////////////////////////////////////////////////////////////
     378// This function implements the "giet_fat_mmap()" system call.
     379// It allocates <count> contiguous pages from the MMAP vseg of the calling vspace.
     380// It maps all these pages directly to the file_cache defined by <fd_id>.
     381// The <offset> in the file is a number of pages.
     382// The <prot> argument defines the access modes MAP_PROT_WRITE and MAP_PROT_EXEC.
     383// In writable mode, the file size is extended to the (offset + count) pages.
     384// In non writable mode, the file size must be >= (offset + count) pages.
     385// It has the following limitations:
     386// - it does not support MAP_PRIVATE (no copy on write).
     387// - it does not support MAP_FIXED (no forced user buffer address).
     388// - it does not support MAP_ANONYMOUS (only file mapping).
     389// - the <offset> and <count> arguments must multiple of 4 Kbytes.
     390///////////////////////////////////////////////////////////////////////////////////
     391// Returns memory buffer vbase in case of success.
     392// Returns 0 on error.
     393///////////////////////////////////////////////////////////////////////////////////
     394int _sys_fat_mmap( unsigned int fd_id,
     395                   unsigned int count,
     396                   unsigned int offset,
     397                   unsigned int prot )
     398{
     399    // takes the FAT lock and register it in thread context
     400    static_scheduler_t*  psched = _get_sched();
     401    unsigned int         ltid   = _get_thread_ltid();
     402    _spin_lock_acquire( &_fat.fat_lock );
     403    _atomic_or( &psched->context[ltid].slot[CTX_LOCKS_ID] , LOCKS_MASK_FAT );
     404
     405    // check fd_id overflow
     406    if ( fd_id >= GIET_OPEN_FILES_MAX )
     407    {
     408        _spin_lock_release( &_fat.fat_lock );
     409        _atomic_and( &psched->context[ltid].slot[CTX_LOCKS_ID] , ~LOCKS_MASK_FAT );
     410
     411        _printf("\n[GIET ERROR] _sys_fat_mmap(): illegal file descriptor\n");
     412        return 0;
     413    }
     414
     415    // check file open
     416    if ( _fat.fd[fd_id].allocated == 0 )
     417    {
     418        _spin_lock_release( &_fat.fat_lock );
     419        _atomic_and( &psched->context[ltid].slot[CTX_LOCKS_ID] , ~LOCKS_MASK_FAT );
     420
     421        _printf("\n[GIET ERROR] _sys_fat_mmap(): file not open\n" );
     422        return 0;
     423    }
     424
     425    // get access modes
     426    unsigned int writable   = prot & MAP_PROT_WRITE;
     427    unsigned int executable = prot & MAP_PROT_EXEC;
     428
     429    // get inode pointer 
     430    fat_inode_t* inode  = _fat.fd[fd_id].inode;
     431
     432    // check file writable
     433    if ( _fat.fd[fd_id].read_only && writable )
     434    {
     435        _spin_lock_release( &_fat.fat_lock );
     436        _atomic_and( &psched->context[ltid].slot[CTX_LOCKS_ID] , ~LOCKS_MASK_FAT );
     437
     438        _printf("\n[GIET ERROR] _sys_fat_mmap(): file <%s> is read-only\n",
     439                inode->name );
     440        return 0;
     441    }
     442
     443    // get vspace index and calling proc coordinates
     444    unsigned int vsid    = _get_context_slot( CTX_VSID_ID );
     445
     446    // compute first and last cluster indexes
     447    unsigned int  first_cluster  = offset;
     448    unsigned int  last_cluster   = offset + count - 1;
     449
     450#if GIET_DEBUG_MMAP
     451unsigned int procid  = _get_procid();
     452unsigned int x_id    = procid >> (Y_WIDTH + P_WIDTH);
     453unsigned int y_id    = (procid >> P_WIDTH) & ((1<<Y_WIDTH)-1);
     454unsigned int p_id    = procid & ((1<<P_WIDTH)-1);
     455if ( _get_proctime() > GIET_DEBUG_MMAP )
     456_printf("\n[DEBUG MMAP] _sys_fat_mmap() : P[%d,%d,%d] enters at cycle %d\n"
     457        " for file %s / size = %x / cluster = %x / cache = %x / desc[0] = %x\n"
     458        " first_cluster = %d / last_cluster = %d\n",
     459        x_id , y_id , p_id , _get_proctime() ,
     460        inode->name , inode->size , inode->cluster ,
     461        (unsigned int)inode->cache , (unsigned int)inode->cache->children[0] ,
     462        first_cluster , last_cluster );
     463#endif
     464
     465    // get buffer vbase from MMAP vseg in calling vspace
     466    unsigned int buffer_vbase = _mmap_pages_alloc( vsid, count );
     467    if ( buffer_vbase == 0 )
     468    {
     469        _spin_lock_release( &_fat.fat_lock );
     470        _atomic_and( &psched->context[ltid].slot[CTX_LOCKS_ID] , ~LOCKS_MASK_FAT );
     471
     472        _printf("\n[GIET ERROR] _sys_fat_mmap(): no space in MMAP vseg to map file %s\n",
     473                _fat.fd[fd_id].inode->name );
     474        return 0;
     475    }
     476 
     477    // set flags for all pages in buffer
     478    unsigned int flags = 0;
     479    flags |= PTE_C;                    // cachable
     480    flags |= PTE_U;                    // user access
     481    flags |= PTE_L;                    // local access (unused)
     482    flags |= PTE_R;                    // remote access (unused)
     483    if ( executable ) flags |= PTE_X;
     484    if ( writable   ) flags |= PTE_W;
     485
     486    // loop on pages to be mapped
     487    unsigned int cid;
     488    unsigned int user_vaddr = buffer_vbase;
     489    for ( cid = first_cluster ; cid <= last_cluster ; cid++ ) 
     490    {
     491        // get file_cache buffer vaddr
     492        unsigned char*     cache_vaddr;
     493        fat_cache_desc_t*  pdesc;
     494        if ( _get_file_cache_buffer( inode,
     495                                     cid,
     496                                     writable,
     497                                     &pdesc ) )
     498        {
     499            _spin_lock_release( &_fat.fat_lock );
     500            _atomic_and( &psched->context[ltid].slot[CTX_LOCKS_ID] , ~LOCKS_MASK_FAT );
     501
     502            _printf("\n[FAT ERROR] _sys_fat_mmap(): cannot access file <%s>\n",
     503                    _fat.fd[fd_id].inode->name );
     504            return 0;
     505        }
     506
     507        cache_vaddr = pdesc->buffer;
     508       
     509        // compute buffer paddr
     510        unsigned long long  cache_paddr;
     511        unsigned int        unused;
     512        cache_paddr = _v2p_translate( (unsigned int)cache_vaddr, &unused );
     513
     514        // map the user_vaddr to cache_paddr
     515        // in all pages tables defined for the vspace
     516        unsigned int x_cur;
     517        unsigned int y_cur;
     518        for  ( x_cur = 0 ; x_cur < X_SIZE ; x_cur++ )
     519        {
     520            for  ( y_cur = 0 ; y_cur < Y_SIZE ; y_cur++ )
     521            {
     522                if ( _ptabs_paddr[vsid][x_cur][y_cur] )  // Page table is defined
     523                {
     524                    _v2p_add_pte2( vsid,
     525                                   x_cur,
     526                                   y_cur,
     527                                   user_vaddr >> 12,
     528                                   flags,
     529                                   cache_paddr >> 12,
     530                                   0 );
     531                }
     532            }
     533        }
     534
     535#if GIET_DEBUG_MMAP
     536if ( _get_proctime() > GIET_DEBUG_MMAP )
     537_printf("\n[DEBUG MMAP] _sys_fat_mmap() : P[%d,%d,%d] map cluster %d\n"
     538        " user_vaddr = %x / cache_paddr = %l\n",
     539        x_id , y_id , p_id , cid , user_vaddr , cache_paddr );
     540#endif
     541
     542        // increment user buffer vaddr
     543        user_vaddr += 4096;
     544    }
     545
     546    // releases the FAT lock
     547    _spin_lock_release( &_fat.fat_lock );
     548    _atomic_and( &psched->context[ltid].slot[CTX_LOCKS_ID] , ~LOCKS_MASK_FAT );
     549
     550#if GIET_DEBUG_MMAP
     551if ( _get_proctime() > GIET_DEBUG_MMAP )
     552_printf("\n[DEBUG MMAP] _sys_fat_mmap() : P[%d,%d,%d] returns buffer %x for file %s\n",
     553        x_id , y_id , p_id , buffer_vbase , inode->name );
     554#endif
     555
     556   // returns pointer on mapped buffer in user space
     557    return buffer_vbase;
     558
     559}  // end _sys_fat_mmap()
     560
     561
     562//////////////////////////////////////////////////////////////////
     563// This function implements the giet_fat_munmap() system call.
     564//////////////////////////////////////////////////////////////////
     565int _sys_fat_munmap( unsigned int vaddr,
     566                     unsigned int count )
     567{
     568    // get vspace index
     569    unsigned int  vsid   = _get_context_slot( CTX_VSID_ID );
     570
     571    // loop on pages
     572    unsigned int page;
     573    for ( page = 0 ; page < count ; page++ )
     574    {
     575        unsigned int vpn = (vaddr>>12) + page;
     576
     577        // loop on all page tables defined for the vspace
     578        unsigned int x_cur;
     579        unsigned int y_cur;
     580        for  ( x_cur = 0 ; x_cur < X_SIZE ; x_cur++ )
     581        {
     582            for  ( y_cur = 0 ; y_cur < Y_SIZE ; y_cur++ )
     583            {
     584                if ( _ptabs_paddr[vsid][x_cur][y_cur] )  // Page table is defined
     585                {
     586                    _v2p_del_pte2( vsid , x_cur , y_cur , vpn );
     587                }
     588            }
     589        }
     590    }
     591    return 0;
     592}  // end _sys_fat_munmap()
     593
     594
     595
    276596//////////////////////////////////////////////////////////////////////////////
    277597//           Applications related syscall handlers
     
    279599
    280600////////////////////////////////////////////////////////////////////////
    281 // This function is called by the _sys_exec_application function
     601// This function is called by the _sys_exec_application() function
    282602// to reload all data segments contained in an application.elf file.
    283603// File checking is minimal, because these segments have already
     
    344664        return 1;
    345665    }
    346     if ( _fat_read( fd, (unsigned int)buf, 4096, 0 ) < 0 )
     666    if ( _fat_read( fd, (unsigned int)buf, 4096, 0, 0, 0 ) < 0 )
    347667    {
    348668        _printf("\n[GIET ERROR] _load_writable_segments() : cannot read\n");
     
    369689        return 1;
    370690    }
    371     if ( _fat_read( fd, (unsigned int)buf, 4096, 0 ) < 0 )
     691    if ( _fat_read( fd, (unsigned int)buf, 4096, 0, 0, 0 ) < 0 )
    372692    {
    373693        _fat_close( fd );
     
    414734                    // compute destination address and extension for _fat_read()
    415735                    unsigned int dest   = (unsigned int)pbase;
    416                     unsigned int extend = (unsigned int)(pbase>>32) | 0xFFFF0000;
     736                    unsigned int extend = (unsigned int)(pbase>>32);
    417737
    418738                    // load the segment
     
    422742                        return 1;
    423743                    }
    424                     if ( _fat_read( fd, dest, seg_size, extend ) < 0 )
     744                    if ( _fat_read( fd, dest, seg_size, extend, 0, FAT_PADDR_MODE ) < 0 )
    425745                    {
    426746                        _fat_close( fd );
  • soft/giet_vm/giet_kernel/sys_handler.h

    r733 r760  
    105105typedef struct nic_chbuf_s
    106106{
    107     unsigned long long   buf_desc[X_SIZE*Y_SIZE];     // kernel chbuf descriptor
    108     unsigned int         xmax;                        // nb clusters in a row
    109     unsigned int         ymax;                        // nb clusters in a column
     107    unsigned long long   buf_desc[X_SIZE*Y_SIZE];    // kernel chbuf descriptor
     108    unsigned int         xmax;                       // nb clusters in a row
     109    unsigned int         ymax;                       // nb clusters in a column
    110110} nic_chbuf_t;
     111
     112
     113//////////////////////////////////////////////////////////////////////////////
     114//           File system related syscall handlers
     115//////////////////////////////////////////////////////////////////////////////
     116
     117extern int _sys_fat_read( unsigned int fd_id,        // file descriptor index
     118                          unsigned int vaddr,        // buffer vbase     
     119                          unsigned int count );      // number of bytes
     120
     121extern int _sys_fat_pread(unsigned int fd_id,        // file descriptor index
     122                          unsigned int vaddr,        // buffer vbase
     123                          unsigned int count,        // number of bytes
     124                          unsigned int offset );     // bytes to skip in file
     125
     126extern int _sys_fat_write( unsigned int fd_id,       // file descriptor index
     127                           unsigned int vaddr,       // buffer vbase
     128                           unsigned int count );     // number of bytes
     129
     130extern int _sys_fat_mmap( unsigned int fd_id,        // file descriptor index
     131                          unsigned int count,        // number of pages
     132                          unsigned int offset,       // pages to skip in file
     133                          unsigned int prot );       // protection modes
     134
     135extern int _sys_fat_munmap( unsigned int vaddr,      // buffer vbase
     136                            unsigned int count );    // number of pages
    111137
    112138
Note: See TracChangeset for help on using the changeset viewer.