Changeset 23 for trunk/kernel/drivers


Ignore:
Timestamp:
Jun 18, 2017, 10:06:41 PM (5 years ago)
Author:
alain
Message:

Introduce syscalls.

Location:
trunk/kernel/drivers/soclib
Files:
3 edited

Legend:

Unmodified
Added
Removed
  • trunk/kernel/drivers/soclib/soclib_bdv.c

    r4 r23  
    5353void __attribute__ ((noinline)) soclib_bdv_cmd( xptr_t th_xp )
    5454{
    55     uint32_t   to_mem;       // command argument
     55    uint32_t   cmd_type;     // IOC_READ / IOC_WRITE / IOC_SYNC_READ
    5656    uint32_t   lba;          // command argument
    5757    uint32_t   count;        // command argument
     
    6464
    6565    // get command arguments and extended pointer on IOC device
    66     to_mem =         hal_remote_lw ( XPTR( th_cxy , &th_ptr->command.ioc.to_mem ) );
    67     lba    =         hal_remote_lw ( XPTR( th_cxy , &th_ptr->command.ioc.lba    ) );
    68     count  =         hal_remote_lw ( XPTR( th_cxy , &th_ptr->command.ioc.count  ) );
    69     buf_xp = (xptr_t)hal_remote_lwd( XPTR( th_cxy , &th_ptr->command.ioc.buf_xp ) );
    70     dev_xp = (xptr_t)hal_remote_lwd( XPTR( th_cxy , &th_ptr->command.ioc.dev_xp ) );
     66    cmd_type =         hal_remote_lw ( XPTR( th_cxy , &th_ptr->command.ioc.type  ) );
     67    lba      =         hal_remote_lw ( XPTR( th_cxy , &th_ptr->command.ioc.lba    ) );
     68    count    =         hal_remote_lw ( XPTR( th_cxy , &th_ptr->command.ioc.count  ) );
     69    buf_xp   = (xptr_t)hal_remote_lwd( XPTR( th_cxy , &th_ptr->command.ioc.buf_xp ) );
     70    dev_xp   = (xptr_t)hal_remote_lwd( XPTR( th_cxy , &th_ptr->command.ioc.dev_xp ) );
    7171
    7272    // get IOC device cluster and local pointer
     
    8585    uint32_t   buf_msb = (uint32_t)(buf_xp>>32);
    8686
    87     // get access type
    88     uint32_t   type =  to_mem ? BDV_OP_READ : BDV_OP_WRITE;
     87    // set operation
     88    uint32_t   op;
     89    if( cmd_type == IOC_WRITE ) op = BDV_OP_WRITE;
     90    else                        op = BDV_OP_READ;
    8991
    9092    // set SOCLIB_BDV registers to start one I/O operation
     
    9496    hal_remote_sw( XPTR( bdv_cxy , bdv_ptr + BDV_LBA_REG        ) , lba     );
    9597    hal_remote_sw( XPTR( bdv_cxy , bdv_ptr + BDV_COUNT_REG      ) , count   );
    96     hal_remote_sw( XPTR( bdv_cxy , bdv_ptr + BDV_OP_REG         ) , type    );
     98    hal_remote_sw( XPTR( bdv_cxy , bdv_ptr + BDV_OP_REG         ) , op      );
    9799
    98     // Block and deschedule server thread
    99     thread_block( CURRENT_THREAD , THREAD_BLOCKED_DEV_ISR );
    100     sched_yield();
     100    // waiting policy  depends on the command type
     101
     102    if( cmd_type == IOC_SYNC_READ )                  // polling policy
     103    {
     104        uint32_t status;
     105        while (1)
     106        {
     107            status = hal_remote_lw( XPTR( bdv_cxy , bdv_ptr + BDV_STATUS_REG ) );
     108
     109            if( status == BDV_READ_SUCCESS ) // successfully completed
     110            {
     111                hal_remote_sw( XPTR( th_cxy , &th_ptr->command.ioc.error ) , 0 );
     112                break;
     113            }
     114            else if( status == BDV_BUSY )   // non completed
     115            {
     116                continue;
     117            }
     118            else                            // error reported
     119            {
     120                hal_remote_sw( XPTR( th_cxy , &th_ptr->command.ioc.error ) , 1 );
     121                break;
     122            }
     123        }
     124    }
     125    else                                            // descheduling + IRQ policy
     126    {
     127        thread_block( CURRENT_THREAD , THREAD_BLOCKED_DEV_ISR );
     128        sched_yield();
     129    }
    101130   
    102131} // end soclib_bdv_cmd()
  • trunk/kernel/drivers/soclib/soclib_hba.c

    r4 r23  
    7272    chdev->ext.ioc.count = block_count;
    7373
    74         // reset SOCLIB_HBA driver global variables
     74    // activate HBA interrupts
     75    hal_remote_sw( XPTR( hba_cxy , hba_ptr + HBA_PXIE_REG ) , 0x1 );
     76
     77        // reset SOCLIB_HBA driver global variable
    7578    hba_active_slots = 0;
    7679
     
    7881
    7982
    80 //////////////////////////////////////////////////////////////////
    81 void __attribute__ ((noinline)) soclib_hba_command( xptr_t th_xp )
     83//////////////////////////////////////////////////////////////
     84void __attribute__ ((noinline)) soclib_hba_cmd( xptr_t th_xp )
    8285{
    8386
    84     uint32_t           to_mem;       // to_mem : command argument
     87    uint32_t           cmd_type;     // IOC_READ / IOC_WRITE / IOC_SYNC_READ
    8588    uint32_t           lba;          // lba    : command argument
    8689    uint32_t           count;        // count  : command argument
    8790    xptr_t             buf_xp;       // buffer : command argument
    8891    xptr_t             dev_xp;       // device : command argument
     92
    8993    uint32_t           cmd_id;       // current slot index in command bit_vector
    9094    hba_cmd_desc_t   * cmd_desc;     // command descriptor pointer   
    9195    hba_cmd_table_t  * cmd_table;    // command table pointer
     96
    9297    bool_t             found;
    9398    uint32_t           iter;
     
    98103
    99104    // get command arguments and extended pointer on IOC device
    100     to_mem    =         hal_remote_lw ( XPTR( th_cxy , &th_ptr->command.ioc.to_mem ) );
     105    cmd_type  =         hal_remote_lw ( XPTR( th_cxy , &th_ptr->command.ioc.type  ) );
    101106    lba       =         hal_remote_lw ( XPTR( th_cxy , &th_ptr->command.ioc.lba    ) );
    102107    count     =         hal_remote_lw ( XPTR( th_cxy , &th_ptr->command.ioc.count  ) );
     
    135140        }
    136141
    137         if( found )  // register and starts the I/O operation
     142        if( found )  // slot available in SOCLIB_HBA
    138143        {
    139144            // compute pointers on command descriptor and command table   
     
    157162            cmd_desc->prdtl[0] = 1;
    158163            cmd_desc->prdtl[1] = 0;
    159             if( to_mem ) cmd_desc->flag[0] = 0x00;
    160             else         cmd_desc->flag[0] = 0x40;     
     164            if( cmd_type == IOC_WRITE ) cmd_desc->flag[0] = 0x40;
     165            else                        cmd_desc->flag[0] = 0x00;     
    161166
    162167#if USE_IOB // software L2/L3 cache coherence
    163168
    164             // compute physical addresses
    165             paddr_t   cmd_desc_paddr;    // command descriptor physical address
    166             paddr_t   cmd_table_paddr;   // command table header physical address
    167             bool_t    ident = CONFIG_KERNEL_IDENTITY;
    168            
    169             error = vmm_v2p_translate( ident , cmd_table , &cmd_table_paddr );
    170             if( error )
    171             {
    172                 printk("\n[PANIC] in %s : cannot get paddr fo cmd_table\n", __FUNCTION__ );
    173                 hal_core_sleep()
    174             }
    175 
    176             error = vmm_v2p_translate( ident , cmd_desc , &cmd_desc_paddr );
    177             if( error )
    178             {
    179                 printk("\n[PANIC] in %s : cannot get paddr fo cmd_desc\n", __FUNCTION__ );
    180                 hal_core_sleep()
    181             }
    182 
    183             // update L3 for command table
    184             dev_mmc_sync( cmd_table_paddr , sizeof(hba_cmd_table_t) );
    185 
    186             // update L3 for command descriptor
    187             dev_mmc_sync( cmd_desc_paddr , sizeof(hba_cmd_desc_t) );
     169            dev_mmc_sync( cmd_table , sizeof(hba_cmd_table_t) );
     170            dev_mmc_sync( cmd_desc , sizeof(hba_cmd_desc_t) );
    188171
    189172#endif // end software L2/L3 cache coherence
    190 
    191             // activates HBA interrupts
    192             hal_remote_sw( XPTR( hba_cxy , hba_ptr + HBA_PXIE_REG ) , 0x1 );
    193173
    194174            // set hba_owner_thread[slot]
    195175            hba_owner_thread[cmd_id] = th_xp;
    196176
     177            // register slot in bit_vector
     178            hba_active_slots |= 1<<cmd_id;
     179 
    197180            // set HBA_PXCI_REG to start transfer
    198181            hal_remote_sw( XPTR( hba_cxy , hba_ptr + HBA_PXCI_REG ) , 1<<cmd_id );
    199182
    200             ioc_dmsg("INFO in %s : thread %x / buffer = %llx at cycle %d\n",
    201             __FUNCTION__ , hal_remote_lw( XPTR( th_cxy , &th_ptr->trdid ) ) ,
    202             buf_xp , hal_time_stamp() );
    203 
    204183            // exit the while
    205184            break;
    206185        }
    207         else   // deschedule if no slot available in SOCLIB_HBA
    208         {
    209             sched_yield();
    210         }
    211     }  // end while
     186        else   // no slot available in SOCLIB_HBA
     187        {
     188            if( cmd_type == IOC_SYNC_READ )     // fatal if synchronous access
     189            {
     190                printk("\n[PANIC] in %s : no slot available for a SYNC_READ\n", __FUNCTION__ );
     191                hal_core_sleep();
     192            }
     193            else                                // retry if asynchronous access.
     194            {
     195                sched_yield();
     196            }
     197        }
     198    }  // end while to get a slot
     199
     200    // waiting policy depends on the command type
     201
     202    if( cmd_type == IOC_SYNC_READ )                // polling, busy waiting
     203    {
     204        uint32_t  pxis;
     205        uint32_t  pxci;
     206        uint32_t  error;
     207        uint32_t  fault_id;
     208        while(1)
     209        {
     210            pxis     = hal_remote_lw( XPTR( hba_cxy , hba_ptr + HBA_PXIS_REG ) );
     211            pxci     = hal_remote_lw( XPTR( hba_cxy , hba_ptr + HBA_PXCI_REG ) );
     212            error    = (pxis & 0x40000000) >> 30;
     213            fault_id = (pxis & 0x1F000000) >> 24;
     214
     215            if( (pxci & (1<<cmd_id)) == 0 )  // completed
     216            {
     217                // release slot
     218                hba_active_slots &= ~(1<<cmd_id);
     219
     220                // set operation status in client thread command
     221                if( error && (fault_id == cmd_id) )
     222                {
     223                    hal_remote_sw( XPTR( th_cxy , &th_ptr->command.ioc.error ) , 1 );
     224                }
     225                else
     226                {
     227                    hal_remote_sw( XPTR( th_cxy , &th_ptr->command.ioc.error ) , 0 );
     228                }
     229
     230                // exit while
     231                break;
     232            }   
     233        }
     234    }
     235    else                                           // descheduling + IRQ
     236    {
     237        thread_block( CURRENT_THREAD , THREAD_BLOCKED_DEV_ISR );
     238        sched_yield();
     239    }
    212240           
    213241} // end soclib_hba_cmd()
     
    229257    uint32_t * hba_ptr  = (uint32_t *)GET_PTR( chdev->base );
    230258
    231     // get HBA_PXIS_REG and HBA_PXIS_REG current values
     259    // get HBA_PXIS_REG and HBA_PXCI_REG current values
    232260    uint32_t current_pxis = hal_remote_lw( XPTR( hba_cxy , hba_ptr + HBA_PXIS_REG ) );
    233261    uint32_t current_pxci = hal_remote_lw( XPTR( hba_cxy , hba_ptr + HBA_PXCI_REG ) );
  • trunk/kernel/drivers/soclib/soclib_hba.h

    r4 r23  
    145145 * @ xp_thread  : extended pointer on the client thread.
    146146 *******************************************************************************************/
    147 extern void soclib_hba_command( xptr_t  thread_xp );
     147extern void soclib_hba_cmd( xptr_t  thread_xp );
    148148
    149149/********************************************************************************************
Note: See TracChangeset for help on using the changeset viewer.