1#!/bin/sh 2# SPDX-License-Identifier: BSD-3-Clause 3# Copyright(c) 2018 Neil Horman <[email protected]> 4 5build_map_changes() 6{ 7 local fname="$1" 8 local mapdb="$2" 9 10 cat "$fname" | awk ' 11 # Initialize our variables 12 BEGIN {map="";sym="";ar="";sec=""; in_sec=0; in_map=0} 13 14 # Anything that starts with + or -, followed by an a 15 # and ends in the string .map is the name of our map file 16 # This may appear multiple times in a patch if multiple 17 # map files are altered, and all section/symbol names 18 # appearing between a triggering of this rule and the 19 # next trigger of this rule are associated with this file 20 /[-+] a\/.*\.map/ {map=$2; in_map=1} 21 22 # Same pattern as above, only it matches on anything that 23 # does not end in 'map', indicating we have left the map chunk. 24 # When we hit this, turn off the in_map variable, which 25 # supresses the subordonate rules below 26 /[-+] a\/.*\.[^map]/ {in_map=0} 27 28 # Triggering this rule, which starts a line and ends it 29 # with a { identifies a versioned section. The section name is 30 # the rest of the line with the + and { symbols remvoed. 31 # Triggering this rule sets in_sec to 1, which actives the 32 # symbol rule below 33 /^.*{/ { 34 if (in_map == 1) { 35 sec=$(NF-1); in_sec=1; 36 } 37 } 38 39 # This rule idenfies the end of a section, and disables the 40 # symbol rule 41 /.*}/ {in_sec=0} 42 43 # This rule matches on a + followed by any characters except a : 44 # (which denotes a global vs local segment), and ends with a ;. 45 # The semicolon is removed and the symbol is printed with its 46 # association file name and version section, along with an 47 # indicator that the symbol is a new addition. Note this rule 48 # only works if we have found a version section in the rule 49 # above (hence the in_sec check) And found a map file (the 50 # in_map check). If we are not in a map chunk, do nothing. If 51 # we are in a map chunk but not a section chunk, record it as 52 # unknown. 53 /^+[^}].*[^:*];/ {gsub(";","");sym=$2; 54 if (in_map == 1) { 55 if (in_sec == 1) { 56 print map " " sym " " sec " add" 57 } else { 58 print map " " sym " unknown add" 59 } 60 } 61 } 62 63 # This is the same rule as above, but the rule matches on a 64 # leading - rather than a +, denoting that the symbol is being 65 # removed. 66 /^-[^}].*[^:*];/ {gsub(";","");sym=$2; 67 if (in_map == 1) { 68 if (in_sec == 1) { 69 print map " " sym " " sec " del" 70 } else { 71 print map " " sym " unknown del" 72 } 73 } 74 }' > "$mapdb" 75 76 sort -u "$mapdb" > "$mapdb.2" 77 mv -f "$mapdb.2" "$mapdb" 78 79} 80 81check_for_rule_violations() 82{ 83 local mapdb="$1" 84 local mname 85 local symname 86 local secname 87 local ar 88 local ret=0 89 90 while read mname symname secname ar 91 do 92 if [ "$ar" = "add" ] 93 then 94 95 if [ "$secname" = "unknown" ] 96 then 97 # Just inform the user of this occurrence, but 98 # don't flag it as an error 99 echo -n "INFO: symbol $syname is added but " 100 echo -n "patch has insuficient context " 101 echo -n "to determine the section name " 102 echo -n "please ensure the version is " 103 echo "EXPERIMENTAL" 104 continue 105 fi 106 107 if [ "$secname" != "EXPERIMENTAL" ] 108 then 109 # Symbols that are getting added in a section 110 # other than the experimental section 111 # to be moving from an already supported 112 # section or its a violation 113 grep -q \ 114 "$mname $symname [^EXPERIMENTAL] del" "$mapdb" 115 if [ $? -ne 0 ] 116 then 117 echo -n "ERROR: symbol $symname " 118 echo -n "is added in the $secname " 119 echo -n "section, but is expected to " 120 echo -n "be added in the EXPERIMENTAL " 121 echo "section of the version map" 122 ret=1 123 fi 124 fi 125 else 126 127 if [ "$secname" != "EXPERIMENTAL" ] 128 then 129 # Just inform users that non-experimenal 130 # symbols need to go through a deprecation 131 # process 132 echo -n "INFO: symbol $symname is being " 133 echo -n "removed, ensure that it has " 134 echo "gone through the deprecation process" 135 fi 136 fi 137 done < "$mapdb" 138 139 return $ret 140} 141 142trap clean_and_exit_on_sig EXIT 143 144mapfile=`mktemp -t dpdk.mapdb.XXXXXX` 145patch=$1 146exit_code=1 147 148clean_and_exit_on_sig() 149{ 150 rm -f "$mapfile" 151 exit $exit_code 152} 153 154build_map_changes "$patch" "$mapfile" 155check_for_rule_violations "$mapfile" 156exit_code=$? 157rm -f "$mapfile" 158 159exit $exit_code 160