xref: /illumos-gate/usr/src/tools/scripts/elfcmp.sh (revision d2d52add)
17c478bd9Sstevel@tonic-gate#!/bin/ksh
27c478bd9Sstevel@tonic-gate#
37c478bd9Sstevel@tonic-gate# CDDL HEADER START
47c478bd9Sstevel@tonic-gate#
57c478bd9Sstevel@tonic-gate# The contents of this file are subject to the terms of the
67c478bd9Sstevel@tonic-gate# Common Development and Distribution License, Version 1.0 only
77c478bd9Sstevel@tonic-gate# (the "License").  You may not use this file except in compliance
87c478bd9Sstevel@tonic-gate# with the License.
97c478bd9Sstevel@tonic-gate#
107c478bd9Sstevel@tonic-gate# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
117c478bd9Sstevel@tonic-gate# or http://www.opensolaris.org/os/licensing.
127c478bd9Sstevel@tonic-gate# See the License for the specific language governing permissions
137c478bd9Sstevel@tonic-gate# and limitations under the License.
147c478bd9Sstevel@tonic-gate#
157c478bd9Sstevel@tonic-gate# When distributing Covered Code, include this CDDL HEADER in each
167c478bd9Sstevel@tonic-gate# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
177c478bd9Sstevel@tonic-gate# If applicable, add the following below this CDDL HEADER, with the
187c478bd9Sstevel@tonic-gate# fields enclosed by brackets "[]" replaced with your own identifying
197c478bd9Sstevel@tonic-gate# information: Portions Copyright [yyyy] [name of copyright owner]
207c478bd9Sstevel@tonic-gate#
217c478bd9Sstevel@tonic-gate# CDDL HEADER END
227c478bd9Sstevel@tonic-gate#
237c478bd9Sstevel@tonic-gate#
247c478bd9Sstevel@tonic-gate# Copyright 2005 Sun Microsystems, Inc.  All rights reserved.
257c478bd9Sstevel@tonic-gate# Use is subject to license terms.
267c478bd9Sstevel@tonic-gate#
277c478bd9Sstevel@tonic-gate# elfcmp - compare significant sections in two ELF files
287c478bd9Sstevel@tonic-gate#
297c478bd9Sstevel@tonic-gate# usage: elfcmp [-v] [-S] [-s section ...] <f1> <f2>
307c478bd9Sstevel@tonic-gate#
317c478bd9Sstevel@tonic-gate
327c478bd9Sstevel@tonic-gateVERBOSE=0
337c478bd9Sstevel@tonic-gateSECTIONLIST=""
347c478bd9Sstevel@tonic-gateSIGNING_CHECK=0
357c478bd9Sstevel@tonic-gateERRORS=0
367c478bd9Sstevel@tonic-gate
377c478bd9Sstevel@tonic-gateusage() {
387c478bd9Sstevel@tonic-gate	echo 'Usage: elfcmp [-v] [-S] [-s section ...] <f1> <f2>' 1>&2
397c478bd9Sstevel@tonic-gate	exit 1
407c478bd9Sstevel@tonic-gate}
417c478bd9Sstevel@tonic-gate
427c478bd9Sstevel@tonic-gatewhile [[ $# > 0 ]]
437c478bd9Sstevel@tonic-gatedo
447c478bd9Sstevel@tonic-gate	case "$1" in
457c478bd9Sstevel@tonic-gate	-v)
467c478bd9Sstevel@tonic-gate		VERBOSE=1
477c478bd9Sstevel@tonic-gate		;;
487c478bd9Sstevel@tonic-gate	-s)
497c478bd9Sstevel@tonic-gate		SECTIONLIST="$2"
507c478bd9Sstevel@tonic-gate		shift
517c478bd9Sstevel@tonic-gate		;;
527c478bd9Sstevel@tonic-gate	-S)
537c478bd9Sstevel@tonic-gate		SIGNING_CHECK=1
547c478bd9Sstevel@tonic-gate		;;
557c478bd9Sstevel@tonic-gate	-*)
567c478bd9Sstevel@tonic-gate		usage
577c478bd9Sstevel@tonic-gate		;;
587c478bd9Sstevel@tonic-gate	*)
597c478bd9Sstevel@tonic-gate		break
607c478bd9Sstevel@tonic-gate		;;
617c478bd9Sstevel@tonic-gate	esac
627c478bd9Sstevel@tonic-gate	shift
637c478bd9Sstevel@tonic-gatedone
647c478bd9Sstevel@tonic-gate
657c478bd9Sstevel@tonic-gateif [[ $# != 2 ]]
667c478bd9Sstevel@tonic-gatethen
677c478bd9Sstevel@tonic-gate	usage
687c478bd9Sstevel@tonic-gatefi
697c478bd9Sstevel@tonic-gate
707c478bd9Sstevel@tonic-gateTMP1=/tmp/elfcmp.1.$$
717c478bd9Sstevel@tonic-gateTMP2=/tmp/elfcmp.2.$$
727c478bd9Sstevel@tonic-gatetrap "rm -f $TMP1 $TMP2" EXIT HUP INT QUIT PIPE TERM
737c478bd9Sstevel@tonic-gate
747c478bd9Sstevel@tonic-gatelist_sections() {
757c478bd9Sstevel@tonic-gate	dump -h "$1" | grep '\[[0-9]' | awk '{print $7}'
767c478bd9Sstevel@tonic-gate}
777c478bd9Sstevel@tonic-gate
787c478bd9Sstevel@tonic-gatelist_alloc_sections() {
797c478bd9Sstevel@tonic-gate	dump -hv "$1" | grep '\[[0-9]' | awk '$3 ~ /A/ {print $4, $5, $6, $7}'
807c478bd9Sstevel@tonic-gate}
817c478bd9Sstevel@tonic-gate
827c478bd9Sstevel@tonic-gatesigning_filter() {
83*d2d52addSAlexander Pyhalov	/usr/bin/grep -v -e \\$SHSTRTAB -e \\.SUNW_signature
847c478bd9Sstevel@tonic-gate}
857c478bd9Sstevel@tonic-gate
867c478bd9Sstevel@tonic-gate# get section lists for both files into temp files
877c478bd9Sstevel@tonic-gate
887c478bd9Sstevel@tonic-gateif [[ "$SECTIONLIST" = "" ]]
897c478bd9Sstevel@tonic-gatethen
907c478bd9Sstevel@tonic-gate	if [[ $SIGNING_CHECK = 1 ]]
917c478bd9Sstevel@tonic-gate	then
927c478bd9Sstevel@tonic-gate		SHSTRNDX=`dump -f "$1" | awk '{if (NR==11) print $5}'`
937c478bd9Sstevel@tonic-gate		SHSTRTAB=`dump -h "$1" | grep "^\\[$SHSTRNDX\\]" | \
947c478bd9Sstevel@tonic-gate			awk '{print $7}'`
957c478bd9Sstevel@tonic-gate		FILTER=signing_filter
967c478bd9Sstevel@tonic-gate	else
977c478bd9Sstevel@tonic-gate		FILTER=cat
987c478bd9Sstevel@tonic-gate	fi
997c478bd9Sstevel@tonic-gate
1007c478bd9Sstevel@tonic-gate	list_sections "$1" | $FILTER | sort >$TMP1
1017c478bd9Sstevel@tonic-gate	list_sections "$2" | $FILTER | sort >$TMP2
1027c478bd9Sstevel@tonic-gateelse
1037c478bd9Sstevel@tonic-gate	echo "$SECTIONLIST" >$TMP1
1047c478bd9Sstevel@tonic-gate	echo "$SECTIONLIST" >$TMP2
1057c478bd9Sstevel@tonic-gatefi
1067c478bd9Sstevel@tonic-gate
1077c478bd9Sstevel@tonic-gate# determine and print which ones aren't in both of the input files
1087c478bd9Sstevel@tonic-gate
1097c478bd9Sstevel@tonic-gateNOT_IN_1=$(comm -13 $TMP1 $TMP2)
1107c478bd9Sstevel@tonic-gateif [[ ! -z "$NOT_IN_1" ]]
1117c478bd9Sstevel@tonic-gatethen
1127c478bd9Sstevel@tonic-gate	echo "Section(s) $NOT_IN_1 not in $1"
1137c478bd9Sstevel@tonic-gate	(( ERRORS += 1 ))
1147c478bd9Sstevel@tonic-gatefi
1157c478bd9Sstevel@tonic-gateNOT_IN_2=$(comm -23 $TMP1 $TMP2)
1167c478bd9Sstevel@tonic-gateif [[ ! -z "$NOT_IN_2" ]]
1177c478bd9Sstevel@tonic-gatethen
1187c478bd9Sstevel@tonic-gate	echo "Section(s) $NOT_IN_2 not in $2"
1197c478bd9Sstevel@tonic-gate	(( ERRORS += 1 ))
1207c478bd9Sstevel@tonic-gatefi
1217c478bd9Sstevel@tonic-gate
1227c478bd9Sstevel@tonic-gate# for all the sections which *are* common, do the following
1237c478bd9Sstevel@tonic-gate
1247c478bd9Sstevel@tonic-gatefor s in $(comm -12 $TMP1 $TMP2)
1257c478bd9Sstevel@tonic-gatedo
1267c478bd9Sstevel@tonic-gate	dump -s -n $s "$1" | sed '/:/d' >$TMP1
1277c478bd9Sstevel@tonic-gate	dump -s -n $s "$2" | sed '/:/d' >$TMP2
1287c478bd9Sstevel@tonic-gate	if cmp -s $TMP1 $TMP2
1297c478bd9Sstevel@tonic-gate	then
1307c478bd9Sstevel@tonic-gate		if [[ $VERBOSE = 1 ]]
1317c478bd9Sstevel@tonic-gate		then
1327c478bd9Sstevel@tonic-gate			echo "Section $s is the same"
1337c478bd9Sstevel@tonic-gate		fi
1347c478bd9Sstevel@tonic-gate	else
1357c478bd9Sstevel@tonic-gate		echo "Section $s differs"
1367c478bd9Sstevel@tonic-gate		if [[ $VERBOSE = 1 ]]
1377c478bd9Sstevel@tonic-gate		then
1387c478bd9Sstevel@tonic-gate			dump -sv -n $s "$1" | sed '/:/d' >$TMP1
1397c478bd9Sstevel@tonic-gate			dump -sv -n $s "$2" | sed '/:/d' >$TMP2
1407c478bd9Sstevel@tonic-gate			diff -c $TMP1 $TMP2
1417c478bd9Sstevel@tonic-gate		fi
1427c478bd9Sstevel@tonic-gate		(( ERRORS += 1 ))
1437c478bd9Sstevel@tonic-gate	fi
1447c478bd9Sstevel@tonic-gatedone
1457c478bd9Sstevel@tonic-gate
1467c478bd9Sstevel@tonic-gate# verify that allocated objects have not moved
1477c478bd9Sstevel@tonic-gate# only applies to signed objects with a program header
1487c478bd9Sstevel@tonic-gate
1497c478bd9Sstevel@tonic-gateif [[ $SIGNING_CHECK = 1 ]]
1507c478bd9Sstevel@tonic-gatethen
1517c478bd9Sstevel@tonic-gate	HDR=$(dump -op $1 | wc -l)
1527c478bd9Sstevel@tonic-gate	if [[ $HDR -gt 2 ]]
1537c478bd9Sstevel@tonic-gate	then
1547c478bd9Sstevel@tonic-gate		list_alloc_sections "$1" | sort >$TMP1
1557c478bd9Sstevel@tonic-gate		list_alloc_sections "$2" | sort >$TMP2
1567c478bd9Sstevel@tonic-gate		if cmp -s $TMP1 $TMP2
1577c478bd9Sstevel@tonic-gate		then
1587c478bd9Sstevel@tonic-gate			if [[ $VERBOSE = 1 ]]
1597c478bd9Sstevel@tonic-gate			then
1607c478bd9Sstevel@tonic-gate				echo "Allocated sections are the same"
1617c478bd9Sstevel@tonic-gate			fi
1627c478bd9Sstevel@tonic-gate		else
1637c478bd9Sstevel@tonic-gate			echo "Allocated section(s) changed"
1647c478bd9Sstevel@tonic-gate			if [[ $VERBOSE = 1 ]]
1657c478bd9Sstevel@tonic-gate			then
1667c478bd9Sstevel@tonic-gate				diff -c $TMP1 $TMP2
1677c478bd9Sstevel@tonic-gate			fi
1687c478bd9Sstevel@tonic-gate			(( ERRORS += 1 ))
1697c478bd9Sstevel@tonic-gate		fi
1707c478bd9Sstevel@tonic-gate	fi
1717c478bd9Sstevel@tonic-gatefi
1727c478bd9Sstevel@tonic-gate
1737c478bd9Sstevel@tonic-gateexit $ERRORS
174