Home | History | Annotate | Line # | Download | only in sh
mkoptions.sh revision 1.2
      1  1.1  kre #! /bin/sh
      2  1.1  kre 
      3  1.2  kre # $NetBSD: mkoptions.sh,v 1.2 2017/05/28 14:14:22 kre Exp $
      4  1.1  kre 
      5  1.1  kre #
      6  1.1  kre # It would be more sensible to generate 2 .h files, one which
      7  1.1  kre # is for everyone to use, defines the "variables" and (perhaps) generates
      8  1.1  kre # the externs (though they could just be explicit in options.h)
      9  1.1  kre # and one just for options.c which generates the initialisation.
     10  1.1  kre #
     11  1.1  kre # But then I'd have to deal with making the Makefile handle that properly...
     12  1.1  kre # (this is simpler there, and it just means a bit more sh compile time.)
     13  1.1  kre 
     14  1.1  kre set -f
     15  1.1  kre IFS=' 	'	# blank, tab (no newline)
     16  1.1  kre 
     17  1.1  kre IF="$1"
     18  1.1  kre OF="${3+$3/}$2"
     19  1.1  kre 
     20  1.2  kre E_FILE=$(${MKTEMP:-mktemp} -t MKO.E.$$)
     21  1.2  kre O_FILE=$(${MKTEMP:-mktemp} -t MKO.O.$$)
     22  1.2  kre trap 'rm -f "${E_FILE}" "${O_FILE}"' EXIT
     23  1.2  kre 
     24  1.2  kre exec 5> "${E_FILE}"
     25  1.2  kre exec 6> "${O_FILE}"
     26  1.2  kre 
     27  1.1  kre {
     28  1.1  kre 	printf '/*\n * File automatically generated by %s.\n' "$0"
     29  1.1  kre 	printf ' * Do not edit, do not add to cvs.\n'
     30  1.1  kre 	printf ' */\n\n'
     31  1.1  kre 
     32  1.1  kre 	printf '#ifdef DEFINE_OPTIONS\n'
     33  1.1  kre 	printf 'struct optent optlist[] = {\n'
     34  1.1  kre } >"${OF}"
     35  1.1  kre 
     36  1.1  kre FIRST=true
     37  1.1  kre 
     38  1.2  kre ${SED:-sed} <"${IF}"			\
     39  1.2  kre 	-e '/^$/d'			\
     40  1.2  kre 	-e '/^#/d'			\
     41  1.2  kre 	-e '/^[ 	]*\//d'		\
     42  1.2  kre 	-e '/^[ 	]*\*/d'		\
     43  1.2  kre 	-e '/^[ 	]*;/d'			|
     44  1.2  kre sort -k2,2f -k2,2r < "${IF}"			|
     45  1.1  kre while read line
     46  1.1  kre do
     47  1.1  kre 	# Look for comments in various styles, and ignore them
     48  1.2  kre 	# (these should generally be already removed by sed above)
     49  1.1  kre 
     50  1.1  kre 	case "${line}" in
     51  1.1  kre 	'')	continue;;
     52  1.1  kre 	/*)	continue;;
     53  1.1  kre 	\**)	continue;;
     54  1.1  kre 	\;*)	continue;;
     55  1.2  kre 	\#*)	continue;;
     56  1.1  kre 	esac
     57  1.1  kre 
     58  1.2  kre 	case "${line}" in
     59  1.2  kre 	*'#if'*)
     60  1.2  kre 		COND="${line#*#}"
     61  1.2  kre 		COND="#${COND%%#*}"
     62  1.2  kre 		;;
     63  1.2  kre 	*)
     64  1.2  kre 		COND=
     65  1.2  kre 		;;
     66  1.2  kre 	esac
     67  1.1  kre 	set -- ${line%%[ 	]#*}
     68  1.1  kre 
     69  1.1  kre 	var="$1" name="$2"
     70  1.1  kre 
     71  1.1  kre 	case "${var}" in
     72  1.1  kre 	('' | [!A-Za-z_]* | *[!A-Za-z0-9_]*)
     73  1.1  kre 		printf >&2 "Bad var name: '%s'\\n" "${var}"
     74  1.1  kre 		# exit 1
     75  1.1  kre 		continue	# just ignore it for now
     76  1.1  kre 	esac
     77  1.1  kre 
     78  1.1  kre 	case "${name}" in
     79  1.1  kre 	?) 	set -- ${var} '' $name $3 $4; name= ;;
     80  1.1  kre 	esac
     81  1.1  kre 
     82  1.1  kre 	chr="$3" set="$4" dflt="$5"
     83  1.1  kre 
     84  1.1  kre 	case "${chr}" in
     85  1.1  kre 	-)	chr= set= dflt="$4";;
     86  1.1  kre 	''|?)	;;
     87  1.1  kre 	*)	printf >&2 'flag "%s": Not a character\n' "${chr}"; continue;;
     88  1.1  kre 	esac
     89  1.1  kre 
     90  1.1  kre 	# options must have some kind of name, or they are useless...
     91  1.1  kre 	test -z "${name}${chr}" && continue
     92  1.1  kre 
     93  1.1  kre 	case "${set}" in
     94  1.1  kre 	-)	set= ;;
     95  1.2  kre 	[01] | [Oo][Nn] | [Oo][Ff][Ff])	dflt="${set}"; set= ;;
     96  1.1  kre 	''|?)	;;
     97  1.1  kre 	*)	printf >&2 'set "%s": Not a character\n' "${set}"; continue;;
     98  1.1  kre 	esac
     99  1.1  kre 
    100  1.2  kre 	case "${dflt}" in
    101  1.2  kre 	'')		;;
    102  1.2  kre 	[Oo][Nn])	dflt=1;;
    103  1.2  kre 	[Oo][Ff][Ff])	dflt=0;;
    104  1.2  kre 	[01])		;;
    105  1.2  kre 	*)	printf >&2 'default "%s" invalid, use 0 off 1 on\n'; continue;;
    106  1.2  kre 	esac
    107  1.2  kre 
    108  1.2  kre 	# validation complete, now to generate output
    109  1.2  kre 
    110  1.2  kre 	if [ -n "${COND}" ]
    111  1.2  kre 	then
    112  1.2  kre 		printf '%s\n' "${COND}" >&4
    113  1.2  kre 		printf '%s\n' "${COND}" >&5
    114  1.2  kre 		printf '%s\n' "${COND}" >&6
    115  1.2  kre 	fi
    116  1.2  kre 
    117  1.2  kre 	printf '\t_SH_OPT_%s,\n' "${var}" >&5
    118  1.1  kre 
    119  1.1  kre 	if [ -n "${name}" ]
    120  1.1  kre 	then
    121  1.2  kre 		printf '    { "%s", ' "${name}"	>&4
    122  1.1  kre 	else
    123  1.2  kre 		printf '    { 0, '		>&4
    124  1.1  kre 	fi
    125  1.1  kre 
    126  1.1  kre 	if [ -n "${chr}" ]
    127  1.1  kre 	then
    128  1.2  kre 		printf "'%s', " "${chr}"	>&4
    129  1.1  kre 	else
    130  1.2  kre 		chr=
    131  1.2  kre 		printf '0, '			>&4
    132  1.1  kre 	fi
    133  1.1  kre 
    134  1.1  kre 	if [ -n "${set}" ]
    135  1.1  kre 	then
    136  1.2  kre 		printf "'%s', 0, " "${set}"	>&4
    137  1.1  kre 	else
    138  1.2  kre 		printf '0, 0, '			>&4
    139  1.1  kre 	fi
    140  1.1  kre 
    141  1.1  kre 	if [ -n "${dflt}" ]
    142  1.1  kre 	then
    143  1.2  kre 		printf '%s },\n' "${dflt}"	>&4
    144  1.1  kre 	else
    145  1.2  kre 		printf '0 },\n'			>&4
    146  1.1  kre 	fi
    147  1.1  kre 
    148  1.2  kre 	printf '#define %s\toptlist[_SH_OPT_%s].val\n' "${var}" "${var}" >&6
    149  1.2  kre 
    150  1.2  kre 	if [ -n "${COND}" ]
    151  1.2  kre 	then
    152  1.2  kre 		printf '#endif\n' >&4
    153  1.2  kre 		printf '#endif\n' >&5
    154  1.2  kre 		printf '#endif\n' >&6
    155  1.2  kre 	fi
    156  1.1  kre 
    157  1.1  kre 	test -z "${chr}" && continue
    158  1.1  kre 
    159  1.2  kre 	printf '%s _SH_OPT_%s %s\n' "${chr}" "${var}" "${COND}"
    160  1.1  kre 
    161  1.2  kre done 4>>"${OF}" | sort -t' ' -k1,1f -k1,1r | while read chr index COND
    162  1.1  kre do
    163  1.1  kre 	if $FIRST
    164  1.1  kre 	then
    165  1.2  kre 		printf '    { 0, 0, 0, 0, 0 }\n};\n'
    166  1.2  kre 		printf '#endif\n\n'
    167  1.2  kre 
    168  1.2  kre 		printf 'enum shell_opt_names {\n'
    169  1.2  kre 		cat "${E_FILE}"
    170  1.2  kre 		printf '};\n\n'
    171  1.2  kre 
    172  1.1  kre 		printf '#ifdef DEFINE_OPTIONS\n'
    173  1.1  kre 		printf 'const unsigned char optorder[] = {\n'
    174  1.1  kre 		FIRST=false
    175  1.1  kre 	fi
    176  1.2  kre 	[ -n "${COND}" ] && printf '%s\n' "${COND}"
    177  1.1  kre 	printf '\t%s,\n' "${index}"
    178  1.2  kre 	[ -n "${COND}" ] && printf '#endif\n'
    179  1.1  kre 
    180  1.1  kre done >>"${OF}"
    181  1.1  kre 
    182  1.1  kre {
    183  1.1  kre 	printf '};\n\n'
    184  1.1  kre 	printf '#define NOPTS (sizeof optlist / sizeof optlist[0] - 1)\n'
    185  1.1  kre 	printf 'int sizeof_optlist = sizeof optlist;\n\n'
    186  1.1  kre 	printf	\
    187  1.1  kre 	   'const int option_flags = (sizeof optorder / sizeof optorder[0]);\n'
    188  1.1  kre 	printf '\n#else\n\n'
    189  1.1  kre 	printf 'extern struct optent optlist[];\n'
    190  1.1  kre 	printf 'extern int sizeof_optlist;\n'
    191  1.1  kre 	printf 'extern const unsigned char optorder[];\n'
    192  1.1  kre 	printf 'extern const int option_flags;\n'
    193  1.2  kre 	printf '\n#endif\n\n'
    194  1.2  kre 
    195  1.2  kre 	cat "${O_FILE}"
    196  1.1  kre } >> "${OF}"
    197  1.1  kre 
    198  1.1  kre exit 0
    199