12 July 2011

Notes on Packages in Solaris 11

While working out details for a separate write up, I started stumbling
through Solaris' new handling of packages, IPS.  Unlike previous versions
of Solaris which used the traditional "pkgXYZ" commands, directory
structures, etc, IPS (image packaging system) uses a completely new
scheme.  The details herein compare some of the surprises I found in
simply trying to identify package ownership of a file and expected
permissions / (uid/gid) ownership of said file.  The host details for
this are:
        HOSTs:          solex, sunspot
        PROMPT:         host [0]
        OSes:           Solaris 11 Express snv_151a (solex)
                        Solaris 10 10/09 u8 (sunspot)
To start, I was trying to verify the package owner of 'pmap' under
Solaris 11 using the traditional 'pkgchk' command:
        solex [0] /usr/sbin/pkgchk -l -p /usr/bin/pmap
        solex [0] /bin/ls -ld /usr/bin/pmap
        -r-xr-xr-x  77 root     bin         8420 Nov  5  2010 /usr/bin/pmap
        solex [0]
The above begets us no errors, but also no data is returned.  We can also
see that 'pmap' does exist as returned by 'ls'.  Something had to install
it though it seems there may be issues with Solaris' package database.
Switching over to our Solaris 10 host (sunspot), 'pkgchk' actually
produces far more useful results, telling us the file is a link and the
name of the owning package (SUNWesu).  This is followed up by 'pkginfo'
for further information about the package:
        sunspot [0] /usr/sbin/pkgchk -l -p /usr/bin/pmap
        Pathname: /usr/bin/pmap
        Type: linked file
        Source of link: ../../usr/lib/isaexec
        Referenced by the following packages:
                SUNWesu
        Current status: installed

        sunspot [0] /usr/bin/pkginfo SUNWesu
        system      SUNWesu Extended System Utilities
        sunspot [0] /usr/bin/pkginfo -l SUNWesu
           PKGINST:  SUNWesu
              NAME:  Extended System Utilities
          CATEGORY:  system
              ARCH:  i386
           VERSION:  11.10.0,REV=2005.01.21.16.34
           BASEDIR:  /
            VENDOR:  Sun Microsystems, Inc.
              DESC:  additional UNIX system utilities, including awk, bc, cal, compress, diff, \
        dos2unix, last, rup, sort, spell, sum, uniq, and uuencode
            PSTAMP:  on10ptchfeatx20090902230800
          INSTDATE:  May 16 2011 20:48
           HOTLINE:  Please contact your local service provider
            STATUS:  completely installed
             FILES:      169 installed pathnames
                          12 shared pathnames
                          21 linked files
                          18 directories
                         107 executables
                        3700 blocks used (approx)
Figuring this might have something to do with the installed package
directories, we check things out for package "SUNWesu" on sunspot to
give us general expectations for solex:
        sunspot [0] /bin/ls -Fb /var/sadm/pkg/SUNWesu
        install/  pkginfo   save/
        sunspot [0] /bin/find /var/sadm/pkg/SUNWesu -print | /bin/wc -l
              13
        sunspot [0] /bin/find /var/sadm/pkg/SUNWesu -exec /bin/grep -l pmap {} \;
        /var/sadm/pkg/SUNWesu/save/pspool/SUNWesu/pkgmap
        sunspot [0] /bin/grep pmap /var/sadm/pkg/SUNWesu/save/pspool/SUNWesu/pkgmap
        1 f none usr/bin/amd64/pmap 0555 root bin 23880 8314 1233854515
        1 f none usr/bin/i86/pmap 0555 root bin 18720 35247 1233854515
        1 l none usr/bin/pmap=../../usr/lib/isaexec
        1 s none usr/proc/bin/pmap=../../bin/pmap
        sunspot [0] /usr/sbin/pkgchk -l -p /usr/bin/amd64/pmap
        Pathname: /usr/bin/amd64/pmap
        Type: regular file
        Expected mode: 0555
        Expected owner: root
        Expected group: bin
        Expected file size (bytes): 23880
        Expected sum(1) of contents: 8314
        Expected last modification: Feb 05 12:21:55 PM 2009
        Referenced by the following packages:
                SUNWesu
        Current status: installed

        sunspot [0]
In the 'ls' above, we can see the install remnants of "SUNWesu" and via
the package's "pkgmap" file, confirm that '/usr/bin/pmap' is a linked
file to 'isaexec'.  Since this is an x64 host, '/usr/bin/amd64/pmap'
will be executed when we run '/usr/bin/pmap'.  Given this, the 'pkgchk'
above verifies 'amd64/pmap' returning back a legible form of the content
output from "pkgmap".  With what we now know from Solaris 10, let's turn
back to Solaris 11 (solex).  Below, 'pkginfo' is run against "SUNWesu"
which gets us nearly the same information as from Solaris 10 (Version
has updated, Vendor has changed, no file details are included):
        solex [0] /usr/bin/pkginfo -l SUNWesu
           PKGINST:  SUNWesu
              NAME:  Extended System Utilities
          CATEGORY:  system
              ARCH:  i386
           VERSION:  11.11,REV=2009.11.11
           BASEDIR:  /
            VENDOR:  Oracle Corporation
              DESC:  additional UNIX system utilities, including awk, bc, cal, compress, diff, \
        dos2unix, last, rup, sort, spell, uniq, and uuencode
          INSTDATE:  Nov 05 2010 09:14
           HOTLINE:  Please contact your local service provider
            STATUS:  completely installed

Unfortunately our luck runs out running 'pkgchk' against "SUNWesu":

        solex [0] /usr/sbin/pkgchk -l SUNWesu
        WARNING: Package <SUNWesu> is installed but empty
Having a look under "/var/sadm/pkg/SUNWesu" gives us two "pkginfo" files
(both identical other than name), considerably less than what we saw in
Solaris 10.  Given the files under "/var/sadm/pkg/SUNWesu", a subsequent
search of the directory also finds no reference to 'pmap' as expected:
        solex [0] /bin/ls -Fb /var/sadm/pkg/SUNWesu
        pkginfo     pkginfo.2
        solex [0] /bin/find /var/sadm/pkg/SUNWesu -exec /bin/grep -l pmap {} \;
        solex [0]
In Solaris 11, IPS was introduced.  Part of the intention seems to
have been consolidation of the "pkgXYZ" commands into a single command,
'pkg', which is a python script rather than a compiled binary.  Using 'pkg
search -l', we can search locally installed packages for our 'pmap' file:
        solex [0] /usr/bin/file /usr/bin/pkg
        /usr/bin/pkg:   executable /usr/bin/python2.6 script
        solex [0] /usr/bin/pkg search -l /usr/bin/pmap
        INDEX      ACTION   VALUE        PACKAGE
        path       hardlink usr/bin/pmap pkg:/system/extended-system-utilities@0.5.11-0.151.0.1
        solex [0] /usr/bin/pkg info -l pkg:/system/extended-system-utilities
                  Name: system/extended-system-utilities
               Summary: Extended System Utilities
           Description: additional UNIX system utilities, including awk, bc, cal,
                        compress, diff, dos2unix, last, rup, sort, spell, uniq, and
                        uuencode
              Category: System/Core
                 State: Installed
             Publisher: solaris
               Version: 0.5.11
         Build Release: 5.11
                Branch: 0.151.0.1
        Packaging Date: November  5, 2010 12:17:09 AM
                  Size: 2.48 MB
                  FMRI: pkg://solaris/system/extended-system-utilities@0.5.11,5.11-0.151.0.1:20101105T001709Z
        solex [0]
Following the "search" above, 'pkg info -l' (-l for local) returns
similar information to the original Solaris 'pkginfo' command.  Of note,
the package is no longer referenced as SUNWesu, but instead named
"system/extended-system-utilities" (it almost feels like naming found
in FreeBSD's ports collection).  Since the information isn't coming from
"/var/sadm/pkg" any longer, checking the pkg(5) man page makes mention of
"$IMAGE_ROOT/var/pkg" where "$IMAGE_ROOT" is equivalent to "/".  Under
"/var/pkg" exists directory "pkg" which contains IPS package data for
each package installed (sub-directories use URL encoded "%2F" for "/"):
        solex [0] /bin/ls -Fb /var/pkg/pkg/system%2Fextended-system-utilities
        0.5.11%2C5.11-0.151.0.1%3A20101105T001709Z/
        solex [0] cd /var/pkg/pkg/system%2Fextended-system-utilities
        solex [0] /bin/ls -Fb 0.5.11%2C5.11-0.151.0.1%3A20101105T001709Z
        license.system-extended-system-utilities.l
        manifest
        manifest.depend
        manifest.dir 
        manifest.dircache
        manifest.file
        manifest.hardlink
        manifest.legacy
        manifest.license
        manifest.link
        manifest.set
        solex [0] cd 0.5.11%2C5.11-0.151.0.1%3A20101105T001709Z
        solex [0] /bin/grep '/usr/bin/pmap' *
        solex [1] /bin/grep 'usr/bin/pmap' *
        manifest:hardlink path=usr/bin/pmap target=../../usr/lib/isaexec
        manifest.hardlink:hardlink path=usr/bin/pmap target=../../usr/lib/isaexec
Quite different from the pre-Solaris 11 "/var/sadm/pkg" files.  In the
above we can see that both "manifest" and "manifest.hardlink" have
references to 'pmap'.  (The leading "/" is stripped off in package files
to allow for package installations in alternate root environments.)
Since we found 'usr/bin/pmap' in "manifest", I reasoned there would be
other references there as well:
        solex [0] /bin/grep pmap manifest
        file bca2a02c3683287a019411edfef9e6d4c71ce937 chash=b49cfdcc0b6bc30d94f1a7c44939015fdda31983 \
         elfarch=i386 elfbits=32 elfhash=954dac0d47b4e721c11550f2903ab05e1be92bdf group=bin mode=0555 \
         owner=root path=usr/bin/i86/pmap pkg.csize=12819 pkg.size=32256 variant.arch=i386
        file e95805f0e5d1a0d1a7484362043bcb96833d5700 chash=bca928ef3204213e9901a0ec23a1a9600837d499 \
         elfarch=i386 elfbits=64 elfhash=a12a2b1792290297b5b047925bc5fda9d36c6a2d group=bin mode=0555 \
         owner=root path=usr/bin/amd64/pmap pkg.csize=14582 pkg.size=39176 variant.arch=i386
        file 409ed49b6797e05104c26f996de59b7d0cd547f3 chash=839c5eb3e4cc5fa6745dbb41d530113a7ef21cfb \
         elfarch=sparc elfbits=64 elfhash=4a74555d4dcb868df47ece2f21f0d9e30034f5d1 group=bin mode=0555 \
         owner=root path=usr/bin/sparcv9/pmap pkg.csize=14872 pkg.size=35728 variant.arch=sparc
        hardlink path=usr/bin/pmap target=../../usr/lib/isaexec
        link path=usr/proc/bin/pmap target=../../bin/pmap
Included in each line of response are the file type, executable
architecture, uid / gid ownership, install permissions and path.
(Given the length of each line, I've broken them up with a "\" to identify
line continuations.) Having found our package information, we can return
to our initial point of interest, useful information from our package
management commands.  To recap and compare, 'pkgchk' under Solaris 10 will
identify the package a file belongs to, type of file, permissions, etc:
        sunspot [0] /usr/sbin/pkgchk -l -p /usr/bin/pmap
        Pathname: /usr/bin/pmap
        Type: linked file
        Source of link: ../../usr/lib/isaexec
        Referenced by the following packages:
                SUNWesu
        Current status: installed

        sunspot [0] /usr/sbin/pkgchk -l -p /usr/bin/amd64/pmap
        Pathname: /usr/bin/amd64/pmap
        Type: regular file
        Expected mode: 0555
        Expected owner: root
        Expected group: bin
        Expected file size (bytes): 23880
        Expected sum(1) of contents: 8314
        Expected last modification: Feb 05 12:21:55 PM 2009
        Referenced by the following packages:
                SUNWesu
        Current status: installed
        sunspot [0]
Under Solaris 11, 'pkg' will return the most of same information, though
in a more complex command:
        solex [0] /usr/bin/pkg search -l -o action.name,mode,owner,group,pkg.size,path,target,pkg.name \
        > /usr/bin/pmap
        ACTION.NAME MODE OWNER GROUP PKG.SIZE PATH         TARGET                PKG.NAME
        hardlink                              usr/bin/pmap ../../usr/lib/isaexec system/extended-system-utilities
        solex [0] /usr/bin/pkg search -l -o action.name,mode,owner,group,pkg.size,path,target,pkg.name \
        > /usr/bin/amd64/pmap
        ACTION.NAME MODE OWNER GROUP PKG.SIZE PATH               TARGET PKG.NAME
        file        0555 root  bin      39176 usr/bin/amd64/pmap        system/extended-system-utilities
Though not as clean as above, the following is a little simpler:
        solex [0] /usr/bin/pkg search -l -o action.raw /usr/bin/amd64/pmap
        ACTION.RAW
        file e95805f0e5d1a0d1a7484362043bcb96833d5700 chash=bca928ef3204213e9901a0ec23a1a9600837d499 \
         elfarch=i386 elfbits=64 elfhash=a12a2b1792290297b5b047925bc5fda9d36c6a2d group=bin mode=0555 \
         owner=root path=usr/bin/amd64/pmap pkg.csize=14582 pkg.size=39176 variant.arch=i386
        solex [0]

see also:
    pkg(1)    pkg(5)
    Package File Ownership