Changes of Revision 11
[-] [+] | Added | extract-modaliases |
@@ -0,0 +1,165 @@ +#! /bin/bash + +LC_ALL=POSIX + +usage() { + cat <<EOF +Usage: ${0##*/} [-i module] [-x module] [-Nv] {module|rpm} ... + +-i Include the specified modules (glob expression). + +-x Exclude the specified modules (glob expression). + +-N Don't try to combine modalias tags that only differ in one character. + +-v Verbose: report which modules define which aliases. +EOF + exit $1 +} + +ARGS=("$@") + +options=`getopt -o i:x:vNh -- "$@"` + +if [ $? -ne 0 ] +then + usage 2 +fi + +eval set -- "$options" + +opt_combine=1 +while :; do + case "$1" in + -i) + include="$include ${2%.ko}" + shift 2 + ;; + -x) + exclude="$exclude ${2%.ko}" + shift 2 + ;; + -v) + opt_verbose=1 + shift ;; + -N) + opt_combine= + shift ;; + -h) + usage 0 + ;; + --) + shift + break + ;; + esac +done + +process_module() { + declare module=$1 base=${1##*/} aliases + + if [ -n "$include" ]; then + included= + for x in $include; do + eval "case \"\${base%.ko}\" in (${x%.ko}) included=1;; esac" + done + else + included=1 + fi + for x in $exclude; do + eval "case \"\${base%.ko}\" in (${x%.ko}) included=;; esac" + done + [ -n "$included" ] || return + + aliases="$(/sbin/modinfo -F alias "$module" \ + | sed -nre 's@^.+:.+$@Supplements: modalias(&)@p')" + if [ -n "$aliases" ]; then + eval "processed_module_${base//[^a-zA-Z0-9_]/_}=$base" + echo "$aliases" \ + | if [ -n "$opt_verbose" ]; then + sed -e "s@\$@ # $base@" + else + cat + fi + fi +} + +print_modaliases() { + declare class=$1 variants=$2 pos=$3 + if [ -n "$variants" ]; then + echo "${class:0:pos}[$variants]${class:pos+1}" + else + [ -z "$class" ] || echo "$class" + fi +} + +combine_modaliases() { + declare tag class variants pos n + read class + while read tag; do + for ((n=0; n<${#class}; n++)); do + if [ "*" != "${class:n:1}" -a \ + "${class:0:n}" = "${tag:0:n}" -a \ + "${class:n+1}" = "${tag:n+1}" ] && + ( [ -z "$pos" ] || [ $n = $pos ] ); then + variants="${variants:-${class:n:1}}${tag:n:1}" + pos=$n + break + fi + done + if [ $n -eq ${#class} ]; then + print_modaliases "$class" "$variants" "$pos" + variants= + pos= + class=$tag + fi + done + print_modaliases "$class" "$variants" "$pos" +} + +tmp=$(mktemp -t ${0##*/}.XXXXXX) +trap "rm -f $tmp" EXIT + +for file in "$@"; do + case "$(file -b "$file")" in + RPM*) + tmpdir=$(mktemp -td ${0##*/}.XXXXXX) + rpm2cpio "$file" | ( cd $tmpdir && cpio -dim --quiet ) + for module in $(find $tmpdir -type f -name '*.ko'); do + process_module "$module" >> $tmp + done + rm -rf $tmpdir + ;; + ELF*) + process_module "$file" >> $tmp + ;; + *) + if [ -e "$file" ]; then + echo "File type of $file not supported" >&2 + exit 1 + fi + file2=$(/sbin/modinfo -F filename "${file%.ko}") + if ! [ -e "$file2" ]; then + echo "No module $file found" >&2 + exit 1 + fi + process_module "$file2" >> $tmp + ;; + esac +done + +if [ -n "${!processed_module_*}" ]; then + echo "# Modules:" $(for m in ${!processed_module_*}; do echo ${!m}; done \ + | sort -u) + + sort -u $tmp \ + | if [ -n "$opt_combine" ]; then + combine_modaliases + else + cat + fi + + echo "# Generated with: ${0##*/} ${ARGS[*]}" +fi + +# vim:softtabstop=4 shiftwidth=4 |