Thursday Oct 28, 2004
In a previous entry, I discussed on how you could
automate the collection of file integrity information using the Solaris 10 Basic Auditing and Reporting Tool
(or "BART"), Process Privileges,
Role-based Access-Control and
Secure Shell. Today,
I would like to talk about how you can quickly and easily validate BART manifests for file
integrity against the
Solaris Fingerprint Database (or the "sfpDB").
Before jumping into the details, I would first like to talk about BART and the sfpDB
including what they are, how they differ and how they can be used to complement one
another. These are important considerations that must be understand in order to be
able to use these technologies effectively.
The Basic Auditing and Reporting Tool is used to collect and compare attributes of filesystem
objects installed on a system. BART collects filesystem object attributes including name,
size, permissions, access control lists, UID, GID, etc. The exact attributes collected are
depend on the type of object being evaluated. For a more detailed description of the attributes
collected, see bart(1M).
You can run BART as many times as you like. In fact, each run of BART captures point in
time information about the filesystem. Any two independent BART runs can be compared to
determine if there have been any changes made to the objects being assessed. This is a
great capability for detecting change. For example, with BART, you can quickly and easily
answer the question: "has this file changed since yesterday"? In fact, since you can
compare any two BART runs, you can select the time duration based on your individual
requirements.
Regardless of the time intervals that you select, however, BART is still not able to
answer the question: "is this a genuine object that Sun shipped?" This is because you
need to manually perform your data collection using BART after the system has been
installed. There is always the possibility (however slight) that someone or something
could have changed a Sun-provided file from its default before you performed your first
BART snapshot. As a result, it is important to be able to determine if the files
contained in your BART manifest are genuine.
Luckily, there is another tool that you can use to help solve this problem. It is called
the Solaris Fingerprint Database
or sfpDB for short. The Solaris Fingerprint Database is a free SunSolve Online service that
enables users to verify the integrity of files distributed with the Solaris Operating Environment.
You can read more about the Solaris Fingerprint Database in the Sun BluePrints article
The Solaris Fingerprint
Database - A Security Tool for Solaris Operating Environment Files.
In a nutshell, the Solaris Fingerprint Database takes as input a list of MD5 file
fingerprints and returns information about any fingerprints that match known files
shipped by Sun. This is precisely where BART comes into play since BART collects
MD5 signatures of the files that it processes. You can extract these fingerprints
from the BART manifest and with some minor manipulation prepare them for submission
to the Solaris Fingerprint Database, either directly using the web site interface
or using the
Solaris Fingerprint Database Companion tool. The Solaris Fingerprint Database
Companion is a small Perl script that automates the submission process.
So, why would you want to do this? Great question! Leveraging the Solaris Fingerprint
Database is very useful when you build your first BART manifest. Since this could
have been done at system installation or perhaps days, weeks or months later, it is
important for your to determine if you are creating a baseline from known good and
genuine files. Further, this same technique can be re-applied to help resolve any
conflicts that may arise from the installation of patches, for example. That way,
you will know if a conflict was generated as a result of a new, genuine Sun file
being installed versus some other type of change.
So, let's look at how you can implement this tip. We will use a very simple BART
rules file to collect file signatures for items in the /usr/lib/nis directory. This
directory was chosen arbitrarily for its relatively small size (making it more useful
as an example). Any directory or set of directories could have been used here. To
instruct BART to create a manifest for the files in /usr/lib/nis, we use the following
command:
# find /usr/lib/nis | bart create -I
! Version 1.0
! Tuesday, October 26, 2004 (03:50:42)
# Format:
#fname D size mode acl dirmtime uid gid
#fname P size mode acl mtime uid gid
#fname S size mode acl mtime uid gid
#fname F size mode acl mtime uid gid contents
#fname L size mode acl lnmtime uid gid dest
#fname B size mode acl mtime uid gid devnode
#fname C size mode acl mtime uid gid devnode
/usr/lib/nis D 512 40755 user::rwx,group::r-x,mask:r-x,other:r-x 4166bb19 0 2
/usr/lib/nis/nisaddent F 63668 100555 user::r-x,group::r-x,mask:r-x,other:r-x 415cec73 0 2 ba94af26a1fa9dbb26ba0e2a07d888ec
/usr/lib/nis/nisauthconf F 10104 100555 user::r-x,group::r-x,mask:r-x,other:r-x 415cec73 0 2 08f50f2555553710f9eb3225ebc7a04e
/usr/lib/nis/nisclient F 38374 100755 user::rwx,group::r-x,mask:r-x,other:r-x 415cec8c 0 2 1bf5c90088933a61c0b1e9138d52b841
/usr/lib/nis/nisctl F 9816 100555 user::r-x,group::r-x,mask:r-x,other:r-x 415cec8b 0 2 fb4cade13611fb4904f06f26cc51ad8b
/usr/lib/nis/nisopaccess F 5545 100755 user::rwx,group::r-x,mask:r-x,other:r-x 415cec8d 0 2 00f19fcd403283f0510efadeafac2e66
/usr/lib/nis/nisping F 9904 100555 user::r-x,group::r-x,mask:r-x,other:r-x 415cec8b 0 2 dd928cf7778e19749b28334dfaf503b2
/usr/lib/nis/nispopulate F 33943 100755 user::rwx,group::r-x,mask:r-x,other:r-x 415cec8d 0 2 5af2053863e687464285d4892bcc4b11
/usr/lib/nis/nisserver F 38443 100755 user::rwx,group::r-x,mask:r-x,other:r-x 415cec8c 0 2 87e05dc59fd5e25f117313a3160c2c33
/usr/lib/nis/nissetup F 10927 100755 user::rwx,group::r-x,mask:r-x,other:r-x 415cec8c 0 2 8bdc76f327b86edee2c1dcafef289cb6
/usr/lib/nis/nisshowcache F 9656 100555 user::r-x,group::r-x,mask:r-x,other:r-x 415cec8b 0 2 a3d06fea784afe9ce6974cfa87dbe1d6
/usr/lib/nis/nisstat F 11056 100555 user::r-x,group::r-x,mask:r-x,other:r-x 415cec8a 0 2 63be71e1fb14121e20e95e1369d1485b
/usr/lib/nis/nisupdkeys F 18172 100555 user::r-x,group::r-x,mask:r-x,other:r-x 415cec8b 0 2 8f0fd3abbefd1ae1ef31083a18d59c18
What you will notice about this output is that the very last field is an MD5
fingerprint when the object type (column 2) is a file (type F). With this
information, it is then easy to construct a command that will create a list of
MD5 fingerprints that can be passed to the Solaris Fingerprint Database in a
format that it will be able to recognize. Basically, we just need to select
any type F (file) records and capture each corresponding fingerprint value.
This can be accomplished using the simple command:
# find /usr/lib/nis | bart create -I | grep -v "^#" | awk '$2 == "F" { print $NF }'
ba94af26a1fa9dbb26ba0e2a07d888ec
08f50f2555553710f9eb3225ebc7a04e
1bf5c90088933a61c0b1e9138d52b841
fb4cade13611fb4904f06f26cc51ad8b
00f19fcd403283f0510efadeafac2e66
dd928cf7778e19749b28334dfaf503b2
5af2053863e687464285d4892bcc4b11
87e05dc59fd5e25f117313a3160c2c33
8bdc76f327b86edee2c1dcafef289cb6
a3d06fea784afe9ce6974cfa87dbe1d6
63be71e1fb14121e20e95e1369d1485b
8f0fd3abbefd1ae1ef31083a18d59c18
Now that you have a list of MD5 fingerprints, you are ready to submit them
to the Solaris Fingerprint Database. The sfpDB will only accept a total
of 256 individual fingerprints at a time. In this case, it is not an issue
since we only generated 12. If we had generated more than 256, which is
likely for a real BART run, then we could use the Solaris Fingerprint
Database Companion to process them since this tool will automatically break
up the list of fingerprints into chunks of 256 and process each chunk
in turn until all of the fingerprints have been processed.
So, let's see what happens when these fingerprints are submitted to the
database. For the sake of simplicity, for this example, I used the sfpDB
web interface
which produced the following result:
Results of Last Search
ba94af26a1fa9dbb26ba0e2a07d888ec - - 0 match(es)
Not found in this database.
08f50f2555553710f9eb3225ebc7a04e - - 0 match(es)
Not found in this database.
1bf5c90088933a61c0b1e9138d52b841 - - 0 match(es)
Not found in this database.
fb4cade13611fb4904f06f26cc51ad8b - - 0 match(es)
Not found in this database.
00f19fcd403283f0510efadeafac2e66 - - 9 match(es)
* canonical-path: /usr/lib/nis/nisopaccess
* package: SUNWnisu
* version: 11.8.0,REV=2000.01.08.18.17
* architecture: i386
* source: Solaris 8/x86
* canonical-path: /usr/lib/nis/nisopaccess
* package: SUNWnisu
* version: 11.8.0,REV=2000.10.28.19.07
* architecture: i386
* source: Trusted Solaris 8/x86
* canonical-path: /usr/lib/nis/nisopaccess
* package: SUNWnisu
* version: 11.8.0,REV=2003.04.03.19.26
* architecture: i386
* source: Trusted Solaris 8/x86
* canonical-path: /usr/lib/nis/nisopaccess
* package: SUNWnisu
* version: 11.9.0,REV=2002.11.04.02.51
* architecture: i386
* source: Solaris 9/x86
* canonical-path: /usr/lib/nis/nisopaccess
* package: SUNWnisu
* version: 11.8.0,REV=2000.01.08.18.12
* architecture: sparc
* source: Solaris 8/SPARC
* canonical-path: /usr/lib/nis/nisopaccess
* package: SUNWnisu
* version: 11.8.0,REV=2000.10.30.04.48
* architecture: sparc
* source: Trusted Solaris 8/SPARC
* canonical-path: /usr/lib/nis/nisopaccess
* package: SUNWnisu
* version: 11.8.0,REV=2001.09.25.00.12
* architecture: sparc
* source: Trusted Solaris 8 4/01
* canonical-path: /usr/lib/nis/nisopaccess
* package: SUNWnisu
* version: 11.8.0,REV=2003.04.03.21.27
* architecture: sparc
* source: Trusted Solaris 8/SPARC
* canonical-path: /usr/lib/nis/nisopaccess
* package: SUNWnisu
* version: 11.9.0,REV=2002.04.06.15.27
* architecture: sparc
* source: Solaris 9/SPARC
dd928cf7778e19749b28334dfaf503b2 - - 0 match(es)
Not found in this database.
5af2053863e687464285d4892bcc4b11 - - 2 match(es)
* canonical-path: /usr/lib/nis/nispopulate
* package: SUNWnisu
* version: 11.9.0,REV=2002.11.04.02.51
* architecture: i386
* source: Solaris 9/x86
* canonical-path: /usr/lib/nis/nispopulate
* package: SUNWnisu
* version: 11.9.0,REV=2002.04.06.15.27
* architecture: sparc
* source: Solaris 9/SPARC
87e05dc59fd5e25f117313a3160c2c33 - - 0 match(es)
Not found in this database.
8bdc76f327b86edee2c1dcafef289cb6 - - 0 match(es)
Not found in this database.
a3d06fea784afe9ce6974cfa87dbe1d6 - - 0 match(es)
Not found in this database.
63be71e1fb14121e20e95e1369d1485b - - 0 match(es)
Not found in this database.
8f0fd3abbefd1ae1ef31083a18d59c18 - - 0 match(es)
Not found in this database.
You will note that a number of files show no matches in the database.
Have no fear - this is due to the fact that the tests are being run
on a pre-release version of Solaris 10. Once Solaris 10 officially
ships, all of the fingerprints will be recorded and should show up
here. You will also note that for the positive matches, the source
showed up as Solaris 9/SPARC, Solaris 9/x86, Trusted Solaris 8/SPARC,
etc. This is because the file is the same on each of those versions
of (Trusted) Solaris including Solaris 10.
Just to make things interesting, the following example shows how you
can automate this using the Solaris Fingerprint Database Companion.
In the following example, I will only look for files that do not
match any of the records in the database:
# find /usr/lib/nis | bart create -I | grep -v "^#" | awk '$2 == "F" { print $NF }' > ./md5.list
# cat ./md5.list
ba94af26a1fa9dbb26ba0e2a07d888ec
08f50f2555553710f9eb3225ebc7a04e
1bf5c90088933a61c0b1e9138d52b841
fb4cade13611fb4904f06f26cc51ad8b
00f19fcd403283f0510efadeafac2e66
dd928cf7778e19749b28334dfaf503b2
5af2053863e687464285d4892bcc4b11
87e05dc59fd5e25f117313a3160c2c33
8bdc76f327b86edee2c1dcafef289cb6
a3d06fea784afe9ce6974cfa87dbe1d6
63be71e1fb14121e20e95e1369d1485b
8f0fd3abbefd1ae1ef31083a18d59c18
# sfpC.pl ./md5.list | grep -- "- 0 match"
ba94af26a1fa9dbb26ba0e2a07d888ec - - 0 match(es)
08f50f2555553710f9eb3225ebc7a04e - - 0 match(es)
1bf5c90088933a61c0b1e9138d52b841 - - 0 match(es)
fb4cade13611fb4904f06f26cc51ad8b - - 0 match(es)
dd928cf7778e19749b28334dfaf503b2 - - 0 match(es)
87e05dc59fd5e25f117313a3160c2c33 - - 0 match(es)
8bdc76f327b86edee2c1dcafef289cb6 - - 0 match(es)
a3d06fea784afe9ce6974cfa87dbe1d6 - - 0 match(es)
63be71e1fb14121e20e95e1369d1485b - - 0 match(es)
8f0fd3abbefd1ae1ef31083a18d59c18 - - 0 match(es)
While this is a quick and easy way to find files that were not shipped
by Sun, it would be nice to have the filename listed in addition to
just the fingerprint so that we do not have to manually correlate them
later. You can do this very easily by constructing the MD5 fingerprints
in a slight different way (which is also readable by the Solaris Fingerprint
Database):
# find /usr/lib/nis | bart create -I |\
awk '$1 ~ /^\// && $2 == "F" { printf "MD5 (%s) = %s\n", $1, $NF; }' > md5.list
# cat ./md5.list
MD5 (/usr/lib/nis/nisaddent) = ba94af26a1fa9dbb26ba0e2a07d888ec
MD5 (/usr/lib/nis/nisauthconf) = 08f50f2555553710f9eb3225ebc7a04e
MD5 (/usr/lib/nis/nisclient) = 1bf5c90088933a61c0b1e9138d52b841
MD5 (/usr/lib/nis/nisctl) = fb4cade13611fb4904f06f26cc51ad8b
MD5 (/usr/lib/nis/nisopaccess) = 00f19fcd403283f0510efadeafac2e66
MD5 (/usr/lib/nis/nisping) = dd928cf7778e19749b28334dfaf503b2
MD5 (/usr/lib/nis/nispopulate) = 5af2053863e687464285d4892bcc4b11
MD5 (/usr/lib/nis/nisserver) = 87e05dc59fd5e25f117313a3160c2c33
MD5 (/usr/lib/nis/nissetup) = 8bdc76f327b86edee2c1dcafef289cb6
MD5 (/usr/lib/nis/nisshowcache) = a3d06fea784afe9ce6974cfa87dbe1d6
MD5 (/usr/lib/nis/nisstat) = 63be71e1fb14121e20e95e1369d1485b
MD5 (/usr/lib/nis/nisupdkeys) = 8f0fd3abbefd1ae1ef31083a18d59c18
# sfpC.pl ./md5.list | grep -- "- 0 match"
ba94af26a1fa9dbb26ba0e2a07d888ec - (/usr/lib/nis/nisaddent) - 0 match(es)
08f50f2555553710f9eb3225ebc7a04e - (/usr/lib/nis/nisauthconf) - 0 match(es)
1bf5c90088933a61c0b1e9138d52b841 - (/usr/lib/nis/nisclient) - 0 match(es)
fb4cade13611fb4904f06f26cc51ad8b - (/usr/lib/nis/nisctl) - 0 match(es)
dd928cf7778e19749b28334dfaf503b2 - (/usr/lib/nis/nisping) - 0 match(es)
87e05dc59fd5e25f117313a3160c2c33 - (/usr/lib/nis/nisserver) - 0 match(es)
8bdc76f327b86edee2c1dcafef289cb6 - (/usr/lib/nis/nissetup) - 0 match(es)
a3d06fea784afe9ce6974cfa87dbe1d6 - (/usr/lib/nis/nisshowcache) - 0 match(es)
63be71e1fb14121e20e95e1369d1485b - (/usr/lib/nis/nisstat) - 0 match(es)
8f0fd3abbefd1ae1ef31083a18d59c18 - (/usr/lib/nis/nisupdkeys) - 0 match(es)
Using the different MD5 fingerprint format, you can now easily see
those files for which a record was not found in the Solaris
Fingerprint Database.
Before I stop, I did want to express one note of caution. BART can be
used to tell you if a file changed between two sets of snapshots. The
Solaris Fingerprint Database can tell you if a file was shipped by Sun.
There is still a problem that exists and of which you must be made
aware. It is possible for an attacker to replace a valid Solaris
binary or library with another from an older (or unpatched) version
of the operating system. While the Solaris Fingerprint Database will
tell you that this is a genuine Sun binary, it may still not be a
binary appropriate for the system. Due to Solaris binary compatibility
guarantees, it is possible for an attacker to replace a binary with
one from a previous version of the OS that may have been vulnerable
in some way.
Another potential issue is that an attacker could have replaced a
valid Sun binary with another. In this case, the name reported
by the Solaris Fingerprint Database "canonical-path" field will
differ from that passed via the MD5 fingerprint.
Both of these issues should raise a big red flag. So what should you
do? When you do detect file conflicts using BART and check them out
using the Solaris Fingerprint Database, be sure to take a look at the
canonical path, package, version and other fields to ensure that they
are appropriate for your system. You can also always take a look at
the fingerprints associated with any patches you applied. Either way,
you should not just let these conflicts slide as they could be an
indication of a security incident or at least a change control problem.
Well, it is about time to draw this article to a close. As always, I hope you
enjoyed this article and will be able to apply the tips contained within to
your environment. Please let me know if you have any suggestions for any
future articles. Thank you for allowing me to share this with you. Until
next time, take care!
Technorati Tag:
OpenSolaris
Solaris
security
Thanks Glenn for this nifty script/tool. Any thing...