Skip to content
Open
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
2 changes: 1 addition & 1 deletion INSTALL
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
Requirements:
- libcurl
- libarchive
- pcre
- pthreads
- re2
2 changes: 1 addition & 1 deletion build-aux/ci-test
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ case $buildmode in
;;
esac

pacman -Syu --noconfirm base-devel git gmock gtest python meson pcre perl
pacman -Syu --noconfirm base-devel git gmock gtest python meson perl re2

# Needed to ensure PATH is properly set for perl, etc.
source /etc/profile
Expand Down
6 changes: 4 additions & 2 deletions man/pkgfile.pod
Original file line number Diff line number Diff line change
Expand Up @@ -63,7 +63,9 @@ Disable case sensitivity in matching.

=item B<-r>, B<--regex>

Enable regular expression matching. See B<pcre>(3).
Enable regular expression matching. The matching is partial meaning it will
match a substring of an entry. See https://github.com/google/re2/wiki/Syntax
for supported syntax.

=item B<-R> I<REPO>, B<--repo=>I<REPO>

Expand Down Expand Up @@ -177,7 +179,7 @@ systemd support, this can be enabled with:

=head1 SEE ALSO

B<pkgfiled>(1), B<repo-add>(8), B<pcre>(3), B<glob>(7), B<pacman.conf>(5)
B<pkgfiled>(1), B<repo-add>(8), B<glob>(7), B<pacman.conf>(5)

=head1 AUTHOR

Expand Down
6 changes: 3 additions & 3 deletions meson.build
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ add_project_arguments(
language: 'cpp',
)

libpcre = dependency('libpcre', version: '>= 8.30')
re2 = dependency('re2')
libarchive = dependency('libarchive', version: '>= 3.2.0')
libcurl = dependency('libcurl')
libsystemd = dependency('libsystemd')
Expand Down Expand Up @@ -57,7 +57,7 @@ libcommon = static_library(
src/queue.hh
'''.split(),
),
dependencies: [libpcre, libarchive, libcurl, pthreads, stdcppfs],
dependencies: [re2, libarchive, libcurl, pthreads, stdcppfs],
install: false,
)

Expand Down Expand Up @@ -191,7 +191,7 @@ if gtest.found() and gmock.found()
'''.split(),
),
link_with: [libcommon, gtest_main],
dependencies: [gmock, gtest, libpcre],
dependencies: [gmock, gtest, re2],
),
protocol: 'gtest',
)
Expand Down
34 changes: 11 additions & 23 deletions src/filter.cc
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@

#include <format>
#include <iostream>
#include <re2/re2.h>

namespace pkgfile {
namespace filter {
Expand Down Expand Up @@ -40,38 +41,25 @@ bool Glob::Matches(std::string_view line) const {
return fnmatch(glob_pattern_.c_str(), std::string(line).c_str(), flags_) == 0;
}

Regex::~Regex() {
pcre_free_study(re_extra_);
pcre_free(re_);
}

// static
std::unique_ptr<Regex> Regex::Compile(const std::string& pattern,
bool case_sensitive) {
const int options = case_sensitive ? 0 : PCRE_CASELESS;
const char* err;
int offset;

pcre* re = pcre_compile(pattern.c_str(), options, &err, &offset, nullptr);
if (re == nullptr) {
std::cerr << std::format("error: failed to compile regex at char {}: {}\n",
offset, err);
return nullptr;
}

pcre_extra* re_extra = pcre_study(re, PCRE_STUDY_JIT_COMPILE, &err);
if (err) {
std::cerr << std::format("error: failed to study regex: {}\n", err);
pcre_free(re);
re2::RE2::Options re2_options;
re2_options.set_case_sensitive(case_sensitive);
re2_options.set_log_errors(false);

auto re = std::make_unique<re2::RE2>(pattern, re2_options);
if (!re->ok()) {
std::cerr << std::format("error: failed to compile regex: {}\n",
re->error());
return nullptr;
}

return std::make_unique<Regex>(re, re_extra);
return std::make_unique<Regex>(std::move(re));
}

bool Regex::Matches(std::string_view line) const {
return pcre_exec(re_, re_extra_, line.data(), line.size(), 0,
PCRE_NO_UTF16_CHECK, nullptr, 0) >= 0;
return re2::RE2::PartialMatch(line, *re_);
}

Exact::Exact(std::string match, bool case_sensitive) {
Expand Down
8 changes: 3 additions & 5 deletions src/filter.hh
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
#pragma once

#include <pcre.h>
#include <re2/re2.h>

#include <functional>
#include <memory>
Expand Down Expand Up @@ -66,17 +66,15 @@ class Bin : public Filter {

class Regex : public Filter {
public:
Regex(pcre* re, pcre_extra* re_extra) : re_(re), re_extra_(re_extra) {}
~Regex();
Regex(std::unique_ptr<re2::RE2> re) : re_(std::move(re)) {}

static std::unique_ptr<Regex> Compile(const std::string& pattern,
bool case_sensitive);

bool Matches(std::string_view line) const override;

private:
pcre* re_;
pcre_extra* re_extra_;
std::unique_ptr<re2::RE2> re_;
};

class Glob : public Filter {
Expand Down