“What did this package install?” sounds like one question, but administrators usually mean one of four things: list paths owned by an installed package, preview an uninstalled repository package, identify the owner of one existing path, or inspect a downloaded archive. Pick the matching database so the result is evidence rather than guesswork.
Package-owned is not the same as package-created
A manifest/database records paths shipped or registered as owned by the package.
Maintainer scripts can create users, directories, caches, databases, symlinks, generated configuration, and service state not represented like ordinary payload files.
Applications create logs, uploads, caches, user preferences, and runtime state after installation.
Configuration-management and administrators can change package-owned files.
Containers, alternatives systems, diversions, overlays, and immutable images can change what appears at a path.
Debian and Ubuntu: list installed package paths
dpkg-query -W -f="${binary:Package} ${Version} ${Architecture} ${db:Status-Abbrev}\n" curl
dpkg-query -L curlcurl 8.x... amd64 ii
/.
/usr
/usr/bin
/usr/bin/curl
/usr/share/doc/curl
...Confirm the exact package before trusting the list
-Wselects package records and the format prints name, version, architecture, and abbreviated status.-Llists paths associated with the installed package.A command can be split across a main package, common/data package, library package, and documentation package.
Multiarch installations may require
package:architectureto disambiguate.The output includes directories and may include conffile paths; it does not prove current content integrity.
Find which installed Debian package owns a path
command -v curl
dpkg-query -S /usr/bin/curl
dpkg-query -S '*/libcurl.so.*'/usr/bin/curl
curl: /usr/bin/curl
libcurl4:amd64: /usr/lib/x86_64-linux-gnu/libcurl.so.4.8.0
libcurl4:amd64: /usr/lib/x86_64-linux-gnu/libcurl.so.4Search exact paths before using patterns
command -vresolves the executable selected by the current shell environment.dpkg-query -Ssearches installed package ownership records.Quote glob characters so the shell does not expand them first.
Several packages can report related paths, diversions, or overlapping metadata cases.
No result can mean an unpackaged/generated file, different root/container, symlink target issue, or database inconsistency.
List only Debian conffiles
dpkg-query -W -f="${Conffiles}\n" openssh-server /etc/init.d/ssh <md5>
/etc/pam.d/sshd <md5>
/etc/ssh/sshd_config <md5>
...Conffiles have upgrade/removal semantics
The field lists files tracked as Debian conffiles for that package.
Recorded hashes help dpkg decide whether the administrator modified a conffile.
Not every application configuration is necessarily a dpkg conffile.
Package removal and purge treat configuration state differently.
Do not replace/remove config based on the manifest alone; back up and understand local changes.
Preview an uninstalled Debian repository package
sudo apt update
sudo apt install apt-file
apt-file list nginx-core
apt-file search --fixed-string /usr/sbin/nginxnginx-core: /usr/sbin/nginx
...
nginx-core: /usr/sbin/nginxRisk level: caution. Review the command before running it.
apt-file searches repository Contents indexes
apt-file listcan inspect package paths without installing/fetching the package.searchanswers which indexed repository packages contain a matching file.Repository source/suite/architecture configuration controls results.
Contents indexes can be missing/stale for some repositories; update and inspect configured indices when results surprise you.
Installing
apt-filechanges the host; review APT’s proposed transaction.
Inspect a downloaded DEB without installing it
dpkg-deb --info ./package_version_arch.deb
dpkg-deb --contents ./package_version_arch.deb new Debian package, version 2.0.
Package: example
Version: ...
drwxr-xr-x root/root ... ./usr/
-rwxr-xr-x root/root ... ./usr/bin/exampleArchive inspection is read-only metadata work
--inforeads control metadata and--contentslists the data archive.This does not install files or execute maintainer scripts.
A downloaded archive may differ from the repository candidate or installed version/architecture.
Verify origin/signature/hash through the package-manager/repository workflow before trusting content.
Do not extract unknown packages into sensitive directories or execute included programs.
RPM systems: list installed package files
rpm -q bash
rpm -ql bash
rpm -qc bash
rpm -qd bashbash-5.x...
/etc/bashrc
/usr/bin/bash
...
... configuration files ...
... documentation files ...RPM query selectors can narrow the manifest
-qqueries the installed RPM database by package name.-llists package paths;-climits to configuration files;-dlimits to documentation.Package labels/names vary by distribution and installed architecture.
rpm -qlvor query formats can include permissions, owner, size, digest-related metadata, and flags.Database output is not a live
ls; verify current filesystem state separately.
Find the installed RPM owner of a file
rpm -qf /usr/bin/bash
rpm -q --queryformat '[%{=NAME} %{FILEMODES:perms} %{FILENAMES}\n]' bash | headbash-5.x...
bash -rwxr-xr-x /usr/bin/bash
...Query formats are useful for audits
-fselects the installed package owning an exact path.The iterator walks parallel file metadata arrays in the RPM header.
=NAMElocks the scalar package name while filenames iterate.Query the real resolved path when symlinks obscure ownership.
Do not parse human-formatted verbose output when a documented query format can provide stable fields.
Preview repository RPM contents
dnf repoquery --available --location bash
dnf repoquery --available --list bash
dnf provides '*/bin/bash'... repository package location ...
/usr/bin/bash
...
bash-... : The GNU Bourne Again shellRepository state determines the answer
repoquery --listlists payload paths for available repository packages without installing them.dnf providessearches providers of a path/pattern.Enabled repositories, modules, release version, architecture, exclusions, and metadata freshness matter.
Several versions/architectures/providers may match.
Refresh metadata through the organization’s normal repository policy before making install decisions.
Inspect a downloaded RPM
rpm -qpi ./package-version.arch.rpm
rpm -qlp ./package-version.arch.rpm
rpm -Kv ./package-version.arch.rpmName : example
Version : ...
...
/usr/bin/example
...
... digests signatures OKThe -p selector means package file
-qpireads archive information and-qlplists its file manifest.-Kvchecks the signatures/digests that the local RPM keyring understands.“OK” is meaningful only if trusted correct signing keys and policy are configured.
Archive inspection does not execute scripts or install content.
Prefer repository/package-manager download and verification workflows over random RPM downloads.
Arch Linux commands
pacman -Q bash
pacman -Ql bash
pacman -Qo /usr/bin/bash
sudo pacman -Fy
pacman -F /usr/bin/bashbash ...
bash /usr/bin/bash
/usr/bin/bash is owned by bash ...
... sync file databases ...
core/bash ... usr/bin/bashLocal and sync file databases are distinct
-Qllists installed package files;-Qofinds installed ownership.-Fsearches synchronized repository file databases, including uninstalled packages.-Fyrefreshes file databases and requires privileges/network; use distribution guidance to avoid partial/unsafe update habits.Package names/repos can differ across configured mirrors.
Generated/unowned paths remain outside the packaged file database.
Alpine Linux commands
apk info -e busybox
apk info -L busybox
apk info -W /bin/busyboxbusybox
busybox-... contains:
/bin/busybox
...
/bin/busybox is owned by busybox-...Ask the installed database first
-etests whether the named package is installed.-Llists installed package contents.-Wreports ownership of a path according to the installed database.BusyBox applets may be symlinks to one binary; inspect link targets as well as owners.
Repository package/archive queries use different
apkoptions and configured indexes; pin commands to the deployed Alpine release.
Verify whether installed payload files changed
# Debian/Ubuntu (installed package checksums when available)
debsums curl
# RPM systems
rpm -V bashNo output commonly means checked files match recorded metadata; differences produce package-tool-specific markers. Missing checksum coverage and configuration-file policy vary.Verification needs careful interpretation
debsumsmay need installation and not every package/file has checksum coverage.rpm -Vcompares recorded attributes and reports compact difference markers.Legitimate administrator/configuration changes can appear.
A clean verification does not prove the whole system is uncompromised; package databases/tools can be attacked too.
Investigate differences using trusted repositories, logs, deployment state, incident procedures, and file ownership—not automatic overwrites.
Why files may not appear in the manifest
Post-install/pre/post transaction scripts generated them.
A service created databases, caches, keys, certificates, sockets, PID files, logs, or state.
A tmpfiles/sysusers mechanism creates paths at boot/install/runtime.
An alternatives/diversion mechanism owns a selected symlink/path.
An administrator, configuration manager, installer, language package manager, Flatpak/Snap/container, or application updater created them.
The path is a mount/overlay bind rather than a file from the host package payload.
Package database versus live filesystem
A manifest can list a path that has since been deleted or replaced.
Permissions, owners, symlink targets, hashes, and capabilities can drift.
A package upgrade may preserve locally modified configuration or create
.dpkg-dist,.rpmnew, or similar artifacts.Files may belong to a package in another container/chroot/root filesystem than the shell you queried.
Architecture/multilib versions can install related paths under separate prefixes.
Use status/verification tools and live
stat/readlink/getcapevidence for the actual filesystem.
Safe automation patterns
#!/usr/bin/env bash
set -euo pipefail
package=${1:?usage: package-files.sh PACKAGE}
if command -v dpkg-query >/dev/null 2>&1; then
dpkg-query -W -f='${db:Status-Abbrev}\n' -- "$package" | grep -qx 'ii '
dpkg-query -L -- "$package"
elif command -v rpm >/dev/null 2>&1; then
rpm -q -- "$package" >/dev/null
rpm -ql -- "$package"
else
printf 'Unsupported package manager\n' >&2
exit 2
fiFail closed on unsupported or absent packages
set -euo pipefailmakes unexpected failures visible.A required positional argument prevents an accidental query of everything.
The Debian branch verifies fully installed abbreviated state before listing.
--ends option parsing for user-supplied package names where supported.Production inventory should emit a defined machine-readable format, package version/architecture/root, exit codes, and tool versions.
Troubleshooting no-result cases
Package not installed: use repository query/index or inspect the downloaded archive.
Command name differs from package name: query the executable path owner first.
Path is a symlink: inspect both link and resolved target ownership.
apt-file finds nothing: update/check Contents indexes, repositories, suite, origin, and architecture.
DNF returns many providers: constrain release, architecture, repo, module, version, and exact path.
File is unowned: check scripts/runtime/config management/other package systems/containers before cleanup.
Wrong filesystem root: enter/query the container, chroot, sysroot, or use supported alternate-root options.
Database says owned but file missing: verify package status/integrity, logs, overlay, local deletion, and reinstall policy.
Forensic and compliance caveats
Package manifests are one provenance source, not a complete software bill of materials.
Maintainer scripts, downloaded plugins/models, vendored dependencies, containers, and application self-updates need separate inventory.
Do not execute suspect binaries or package scripts while investigating.
Capture hashes, metadata, package database, logs, mounts, and repository/key configuration according to incident procedures.
Query output can reveal sensitive paths/software; sanitize before sharing.
For strong evidence, collect from a trusted environment and preserve chain of custody.
Command decision table
Installed Debian package →
dpkg-query -L; owner →dpkg-query -S.Uninstalled Debian repository package →
apt-file list; provider →apt-file search.Downloaded DEB →
dpkg-deb --contents.Installed RPM package →
rpm -ql; owner →rpm -qf.Uninstalled RPM repository package →
dnf repoquery --list; provider →dnf provides.Downloaded RPM →
rpm -qlpplus signature/digest verification.Arch installed/repository →
pacman -Ql/-Qoorpacman -F.Alpine installed →
apk info -L/-W.
Verification checklist
Distribution, release, architecture, root/container, repository set, package name, version, and install status are known.
The query source matches the question: installed DB, repository index, or archive.
Ownership and symlink/resolved-target behavior are checked for individual paths.
Config/docs and integrity attributes are queried when relevant.
Generated/runtime/local/other-package-system files are not mistaken for manifest payload.
Results and exit codes are captured reproducibly without destructive cleanup or untrusted execution.
Primary references
dpkg-query manual documents installed package listing, search, status, formats, and exit behavior.
Ubuntu apt-file manual documents repository Contents list/search, index limitations, filters, and exit codes.
dpkg-deb manual documents DEB archive information/content inspection.
RPM manual documents installed/archive selectors, file lists, config/docs, ownership, verification, and signatures.
RPM query-format manual documents file metadata iteration for automation.
Use the installed distribution’s
manpages for exact DNF, pacman, and apk behavior because releases/options evolve.
Comments and corrections