Subversion Repositories DevTools

Rev

Go to most recent revision | Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
1530 dpurdie 1
#set -x
2
# This script initializes the backout data for a patch package
3
# directory format options.
4
# 
5
#       @(#)preinstall 1.10 99/04/23 SMI
6
#
7
# Copyright (c) 1995 by Sun Microsystems, Inc.
8
# All rights reserved
9
#
10
 
11
PATH=/usr/sadm/bin:$PATH
12
recovery="no"
13
 
14
if [ "$PKG_INSTALL_ROOT" = "/" ]; then
15
	PKG_INSTALL_ROOT=""
16
fi
17
 
18
# Check to see if this is a patch installation retry.
19
if [ "$INTERRUPTION" = "yes" ]; then
20
    if [ -d "$PKG_INSTALL_ROOT/var/tmp/$SUNW_PATCHID.$PKGINST" ] || [ -d "$PATCH_BUILD_DIR/$SUNW_PATCHID.$PKGINST" ]; then
21
        recovery="yes"
22
    fi
23
fi
24
 
25
if [ -n "$PATCH_BUILD_DIR" -a -d "$PATCH_BUILD_DIR" ]; then
26
	BUILD_DIR="$PATCH_BUILD_DIR/$SUNW_PATCHID.$PKGINST"
27
else
28
	BUILD_DIR="$PKG_INSTALL_ROOT/var/tmp/$SUNW_PATCHID.$PKGINST"
29
fi
30
 
31
FILE_DIR=$BUILD_DIR/files
32
RELOC_DIR=$BUILD_DIR/files/reloc
33
ROOT_DIR=$BUILD_DIR/files/root
34
PROTO_FILE=$BUILD_DIR/prototype
35
ORIGPKGINFO=$PKG_INSTALL_ROOT/var/sadm/pkg/$PKGINST/pkginfo
36
PKGINFO_FILE=$BUILD_DIR/pkginfo
37
THIS_DIR=`dirname $0`
38
INSTALLINGPKGINFO=`dirname $THIS_DIR`
39
 
40
if [ "$PATCH_PROGRESSIVE" = "true" ]; then
41
	# If this is being used in an old-style patch, insert
42
	# the old-style script commands here.
43
 
44
	#XXXOld_CommandsXXX#
45
 
46
	exit 0
47
fi
48
 
49
#
50
# Unless specifically denied, initialize the backout patch data by
51
# creating the build directory and copying over the original pkginfo
52
# which pkgadd saved in case it had to be restored.
53
#
54
if [ "$PATCH_NO_UNDO" != "true" ] && [ "$recovery" = "no" ]; then
55
	if [ -d $BUILD_DIR ]; then
56
		rm -r $BUILD_DIR
57
	fi
58
 
59
	# If this is a retry of the same patch then recovery is set to
60
	# yes. Which means there is a build directory already in
61
	# place with the correct backout data.
62
 
63
	if [ "$recovery" = "no" ]; then
64
		mkdir $BUILD_DIR
65
		mkdir -p $RELOC_DIR
66
		mkdir $ROOT_DIR
67
	fi
68
 
69
	#
70
	# Here we initialize the backout pkginfo file by first
71
	# copying over the old pkginfo file and then adding the
72
	# ACTIVE_PATCH parameter so the backout will know what patch
73
	# it's backing out.
74
	#
75
	# NOTE : Within the installation, pkgparam returns the
76
	# original data.
77
	#
78
	pkgparam -v $PKGINST | nawk '
79
		$1 ~ /PATCHLIST/	{ next; }
80
		$1 ~ /CLASSES/		{ next; }
81
		$1 ~ /PATCH_OBSOLETES/	{ next; }
82
		$1 ~ /ACTIVE_OBSOLETES/	{ next; }
83
		$1 ~ /SUNW_OBSOLETES/	{ next; }
84
		$1 ~ /ACTIVE_PATCH/	{ next; }
85
		$1 ~ /SUNW_PATCHID/	{ next; }
86
		$1 ~ /UPDATE/		{ next; }
87
		$1 ~ /SCRIPTS_DIR/	{ next; }
88
		$1 ~ /PATCH_NO_UNDO/	{ next; }
89
		$1 ~ /INSTDATE/		{ next; }
90
		$1 ~ /PKGINST/		{ next; }
91
		$1 ~ /OAMBASE/		{ next; }
92
		$1 ~ /PATH/		{ next; }
93
		{ print; } ' | sed s,\'\"\'\"\',ApOsTrOpHe,g > $PKGINFO_FILE
94
 
95
        # The previous is needed to workaround pkgparam
96
        # inserting '"'"' for every ' it finds in the
97
        # pkginfo file. see bugid 4052001.
98
 
99
	# If there is an undo script delivered with this patch pkg
100
	# there is a possibility that when the patch gets backed out
101
	# it may not get executed due to the CLASSES macro in the
102
	# original pkginfo file may not contain the class
103
	# identifier. Thus we need to merge the old CLASSES macro and
104
	# the installing patch pkgs CLASSES macro.
105
 
106
	nawk ' $1 ~ /CLASSES/ {print $0} ' $INSTALLINGPKGINFO/pkginfo \
107
		| sed s/CLASSES=// > /tmp/installingCLASSES.$$
108
 
109
	classIDs=`nawk ' $1 ~ /CLASSES/ {print $0} ' $ORIGPKGINFO \
110
		| sed s/CLASSES=//`
111
 
112
	for instClass in $classIDs; do
113
		notFound=`grep "$instClass" /tmp/installingCLASSES.$$`
114
		if [ -z "$notFound" ]; then
115
			newCLASSESlist="$instClass $newCLASSESlist"
116
		fi
117
		notFound=""
118
	done
119
 
120
	classes=`nawk ' $1 ~ /CLASSES/ {print $0} ' $ORIGPKGINFO`  
121
	newCLASSESlist="$classes $newCLASSESlist"  
122
 
123
	echo "$newCLASSESlist" >> $PKGINFO_FILE
124
	echo "ACTIVE_PATCH=$SUNW_PATCHID" >> $PKGINFO_FILE
125
	echo "ACTIVE_OBSOLETES=$ACTIVE_OBSOLETES" >> $PKGINFO_FILE
126
 
127
	rm /tmp/installingCLASSES.$$
128
 
129
	# And now initialize the backout prototype file with the
130
	# pkginfo file just formulated.
131
	echo "i pkginfo" > $PROTO_FILE
132
 
133
	# Copy over the backout scripts including the undo class
134
	# action scripts
135
	for script in $SCRIPTS_DIR/*; do
136
		srcscript=`basename $script`
137
		targscript=`echo $srcscript | nawk '
138
			{ script=$0; }
139
			/u\./ {
140
				sub("u.", "i.", script);
141
				print script;
142
				next;
143
			}
144
			/patch_/ {
145
				sub("patch_", "", script);
146
				print script;
147
				next;
148
			}
149
			{ print "dont_use" } '`
150
		if [ "$targscript" = "dont_use" ]; then
151
			continue
152
		fi
153
 
154
		echo "i $targscript=$FILE_DIR/$targscript" >> $PROTO_FILE
155
		cp $SCRIPTS_DIR/$srcscript $FILE_DIR/$targscript
156
	done
157
 
158
	#
159
	# Now add entries to the prototype file that won't be passed to
160
	# class action scripts. If the entry is brand new, add it to the
161
	# deletes file for the backout package.
162
	#
163
	Our_Pkgmap=`dirname $SCRIPTS_DIR`/pkgmap
164
	BO_Deletes=$FILE_DIR/deletes
165
 
166
	nawk -v basedir=${BASEDIR:-/} '
167
		BEGIN { count=0; }
168
		{
169
			token = $2;
170
			ftype = $1;
171
		}
172
		$1 ~ /[#\!:]/ { next; }
173
		$1 ~ /[0123456789]/ {
174
			if ( NF >= 3) {
175
				token = $3;
176
				ftype = $2;
177
			} else {
178
				next;
179
			}
180
		}
181
		{ if (ftype == "i" || ftype == "e" || ftype == "f" || ftype == "v" || ftype == "d") { next; } }
182
		{
183
			equals=match($4, "=")-1;
184
			if ( equals == -1 ) { print $3, $4; }
185
			else { print $3, substr($4, 0, equals); }
186
		}
187
		' < $Our_Pkgmap | while read class path; do
188
			#
189
			# NOTE: If pkgproto is passed a file that is
190
			# actually a hard link to another file, it
191
			# will return ftype "f" because the first link
192
			# in the list (consisting of only one file) is
193
			# viewed by pkgproto as the source and always
194
			# gets ftype "f".
195
			#
196
			# If this isn't replacing something, then it
197
			# just goes to the deletes list.
198
			#
199
			if valpath -l $path; then
200
				Chk_Path="$BASEDIR/$path"
201
				Build_Path="$RELOC_DIR/$path"
202
				Proto_From="$BASEDIR"
203
			else	# It's an absolute path
204
				Chk_Path="$PKG_INSTALL_ROOT$path"
205
				Build_Path="$ROOT_DIR$path"
206
				Proto_From="$PKG_INSTALL_ROOT"
207
			fi
208
 
209
			#
210
			# Hard links have to be restored as regular files.
211
			# Unlike the others in this group, an actual
212
			# object will be required for the pkgmk.
213
			#
214
       			if [ -f "$Chk_Path" -a ! -h "$Chk_Path" ] ; then
215
				mkdir -p `dirname $Build_Path`
216
				cp -p $Chk_Path $Build_Path
217
				cd $Proto_From
218
				pkgproto -c $class "$Build_Path=$path" 1>> $PROTO_FILE 2> /dev/null
219
				cd $THIS_DIR
220
			elif [ -h "$Chk_Path" -o \
221
			     -c "$Chk_Path" -o \
222
			     -b "$Chk_Path" -o \
223
			     -p "$Chk_Path" ]; then
224
				pkgproto -c $class "$Chk_Path" 1>> $PROTO_FILE 2> /dev/null
225
			else
226
				echo $path >> $BO_Deletes
227
			fi
228
		done
229
fi
230
 
231
# If additional operations are required for this package, place
232
# those package-specific commands here.
233
 
234
#XXXSpecial_CommandsXXX#
235
 
236
exit 0