[BACK]Return to makesyscalls.sh CVS log [TXT][DIR] Up to [local] / sys / kern

Annotation of sys/kern/makesyscalls.sh, Revision 1.1.1.1

1.1       nbrk        1: #! /bin/sh -
                      2: #      $OpenBSD: makesyscalls.sh,v 1.10 2002/03/14 23:44:37 millert Exp $
                      3: #      $NetBSD: makesyscalls.sh,v 1.26 1998/01/09 06:17:51 thorpej Exp $
                      4: #
                      5: # Copyright (c) 1994,1996 Christopher G. Demetriou
                      6: # All rights reserved.
                      7: #
                      8: # Redistribution and use in source and binary forms, with or without
                      9: # modification, are permitted provided that the following conditions
                     10: # are met:
                     11: # 1. Redistributions of source code must retain the above copyright
                     12: #    notice, this list of conditions and the following disclaimer.
                     13: # 2. Redistributions in binary form must reproduce the above copyright
                     14: #    notice, this list of conditions and the following disclaimer in the
                     15: #    documentation and/or other materials provided with the distribution.
                     16: # 3. All advertising materials mentioning features or use of this software
                     17: #    must display the following acknowledgement:
                     18: #      This product includes software developed for the NetBSD Project
                     19: #      by Christopher G. Demetriou.
                     20: # 4. The name of the author may not be used to endorse or promote products
                     21: #    derived from this software without specific prior written permission
                     22: #
                     23: # THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
                     24: # IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
                     25: # OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
                     26: # IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
                     27: # INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
                     28: # NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
                     29: # DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
                     30: # THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
                     31: # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
                     32: # THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
                     33:
                     34: #      @(#)makesyscalls.sh     8.1 (Berkeley) 6/10/93
                     35:
                     36: set -e
                     37:
                     38: case $# in
                     39:     2) ;;
                     40:     *) echo "Usage: $0 config-file input-file" 1>&2
                     41:        exit 1
                     42:        ;;
                     43: esac
                     44:
                     45: # source the config file.
                     46: case $1 in
                     47:     /*)        . $1
                     48:        ;;
                     49:     *) . ./$1
                     50:        ;;
                     51: esac
                     52:
                     53: # the config file sets the following variables:
                     54: #      sysnames        the syscall names file
                     55: #      sysnumhdr       the syscall numbers file
                     56: #      syssw           the syscall switch file
                     57: #      sysarghdr       the syscall argument struct definitions
                     58: #      compatopts      those syscall types that are for 'compat' syscalls
                     59: #      switchname      the name for the 'struct sysent' we define
                     60: #      namesname       the name for the 'char *[]' we define
                     61: #      constprefix     the prefix for the system call constants
                     62: #
                     63: # NOTE THAT THIS makesyscalls.sh DOES NOT SUPPORT 'LIBCOMPAT'.
                     64:
                     65: # tmp files:
                     66: sysdcl="sysent.dcl"
                     67: sysprotos="sys.protos"
                     68: syscompat_pref="sysent."
                     69: sysent="sysent.switch"
                     70:
                     71: trap "rm $sysdcl $sysprotos $sysent" 0
                     72:
                     73: # Awk program (must support nawk extensions)
                     74: # Use "awk" at Berkeley, "nawk" or "gawk" elsewhere.
                     75: awk=${AWK:-awk}
                     76:
                     77: # Does this awk have a "toupper" function? (i.e. is it GNU awk)
                     78: isgawk=`$awk 'BEGIN { print toupper("true"); exit; }' 2>/dev/null`
                     79:
                     80: # If this awk does not define "toupper" then define our own.
                     81: if [ "$isgawk" = TRUE ] ; then
                     82:        # GNU awk provides it.
                     83:        toupper=
                     84: else
                     85:        # Provide our own toupper()
                     86:        toupper='
                     87: function toupper(str) {
                     88:        _toupper_cmd = "echo "str" |tr a-z A-Z"
                     89:        _toupper_cmd | getline _toupper_str;
                     90:        close(_toupper_cmd);
                     91:        return _toupper_str;
                     92: }'
                     93: fi
                     94:
                     95: # before handing it off to awk, make a few adjustments:
                     96: #      (1) insert spaces around {, }, (, ), *, and commas.
                     97: #      (2) get rid of any and all dollar signs (so that rcs id use safe)
                     98: #
                     99: # The awk script will deal with blank lines and lines that
                    100: # start with the comment character (';').
                    101:
                    102: sed -e '
                    103: s/\$//g
                    104: :join
                    105:        /\\$/{a\
                    106:
                    107:        N
                    108:        s/\\\n//
                    109:        b join
                    110:        }
                    111: 2,${
                    112:        /^#/!s/\([{}()*,]\)/ \1 /g
                    113: }
                    114: ' < $2 | $awk "
                    115: $toupper
                    116: BEGIN {
                    117:        # to allow nested #if/#else/#endif sets
                    118:        savedepth = 0
                    119:
                    120:        sysnames = \"$sysnames\"
                    121:        sysprotos = \"$sysprotos\"
                    122:        sysnumhdr = \"$sysnumhdr\"
                    123:        sysarghdr = \"$sysarghdr\"
                    124:        switchname = \"$switchname\"
                    125:        namesname = \"$namesname\"
                    126:        constprefix = \"$constprefix\"
                    127:
                    128:        sysdcl = \"$sysdcl\"
                    129:        syscompat_pref = \"$syscompat_pref\"
                    130:        sysent = \"$sysent\"
                    131:        infile = \"$2\"
                    132:
                    133:        compatopts = \"$compatopts\"
                    134:        "'
                    135:
                    136:        printf "/*\t\$OpenBSD\$\t*/\n\n" > sysdcl
                    137:        printf "/*\n * System call switch table.\n *\n" > sysdcl
                    138:        printf " * DO NOT EDIT-- this file is automatically generated.\n" > sysdcl
                    139:
                    140:        ncompat = split(compatopts,compat)
                    141:        for (i = 1; i <= ncompat; i++) {
                    142:                compat_upper[i] = toupper(compat[i])
                    143:
                    144:                printf "\n#ifdef %s\n", compat_upper[i] > sysent
                    145:                printf "#define %s(func) __CONCAT(%s_,func)\n", compat[i], \
                    146:                    compat[i] > sysent
                    147:                printf "#else\n" > sysent
                    148:                printf "#define %s(func) sys_nosys\n", compat[i] > sysent
                    149:                printf "#endif\n" > sysent
                    150:        }
                    151:
                    152:        printf "\n#define\ts(type)\tsizeof(type)\n\n" > sysent
                    153:        printf "struct sysent %s[] = {\n",switchname > sysent
                    154:
                    155:        printf "/*\t\$OpenBSD\$\t*/\n\n" > sysnames
                    156:        printf "/*\n * System call names.\n *\n" > sysnames
                    157:        printf " * DO NOT EDIT-- this file is automatically generated.\n" > sysnames
                    158:
                    159:        printf "\n/*\n * System call prototypes.\n */\n\n" > sysprotos
                    160:
                    161:        printf "/*\t\$OpenBSD\$\t*/\n\n" > sysnumhdr
                    162:        printf "/*\n * System call numbers.\n *\n" > sysnumhdr
                    163:        printf " * DO NOT EDIT-- this file is automatically generated.\n" > sysnumhdr
                    164:
                    165:        printf "/*\t\$OpenBSD\$\t*/\n\n" > sysarghdr
                    166:        printf "/*\n * System call argument lists.\n *\n" > sysarghdr
                    167:        printf " * DO NOT EDIT-- this file is automatically generated.\n" > sysarghdr
                    168: }
                    169: NR == 1 {
                    170:        printf " * created from%s\n */\n\n", $0 > sysdcl
                    171:
                    172:        printf " * created from%s\n */\n\n", $0 > sysnames
                    173:        printf "char *%s[] = {\n",namesname > sysnames
                    174:
                    175:        printf " * created from%s\n */\n\n", $0 > sysnumhdr
                    176:
                    177:        printf " * created from%s\n */\n\n", $0 > sysarghdr
                    178:        printf "#ifdef\tsyscallarg\n" > sysarghdr
                    179:        printf "#undef\tsyscallarg\n" > sysarghdr
                    180:        printf "#endif\n\n" > sysarghdr
                    181:        printf "#define\tsyscallarg(x)\t\t\t\t\t\t\t\\\n" > sysarghdr
                    182:        printf "\tunion {\t\t\t\t\t\t\t\t\\\n" > sysarghdr
                    183:        printf "\t\tregister_t pad;\t\t\t\t\t\t\\\n" > sysarghdr
                    184:        printf "\t\tstruct { x datum; } le;\t\t\t\t\t\\\n" > sysarghdr
                    185:        printf "\t\tstruct {\t\t\t\t\t\t\\\n" > sysarghdr
                    186:        printf "\t\t\tint8_t pad[ (sizeof (register_t) < sizeof (x))\t\\\n" \
                    187:                > sysarghdr
                    188:        printf "\t\t\t\t? 0\t\t\t\t\t\\\n" > sysarghdr
                    189:        printf "\t\t\t\t: sizeof (register_t) - sizeof (x)];\t\\\n" \
                    190:                > sysarghdr
                    191:        printf "\t\t\tx datum;\t\t\t\t\t\\\n" > sysarghdr
                    192:        printf "\t\t} be;\t\t\t\t\t\t\t\\\n" > sysarghdr
                    193:        printf "\t}\n" > sysarghdr
                    194:        next
                    195: }
                    196: NF == 0 || $1 ~ /^;/ {
                    197:        next
                    198: }
                    199: $1 ~ /^#[      ]*include/ {
                    200:        print > sysdcl
                    201:        next
                    202: }
                    203: $1 ~ /^#[      ]*if/ {
                    204:        print > sysent
                    205:        print > sysprotos
                    206:        print > sysnames
                    207:        savesyscall[++savedepth] = syscall
                    208:        next
                    209: }
                    210: $1 ~ /^#[      ]*else/ {
                    211:        print > sysent
                    212:        print > sysprotos
                    213:        print > sysnames
                    214:        if (savedepth <= 0) {
                    215:                printf "%s: line %d: unbalenced #else\n", \
                    216:                    infile, NR
                    217:                exit 1
                    218:        }
                    219:        syscall = savesyscall[savedepth]
                    220:        next
                    221: }
                    222: $1 ~ /^#/ {
                    223:        if ($1 ~ /^#[       ]*endif/) {
                    224:                if (savedepth <= 0) {
                    225:                        printf "%s: line %d: unbalenced #endif\n", \
                    226:                            infile, NR
                    227:                        exit 1
                    228:                }
                    229:                savedepth--;
                    230:        }
                    231:        print > sysent
                    232:        print > sysprotos
                    233:        print > sysnames
                    234:        next
                    235: }
                    236: syscall != $1 {
                    237:        printf "%s: line %d: syscall number out of sync at %d\n", \
                    238:           infile, NR, syscall
                    239:        printf "line is:\n"
                    240:        print
                    241:        exit 1
                    242: }
                    243: function parserr(was, wanted) {
                    244:        printf "%s: line %d: unexpected %s (expected %s)\n", \
                    245:            infile, NR, was, wanted
                    246:        exit 1
                    247: }
                    248: function parseline() {
                    249:        f=3                     # toss number and type
                    250:        if ($NF != "}") {
                    251:                funcalias=$NF
                    252:                end=NF-1
                    253:        } else {
                    254:                funcalias=""
                    255:                end=NF
                    256:        }
                    257:        if ($f ~ /^[a-z0-9_]*$/) {      # allow syscall alias
                    258:                funcalias=$f
                    259:                f++
                    260:        }
                    261:        if ($f != "{")
                    262:                parserr($f, "{")
                    263:        f++
                    264:        if ($end != "}")
                    265:                parserr($end, "}")
                    266:        end--
                    267:        if ($end != ";")
                    268:                parserr($end, ";")
                    269:        end--
                    270:        if ($end != ")")
                    271:                parserr($end, ")")
                    272:        end--
                    273:
                    274:        returntype = oldf = "";
                    275:        do {
                    276:                if (returntype != "" && oldf != "*")
                    277:                        returntype = returntype" ";
                    278:                returntype = returntype$f;
                    279:                oldf = $f;
                    280:                f++
                    281:        } while (f < (end - 1) && $(f+1) != "(");
                    282:        if (f == (end - 1)) {
                    283:                parserr($f, "function argument definition (maybe \"(\"?)");
                    284:        }
                    285:
                    286:        funcname=$f
                    287:        if (funcalias == "") {
                    288:                funcalias=funcname
                    289:                sub(/^([^_]+_)*sys_/, "", funcalias)
                    290:        }
                    291:        f++
                    292:
                    293:        if ($f != "(")
                    294:                parserr($f, ")")
                    295:        f++
                    296:
                    297:        argc=0;
                    298:        if (f == end) {
                    299:                if ($f != "void")
                    300:                        parserr($f, "argument definition")
                    301:                isvarargs = 0;
                    302:                varargc = 0;
                    303:                return
                    304:        }
                    305:
                    306:        # some system calls (open() and fcntl()) can accept a variable
                    307:        # number of arguments.  If syscalls accept a variable number of
                    308:        # arguments, they must still have arguments specified for
                    309:        # the remaining argument "positions," because of the way the
                    310:        # kernel system call argument handling works.
                    311:        #
                    312:        # Indirect system calls, e.g. syscall(), are exceptions to this
                    313:        # rule, since they are handled entirely by machine-dependent code
                    314:        # and do not need argument structures built.
                    315:
                    316:        isvarargs = 0;
                    317:        while (f <= end) {
                    318:                if ($f == "...") {
                    319:                        f++;
                    320:                        isvarargs = 1;
                    321:                        varargc = argc;
                    322:                        continue;
                    323:                }
                    324:                argc++
                    325:                argtype[argc]=""
                    326:                oldf=""
                    327:                while (f < end && $(f+1) != ",") {
                    328:                        if (argtype[argc] != "" && oldf != "*")
                    329:                                argtype[argc] = argtype[argc]" ";
                    330:                        argtype[argc] = argtype[argc]$f;
                    331:                        oldf = $f;
                    332:                        f++
                    333:                }
                    334:                if (argtype[argc] == "")
                    335:                        parserr($f, "argument definition")
                    336:                argname[argc]=$f;
                    337:                f += 2;                 # skip name, and any comma
                    338:        }
                    339:        # must see another argument after varargs notice.
                    340:        if (isvarargs) {
                    341:                if (argc == varargc && $2 != "INDIR")
                    342:                        parserr($f, "argument definition")
                    343:        } else
                    344:                varargc = argc;
                    345: }
                    346: function putent(nodefs, compatwrap) {
                    347:        # output syscall declaration for switch table.  INDIR functions
                    348:        # get none, since they always have sys_nosys() for their table
                    349:        # entries.
                    350:        if (nodefs != "INDIR") {
                    351:                prototype = "(struct proc *, void *, register_t *)"
                    352:                if (compatwrap == "")
                    353:                        printf("int\t%s%s;\n", funcname,
                    354:                            prototype) > sysprotos
                    355:                else
                    356:                        printf("int\t%s_%s%s;\n", compatwrap, funcname,
                    357:                            prototype) > sysprotos
                    358:        }
                    359:
                    360:        # output syscall switch entry
                    361:        if (nodefs == "INDIR") {
                    362:                printf("\t{ 0, 0,\n\t    sys_nosys },\t\t\t/* %d = %s (indir) */\n", \
                    363:                    syscall, funcalias) > sysent
                    364:        } else {
                    365: #              printf("\t{ { %d", argc) > sysent
                    366: #              for (i = 1; i <= argc; i++) {
                    367: #                      if (i == 5)             # wrap the line
                    368: #                              printf(",\n\t    ") > sysent
                    369: #                      else
                    370: #                              printf(", ") > sysent
                    371: #                      printf("s(%s)", argtypenospc[i]) > sysent
                    372: #              }
                    373:                printf("\t{ %d, ", argc) > sysent
                    374:                if (argc == 0)
                    375:                        printf("0") > sysent
                    376:                else if (compatwrap == "")
                    377:                        printf("s(struct %s_args)", funcname) > sysent
                    378:                else
                    379:                        printf("s(struct %s_%s_args)", compatwrap,
                    380:                            funcname) > sysent
                    381:                if (compatwrap == "")
                    382:                        wfn = sprintf("%s", funcname);
                    383:                else
                    384:                        wfn = sprintf("%s(%s)", compatwrap, funcname);
                    385:                printf(",\n\t    %s },", wfn) > sysent
                    386:                for (i = 0; i < (33 - length(wfn)) / 8; i++)
                    387:                        printf("\t") > sysent
                    388:                if (compatwrap == "")
                    389:                        printf("/* %d = %s */\n", syscall, funcalias) > sysent
                    390:                else
                    391:                        printf("/* %d = %s %s */\n", syscall, compatwrap,
                    392:                            funcalias) > sysent
                    393:        }
                    394:
                    395:        # output syscall name for names table
                    396:        if (compatwrap == "")
                    397:                printf("\t\"%s\",\t\t\t/* %d = %s */\n", funcalias, syscall,
                    398:                    funcalias) > sysnames
                    399:        else
                    400:                printf("\t\"%s_%s\",\t/* %d = %s %s */\n", compatwrap,
                    401:                    funcalias, syscall, compatwrap, funcalias) > sysnames
                    402:
                    403:        # output syscall number of header, if appropriate
                    404:        if (nodefs == "" || nodefs == "NOARGS" || nodefs == "INDIR") {
                    405:                # output a prototype, to be used to generate lint stubs in
                    406:                # libc.
                    407:                printf("/* syscall: \"%s\" ret: \"%s\" args:", funcalias,
                    408:                    returntype) > sysnumhdr
                    409:                for (i = 1; i <= varargc; i++)
                    410:                        printf(" \"%s\"", argtype[i]) > sysnumhdr
                    411:                if (isvarargs)
                    412:                        printf(" \"...\"") > sysnumhdr
                    413:                printf(" */\n") > sysnumhdr
                    414:
                    415:                printf("#define\t%s%s\t%d\n\n", constprefix, funcalias,
                    416:                    syscall) > sysnumhdr
                    417:        } else if (nodefs != "NODEF")
                    418:                printf("\t\t\t\t/* %d is %s %s */\n\n", syscall,
                    419:                    compatwrap, funcalias) > sysnumhdr
                    420:
                    421:        # output syscall argument structure, if it has arguments
                    422:        if (argc != 0 && nodefs != "NOARGS" && nodefs != "INDIR") {
                    423:                if (compatwrap == "")
                    424:                        printf("\nstruct %s_args {\n", funcname) > sysarghdr
                    425:                else
                    426:                        printf("\nstruct %s_%s_args {\n", compatwrap,
                    427:                            funcname) > sysarghdr
                    428:                for (i = 1; i <= argc; i++)
                    429:                        printf("\tsyscallarg(%s) %s;\n", argtype[i],
                    430:                            argname[i]) > sysarghdr
                    431:                printf("};\n") > sysarghdr
                    432:        }
                    433: }
                    434: $2 == "STD" {
                    435:        parseline()
                    436:        putent("", "");
                    437:        syscall++
                    438:        next
                    439: }
                    440: $2 == "NODEF" || $2 == "NOARGS" || $2 == "INDIR" {
                    441:        parseline()
                    442:        putent($2, "")
                    443:        syscall++
                    444:        next
                    445: }
                    446: $2 == "OBSOL" || $2 == "UNIMPL" {
                    447:        if ($2 == "OBSOL")
                    448:                comment="obsolete"
                    449:        else
                    450:                comment="unimplemented"
                    451:        for (i = 3; i <= NF; i++)
                    452:                comment=comment " " $i
                    453:
                    454:        printf("\t{ 0, 0,\n\t    sys_nosys },\t\t\t/* %d = %s */\n", \
                    455:            syscall, comment) > sysent
                    456:        printf("\t\"#%d (%s)\",\t\t/* %d = %s */\n", \
                    457:            syscall, comment, syscall, comment) > sysnames
                    458:        if ($2 != "UNIMPL")
                    459:                printf("\t\t\t\t/* %d is %s */\n", syscall, comment) > sysnumhdr
                    460:        syscall++
                    461:        next
                    462: }
                    463: {
                    464:        for (i = 1; i <= ncompat; i++) {
                    465:                if ($2 == compat_upper[i]) {
                    466:                        parseline();
                    467:                        putent("COMMENT", compat[i])
                    468:                        syscall++
                    469:                        next
                    470:                }
                    471:        }
                    472:        printf "%s: line %d: unrecognized keyword %s\n", infile, NR, $2
                    473:        exit 1
                    474: }
                    475: END {
                    476:        printf("};\n\n") > sysent
                    477:        printf("};\n") > sysnames
                    478:        printf("#define\t%sMAXSYSCALL\t%d\n", constprefix, syscall) > sysnumhdr
                    479: } '
                    480:
                    481: cat $sysprotos >> $sysarghdr
                    482: cat $sysdcl $sysent > $syssw
                    483:
                    484: #chmod 444 $sysnames $sysnumhdr $syssw

CVSweb