Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Rewrite dpkginfo probe without using APT #2046

Merged
merged 1 commit into from
Nov 9, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions .github/workflows/build.yml
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ jobs:
- name: Install Deps
run: |
sudo apt-get update
sudo apt-get -y install lcov swig xsltproc rpm-common lua5.3 libpcre2-dev libyaml-dev libapt-pkg-dev libdbus-1-dev libdbus-glib-1-dev libcurl4-openssl-dev libgcrypt-dev libselinux1-dev libgconf2-dev libacl1-dev libblkid-dev libcap-dev libxml2-dev libxslt1-dev libxml-parser-perl libxml-xpath-perl libperl-dev librpm-dev librtmp-dev libxmlsec1-dev libxmlsec1-openssl python3-dbusmock python3-pytest
sudo apt-get -y install lcov swig xsltproc rpm-common lua5.3 libpcre2-dev libyaml-dev libdbus-1-dev libdbus-glib-1-dev libcurl4-openssl-dev libgcrypt-dev libselinux1-dev libgconf2-dev libacl1-dev libblkid-dev libcap-dev libxml2-dev libxslt1-dev libxml-parser-perl libxml-xpath-perl libperl-dev librpm-dev librtmp-dev libxmlsec1-dev libxmlsec1-openssl python3-dbusmock python3-pytest
sudo apt-get -y remove rpm

# Runs a set of commands using the runners shell
Expand All @@ -57,7 +57,7 @@ jobs:
image: fedora:latest
steps:
- name: Install Deps
run: dnf install -y cmake git dbus-devel GConf2-devel libacl-devel libblkid-devel libcap-devel libcurl-devel libgcrypt-devel libselinux-devel libxml2-devel libxslt-devel libattr-devel make openldap-devel pcre2-devel perl-XML-Parser perl-XML-XPath perl-devel python3-devel python3-dbusmock rpm-devel swig bzip2-devel gcc-c++ libyaml-devel xmlsec1-devel xmlsec1-openssl-devel hostname bzip2 lua rpm-build which strace apt-devel python3-pytest
run: dnf install -y cmake git dbus-devel GConf2-devel libacl-devel libblkid-devel libcap-devel libcurl-devel libgcrypt-devel libselinux-devel libxml2-devel libxslt-devel libattr-devel make openldap-devel pcre2-devel perl-XML-Parser perl-XML-XPath perl-devel python3-devel python3-dbusmock rpm-devel swig bzip2-devel gcc-c++ libyaml-devel xmlsec1-devel xmlsec1-openssl-devel hostname bzip2 lua rpm-build which strace python3-pytest
- name: Checkout
uses: actions/checkout@v3
with:
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/codeql.yml
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ jobs:
- name: Install Deps
run: |
sudo apt-get update
sudo apt-get -y install lcov swig xsltproc rpm-common lua5.3 libyaml-dev libapt-pkg-dev libdbus-1-dev libdbus-glib-1-dev libcurl4-openssl-dev libgcrypt-dev libselinux1-dev libgconf2-dev libacl1-dev libblkid-dev libcap-dev libxml2-dev libxslt1-dev libxml-parser-perl libxml-xpath-perl libperl-dev librpm-dev librtmp-dev libxmlsec1-dev libxmlsec1-openssl python3-dbusmock
sudo apt-get -y install lcov swig xsltproc rpm-common lua5.3 libyaml-dev libdbus-1-dev libdbus-glib-1-dev libcurl4-openssl-dev libgcrypt-dev libselinux1-dev libgconf2-dev libacl1-dev libblkid-dev libcap-dev libxml2-dev libxslt1-dev libxml-parser-perl libxml-xpath-perl libperl-dev librpm-dev librtmp-dev libxmlsec1-dev libxmlsec1-openssl python3-dbusmock
sudo apt-get -y remove rpm

# Initializes the CodeQL tools for scanning.
Expand Down
4 changes: 2 additions & 2 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -299,7 +299,7 @@ cmake_dependent_option(OPENSCAP_PROBE_UNIX_UNAME "Unix uname probe" ON "ENABLE_P
cmake_dependent_option(OPENSCAP_PROBE_UNIX_XINETD "Unix xinetd probe" ON "ENABLE_PROBES_UNIX" OFF)

# LINUX PROBES
cmake_dependent_option(OPENSCAP_PROBE_LINUX_DPKGINFO "Linux dpkginfo probe" ON "ENABLE_PROBES_LINUX; APTPKG_FOUND" OFF)
cmake_dependent_option(OPENSCAP_PROBE_LINUX_DPKGINFO "Linux dpkginfo probe" ON "ENABLE_PROBES_LINUX" OFF)
cmake_dependent_option(OPENSCAP_PROBE_LINUX_IFLISTENERS "Linux iflisteners probe" ON "ENABLE_PROBES_LINUX" OFF)
cmake_dependent_option(OPENSCAP_PROBE_LINUX_INETLISTENINGSERVERS "Linux inetlisteningservers probe" ON "ENABLE_PROBES_LINUX" OFF)
cmake_dependent_option(OPENSCAP_PROBE_LINUX_PARTITION "Linux partition probe" ON "ENABLE_PROBES_LINUX; BLKID_FOUND" OFF)
Expand Down Expand Up @@ -433,7 +433,7 @@ message(STATUS " Unix xinetd probe: ${OPENSCAP_PROBE_UNIX_XINETD}")
message(STATUS " ")

message(STATUS "Linux probes: ${ENABLE_PROBES_LINUX}")
message(STATUS " Linux dpkginfo probe (depends on aptpkg): ${OPENSCAP_PROBE_LINUX_DPKGINFO}")
message(STATUS " Linux dpkginfo probe: ${OPENSCAP_PROBE_LINUX_DPKGINFO}")
message(STATUS " Linux iflisteners probe: ${OPENSCAP_PROBE_LINUX_IFLISTENERS}")
message(STATUS " Linux inetlisteningservers probe: ${OPENSCAP_PROBE_LINUX_INETLISTENINGSERVERS}")
message(STATUS " Linux partition probe (depends on blkid): ${OPENSCAP_PROBE_LINUX_PARTITION}")
Expand Down
30 changes: 0 additions & 30 deletions cmake/FindAptPkg.cmake

This file was deleted.

4 changes: 2 additions & 2 deletions docs/developer/developer.adoc
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,7 @@ sudo dnf install \
cmake dbus-devel GConf2-devel libacl-devel libblkid-devel libcap-devel libcurl-devel \
libgcrypt-devel libselinux-devel libxml2-devel libxslt-devel libattr-devel make openldap-devel \
pcre-devel perl-XML-Parser perl-XML-XPath perl-devel python3-devel python3-dbusmock rpm-devel swig \
bzip2-devel gcc-c++ libyaml-devel xmlsec1-devel xmlsec1-openssl-devel apt-devel
bzip2-devel gcc-c++ libyaml-devel xmlsec1-devel xmlsec1-openssl-devel
----

On RHEL 8+ / CentOS 8+, the command to install the build dependencies is:
Expand All @@ -85,7 +85,7 @@ On Ubuntu 16.04, Debian 8 or Debian 9, the command to install the build dependen
sudo apt-get install -y cmake libdbus-1-dev libdbus-glib-1-dev libcurl4-openssl-dev \
libgcrypt20-dev libselinux1-dev libxslt1-dev libgconf2-dev libacl1-dev libblkid-dev \
libcap-dev libxml2-dev libldap2-dev libpcre3-dev python-dev swig libxml-parser-perl \
libxml-xpath-perl libperl-dev libbz2-dev librpm-dev g++ libapt-pkg-dev libyaml-dev \
libxml-xpath-perl libperl-dev libbz2-dev librpm-dev g++ libyaml-dev \
libxmlsec1-dev libxmlsec1-openssl
----

Expand Down
6 changes: 0 additions & 6 deletions openscap.spec
Original file line number Diff line number Diff line change
Expand Up @@ -13,9 +13,6 @@ BuildRequires: cmake >= 2.6
BuildRequires: gcc
BuildRequires: gcc-c++
BuildRequires: swig libxml2-devel libxslt-devel perl-generators perl-XML-Parser
%if 0%{?fedora}
BuildRequires: apt-devel
%endif
BuildRequires: rpm-devel
BuildRequires: libgcrypt-devel
%if 0%{?fedora}
Expand Down Expand Up @@ -47,9 +44,6 @@ Requires: libacl
Requires: libblkid
Requires: libcap
Requires: libselinux
%if 0%{?fedora}
Requires: apt-libs
%endif
Requires: openldap
Requires: popt
# Fedora has procps-ng, which provides procps
Expand Down
3 changes: 0 additions & 3 deletions src/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -115,9 +115,6 @@ endif()
if(DBUS_FOUND)
target_link_libraries(openscap ${DBUS_LIBRARIES})
endif()
if(APTPKG_FOUND)
target_link_libraries(openscap ${APTPKG_LIBRARIES})
endif()
if(ACL_FOUND)
target_link_libraries(openscap ${ACL_LIBRARY})
endif()
Expand Down
2 changes: 1 addition & 1 deletion src/OVAL/probes/probe-table.c
Original file line number Diff line number Diff line change
Expand Up @@ -257,7 +257,7 @@ static const probe_table_entry_t probe_table[] = {
{OVAL_INDEPENDENT_YAML_FILE_CONTENT, NULL, yamlfilecontent_probe_main, NULL, yamlfilecontent_probe_offline_mode_supported},
#endif
#ifdef OPENSCAP_PROBE_LINUX_DPKGINFO
{OVAL_LINUX_DPKG_INFO, dpkginfo_probe_init, dpkginfo_probe_main, dpkginfo_probe_fini, dpkginfo_probe_offline_mode_supported},
{OVAL_LINUX_DPKG_INFO, NULL, dpkginfo_probe_main, NULL, dpkginfo_probe_offline_mode_supported},
#endif
#ifdef OPENSCAP_PROBE_LINUX_IFLISTENERS
{OVAL_LINUX_IFLISTENERS, NULL, iflisteners_probe_main, NULL, NULL},
Expand Down
5 changes: 1 addition & 4 deletions src/OVAL/probes/unix/linux/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,13 +1,10 @@
if(OPENSCAP_PROBE_LINUX_DPKGINFO)
list(APPEND LINUX_PROBES_SOURCES
"dpkginfo-helper.cxx"
"dpkginfo-helper.c"
"dpkginfo-helper.h"
"dpkginfo_probe.c"
"dpkginfo_probe.h"
)
list(APPEND LINUX_PROBES_INCLUDE_DIRECTORIES
${APTPKG_INCLUDE_DIR}
)
endif()

if(OPENSCAP_PROBE_LINUX_IFLISTENERS)
Expand Down
179 changes: 179 additions & 0 deletions src/OVAL/probes/unix/linux/dpkginfo-helper.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,179 @@
#ifdef HAVE_CONFIG_H
#include <config.h>
#endif

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#include <limits.h>

#include "debug_priv.h"
#include "dpkginfo-helper.h"

#define DPKG_STATUS_BUFFER_SIZE 4096

static char* trimleft(char *str)
{
while (isspace((unsigned char)*str))
str++;

if (*str == 0)
return str;

return str;
}

static int version(struct dpkginfo_reply_t *reply)
{
char *evr, *epoch, *version, *release;

if (reply->evr == NULL)
return -1;

evr = strdup(reply->evr);
if (evr == NULL)
return -1;

if ((epoch = strchr(evr, ':')) != NULL) {
*epoch++ = '\0';
reply->epoch = strdup(evr);
if (reply->epoch == NULL)
goto err;
} else {
reply->epoch = strdup("0");
if (reply->epoch == NULL)
goto err;
epoch = evr;
}

version = epoch;
if ((release = strchr(version, '-')) != NULL) {
*release++ = '\0';
reply->release = strdup(release);
if (reply->release == NULL)
goto err;
}
reply->version = strdup(version);
if (reply->version == NULL)
goto err;

free(evr);
return 0;
err:
evgenyz marked this conversation as resolved.
Show resolved Hide resolved
free(evr);
return -1;
}

struct dpkginfo_reply_t* dpkginfo_get_by_name(const char *name, int *err)
{
FILE *f;
char buf[DPKG_STATUS_BUFFER_SIZE], path[PATH_MAX], *root, *key, *value;
struct dpkginfo_reply_t *reply;

*err = 0;
reply = NULL;

root = getenv("OSCAP_PROBE_ROOT");
if (root != NULL)
snprintf(path, PATH_MAX, "%s/var/lib/dpkg/status", root);
else
snprintf(path, PATH_MAX, "/var/lib/dpkg/status");

f = fopen(path, "r");
Fixed Show fixed Hide fixed

Check failure

Code scanning / CodeQL

Uncontrolled data used in path expression High

This argument to a file access function is derived from
user input (an environment variable)
and then passed to fopen(__filename).
if (f == NULL) {
dW("%s not found.", path);
*err = -1;
return NULL;
}

dD("Searching package \"%s\".", name);

while (fgets(buf, DPKG_STATUS_BUFFER_SIZE, f)) {
if (buf[0] == '\n') {
// New package entry.
if (reply != NULL) {
// Package found.
goto out;
}
continue;
}
if (isspace(buf[0])) {
// Ignore line beginning by a space.
continue;
}
buf[strcspn(buf, "\n")] = 0;
key = buf;
value = strchr(buf, ':');
if (value == NULL) {
// Ignore truncated line.
continue;
}
*value++ = '\0';
value = trimleft(value);
// Package should be the first line.
if (strcmp(key, "Package") == 0) {
if (strcmp(value, name) == 0) {
if (reply != NULL)
continue;
reply = calloc(1, sizeof(*reply));
if (reply == NULL)
goto err;
reply->name = strdup(value);
if (reply->name == NULL)
goto err;
}
} else if (reply != NULL) {
if (strcmp(key, "Status") == 0) {
if (strcmp(value, "install") != 0) {
// Package deinstalled.
dD("Package \"%s\" has been deinstalled.", name);
dpkginfo_free_reply(reply);
reply = NULL;
continue;
}
} else if (strcmp(key, "Architecture") == 0) {
reply->arch = strdup(value);
if (reply->arch == NULL)
goto err;
} else if (strcmp(key, "Version") == 0) {
reply->evr = strdup(value);
if (reply->evr == NULL)
goto err;
if (version(reply) < 0)
goto err;
}
}
}

// Reached end of file.

out:
if (reply != NULL) {
// Package found.
dD("Package \"%s\" found (arch=%s evr=%s epoch=%s version=%s release=%s).",
name, reply->arch, reply->evr, reply->epoch, reply->version, reply->release);
*err = 1;
}
fclose(f);
return reply;
err:
dW("Insufficient memory available to allocate duplicate string.");
fclose(f);
dpkginfo_free_reply(reply);
*err = -1;
return NULL;
}

void dpkginfo_free_reply(struct dpkginfo_reply_t *reply)
{
if (reply) {
free(reply->name);
free(reply->arch);
free(reply->epoch);
free(reply->release);
free(reply->version);
free(reply->evr);
free(reply);
}
}
Loading