1#! /bin/sh 2# $NetBSD: mknodes.sh,v 1.4 2019/01/19 13:08:50 kre Exp $ 3 4# Copyright (c) 2003 The NetBSD Foundation, Inc. 5# All rights reserved. 6# 7# This code is derived from software contributed to The NetBSD Foundation 8# by David Laight. 9# 10# Redistribution and use in source and binary forms, with or without 11# modification, are permitted provided that the following conditions 12# are met: 13# 1. Redistributions of source code must retain the above copyright 14# notice, this list of conditions and the following disclaimer. 15# 2. Redistributions in binary form must reproduce the above copyright 16# notice, this list of conditions and the following disclaimer in the 17# documentation and/or other materials provided with the distribution. 18# 19# THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 20# ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 21# TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 22# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 23# BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 24# CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 25# SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 26# INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 27# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 28# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 29# POSSIBILITY OF SUCH DAMAGE. 30 31nodetypes=$1 32nodes_pat=$2 33objdir="$3" 34 35exec <$nodetypes 36exec >$objdir/nodes.h.tmp 37 38echo "/*" 39echo " * This file was generated by mknodes.sh" 40echo " */" 41echo 42 43tagno=0 44while IFS=; read -r line; do 45 line="${line%%#*}" 46 IFS=' ' 47 set -- $line 48 IFS= 49 [ -z "$2" ] && continue 50 case "$line" in 51 [" "]* ) 52 IFS=' ' 53 [ $field = 0 ] && struct_list="$struct_list $struct" 54 eval field_${struct}_$field=\"\$*\" 55 eval numfld_$struct=\$field 56 field=$(($field + 1)) 57 ;; 58 * ) 59 define=$1 60 struct=$2 61 echo "#define $define $tagno" 62 tagno=$(($tagno + 1)) 63 eval define_$struct=\"\$define_$struct \$define\" 64 struct_define="$struct_define $struct" 65 field=0 66 ;; 67 esac 68done 69 70echo 71 72IFS=' ' 73for struct in $struct_list; do 74 echo 75 echo 76 echo "struct $struct {" 77 field=0 78 while 79 eval line=\"\$field_${struct}_$field\" 80 field=$(($field + 1)) 81 [ -n "$line" ] 82 do 83 IFS=' ' 84 set -- $line 85 name=$1 86 case "$name" in 87 type) if [ -n "$typetype" ] && [ "$typetype" != "$2" ] 88 then 89 echo >&2 "Conflicting type fields: node" \ 90 "$struct has $2, others $typetype" 91 exit 1 92 fi 93 if [ $field -ne 1 ] 94 then 95 echo >&2 "Node $struct has type as field" \ 96 "$field (should only be first)" 97 exit 1 98 fi 99 typetype=$2 100 ;; 101 *) 102 if [ $field -eq 1 ] 103 then 104 echo >&2 "Node $struct does not have" \ 105 "type as first field" 106 exit 1 107 fi 108 ;; 109 esac 110 case $2 in 111 nodeptr ) type="union node *";; 112 nodelist ) type="struct nodelist *";; 113 string ) type="char *";; 114 int*_t | uint*_t | int ) type="$2 ";; 115 * ) name=; shift 2; type="$*";; 116 esac 117 echo " $type$name;" 118 done 119 echo "};" 120done 121 122echo 123echo 124echo "union node {" 125echo " $typetype type;" 126for struct in $struct_list; do 127 echo " struct $struct $struct;" 128done 129echo "};" 130echo 131echo 132echo "struct nodelist {" 133echo " struct nodelist *next;" 134echo " union node *n;" 135echo "};" 136echo 137echo 138echo 'struct funcdef;' 139echo 'struct funcdef *copyfunc(union node *);' 140echo 'union node *getfuncnode(struct funcdef *);' 141echo 'void reffunc(struct funcdef *);' 142echo 'void unreffunc(struct funcdef *);' 143echo 'void freefunc(struct funcdef *);' 144 145mv $objdir/nodes.h.tmp $objdir/nodes.h || exit 1 146 147exec <$nodes_pat 148exec >$objdir/nodes.c.tmp 149 150echo "/*" 151echo " * This file was generated by mknodes.sh" 152echo " */" 153echo 154 155while IFS=; read -r line; do 156 IFS=' ' 157 set -- $line 158 IFS= 159 case "$1" in 160 '%SIZES' ) 161 echo "static const short nodesize[$tagno] = {" 162 IFS=' ' 163 for struct in $struct_define; do 164 echo " SHELL_ALIGN(sizeof (struct $struct))," 165 done 166 echo "};" 167 ;; 168 '%CALCSIZE' ) 169 echo " if (n == NULL)" 170 echo " return;" 171 echo " res->bsize += nodesize[n->type];" 172 echo " switch (n->type) {" 173 IFS=' ' 174 for struct in $struct_list; do 175 eval defines=\"\$define_$struct\" 176 for define in $defines; do 177 echo " case $define:" 178 done 179 eval field=\$numfld_$struct 180 while 181 [ $field != 0 ] 182 do 183 eval line=\"\$field_${struct}_$field\" 184 field=$(($field - 1)) 185 IFS=' ' 186 set -- $line 187 name=$1 188 cl=", res)" 189 case $2 in 190 nodeptr ) fn=calcsize;; 191 nodelist ) fn=sizenodelist;; 192 string ) fn="res->ssize += strlen" 193 cl=") + 1";; 194 * ) continue;; 195 esac 196 echo " ${fn}(n->$struct.$name${cl};" 197 done 198 echo " break;" 199 done 200 echo " };" 201 ;; 202 '%COPY' ) 203 echo " if (n == NULL)" 204 echo " return NULL;" 205 echo " new = st->block;" 206 echo " st->block = (char *) st->block + nodesize[n->type];" 207 echo " switch (n->type) {" 208 IFS=' ' 209 for struct in $struct_list; do 210 eval defines=\"\$define_$struct\" 211 for define in $defines; do 212 echo " case $define:" 213 done 214 eval field=\$numfld_$struct 215 while 216 [ $field != 0 ] 217 do 218 eval line=\"\$field_${struct}_$field\" 219 field=$(($field - 1)) 220 IFS=' ' 221 set -- $line 222 name=$1 223 case $2 in 224 nodeptr ) fn="copynode(";; 225 nodelist ) fn="copynodelist(";; 226 string ) fn="nodesavestr(";; 227 int*_t| uint*_t | int ) fn=;; 228 * ) continue;; 229 esac 230 f="$struct.$name" 231 echo " new->$f = ${fn}n->$f${fn:+, st)};" 232 done 233 echo " break;" 234 done 235 echo " };" 236 echo " new->type = n->type;" 237 ;; 238 * ) echo "$line";; 239 esac 240done 241 242mv $objdir/nodes.c.tmp $objdir/nodes.c || exit 1 243