5 # The contents of this file are subject to the terms of the
6 # Common Development and Distribution License (the "License").
7 # You may not use this file except in compliance with the License.
8 #
9 # You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10 # or http://www.opensolaris.org/os/licensing.
11 # See the License for the specific language governing permissions
12 # and limitations under the License.
13 #
14 # When distributing Covered Code, include this CDDL HEADER in each
15 # file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16 # If applicable, add the following below this CDDL HEADER, with the
17 # fields enclosed by brackets "[]" replaced with your own identifying
18 # information: Portions Copyright [yyyy] [name of copyright owner]
19 #
20 # CDDL HEADER END
21 #
22
23 #
24 # Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
25 #
26
27 #
28 # Check ELF information.
29 #
30 # This script descends a directory hierarchy inspecting ELF dynamic executables
31 # and shared objects. The general theme is to verify that common Makefile rules
32 # have been used to build these objects. Typical failures occur when Makefile
33 # rules are re-invented rather than being inherited from "cmd/lib" Makefiles.
34 #
35 # As always, a number of components don't follow the rules, and these are
36 # excluded to reduce this scripts output.
37 #
38 # By default any file that has conditions that should be reported is first
39 # listed and then each condition follows. The -o (one-line) option produces a
40 # more terse output which is better for sorting/diffing with "nightly".
41 #
42 # NOTE: missing dependencies, symbols or versions are reported by running the
43 # file through ldd(1). As objects within a proto area are built to exist in a
44 # base system, standard use of ldd(1) will bind any objects to dependencies
45 # that exist in the base system. It is frequently the case that newer objects
46 # exist in the proto area that are required to satisfy other objects
47 # dependencies, and without using these newer objects an ldd(1) will produce
48 # misleading error messages. To compensate for this, the -D/-d options, or the
49 # existence of the CODEMSG_WS/ROOT environment variables, cause the creation of
50 # alternative dependency mappings via crle(1) configuration files that establish
51 # any proto shared objects as alternatives to their base system location. Thus
52 # ldd(1) can be executed against these configuration files so that objects in a
53 # proto area bind to their dependencies in the same proto area.
54
55
56 # Define all global variables (required for strict)
57 use vars qw($Prog $Env $Ena64 $Tmpdir);
58 use vars qw($LddNoU $Conf32 $Conf64);
59 use vars qw(%opt);
60 use vars qw($ErrFH $ErrTtl $InfoFH $InfoTtl $OutCnt1 $OutCnt2);
61
62 # An exception file is used to specify regular expressions to match
63 # objects. These directives specify special attributes of the object.
64 # The regular expressions are read from the file and compiled into the
65 # regular expression variables.
66 #
67 # The name of each regular expression variable is of the form
68 #
69 # $EXRE_xxx
70 #
71 # where xxx is the name of the exception in lower case. For example,
72 # the regular expression variable for EXEC_STACK is $EXRE_exec_stack.
73 #
74 # onbld_elfmod::LoadExceptionsToEXRE() depends on this naming convention
75 # to initialize the regular expression variables, and to detect invalid
76 # exception names.
77 #
854 sub ProcFindElf {
855 my $file = $_[0];
856 my $line;
857 my $LineNum;
858
859 my $prefix = OpenFindElf($file, \*FIND_ELF, \$LineNum);
860
861 while ($line = onbld_elfmod::GetLine(\*FIND_ELF, \$LineNum)) {
862 next if !($line =~ /^OBJECT\s/i);
863
864 my ($item, $class, $type, $verdef, $obj) =
865 split(/\s+/, $line, 5);
866
867 ProcFile("$prefix/$obj", $obj, $class, $type, $verdef);
868 }
869
870 close FIND_ELF;
871 }
872
873
874 ## AltObjectConfig(file)
875 #
876 # Recurse through a directory hierarchy looking for appropriate dependencies
877 # to map from their standard system locations to the proto area via a crle
878 # config file.
879 #
880 # entry:
881 # file - File of ELF objects, in 'find_elf -r' format, to examine.
882 #
883 # exit:
884 # Scripts are generated for the 32 and 64-bit cases to run crle
885 # and create runtime configuration files that will establish
886 # alternative dependency mappings for the objects identified.
887 #
888 # $Env - Set to environment variable definitions that will cause
889 # the config files generated by this routine to be used
890 # by ldd.
891 # $Conf32, $Conf64 - Undefined, or set to the config files generated
892 # by this routine. If defined, the caller is responsible for
893 # unlinking the files before exiting.
894 #
895 sub AltObjectConfig {
896 my $file = $_[0];
897 my ($Crle32, $Crle64);
898 my $line;
899 my $LineNum;
900 my $obj_path;
901 my $obj_active = 0;
902 my $obj_class;
903
904 my $prefix = OpenFindElf($file, \*FIND_ELF);
905
906 LINE:
907 while ($line = onbld_elfmod::GetLine(\*FIND_ELF, \$LineNum)) {
908 ITEM: {
909
910 if ($line =~ /^OBJECT\s/i) {
911 my ($item, $class, $type, $verdef, $obj) =
912 split(/\s+/, $line, 5);
913
914 if ($type eq 'DYN') {
915 $obj_active = 1;
916 $obj_path = $obj;
917 $obj_class = $class;
918 } else {
919 # Only want sharable objects
920 $obj_active = 0;
921 }
922 last ITEM;
923 }
924
925 # We need to follow links to sharable objects so
926 # that any dependencies are expressed in all their
927 # available forms. We depend on ALIAS lines directly
928 # following the object they alias, so if we have
929 # a current object, this alias belongs to it.
930 if ($obj_active && ($line =~ /^ALIAS\s/i)) {
931 my ($item, $real_obj, $obj) =
932 split(/\s+/, $line, 3);
933 $obj_path = $obj;
934 last ITEM;
935 }
936
937 # Skip unrecognized item
938 next LINE;
939 }
940
941 next if !$obj_active;
942
943 my $full = "$prefix/$obj_path";
944
945 next if defined($EXRE_nocrlealt) &&
946 ($obj_path =~ $EXRE_nocrlealt);
947
948 my $Dir = $full;
949 $Dir =~ s/^(.*)\/.*$/$1/;
950
951 # Create a crle(1) script for the dependency we've found.
952 # We build separate scripts for the 32 and 64-bit cases.
953 # We create and initialize each script when we encounter
954 # the first object that needs it.
955 if ($obj_class == 32) {
956 if (!$Crle32) {
957 $Crle32 = "$Tmpdir/$Prog.crle32.$$";
958 open(CRLE32, "> $Crle32") ||
959 die "$Prog: open failed: $Crle32: $!";
960 print CRLE32 "#!/bin/sh\ncrle \\\n";
961 }
962 print CRLE32 "\t-o $Dir -a /$obj_path \\\n";
963 } elsif ($Ena64) {
964 if (!$Crle64) {
965 $Crle64 = "$Tmpdir/$Prog.crle64.$$";
966 open(CRLE64, "> $Crle64") ||
967 die "$Prog: open failed: $Crle64: $!";
968 print CRLE64 "#!/bin/sh\ncrle -64\\\n";
969 }
970 print CRLE64 "\t-o $Dir -a /$obj_path \\\n";
971 }
972 }
973
974 close FIND_ELF;
975
976
977 # Now that the config scripts are complete, use them to generate
978 # runtime linker config files.
979 if ($Crle64) {
980 $Conf64 = "$Tmpdir/$Prog.conf64.$$";
981 print CRLE64 "\t-c $Conf64\n";
982
983 chmod 0755, $Crle64;
984 close CRLE64;
985
986 undef $Conf64 if system($Crle64);
987
988 # Done with the script
989 unlink $Crle64;
990 }
991 if ($Crle32) {
992 $Conf32 = "$Tmpdir/$Prog.conf32.$$";
993 print CRLE32 "\t-c $Conf32\n";
994
995 chmod 0755, $Crle32;
996 close CRLE32;
997
998 undef $Conf32 if system($Crle32);
999
1000 # Done with the script
1001 unlink $Crle32;
1002 }
1003
1004 # Set $Env so that we will use the config files generated above
1005 # when we run ldd.
1006 if ($Crle64 && $Conf64 && $Crle32 && $Conf32) {
1007 $Env = "-e LD_FLAGS=config_64=$Conf64,config_32=$Conf32";
1008 } elsif ($Crle64 && $Conf64) {
1009 $Env = "-e LD_FLAGS=config_64=$Conf64";
1010 } elsif ($Crle32 && $Conf32) {
1011 $Env = "-e LD_FLAGS=config_32=$Conf32";
1034 require "$moddir/onbld_elfmod.pm";
1035
1036 # Determine what machinery is available.
1037 my $Mach = `uname -p`;
1038 my$Isalist = `isalist`;
1039 if ($Mach =~ /sparc/) {
1040 if ($Isalist =~ /sparcv9/) {
1041 $Ena64 = "ok";
1042 }
1043 } elsif ($Mach =~ /i386/) {
1044 if ($Isalist =~ /amd64/) {
1045 $Ena64 = "ok";
1046 }
1047 }
1048
1049 # $Env is used with all calls to ldd. It is set by AltObjectConfig to
1050 # cause an alternate object mapping runtime config file to be used.
1051 $Env = '';
1052
1053 # Check that we have arguments.
1054 if ((getopts('D:d:E:e:f:I:imosvw:', \%opt) == 0) ||
1055 (!$opt{f} && ($#ARGV == -1))) {
1056 print "usage: $Prog [-imosv] [-D depfile | -d depdir] [-E errfile]\n";
1057 print "\t\t[-e exfile] [-f listfile] [-I infofile] [-w outdir]\n";
1058 print "\t\t[file | dir]...\n";
1059 print "\n";
1060 print "\t[-D depfile]\testablish dependencies from 'find_elf -r' file list\n";
1061 print "\t[-d depdir]\testablish dependencies from under directory\n";
1062 print "\t[-E errfile]\tdirect error output to file\n";
1063 print "\t[-e exfile]\texceptions file\n";
1064 print "\t[-f listfile]\tuse file list produced by find_elf -r\n";
1065 print "\t[-I infofile]\tdirect informational output (-i, -v) to file\n";
1066 print "\t[-i]\t\tproduce dynamic table entry information\n";
1067 print "\t[-m]\t\tprocess mcs(1) comments\n";
1068 print "\t[-o]\t\tproduce one-liner output (prefixed with pathname)\n";
1069 print "\t[-s]\t\tprocess .stab and .symtab entries\n";
1070 print "\t[-v]\t\tprocess version definition entries\n";
1071 print "\t[-w outdir]\tinterpret all files relative to given directory\n";
1072 exit 1;
1073 }
1074
1075 die "$Prog: -D and -d options are mutually exclusive\n" if ($opt{D} && $opt{d});
1076
1077 $Tmpdir = "/tmp" if (!($Tmpdir = $ENV{TMPDIR}) || (! -d $Tmpdir));
1078
1079 # If -w, change working directory to given location
1080 !$opt{w} || chdir($opt{w}) || die "$Prog: can't cd to $opt{w}";
1081
1082 # Locate and process the exceptions file
1083 onbld_elfmod::LoadExceptionsToEXRE('check_rtime');
1084
1085 # Is there a proto area available, either via the -d option, or because
1086 # we are part of an activated workspace?
1087 my $Proto;
1088 if ($opt{d}) {
1089 # User specified dependency directory - make sure it exists.
1090 -d $opt{d} || die "$Prog: $opt{d} is not a directory\n";
1091 $Proto = $opt{d};
1092 } elsif ($ENV{CODEMGR_WS}) {
1093 my $Root;
1094
1095 # Without a user specified dependency directory see if we're
1096 # part of a codemanager workspace and if a proto area exists.
1097 $Proto = $Root if ($Root = $ENV{ROOT}) && (-d $Root);
1098 }
1099
1100 # If we are basing this analysis off the sharable objects found in
1101 # a proto area, then gather dependencies and construct an alternative
1102 # dependency mapping via a crle(1) configuration file.
1103 #
1104 # To support alternative dependency mapping we'll need ldd(1)'s
1105 # -e option. This is relatively new (s81_30), so make sure
1106 # ldd(1) is capable before gathering any dependency information.
1107 if ($opt{D} || $Proto) {
1108 if (system('ldd -e /usr/lib/lddstub 2> /dev/null')) {
1109 print "ldd: does not support -e, unable to ";
1110 print "create alternative dependency mappingings.\n";
1111 print "ldd: option added under 4390308 (s81_30).\n\n";
1112 } else {
1113 # If -D was specified, it supplies a list of files in
1114 # 'find_elf -r' format, and can use it directly. Otherwise,
1115 # we will run find_elf as a child process to find the
1116 # sharable objects found under $Proto.
1117 AltObjectConfig($opt{D} ? $opt{D} : "find_elf -frs $Proto|");
1118 }
1119 }
1120
1121 # To support unreferenced dependency detection we'll need ldd(1)'s -U
1122 # option. This is relatively new (4638070), and if not available we
1123 # can still fall back to -u. Even with this option, don't use -U with
1124 # releases prior to 5.10 as the cleanup for -U use only got integrated
1125 # into 5.10 under 4642023. Note, that nightly doesn't typically set a
1126 # RELEASE from the standard <env> files. Users who wish to disable use
1127 # of ldd(1)'s -U should set (or uncomment) RELEASE in their <env> file
1128 # if using nightly, or otherwise establish it in their environment.
1129 if (system('ldd -U /usr/lib/lddstub 2> /dev/null')) {
1130 $LddNoU = 1;
1131 } else {
1132 my($Release);
1133
1134 if (($Release = $ENV{RELEASE}) && (cmp_os_ver($Release, "<", "5.10"))) {
1135 $LddNoU = 1;
1136 } else {
1137 $LddNoU = 0;
|
5 # The contents of this file are subject to the terms of the
6 # Common Development and Distribution License (the "License").
7 # You may not use this file except in compliance with the License.
8 #
9 # You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10 # or http://www.opensolaris.org/os/licensing.
11 # See the License for the specific language governing permissions
12 # and limitations under the License.
13 #
14 # When distributing Covered Code, include this CDDL HEADER in each
15 # file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16 # If applicable, add the following below this CDDL HEADER, with the
17 # fields enclosed by brackets "[]" replaced with your own identifying
18 # information: Portions Copyright [yyyy] [name of copyright owner]
19 #
20 # CDDL HEADER END
21 #
22
23 #
24 # Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
25 # Copyright 2015, Nexenta Systems Inc.
26 #
27
28 #
29 # Check ELF information.
30 #
31 # This script descends a directory hierarchy inspecting ELF dynamic executables
32 # and shared objects. The general theme is to verify that common Makefile rules
33 # have been used to build these objects. Typical failures occur when Makefile
34 # rules are re-invented rather than being inherited from "cmd/lib" Makefiles.
35 #
36 # As always, a number of components don't follow the rules, and these are
37 # excluded to reduce this scripts output.
38 #
39 # By default any file that has conditions that should be reported is first
40 # listed and then each condition follows. The -o (one-line) option produces a
41 # more terse output which is better for sorting/diffing with "nightly".
42 #
43 # NOTE: missing dependencies, symbols or versions are reported by running the
44 # file through ldd(1). As objects within a proto area are built to exist in a
45 # base system, standard use of ldd(1) will bind any objects to dependencies
46 # that exist in the base system. It is frequently the case that newer objects
47 # exist in the proto area that are required to satisfy other objects
48 # dependencies, and without using these newer objects an ldd(1) will produce
49 # misleading error messages. To compensate for this, the -D/-d options, or the
50 # existence of the CODEMSG_WS/ROOT environment variables, cause the creation of
51 # alternative dependency mappings via crle(1) configuration files that establish
52 # any proto shared objects as alternatives to their base system location. Thus
53 # ldd(1) can be executed against these configuration files so that objects in a
54 # proto area bind to their dependencies in the same proto area.
55
56
57 # Define all global variables (required for strict)
58 use vars qw($Prog $Env $Ena64 $Tmpdir $Adjunct $Proto);
59 use vars qw($LddNoU $Conf32 $Conf64);
60 use vars qw(%opt);
61 use vars qw($ErrFH $ErrTtl $InfoFH $InfoTtl $OutCnt1 $OutCnt2);
62
63 # An exception file is used to specify regular expressions to match
64 # objects. These directives specify special attributes of the object.
65 # The regular expressions are read from the file and compiled into the
66 # regular expression variables.
67 #
68 # The name of each regular expression variable is of the form
69 #
70 # $EXRE_xxx
71 #
72 # where xxx is the name of the exception in lower case. For example,
73 # the regular expression variable for EXEC_STACK is $EXRE_exec_stack.
74 #
75 # onbld_elfmod::LoadExceptionsToEXRE() depends on this naming convention
76 # to initialize the regular expression variables, and to detect invalid
77 # exception names.
78 #
855 sub ProcFindElf {
856 my $file = $_[0];
857 my $line;
858 my $LineNum;
859
860 my $prefix = OpenFindElf($file, \*FIND_ELF, \$LineNum);
861
862 while ($line = onbld_elfmod::GetLine(\*FIND_ELF, \$LineNum)) {
863 next if !($line =~ /^OBJECT\s/i);
864
865 my ($item, $class, $type, $verdef, $obj) =
866 split(/\s+/, $line, 5);
867
868 ProcFile("$prefix/$obj", $obj, $class, $type, $verdef);
869 }
870
871 close FIND_ELF;
872 }
873
874
875 ## AltObjectConfig(proto, adjunct)
876 #
877 # Recurse through a directory hierarchy looking for appropriate dependencies
878 # to map from their standard system locations to the proto area via a crle
879 # config file.
880 #
881 # entry:
882 # proto, adjunct - Files of ELF objects, in 'find_elf -r' format, to
883 # examine.
884 #
885 # exit:
886 # Scripts are generated for the 32 and 64-bit cases to run crle
887 # and create runtime configuration files that will establish
888 # alternative dependency mappings for the objects identified.
889 #
890 # $Env - Set to environment variable definitions that will cause
891 # the config files generated by this routine to be used
892 # by ldd.
893 # $Conf32, $Conf64 - Undefined, or set to the config files generated
894 # by this routine. If defined, the caller is responsible for
895 # unlinking the files before exiting.
896 #
897 sub AltObjectConfig {
898 my $file = $_[0];
899 my ($Crle32, $Crle64);
900 my $line;
901 my $LineNum;
902 my $obj_path;
903 my $obj_active = 0;
904 my $obj_class;
905
906 my $prefix;
907 FILE:
908 while ($prefix = OpenFindElf($file, \*FIND_ELF)) {
909
910 LINE:
911 while ($line = onbld_elfmod::GetLine(\*FIND_ELF, \$LineNum)) {
912 ITEM: {
913
914 if ($line =~ /^OBJECT\s/i) {
915 my ($item, $class, $type, $verdef, $obj)
916 = split(/\s+/, $line, 5);
917
918 if ($type eq 'DYN') {
919 $obj_active = 1;
920 $obj_path = $obj;
921 $obj_class = $class;
922 } else {
923 # Only want sharable objects
924 $obj_active = 0;
925 }
926 last ITEM;
927 }
928
929 # We need to follow links to sharable objects
930 # so that any dependencies are expressed in all
931 # their available forms. We depend on ALIAS
932 # lines directly following the object they
933 # alias, so if we have a current object, this
934 # alias belongs to it.
935 if ($obj_active && ($line =~ /^ALIAS\s/i)) {
936 my ($item, $real_obj, $obj) =
937 split(/\s+/, $line, 3);
938 $obj_path = $obj;
939 last ITEM;
940 }
941
942 # Skip unrecognized item
943 next LINE;
944 }
945
946 next if !$obj_active;
947
948 my $full = "$prefix/$obj_path";
949
950 next if defined($EXRE_nocrlealt) &&
951 ($obj_path =~ $EXRE_nocrlealt);
952
953 my $Dir = $full;
954 $Dir =~ s/^(.*)\/.*$/$1/;
955
956 # Create a crle(1) script for the dependency we've
957 # found. We build separate scripts for the 32 and 64-bit
958 # cases. We create and initialize each script when we
959 # encounter the first object that needs it.
960 if ($obj_class == 32) {
961 if (!$Crle32) {
962 $Crle32 = "$Tmpdir/$Prog.crle32.$$";
963 open(CRLE32, "> $Crle32") || die
964 "$Prog: open failed: $Crle32: $!";
965 print CRLE32 "#!/bin/sh\ncrle \\\n";
966 }
967 print CRLE32 "\t-o $Dir -a /$obj_path \\\n";
968 } elsif ($Ena64) {
969 if (!$Crle64) {
970 $Crle64 = "$Tmpdir/$Prog.crle64.$$";
971 open(CRLE64, "> $Crle64") || die
972 "$Prog: open failed: $Crle64: $!";
973 print CRLE64 "#!/bin/sh\ncrle -64\\\n";
974 }
975 print CRLE64 "\t-o $Dir -a /$obj_path \\\n";
976 }
977 }
978
979 close FIND_ELF;
980 if ($file eq $_[0]) {
981 $file = $_[1];
982 next FILE;
983 }
984
985 last FILE;
986 }
987
988 # Now that the config scripts are complete, use them to generate
989 # runtime linker config files.
990 $Adjunct //= "";
991
992 if ($Crle64) {
993 print CRLE64
994 "\t-l ${Proto}/lib/64:${Proto}/usr/lib/64 \\\n";
995
996 print CRLE64
997 "\t-l ${Adjunct}/lib/64:${Adjunct}/usr/lib/64 \\\n";
998
999 $Conf64 = "$Tmpdir/$Prog.conf64.$$";
1000 print CRLE64 "\t-c $Conf64\n";
1001
1002 chmod 0755, $Crle64;
1003 close CRLE64;
1004
1005 undef $Conf64 if system($Crle64);
1006
1007 # Done with the script
1008 unlink $Crle64;
1009 }
1010 if ($Crle32) {
1011 print CRLE32 "\t-l ${Proto}/lib:${Proto}/usr/lib \\\n";
1012 print CRLE32 "\t-l ${Adjunct}/lib:${Adjunct}/usr/lib \\\n";
1013
1014 $Conf32 = "$Tmpdir/$Prog.conf32.$$";
1015 print CRLE32 "\t-c $Conf32\n";
1016
1017 chmod 0755, $Crle32;
1018 close CRLE32;
1019
1020 undef $Conf32 if system($Crle32);
1021
1022 # Done with the script
1023 unlink $Crle32;
1024 }
1025
1026 # Set $Env so that we will use the config files generated above
1027 # when we run ldd.
1028 if ($Crle64 && $Conf64 && $Crle32 && $Conf32) {
1029 $Env = "-e LD_FLAGS=config_64=$Conf64,config_32=$Conf32";
1030 } elsif ($Crle64 && $Conf64) {
1031 $Env = "-e LD_FLAGS=config_64=$Conf64";
1032 } elsif ($Crle32 && $Conf32) {
1033 $Env = "-e LD_FLAGS=config_32=$Conf32";
1056 require "$moddir/onbld_elfmod.pm";
1057
1058 # Determine what machinery is available.
1059 my $Mach = `uname -p`;
1060 my$Isalist = `isalist`;
1061 if ($Mach =~ /sparc/) {
1062 if ($Isalist =~ /sparcv9/) {
1063 $Ena64 = "ok";
1064 }
1065 } elsif ($Mach =~ /i386/) {
1066 if ($Isalist =~ /amd64/) {
1067 $Ena64 = "ok";
1068 }
1069 }
1070
1071 # $Env is used with all calls to ldd. It is set by AltObjectConfig to
1072 # cause an alternate object mapping runtime config file to be used.
1073 $Env = '';
1074
1075 # Check that we have arguments.
1076 if ((getopts('A:a:D:d:E:e:f:I:imosvw:', \%opt) == 0) ||
1077 (!$opt{f} && ($#ARGV == -1))) {
1078 print "usage: $Prog [-imosv] [-A depfile | -a depdir ] [-D depfile | -d depdir] [-E errfile]\n";
1079 print "\t\t[-e exfile] [-f listfile] [-I infofile] [-w outdir]\n";
1080 print "\t\t[file | dir]...\n";
1081 print "\n";
1082 print "\t[-A depfile]\testablish adjunct dependencies from 'find_elf -r' file list\n";
1083 print "\t[-a depdir]\testablish adjunct dependencies from under directory\n";
1084 print "\t[-D depfile]\testablish dependencies from 'find_elf -r' file list\n";
1085 print "\t[-d depdir]\testablish dependencies from under directory\n";
1086 print "\t[-E errfile]\tdirect error output to file\n";
1087 print "\t[-e exfile]\texceptions file\n";
1088 print "\t[-f listfile]\tuse file list produced by find_elf -r\n";
1089 print "\t[-I infofile]\tdirect informational output (-i, -v) to file\n";
1090 print "\t[-i]\t\tproduce dynamic table entry information\n";
1091 print "\t[-m]\t\tprocess mcs(1) comments\n";
1092 print "\t[-o]\t\tproduce one-liner output (prefixed with pathname)\n";
1093 print "\t[-s]\t\tprocess .stab and .symtab entries\n";
1094 print "\t[-v]\t\tprocess version definition entries\n";
1095 print "\t[-w outdir]\tinterpret all files relative to given directory\n";
1096 exit 1;
1097 }
1098
1099 die "$Prog: -A and -a options are mutually exclusive\n" if ($opt{A} && $opt{a});
1100 die "$Prog: -D and -d options are mutually exclusive\n" if ($opt{D} && $opt{d});
1101
1102 $Tmpdir = "/tmp" if (!($Tmpdir = $ENV{TMPDIR}) || (! -d $Tmpdir));
1103
1104 # If -w, change working directory to given location
1105 !$opt{w} || chdir($opt{w}) || die "$Prog: can't cd to $opt{w}";
1106
1107 # Locate and process the exceptions file
1108 onbld_elfmod::LoadExceptionsToEXRE('check_rtime');
1109
1110 # Is there a proto area available, either via the -d option, or because
1111 # we are part of an activated workspace?
1112 if ($opt{d}) {
1113 # User specified dependency directory - make sure it exists.
1114 -d $opt{d} || die "$Prog: $opt{d} is not a directory\n";
1115 $Proto = $opt{d};
1116 } elsif ($ENV{CODEMGR_WS}) {
1117 my $Root;
1118
1119 # Without a user specified dependency directory see if we're
1120 # part of a codemanager workspace and if a proto area exists.
1121 $Proto = $Root if ($Root = $ENV{ROOT}) && (-d $Root);
1122 }
1123
1124 # Is there an adjunct proto area available, either via the -a option,
1125 # or because we are part of an activated workspace?
1126 if ($opt{a}) {
1127 # User specified dependency directory - make sure it exists.
1128 -d $opt{a} || die "$Prog: $opt{a} is not a directory\n";
1129 $Adjunct = $opt{a};
1130 } elsif ($ENV{CODEMGR_WS}) {
1131 my $Root;
1132
1133 # Without a user specified dependency directory see if we're
1134 # part of a codemanager workspace and if an adjunct proto area
1135 # exists.
1136 $Adjunct = $Root if ($Root = $ENV{ADJUNCT_PROTO}) && (-d $Root);
1137 }
1138
1139 # If we are basing this analysis off the sharable objects found in
1140 # a proto area, then gather dependencies and construct an alternative
1141 # dependency mapping via a crle(1) configuration file.
1142 #
1143 # To support alternative dependency mapping we'll need ldd(1)'s
1144 # -e option. This is relatively new (s81_30), so make sure
1145 # ldd(1) is capable before gathering any dependency information.
1146 if ($opt{D} || $Proto || $Adjunct) {
1147 if (system('ldd -e /usr/lib/lddstub 2> /dev/null')) {
1148 print "ldd: does not support -e, unable to ";
1149 print "create alternative dependency mappingings.\n";
1150 print "ldd: option added under 4390308 (s81_30).\n\n";
1151 } else {
1152 # If -D or -A was specified, it supplies a list of files in
1153 # 'find_elf -r' format, and can use it directly. Otherwise,
1154 # we will run find_elf as a child process to find the
1155 # sharable objects found under $Proto.
1156 AltObjectConfig($opt{D} ? $opt{D} : "find_elf -frs $Proto|",
1157 $opt{A} ? $opt{A} : $Adjunct ? "find_elf -frs $Adjunct|" : "/dev/null");
1158 }
1159 }
1160
1161 # To support unreferenced dependency detection we'll need ldd(1)'s -U
1162 # option. This is relatively new (4638070), and if not available we
1163 # can still fall back to -u. Even with this option, don't use -U with
1164 # releases prior to 5.10 as the cleanup for -U use only got integrated
1165 # into 5.10 under 4642023. Note, that nightly doesn't typically set a
1166 # RELEASE from the standard <env> files. Users who wish to disable use
1167 # of ldd(1)'s -U should set (or uncomment) RELEASE in their <env> file
1168 # if using nightly, or otherwise establish it in their environment.
1169 if (system('ldd -U /usr/lib/lddstub 2> /dev/null')) {
1170 $LddNoU = 1;
1171 } else {
1172 my($Release);
1173
1174 if (($Release = $ENV{RELEASE}) && (cmp_os_ver($Release, "<", "5.10"))) {
1175 $LddNoU = 1;
1176 } else {
1177 $LddNoU = 0;
|