Using dpkg and apt facilities (mostly under Ubuntu)
dpkg and related command examples
Perhaps also see:
Basic package maintenance
The original focus of this page was "non-obvious" commands not related to normal package installation, with a view to possible package authorship. However, it seems appropriate to review here the basic use of apt-get
also.
Bring all installed packages up-to-date
sudo apt-get update
Followed by one of...
sudo apt-get upgrade
sudo apt-get dist-upgrade
Install a new package and its dependencies
sudo apt-get install _packagename_
Redo configuration of a previously installed package
sudo apt-get --reconfigure install _packagename_
Determine what an apt-get upgrade will do
sudo apt-get update
Then:
sudo apt-get --assume-no -u upgrade
Simulate root well enough that non-superuser could build a .deb
Crude look at .deb file contents
ar tv _file.deb_
Contents are always one file, plus two compressed tars. The tar files can be examined using
tar
. That is, after extracing them using
ar x
. See
ar(1)
.
Caveat: More recent .deb files tend to contain data.tar.xz which can be difficult to decompress on older systems. (Or even on a modern system; you need to install
xz-utils
; apparently
dpkg
and friends can do the expansion without that package installed!(?!)
Inspect contents of a .deb without unpacking
Control information:
dpkg --info _file.deb_
dpkg -I _file.deb_
Data/files:
dpkg --contents _file.deb_
dpkg -c _file.deb_
A deb view of the current machine architecture
dpkg-architecture
This requires the
dpkg-dev
package.
Fundamental command to create a .deb package file from prepared contents
dpkg-deb -b . debfile
dpkg-deb --build directory . debfile
Current directory must contain
DEBIAN
directory with appropriate contents (which become the
control.tar.gz
), and a number of trees of files to install. This contstructs the
ar
format
.deb
file from those current directory contents; it does not run any compilers or makefiles, etc.
Alternately, a different
directory
name can be specified instead of ".".
Warning: Reading around the web, you find it unlikely that you will get the contents correct. Suggestions are to use the dpkg-buildpackage command (from package dpkg-dev), likely via a cover debuild. (from package devscripts). Testing the debuild procedure, e.g. with a seemingly simple package like binutils can take a long time. And use a somewhat surprising amount of filespace.
A better candidate seems to be the chrpath package. In fact, it looks like the "build all architectures" phenomenon may be specific to binutils (perhaps related to being run in a container?)
Regarding simple
dpkg-deb -b
however, see
#RawExpansion.
Reveal where apt-get will fetch a package from
apt-get --print-uris download _packagename_
Caveat: It seems this command might not work (will give null output) if you are in a directory to which the dpkg file has already been downloaded.
Note: the option is --print-uris not --print-urLs.
Reveal where apt-get will fetch package source from
Everything to do with obtaining source packages is dependent upon the setup of the server you are using. If the (assuming Ubuntu here) effective /etc/apt/sources.list file does not include the relevant deb-src lines, you will not be able to obtain the source. You might be able to do it yourself in a container, or (possibly) even fake it in a chroot. Or, if someone knows some sufficient magic options to give apt-get/apt, I'd appreciate hearing about them.
Aside: Perhaps note in the above the overloading of the English word source in the apt/dpkg context.
apt-get --print-uris source _packagename_
Typically three files, plus a note about the maintenance repository.
Note: the option is --print-uris not --print-urLs.
Consequently, obtain .deb file or source
apt-get download _packagename_
apt-get source _packagename_
apt-get source
actually clutters the current directory with files and a directory having old time stamps. So you want to
cd
to an appropriate directory first.
Caveat: When working as super-user, download
often seems to fail the first time, then apparently work after repeated. (Although, in fact, the file was likely actually downloaded the first time).
Also
apt-get --download-only source _packagename_
will suppress the expansion of the tar files. Note that the "expansion of tar files" is not simple.
Do a raw expansion of a .deb file
sudo dpkg-deb -R _debfile_ _directory_
sudo dpkg-deb --raw-extract _debfile_ _directory_
This is very useful for getting an understanding of the Debian package structure. Medium-sized packages, with some installation complexity are good candidates to look at, since they will reveal more facilities available in the DEBIAN subdirectory.
postfix
is a good such example.
Expansion can be done without
sudo
, but some file characteristics will not be set. Using
fakeroot
can be a good option.
Note that this command is sort of the complement of
dpkg-deb -b
. That is, it produces a directory which can be turned back into a .deb file by using
dpkg-deb -b
. Perhaps after making small changes, such as to version number.
Determining build-dependencies
Sometimes the installation (or deinstallation!) of other packages is required to build a package.
sudo apt-get --assume-no build-dep _packagename_
will preview those requirements. (Without
--assume-no
installation changes
might proceed without confirmation). As non-superuser, one can do the following:
apt-get --assume-no --simulate build-dep _packagename_
apt-get --assume-no -s build-dep _packagename_
However, that produces more output because it seems to go ahead and print all
the downloads which would be required.
Caveat: Especially if trying to experiment in minimalist containers, it is quite easy to have your environment in a state where source locations cannot be determined.
/etc/apt/sources.list and /etc/apt/sources.list.d; perhaps the simple solution is replicating any URL lines there with "deb" changed to "deb-src"?
Will that ever go wrong? Has this gotten worse in 16.04?
Download and compile ("build") source
And to download source and unpack and compile it (does not require superuser,
if all build dependencies were previously installed).
apt-get --compile source _packagename_
apt-get -b source _packagename_
Remember to chdir to an appropriate directory first, because files with old timestamps are created.
A conveniently simple example to try, which has few build dependencies, is
apt-get -b source openssl-blacklist
It would seem these "apt-get" options are distinct from the elsewhere mentioned dpkg-buildpackage and debuild (and also the -b
option of dpkg
)
And in more recent distributions openssl-blacklist seems to have gone away?
chrpath is perhaps a suitable small test replacement.
Check for installation status, or guess at packagename
You can run the following as non-superuser. It will tell you if a package
is already installed (and up-to-date), and alert you if you give an invalid
name.
apt-get --simulate install _packagename_
apt-get -s install _packagename_
You can also do it as super-user, but you want to be sure to specify the "--simulate" option or unwanted installation can result.
The above has some advantages over the similar
dpkg-query --list _packagename_
dpkg-query -l _packagename_
Or
dpkg-query --list | grep _pattern_
The
apt-get
approach will search for packages at other (configured)
repositories, not just on the current host. On the other hand,
apt-get
cannot search for packages matching a pattern.
List the files contributed by (attributed to) a package
dpkg-query --listfiles _packagename_
dpkg-query -L _packagename_
Install a package from a local .deb file
dpkg --install _file.deb_
dpkg -i _file.deb_
Determine what process has dpkg directory locked
sudo apt-get install psmisc
fuser /var/lib/dpkg/lock
Search for subset of all available packages
sudo apt-cache search _pattern_
In particular, if you have the
depot.cs.uwaterloo.ca
repository correctly configured, using
pattern of "uwcs" should show you a reasonably large list of local "uwcs" packages (mostly metapackages).
Update tzdata package timezone with no interaction
This section should be moved to another page when I find or create such a page.
echo 'America/Toronto' > /etc/timezone
rm /etc/localtime
dpkg-reconfigure -f noninteractive tzdata
rm /etc/localtime
should not be necessary, but it apparently is.
See
Obviously(?) you can use any stream source for
/etc/timezone
.
E.g. when setting up a container (as in
/usr/share/lxc/templates/*
)
you might want to use the baremetal
/etc/timezone
to do this setup.
file and directory locations related to dpkg and apt
/var/lib/dpkg/status
- This is the registry of installed packages. It is immensely useful. It is actually the raw material for
dpkg-query --list
/var/lib/dpkg/lock
- This is the lockfile used to allow only one
dpkg
process at a time to attempt to change the package registry.
/var/lib/dpkg/info/*
- There are lots of files here, with names corresponding to installed packages. Many of them correspond directly to files you see under the DEBIAN directory in the result of
dpkg-deb -R packagename
.
/var/lib/dpkg/info/*.list
- These files, with names generated to correspond to all (successfully installed?) packages, list the registered contents of each package.
/var/lib/dpkg/
- There is more stuff here, but the previous is the most useful.
/etc/apt/sources.list
- File containing information on what repositories
apt-get
will use.
/etc/apt/sources.list.d
- Directory analogous to previous, with potentially many files to be processed.
/var/lib/apt/lists
- Directory containing the information
apt-get install
, etc, used to find the location of packages available for downloading.
- This is what gets updated when you run
apt-get update
.
/etc/apt/
- There is other related information under
/etc/apt
Heretical thoughts about =dpkg-deb -b and dpkg-deb -R
While it is easy to find admonition to use complex tools to generate
a
.deb
(
dpkg
) file, fundamentally a
.deb
file is just a tar file
together with a set of control files which can perform operations
pre- and post- expansion. Upon success, the contents of the archive
are registered (by
dpkg
in
/var/lib/dpkg/status
and
/var/lib/dpkg/info/*
, principally
/var/lib/dpkg/info/packagename.list
) as "belonging"
to the package.
Therefore, if you can create a tree of files, perhaps including
architecture-dependant binaries, by some well-defined methodology
(or perhaps initially not so well-defined, hoping to migrate to
better definition later), placing them manually under the directory
and file structure such as you can infer by
dpkg -R
of a few
packages, and then manually creating suitable DEBIAN directory contents,
and then using
dpkg-deb -b
to create a
.deb
file can be a useful
way to easily transport such files from machine to machine (or,
for initial experimentation, container (lxc container, perhaps) to
container).
--
AdrianPepper - 2019-03-04