Back to home page

OSCL-LXR

 
 

    


0001 #!/bin/sh
0002 # SPDX-License-Identifier: GPL-2.0
0003 #
0004 # Generate system call table and header files
0005 #
0006 # Copyright IBM Corp. 2018
0007 # Author(s):  Hendrik Brueckner <brueckner@linux.vnet.ibm.com>
0008 
0009 #
0010 # File path to the system call table definition.
0011 # You can set the path with the -i option.  If omitted,
0012 # system call table definitions are read from standard input.
0013 #
0014 SYSCALL_TBL=""
0015 
0016 
0017 create_syscall_table_entries()
0018 {
0019         local nr abi name entry64 entry32 _ignore
0020         local temp=$(mktemp ${TMPDIR:-/tmp}/syscalltbl-common.XXXXXXXXX)
0021 
0022         (
0023         #
0024         # Initialize with 0 to create an NI_SYSCALL for 0
0025         #
0026         local prev_nr=0 prev_32=sys_ni_syscall prev_64=sys_ni_syscall
0027         while read nr abi name entry64 entry32 _ignore; do
0028                 test x$entry32 = x- && entry32=sys_ni_syscall
0029                 test x$entry64 = x- && entry64=sys_ni_syscall
0030 
0031                 if test $prev_nr -eq $nr; then
0032                         #
0033                         # Same syscall but different ABI, just update
0034                         # the respective entry point
0035                         #
0036                         case $abi in
0037                         32)
0038                                 prev_32=$entry32
0039                         ;;
0040                         64)
0041                                 prev_64=$entry64
0042                         ;;
0043                         esac
0044                         continue;
0045                 else
0046                         printf "%d\t%s\t%s\n" $prev_nr $prev_64 $prev_32
0047                 fi
0048 
0049                 prev_nr=$nr
0050                 prev_64=$entry64
0051                 prev_32=$entry32
0052         done
0053         printf "%d\t%s\t%s\n" $prev_nr $prev_64 $prev_32
0054         ) >> $temp
0055 
0056         #
0057         # Check for duplicate syscall numbers
0058         #
0059         if ! cat $temp |cut -f1 |uniq -d 2>&1; then
0060                 echo "Error: generated system call table contains duplicate entries: $temp" >&2
0061                 exit 1
0062         fi
0063 
0064         #
0065         # Generate syscall table
0066         #
0067         prev_nr=0
0068         while read nr entry64 entry32; do
0069                 while test $prev_nr -lt $((nr - 1)); do
0070                         printf "NI_SYSCALL\n"
0071                         prev_nr=$((prev_nr + 1))
0072                 done
0073                 if test x$entry64 = xsys_ni_syscall &&
0074                    test x$entry32 = xsys_ni_syscall; then
0075                         printf "NI_SYSCALL\n"
0076                 else
0077                         printf "SYSCALL(%s,%s)\n" $entry64 $entry32
0078                 fi
0079                 prev_nr=$nr
0080         done < $temp
0081         rm $temp
0082 }
0083 
0084 generate_syscall_table()
0085 {
0086         cat <<-EoHEADER
0087         /* SPDX-License-Identifier: GPL-2.0 */
0088         /*
0089          * Definitions for sys_call_table, each line represents an
0090          * entry in the table in the form
0091          * SYSCALL(64 bit syscall, 31 bit emulated syscall)
0092          *
0093          * This file is meant to be included from entry.S.
0094          */
0095 
0096         #define NI_SYSCALL SYSCALL(sys_ni_syscall,sys_ni_syscall)
0097 
0098 EoHEADER
0099         grep -Ev '^(#|[[:blank:]]*$)' $SYSCALL_TBL      \
0100                 |sort -k1 -n                            \
0101                 |create_syscall_table_entries
0102 }
0103 
0104 create_header_defines()
0105 {
0106         local nr abi name _ignore
0107 
0108         while read nr abi name _ignore; do
0109                 printf "#define __NR_%s %d\n" $name $nr
0110         done
0111 }
0112 
0113 normalize_fileguard()
0114 {
0115         local fileguard="$1"
0116 
0117         echo "$1" |tr '[[:lower:]]' '[[:upper:]]' \
0118                   |sed -e 's/[^A-Z0-9_]/_/g' -e 's/__/_/g'
0119 }
0120 
0121 generate_syscall_header()
0122 {
0123         local abis=$(echo "($1)" | tr ',' '|')
0124         local filename="$2"
0125         local fileguard suffix
0126 
0127         if test "$filename"; then
0128                 fileguard=$(normalize_fileguard "__UAPI_ASM_S390_$2")
0129         else
0130                 case "$abis" in
0131                 *64*) suffix=64 ;;
0132                 *32*) suffix=32 ;;
0133                 esac
0134                 fileguard=$(normalize_fileguard "__UAPI_ASM_S390_SYSCALLS_$suffix")
0135         fi
0136 
0137         cat <<-EoHEADER
0138         /* SPDX-License-Identifier: GPL-2.0 WITH Linux-syscall-note */
0139         #ifndef ${fileguard}
0140         #define ${fileguard}
0141 
0142 EoHEADER
0143 
0144         grep -E "^[[:digit:]]+[[:space:]]+${abis}" $SYSCALL_TBL \
0145                 |sort -k1 -n                                    \
0146                 |create_header_defines
0147 
0148         cat <<-EoFOOTER
0149 
0150         #endif /* ${fileguard} */
0151 EoFOOTER
0152 }
0153 
0154 __max_syscall_nr()
0155 {
0156         local abis=$(echo "($1)" | tr ',' '|')
0157 
0158         grep -E "^[[:digit:]]+[[:space:]]+${abis}" $SYSCALL_TBL  \
0159                 |sed -ne 's/^\([[:digit:]]*\)[[:space:]].*/\1/p' \
0160                 |sort -n                                         \
0161                 |tail -1
0162 }
0163 
0164 
0165 generate_syscall_nr()
0166 {
0167         local abis="$1"
0168         local max_syscall_nr num_syscalls
0169 
0170         max_syscall_nr=$(__max_syscall_nr "$abis")
0171         num_syscalls=$((max_syscall_nr + 1))
0172 
0173         cat <<-EoHEADER
0174         /* SPDX-License-Identifier: GPL-2.0 WITH Linux-syscall-note */
0175         #ifndef __ASM_S390_SYSCALLS_NR
0176         #define __ASM_S390_SYSCALLS_NR
0177 
0178         #define NR_syscalls ${num_syscalls}
0179 
0180         #endif /* __ASM_S390_SYSCALLS_NR */
0181 EoHEADER
0182 }
0183 
0184 
0185 #
0186 # Parse command line arguments
0187 #
0188 do_syscall_header=""
0189 do_syscall_table=""
0190 do_syscall_nr=""
0191 output_file=""
0192 abi_list="common,64"
0193 filename=""
0194 while getopts ":HNSXi:a:f:" arg; do
0195         case $arg in
0196         a)
0197                 abi_list="$OPTARG"
0198                 ;;
0199         i)
0200                 SYSCALL_TBL="$OPTARG"
0201                 ;;
0202         f)
0203                 filename=${OPTARG##*/}
0204                 ;;
0205         H)
0206                 do_syscall_header=1
0207                 ;;
0208         N)
0209                 do_syscall_nr=1
0210                 ;;
0211         S)
0212                 do_syscall_table=1
0213                 ;;
0214         X)
0215                 set -x
0216                 ;;
0217         :)
0218                 echo "Missing argument for -$OPTARG" >&2
0219                 exit 1
0220         ;;
0221         \?)
0222                 echo "Invalid option specified" >&2
0223                 exit 1
0224         ;;
0225         esac
0226 done
0227 
0228 test "$do_syscall_header" && generate_syscall_header "$abi_list" "$filename"
0229 test "$do_syscall_table" && generate_syscall_table
0230 test "$do_syscall_nr" && generate_syscall_nr "$abi_list"
0231 
0232 exit 0