Annotation of XNU/bsd/dev/ppc/systemcalls.c, revision 1.1.1.1

1.1       root        1: /*
                      2:  * Copyright (c) 2000 Apple Computer, Inc. All rights reserved.
                      3:  *
                      4:  * @APPLE_LICENSE_HEADER_START@
                      5:  * 
                      6:  * The contents of this file constitute Original Code as defined in and
                      7:  * are subject to the Apple Public Source License Version 1.1 (the
                      8:  * "License").  You may not use this file except in compliance with the
                      9:  * License.  Please obtain a copy of the License at
                     10:  * http://www.apple.com/publicsource and read it before using this file.
                     11:  * 
                     12:  * This Original Code and all software distributed under the License are
                     13:  * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER
                     14:  * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
                     15:  * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
                     16:  * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT.  Please see the
                     17:  * License for the specific language governing rights and limitations
                     18:  * under the License.
                     19:  * 
                     20:  * @APPLE_LICENSE_HEADER_END@
                     21:  */
                     22: /*
                     23:  * Copyright (c) 1997 Apple Computer, Inc.
                     24:  *
                     25:  * PowerPC Family:     System Call handlers.
                     26:  *
                     27:  * HISTORY
                     28:  * 27-July-97  A. Ramesh  
                     29:  *     Adopted for Common Core.
                     30:  */
                     31:  
                     32: #include <mach/mach_types.h>
                     33: #include <mach/error.h>
                     34: 
                     35: #include <kern/syscall_sw.h>
                     36: #include <kern/kdp.h>
                     37: 
                     38: #include <machdep/ppc/frame.h>
                     39: #include <machdep/ppc/thread.h>
                     40: #include <machdep/ppc/asm.h>
                     41: #include <machdep/ppc/proc_reg.h>
                     42: #include <machdep/ppc/trap.h>
                     43: #include <machdep/ppc/exception.h>
                     44: 
                     45: 
                     46: #define        ERESTART        -1              /* restart syscall */
                     47: #define        EJUSTRETURN     -2              /* don't modify regs, just return */
                     48: 
                     49: 
                     50: struct unix_syscallargs {
                     51:        int flavor;
                     52:        int r3;
                     53:        int arg1, arg2,arg3,arg4,arg5,arg6,arg7,arg8,arg9;
                     54: };
                     55: extern struct sysent {         /* system call table */
                     56:        int16_t         sy_narg;        /* number of args */
                     57:        int16_t         sy_parallel;/* can execute in parallel */
                     58:        int32_t         (*sy_call)();   /* implementing function */
                     59: } sysent[];
                     60: 
                     61: /*
                     62: ** Function:   unix_syscall
                     63: **
                     64: ** Inputs:     pcb     - pointer to Process Control Block
                     65: **             arg1    - arguments to mach system calls
                     66: **             arg2
                     67: **             arg3
                     68: **             arg4
                     69: **             arg5
                     70: **             arg6
                     71: **             arg7
                     72: **
                     73: ** Outputs:    none
                     74: */
                     75: void
                     76: unix_syscall(
                     77:     struct pcb * pcb,
                     78:     int arg1,
                     79:     int arg2,
                     80:     int arg3,
                     81:     int arg4,
                     82:     int arg5,
                     83:     int arg6,
                     84:     int arg7 
                     85:     )
                     86: {
                     87:     struct ppc_saved_state     *regs;
                     88:     thread_t                   thread;
                     89:     struct proc                        *p;
                     90:    struct sysent               *callp;
                     91:     int                                nargs, error;
                     92:     unsigned short             code;
                     93:     int                                rval[2];
                     94:        struct unix_syscallargs sarg;
                     95: 
                     96:     if (!USERMODE(pcb->ss.srr1))
                     97:        panic("unix_syscall");
                     98: 
                     99:     regs = &pcb->ss;
                    100:     thread = current_thread();
                    101: 
                    102: 
                    103:     /*
                    104:     ** Get index into sysent table
                    105:     */   
                    106:     code = regs->r0;
                    107: 
                    108:     
                    109:        /*
                    110:        ** Set up call pointer
                    111:        */
                    112:        callp = (code >= nsysent) ? &sysent[63] : &sysent[code];
                    113: 
                    114:        sarg. flavor = (callp == sysent): 1: 0;
                    115:        sarg. r3 = regs->r3;
                    116:        sarg. arg1 = arg1;
                    117:        sarg. arg2 = arg2;
                    118:        sarg. arg3 = arg3;
                    119:        sarg. arg4 = arg4;
                    120:        sarg. arg5 = arg5;
                    121:        sarg. arg6 = arg6;
                    122:        sarg. arg7 = arg7;
                    123: 
                    124:     set_bsduthreadargs(thread,pcb,&sarg);
                    125: 
                    126: 
                    127:        if (callp->sy_narg > 8)
                    128:        panic("unix_syscall: max arg count exceeded");
                    129: 
                    130:        rval[0] = 0;
                    131: 
                    132:        /* r4 is volatile, if we set it to regs->r4 here the child
                    133:         * will have parents r4 after execve */
                    134:        rval[1] = 0;
                    135: 
                    136:        error = 0; /* Start with a good value */
                    137: 
                    138:        /*
                    139:        ** the PPC runtime calls cerror after every unix system call, so
                    140:        ** assume no error and adjust the "pc" to skip this call.
                    141:        ** It will be set back to the cerror call if an error is detected.
                    142:        */
                    143:        regs->srr0 += 4;
                    144:        vt = get_bsduthreadarg(thread);
                    145:        p = ((struct proc *)get_bsdtask_info(current_task()));
                    146:        error = (*(callp->sy_call))(p, (caddr_t)vt, rval);
                    147: 
                    148:     if (error == ERESTART) {
                    149:        regs->srr0 -= 8;
                    150:     }
                    151:     else if (error != EJUSTRETURN) {
                    152:        if (error)
                    153:        {
                    154:            regs->r3 = error;
                    155:            /* set the "pc" to execute cerror routine */
                    156:            regs->srr0 -= 4;
                    157:        } else { /* (not error) */
                    158:            regs->r3 = rval[0];
                    159:            regs->r4 = rval[1];
                    160:        } 
                    161:     }
                    162:     /* else  (error == EJUSTRETURN) { nothing } */
                    163: 
                    164:     thread_exception_return();
                    165:     /* NOTREACHED */
                    166:        
                    167: }
                    168: 

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.