//drivel.com/jlick/cgi-bin/follow Multi-Platform Package Notes

Multi-Platform Package Notes



SYNOPSIS: Distributing software in pkg format on Solaris systems is a convenient way that allows systems administer to easily both install and remove a piece of software in a consistent manner. While there are several easy tutorials on making traditional packages, they do not cover more advanced usages of the pkg format. One such use is making a package which contains binaries for more than one platform type, such as for both sparc and i386 systems. This would allow you to distribute one package which would install the appropriate version on any system. This document will show how to create such a package.



PREREQUISITES: This document assumes a general familiarity with creating packages. If you are not familiar with this process, consult one of the following:



BACKGROUND: After learning the basics of building packages, I wanted to make packages of some of the software I normally install on several systems. Since I have both sparc and i386 type Solaris systems, it would have been a lot more convenient to be able to make a single package which could install on both. And I knew it was possible, because Sun packages such as Solstice Disksuite came this way. I came up with this method by poring not guaranteed to be 100% correct, but it has worked for me so far. This will walk you through how to create a sample Multi-Platform Package. After creating this simple package you should be able to create other Multi-Platform Packages on your own.



STARTING OUT: The package we will make will be called JLmultpkg. In a convenient location, do a "mkdir -p multipkg/JLmultpkg-proto" and go into that directory. The rest of this document will use paths relative to this directory unless otherwise noted. Create a "copyright" file as normal. Then create a basic pkginfo file.

In pkginfo there are a few differences from the typical entries. For ARCH, instead of just "sparc" for example, you would list "sparc,i386" if you have both Sparc and i386 binaries. You can also set this to "all" but that would pose problems if for example a user tried to install this on a PowerPC system and the requisite binaries were not available. If you want to support other systems besides Sparc and i386, just list the architectures for each system. "uname -p" will tell you the right processor name to use. Avoid using the kernel architecture names (sun4m, sun4c, sun4d, etc.) unless your package is really limited to that kernel. The next time a new architecture comes out (e.g. sun4u), your package would no longer install on those new systems.

You also need to add a CLASSES setting to tell it which classes (the second field in prototype or third field in pkgmap) to install by default. Set this to "none" By default pkgadd will attempt to add all available classes, but we are going to use the class field to tell pkgadd which files to install for each architecture. Setting this to "none" will tell pkgadd to add at error because it will find multiple copies of things to install and get confused.

Finally you need to set I386LOC and SPARCLOC to /. These will be expanded into variables later. These variable names will be embedded into pathnames in the package layout and the prototype file, and are simply ways to have two sets of binaries side by side in seperate directories. Since the variable gets expanded to / it is a nullop and puts the binaries in the same place at the end of everything.

A simple pkginfo file would thus look like this:

PKG="JLmultpkg"
NAME="Multi-Platform Package Test"
VERSION=1.0.0
CATEGORY=system
CLASSES=none
ARCH=sparc,i386
VENDOR="James Lick"
BASEDIR=/
I386LOC=/
SPARCLOC=/



LAYING OUT FILES: This package will install two files on any system, a platform independent shell script, installed as /usr/sbin/systype, and a platform specific data file, installed as /etc/mytype. Since we are supporting two system types, we will need three files: One copy of systype and two copies of do something like this, but this is just a silly example to show how to have both platform independent and specific files in the same package. A more typical example is where binaries and libraries would be platform specific and manual pages and header files would be platform independent. No sense in having these files duplicated more than once!

% mkdir -p usr/sbin
% cat > usr/sbin/systype


echo "This system type is `cat /etc/mytype`."
^D
% chmod 555 usr/sbin/systype

them in different subdirectories depending on the architecture:

% mkdir -p etc/\$I386LOC
% echo "i386" > etc/\$I386LOC/mytype
% mkdir -p etc/\$SPARCLOC
% echo "sparc" > etc/\$SPARCLOC/mytype

Then setup the basic prototype file:

% find usr etc -print | pkgproto > prototype

Edit prototype to add in the required files and get rid of the shared the ownership and permissions, etc.:

i pkginfo
i copyright
f none usr/sbin/systype 0555 bin bin
f none etc/$I386LOC/mytype 0444 bin bin
f none etc/$SPARCLOC/mytype 0444 bin bin



THE MAGIC: Now comes the magic that makes the Multi-Platform stuff really work. First we need to create a script which will add the platform specific type to the CLASSES setting. This script is called request and will be run by the pkgadd program. The output file is read to set or reset variables. In our case we want to add the "uname -p" to CLASSES. Edit "request" and insert the following:



cat >$1 <<EOF
CLASSES="${CLASSES} `uname -p`"
export CLASSES
EOF

Then you need to add request as an install item to prototype, and change the class to sparc or i386 for the two platform specific files. Your prototype file would then look like:

i request
i pkginfo
i copyright
f none usr/sbin/systype 0555 bin bin
f i386 etc/$I386LOC/mytype 0444 bin bin
f sparc etc/$SPARCLOC/mytype 0444 bin bin



FINISHING UP: setup to an actual package:

% pkgmk -o -r `pwd` -d ..


WARNING: missing directory entry for <etc>
WARNING: missing directory entry for <etc/$I386LOC>
WARNING: missing directory entry for <etc/$SPARCLOC>
WARNING: missing directory entry for <usr>
WARNING: missing directory entry for <usr/sbin>
WARNING: parameter <PSTAMP> set to "hacienda.shoreside.com970322020250"
WARNING: unreferenced class <i386> in prototype file
WARNING: unreferenced class <sparc> in prototype file

part 1 -- 28 blocks, 14 entries

/home/jlick/multipkg/JLmultpkg/pkgmap
/home/jlick/multipkg/JLmultpkg/pkginfo
/home/jlick/multipkg/JLmultpkg/install/copyright
/home/jlick/multipkg/JLmultpkg/reloc/etc/$I386LOC/mytype
/home/jlick/multipkg/JLmultpkg/reloc/etc/$SPARCLOC/mytype
/home/jlick/multipkg/JLmultpkg/install/request
/home/jlick/multipkg/JLmultpkg/reloc/usr/sbin/systype


%

This will create the finished package and place it in the ".." directory.



TRYING IT OUT: Try installing it on different systems and test it out:

% cd ..
% su
Password:


Processing package instance <JLmultpkg> from </home/jlick/multipkg>

Multi-Platform Package Test
(sparc,i386) 1.0.0
Copyright (C) 1997 by James Lick
Using </> as the package base directory.






Installing Multi-Platform Package Test as <JLmultpkg>


/usr/sbin/systype
[ verifying class <none> ]
/etc/mytype
[ verifying class <sparc> ]

Installation of <JLmultpkg> was successful.

This system type is sparc.


The following package is currently installed:
   JLmultpkg Multi-Platform Package Test
                   (sparc,i386) 1.0.0

Do you want to remove this package? y





/etc/mytype

/usr/sbin/systype


Removal of <JLmultpkg> was successful.

Try adding the package to both a sparc and i386 system and /usr/sbin/systype will show the appropriate architecture when run. Check /etc/mytype to see that it really did install a different file on each system type.



SHORTCUTS FOR THE LAZY: to do all the above work and can just download a tarball with all the prototypes and the finished package as multipkg.tar.gz.


Author: James Lick / E-mail: james.lick@gmail.com