The Design and Implementation of the FreeBSD Operating System, Second Edition
Now available: The Design and Implementation of the FreeBSD Operating System (Second Edition)


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]

FreeBSD/Linux Kernel Cross Reference
sys/tools/vnode_if.awk

Version: -  FREEBSD  -  FREEBSD-13-STABLE  -  FREEBSD-13-0  -  FREEBSD-12-STABLE  -  FREEBSD-12-0  -  FREEBSD-11-STABLE  -  FREEBSD-11-0  -  FREEBSD-10-STABLE  -  FREEBSD-10-0  -  FREEBSD-9-STABLE  -  FREEBSD-9-0  -  FREEBSD-8-STABLE  -  FREEBSD-8-0  -  FREEBSD-7-STABLE  -  FREEBSD-7-0  -  FREEBSD-6-STABLE  -  FREEBSD-6-0  -  FREEBSD-5-STABLE  -  FREEBSD-5-0  -  FREEBSD-4-STABLE  -  FREEBSD-3-STABLE  -  FREEBSD22  -  l41  -  OPENBSD  -  linux-2.6  -  MK84  -  PLAN9  -  xnu-8792 
SearchContext: -  none  -  3  -  10 

    1 #!/usr/bin/awk -f
    2 
    3 #-
    4 # Copyright (c) 1992, 1993
    5 #       The Regents of the University of California.  All rights reserved.
    6 #
    7 # Redistribution and use in source and binary forms, with or without
    8 # modification, are permitted provided that the following conditions
    9 # are met:
   10 # 1. Redistributions of source code must retain the above copyright
   11 #    notice, this list of conditions and the following disclaimer.
   12 # 2. Redistributions in binary form must reproduce the above copyright
   13 #    notice, this list of conditions and the following disclaimer in the
   14 #    documentation and/or other materials provided with the distribution.
   15 # 4. Neither the name of the University nor the names of its contributors
   16 #    may be used to endorse or promote products derived from this software
   17 #    without specific prior written permission.
   18 #
   19 # THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
   20 # ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
   21 # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
   22 # ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
   23 # FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
   24 # DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
   25 # OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
   26 # HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
   27 # LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
   28 # OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
   29 # SUCH DAMAGE.
   30 #
   31 #       @(#)vnode_if.sh 8.1 (Berkeley) 6/10/93
   32 # $FreeBSD$
   33 #
   34 # Script to produce VFS front-end sugar.
   35 #
   36 # usage: vnode_if.awk <srcfile> [-c | -h]
   37 #       (where <srcfile> is currently /sys/kern/vnode_if.src)
   38 #
   39 
   40 function usage()
   41 {
   42         print "usage: vnode_if.awk <srcfile> [-c|-h]";
   43         exit 1;
   44 }
   45 
   46 function die(msg, what)
   47 {
   48         printf msg "\n", what > "/dev/stderr";
   49         exit 1;
   50 }
   51 
   52 function t_spc(type)
   53 {
   54         # Append a space if the type is not a pointer
   55         return (type ~ /\*$/) ? type : type " ";
   56 }
   57 
   58 # These are just for convenience ...
   59 function printc(s) {print s > cfile;}
   60 function printh(s) {print s > hfile;}
   61 
   62 function add_debug_code(name, arg, pos)
   63 {
   64         if (arg == "vpp")
   65                 arg = "*vpp";
   66         if (lockdata[name, arg, pos] && (lockdata[name, arg, pos] != "-")) {
   67                 if (arg ~ /^\*/) {
   68                         printh("\tif ("substr(arg, 2)" != NULL) {");
   69                 }
   70                 printh("\tASSERT_VI_UNLOCKED("arg", \""uname"\");");
   71                 # Add assertions for locking
   72                 if (lockdata[name, arg, pos] == "L")
   73                         printh("\tASSERT_VOP_LOCKED("arg", \""uname"\");");
   74                 else if (lockdata[name, arg, pos] == "U")
   75                         printh("\tASSERT_VOP_UNLOCKED("arg", \""uname"\");");
   76                 else if (0) {
   77                         # XXX More checks!
   78                 }
   79                 if (arg ~ /^\*/) {
   80                         printh("\t}");
   81                 }
   82         }
   83 }
   84 
   85 function add_debug_pre(name)
   86 {
   87         if (lockdata[name, "pre"]) {
   88                 printh("#ifdef  DEBUG_VFS_LOCKS");
   89                 printh("\t"lockdata[name, "pre"]"(&a);");
   90                 printh("#endif");
   91         }
   92 }
   93 
   94 function add_debug_post(name)
   95 {
   96         if (lockdata[name, "post"]) {
   97                 printh("#ifdef  DEBUG_VFS_LOCKS");
   98                 printh("\t"lockdata[name, "post"]"(&a, rc);");
   99                 printh("#endif");
  100         }
  101 }
  102 
  103 function find_arg_with_type (type)
  104 {
  105         for (jj = 0; jj < numargs; jj++) {
  106                 if (types[jj] == type) {
  107                         return "VOPARG_OFFSETOF(struct " \
  108                             name "_args,a_" args[jj] ")";
  109                 }
  110         }
  111 
  112         return "VDESC_NO_OFFSET";
  113 }
  114 
  115 BEGIN{
  116 
  117 # Process the command line
  118 for (i = 1; i < ARGC; i++) {
  119         arg = ARGV[i];
  120         if (arg !~ /^-[ch]+$/ && arg !~ /\.src$/)
  121                 usage();
  122         if (arg ~ /^-.*c/)
  123                 cfile = "vnode_if.c";
  124         if (arg ~ /^-.*h/)
  125                 hfile = "vnode_if.h";
  126         if (arg ~ /\.src$/)
  127                 srcfile = arg;
  128 }
  129 ARGC = 1;
  130 
  131 if (!cfile && !hfile)
  132         exit 0;
  133 
  134 if (!srcfile)
  135         usage();
  136 
  137 common_head = \
  138     "/*\n" \
  139     " * This file is produced automatically.\n" \
  140     " * Do not modify anything in here by hand.\n" \
  141     " *\n" \
  142     " * Created from $FreeBSD$\n" \
  143     " */\n" \
  144     "\n";
  145 
  146 if (hfile)
  147         printh(common_head "extern struct vnodeop_desc vop_default_desc;");
  148 
  149 if (cfile) {
  150         printc(common_head \
  151             "#include <sys/param.h>\n" \
  152             "#include <sys/systm.h>\n" \
  153             "#include <sys/vnode.h>\n" \
  154             "\n" \
  155             "struct vnodeop_desc vop_default_desc = {\n" \
  156             "   1,\t\t\t/* special case, vop_default => 1 */\n" \
  157             "   \"default\",\n" \
  158             "   0,\n" \
  159             "   NULL,\n" \
  160             "   VDESC_NO_OFFSET,\n" \
  161             "   VDESC_NO_OFFSET,\n" \
  162             "   VDESC_NO_OFFSET,\n" \
  163             "   VDESC_NO_OFFSET,\n" \
  164             "   NULL,\n" \
  165             "};\n");
  166 }
  167 
  168 while ((getline < srcfile) > 0) {
  169         if (NF == 0)
  170                 continue;
  171         if ($1 ~ /^#%/) {
  172                 if (NF != 6  ||  $1 != "#%"  || \
  173                     $2 !~ /^[a-z]+$/  ||  $3 !~ /^[a-z]+$/  || \
  174                     $4 !~ /^.$/  ||  $5 !~ /^.$/  ||  $6 !~ /^.$/)
  175                         continue;
  176                 if ($3 == "vpp")
  177                         $3 = "*vpp";
  178                 lockdata["vop_" $2, $3, "Entry"] = $4;
  179                 lockdata["vop_" $2, $3, "OK"]    = $5;
  180                 lockdata["vop_" $2, $3, "Error"] = $6;                  
  181                 continue;
  182         }
  183 
  184         if ($1 ~ /^#!/) {
  185                 if (NF != 4 || $1 != "#!")
  186                         continue;
  187                 if ($3 != "pre" && $3 != "post")
  188                         continue;
  189                 lockdata["vop_" $2, $3] = $4;
  190                 continue;
  191         }
  192         if ($1 ~ /^#/)
  193                 continue;
  194 
  195         # Get the function name.
  196         name = $1;
  197         uname = toupper(name);
  198 
  199         # Start constructing a ktrpoint string
  200         ctrstr = "\"" uname;
  201         # Get the function arguments.
  202         for (numargs = 0; ; ++numargs) {
  203                 if ((getline < srcfile) <= 0) {
  204                         die("Unable to read through the arguments for \"%s\"",
  205                             name);
  206                 }
  207                 if ($1 ~ /^\};/)
  208                         break;
  209 
  210                 # Delete comments, if any.
  211                 gsub (/\/\*.*\*\//, "");
  212 
  213                 # Condense whitespace and delete leading/trailing space.
  214                 gsub(/[[:space:]]+/, " ");
  215                 sub(/^ /, "");
  216                 sub(/ $/, "");
  217 
  218                 # Pick off direction.
  219                 if ($1 != "INOUT" && $1 != "IN" && $1 != "OUT")
  220                         die("No IN/OUT direction for \"%s\".", $0);
  221                 dirs[numargs] = $1;
  222                 sub(/^[A-Z]* /, "");
  223 
  224                 if ((reles[numargs] = $1) == "WILLRELE")
  225                         sub(/^[A-Z]* /, "");
  226                 else
  227                         reles[numargs] = "WONTRELE";
  228 
  229                 # kill trailing ;
  230                 if (sub(/;$/, "") < 1)
  231                         die("Missing end-of-line ; in \"%s\".", $0);
  232 
  233                 # pick off variable name
  234                 if ((argp = match($0, /[A-Za-z0-9_]+$/)) < 1)
  235                         die("Missing var name \"a_foo\" in \"%s\".", $0);
  236                 args[numargs] = substr($0, argp);
  237                 $0 = substr($0, 1, argp - 1);
  238 
  239                 # what is left must be type
  240                 # remove trailing space (if any)
  241                 sub(/ $/, "");
  242                 types[numargs] = $0;
  243 
  244                 # We can do a maximum of 6 arguments to CTR*
  245                 if (numargs <= 6) {
  246                         if (numargs == 0)
  247                                 ctrstr = ctrstr "(" args[numargs];
  248                         else
  249                                 ctrstr = ctrstr ", " args[numargs];
  250                         if (types[numargs] ~ /\*/)
  251                                 ctrstr = ctrstr " 0x%lX";
  252                         else
  253                                 ctrstr = ctrstr " %ld";
  254                 }
  255         }
  256         if (numargs > 6)
  257                 ctrargs = 6;
  258         else
  259                 ctrargs = numargs;
  260         ctrstr = "\tCTR" ctrargs "(KTR_VOP, " ctrstr ")\"";
  261         for (i = 0; i < ctrargs; ++i)
  262                 ctrstr = ctrstr ", " args[i];
  263         ctrstr = ctrstr ");";
  264 
  265         if (hfile) {
  266                 # Print out the vop_F_args structure.
  267                 printh("struct "name"_args {\n\tstruct vnodeop_desc *a_desc;");
  268                 for (i = 0; i < numargs; ++i)
  269                         printh("\t" t_spc(types[i]) "a_" args[i] ";");
  270                 printh("};");
  271 
  272                 # Print out extern declaration.
  273                 printh("extern struct vnodeop_desc " name "_desc;");
  274 
  275                 # Print out function.
  276                 printh("static __inline int " uname "(");
  277                 for (i = 0; i < numargs; ++i) {
  278                         printh("\t" t_spc(types[i]) args[i] \
  279                             (i < numargs - 1 ? "," : ")"));
  280                 }
  281                 printh("{\n\tstruct " name "_args a;");
  282                 printh("\tint rc;");
  283                 printh("\ta.a_desc = VDESC(" name ");");
  284                 for (i = 0; i < numargs; ++i)
  285                         printh("\ta.a_" args[i] " = " args[i] ";");
  286                 for (i = 0; i < numargs; ++i)
  287                         add_debug_code(name, args[i], "Entry");
  288                 add_debug_pre(name);
  289                 printh("\trc = VCALL(" args[0] ", VOFFSET(" name "), &a);");
  290                 printh(ctrstr);
  291                 printh("if (rc == 0) {");
  292                 for (i = 0; i < numargs; ++i)
  293                         add_debug_code(name, args[i], "OK");
  294                 printh("} else {");
  295                 for (i = 0; i < numargs; ++i)
  296                         add_debug_code(name, args[i], "Error");
  297                 printh("}");
  298                 add_debug_post(name);
  299                 printh("\treturn (rc);\n}");
  300         }
  301 
  302         if (cfile) {
  303                 # Print out the vop_F_vp_offsets structure.  This all depends
  304                 # on naming conventions and nothing else.
  305                 printc("static int " name "_vp_offsets[] = {");
  306                 # as a side effect, figure out the releflags
  307                 releflags = "";
  308                 vpnum = 0;
  309                 for (i = 0; i < numargs; i++) {
  310                         if (types[i] == "struct vnode *") {
  311                                 printc("\tVOPARG_OFFSETOF(struct " name \
  312                                     "_args,a_" args[i] "),");
  313                                 if (reles[i] == "WILLRELE") {
  314                                         releflags = releflags \
  315                                             "|VDESC_VP" vpnum "_WILLRELE";
  316                                 }
  317                                 vpnum++;
  318                         }
  319                 }
  320 
  321                 sub(/^\|/, "", releflags);
  322                 printc("\tVDESC_NO_OFFSET");
  323                 printc("};");
  324 
  325                 # Print out the vnodeop_desc structure.
  326                 printc("struct vnodeop_desc " name "_desc = {");
  327                 # offset
  328                 printc("\t0,");
  329                 # printable name
  330                 printc("\t\"" name "\",");
  331                 # flags
  332                 vppwillrele = "";
  333                 for (i = 0; i < numargs; i++) {
  334                         if (types[i] == "struct vnode **" && \
  335                             reles[i] == "WILLRELE") {
  336                                 vppwillrele = "|VDESC_VPP_WILLRELE";
  337                         }
  338                 }
  339 
  340                 if (!releflags)
  341                         releflags = "0";
  342                 printc("\t" releflags vppwillrele ",");
  343 
  344                 # vp offsets
  345                 printc("\t" name "_vp_offsets,");
  346                 # vpp (if any)
  347                 printc("\t" find_arg_with_type("struct vnode **") ",");
  348                 # cred (if any)
  349                 printc("\t" find_arg_with_type("struct ucred *") ",");
  350                 # thread (if any)
  351                 printc("\t" find_arg_with_type("struct thread *") ",");
  352                 # componentname
  353                 printc("\t" find_arg_with_type("struct componentname *") ",");
  354                 # transport layer information
  355                 printc("\tNULL,\n};\n");
  356         }
  357 }
  358  
  359 if (hfile)
  360         close(hfile);
  361 if (cfile)
  362         close(cfile);
  363 close(srcfile);
  364 
  365 exit 0;
  366 
  367 }

Cache object: aa13ac179bd7dfb7596848bcca3f16e3


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]


This page is part of the FreeBSD/Linux Linux Kernel Cross-Reference, and was automatically generated using a modified version of the LXR engine.