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

Introduce syscalls.

File:
1 moved

Legend:

Unmodified
Added
Removed
  • trunk/kernel/syscalls/sys_condvar.c

    r15 r23  
    11/*
    2  * sys_cond_var: interface to access condition vraibles service
     2 * sys_condvar.c - Access a POSIX condvar.
    33 *
    4  * Copyright (c) 2008,2009,2010,2011,2012 Ghassan Almaless
    5  * Copyright (c) 2011,2012 UPMC Sorbonne Universites
     4 * Author    Alain Greiner  (2016,2017)
    65 *
    7  * This file is part of ALMOS-kernel.
     6 * Copyright (c) UPMC Sorbonne Universites
    87 *
    9  * ALMOS-kernel is free software; you can redistribute it and/or modify it
     8 * This file is part of ALMOS-MKH.
     9 *
     10 * ALMOS-MKH is free software; you can redistribute it and/or modify it
    1011 * under the terms of the GNU General Public License as published by
    1112 * the Free Software Foundation; version 2.0 of the License.
    1213 *
    13  * ALMOS-kernel is distributed in the hope that it will be useful, but
     14 * ALMOS-MKH is distributed in the hope that it will be useful, but
    1415 * WITHOUT ANY WARRANTY; without even the implied warranty of
    1516 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
     
    1718 *
    1819 * You should have received a copy of the GNU General Public License
    19  * along with ALMOS-kernel; if not, write to the Free Software Foundation,
     20 * along with ALMOS-MKH; if not, write to the Free Software Foundation,
    2021 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
    2122 */
    2223
    23 #include <types.h>
     24#include <hal_types.h>
     25#include <hal_special.h>
    2426#include <errno.h>
    2527#include <thread.h>
    26 #include <kmem.h>
    27 #include <task.h>
     28#include <printk.h>
    2829#include <vmm.h>
    29 #include <kmagics.h>
    30 #include <semaphore.h>
    31 #include <cond_var.h>
     30#include <syscalls.h>
     31#include <remote_condvar.h>
    3232
    33 static inline bool_t isBadSem(struct semaphore_s *sem)
    34 {
    35         return vmm_check_object(sem, struct semaphore_s, SEMAPHORE_ID);
    36 }
     33////////////////////////////////////////
     34int sys_condvar( void         * condvar,
     35                 uint32_t       operation,
     36                 void         * mutex )
     37{
     38        error_t    error;
     39    paddr_t    paddr;
     40 
     41    thread_t * this = CURRENT_THREAD;
    3742
    38 static inline bool_t isBadCV(struct cv_s *cv)
    39 {
    40         return vmm_check_object(cv, struct cv_s, COND_VAR_ID);
    41 }
     43    // check condvar in user vspace
     44        error = vmm_v2p_translate( false , condvar , &paddr );
     45        if( error )
     46    {
     47        printk("\n[ERROR] in %s : illegal condvar virtual address = %x\n",
     48               __FUNCTION__ , (intptr_t)condvar );
     49        this->errno = error;
     50        return -1;
     51    }
    4252
    43 int sys_cond_var(struct cv_s **cv, uint_t operation, struct semaphore_s **sem)
    44 {
    45         kmem_req_t req;
    46         struct cv_s *icv;
    47         struct semaphore_s *isem;
    48         error_t err = EINVAL;
    49  
    50         if((err = vmm_check_address("usr cv ptr", current_task,cv,sizeof(struct cv_s*))))
    51                 goto SYS_COND_END;
     53    // execute requested operation
     54        switch( operation )
     55        {
     56        //////////////////
     57        case CONDVAR_INIT:
     58        {
     59            error = remote_condvar_create( (intptr_t)condvar );
     60   
     61                    if( error )
     62            {
     63                printk("\n[ERROR] in %s : cannot create condvar = %x\n",
     64                       __FUNCTION__ , (intptr_t)condvar );
     65                this->errno = error;
     66                return -1;
     67            }
     68                    break;
     69        }
     70        //////////////////
     71            case CONDVAR_WAIT:
     72        {
     73            // check mutex in user vspace
     74                error = vmm_v2p_translate( false , mutex , &paddr );
    5275
    53         if((err = cpu_copy_from_uspace(&icv, cv, sizeof(struct cv_s *))))
    54                 goto SYS_COND_END;
     76                if( error )
     77            {
     78                printk("\n[ERROR] in %s : illegal condvar virtual address = %x\n",
     79                       __FUNCTION__ , (intptr_t)condvar );
     80                this->errno = error;
     81                return -1;
     82            }
    5583
    56         switch(operation)
    57         {
    58         case CV_INIT:
    59                 req.type  = KMEM_CV;
    60                 req.size  = sizeof(*icv);
    61                 req.flags = AF_USER;
     84            xptr_t condvar_xp = remote_condvar_from_ident( (intptr_t)condvar );
     85
     86            if( condvar_xp == XPTR_NULL )     // user error
     87            {
     88                printk("\n[ERROR] in %s : condvar %x not registered\n",
     89                       __FUNCTION__ , (intptr_t)condvar );
     90                this->errno = EINVAL;
     91                return -1;
     92            }
    6293   
    63                 if((icv = kmem_alloc(&req)) == NULL)
    64                 {
    65                         err = ENOMEM;
    66                         break;
     94            xptr_t mutex_xp = remote_condvar_from_ident( (intptr_t)condvar );
     95            if( mutex_xp == XPTR_NULL )     // user error
     96            {
     97                printk("\n[ERROR] in %s : mutex %x not registered\n",
     98                       __FUNCTION__ , (intptr_t)condvar );
     99                this->errno = EINVAL;
     100                return -1;
     101            }
     102
     103            remote_condvar_wait( condvar_xp , mutex_xp );
     104
     105            break;
     106        }
     107        ////////////////////
     108            case CONDVAR_SIGNAL:
     109        {
     110            xptr_t condvar_xp = remote_condvar_from_ident( (intptr_t)condvar );
     111
     112            if( condvar_xp == XPTR_NULL )     // user error
     113            {
     114                printk("\n[ERROR] in %s : condvar %x not registered\n",
     115                       __FUNCTION__ , (intptr_t)condvar );
     116                this->errno = EINVAL;
     117                return -1;
     118            }
     119
     120            remote_condvar_signal( condvar_xp );
     121           
     122            break;
     123        }
     124        ///////////////////////
     125            case CONDVAR_BROADCAST:
     126        {
     127            xptr_t condvar_xp = remote_condvar_from_ident( (intptr_t)condvar );
     128
     129            if( condvar_xp == XPTR_NULL )     // user error
     130            {
     131                printk("\n[ERROR] in %s : condvar %x not registered\n",
     132                       __FUNCTION__ , (intptr_t)condvar );
     133                this->errno = EINVAL;
     134                return -1;
     135            }
     136
     137            remote_condvar_broadcast( condvar_xp );
     138
     139            break;
     140        }
     141        /////////////////////
     142            case CONDVAR_DESTROY:
     143        {
     144            xptr_t condvar_xp = remote_condvar_from_ident( (intptr_t)condvar );
     145
     146            if( condvar_xp == XPTR_NULL )     // user error
     147            {
     148                printk("\n[ERROR] in %s : condvar %x not registered\n",
     149                       __FUNCTION__ , (intptr_t)condvar );
     150                this->errno = EINVAL;
     151                return -1;
     152            }
     153
     154            remote_condvar_destroy( condvar_xp );
     155
     156            break;
    67157                }
    68    
    69                 if((err = cv_init(icv)))
    70                         break;
    71    
    72                 if((err = cpu_copy_to_uspace(cv, &icv, sizeof(struct cv_s *))))
    73                 {
    74                         req.ptr = icv;
    75                         kmem_free(&req);
    76                 }
     158        /////////
     159            default:
     160        {
     161            printk("\n[PANIC] in %s : illegal operation type\n", __FUNCTION__ );
     162            hal_core_sleep();
     163        }
     164        }   // end switch
    77165
    78                 break;
     166        return 0;
    79167
    80         case CV_WAIT:
    81                 err = vmm_check_address("usr sem ptr",
    82                                         current_task,
    83                                         sem, sizeof(struct semaphore_s*));
     168}  // enc sys_condvar()
    84169
    85                 if(err) break;
    86 
    87                 if((err = cpu_copy_from_uspace(&isem, sem, sizeof(struct semaphore_s *))))
    88                         break;
    89 
    90                 if(isBadSem(isem))
    91                         break;
    92 
    93                 if(isBadCV(icv))
    94                         break;
    95    
    96                 return cv_wait(icv, isem);
    97 
    98         case CV_SIGNAL:
    99                 if(isBadCV(icv))
    100                         break;
    101    
    102                 return cv_signal(icv);
    103 
    104         case CV_BROADCAST:
    105                 if(isBadCV(icv))
    106                         break;
    107    
    108                 return cv_broadcast(icv);
    109 
    110         case CV_DESTROY:
    111                 if(isBadCV(icv))
    112                         break;
    113    
    114                 if((err = cv_destroy(icv)))
    115                         break;
    116    
    117                 req.type = KMEM_CV;
    118                 req.ptr  = icv;
    119                 kmem_free(&req);
    120                 return 0;
    121 
    122         default:
    123                 err = EINVAL;
    124         }
    125 
    126 SYS_COND_END:
    127         current_thread->info.errno = err;
    128         return err;
    129 }
    130 
    131 KMEM_OBJATTR_INIT(cv_kmem_init)
    132 {
    133         attr->type   = KMEM_CV;
    134         attr->name   = "KCM Condition Variable";
    135         attr->size   = sizeof(struct cv_s);
    136         attr->aligne = 0;
    137         attr->min    = CONFIG_CONDTION_VAR_MIN;
    138         attr->max    = CONFIG_CONDTION_VAR_MAX;
    139         attr->ctor   = NULL;
    140         attr->dtor   = NULL;
    141  
    142         return 0;
    143 }
Note: See TracChangeset for help on using the changeset viewer.