Makes operator to use string_view

This commit is contained in:
Felipe Zimmerle 2019-03-05 12:26:44 -03:00
parent 96efe83174
commit fc24f34843
No known key found for this signature in database
GPG Key ID: E6DFB08CE8B11277
85 changed files with 1954 additions and 298 deletions

View File

@ -27,10 +27,13 @@
#include <vector>
#include <algorithm>
#include <memory>
#include "modsecurity/string_view.hpp"
#endif
#include "modsecurity/variable_value.h"
#ifndef HEADERS_MODSECURITY_ANCHORED_SET_VARIABLE_H_
#define HEADERS_MODSECURITY_ANCHORED_SET_VARIABLE_H_
@ -79,6 +82,12 @@ class AnchoredSetVariable : public std::unordered_multimap<std::string,
void set(const std::string &key, const std::string &value,
size_t offset);
void set(const std::string &key, const bpstd::string_view &value,
size_t offset);
void set(const std::string &key, const char *value,
size_t offset);
void set(const std::string &key, const std::string &value,
size_t offset, size_t len);

View File

@ -26,10 +26,14 @@
#include <utility>
#include <vector>
#include <memory>
#include <cstring>
#include "modsecurity/string_view.hpp"
#endif
#include "modsecurity/variable_value.h"
#ifndef HEADERS_MODSECURITY_ANCHORED_VARIABLE_H_
#define HEADERS_MODSECURITY_ANCHORED_VARIABLE_H_
@ -59,6 +63,8 @@ class AnchoredVariable {
void unset();
void set(const std::string &a, size_t offset);
void set(const bpstd::string_view &a, size_t offset);
void set(const char *a, size_t offset);
void set(const std::string &a, size_t offset, size_t offsetLen);
void append(const std::string &a, size_t offset,
bool spaceSeparator = false);

File diff suppressed because it is too large Load Diff

View File

@ -48,11 +48,13 @@ pkginclude_HEADERS = \
../headers/modsecurity/rules_set_phases.h \
../headers/modsecurity/rules_set_properties.h \
../headers/modsecurity/rules_exceptions.h \
../headers/modsecurity/string_view.hpp \
../headers/modsecurity/transaction.h \
../headers/modsecurity/variable_origin.h \
../headers/modsecurity/variable_value.h
libmodsecurity_includesub_collection_HEADERS = \
../headers/modsecurity/collection/collection.h \
../headers/modsecurity/collection/collections.h

View File

@ -80,6 +80,36 @@ void AnchoredSetVariable::set(const std::string &key,
}
void AnchoredSetVariable::set(const std::string &key,
const bpstd::string_view &value, size_t offset) {
std::unique_ptr<VariableOrigin> origin(new VariableOrigin());
std::string *v = new std::string(value.c_str());
VariableValue *var = new VariableValue(&m_name, &key, v);
delete v;
origin->m_offset = offset;
origin->m_length = value.size();
var->addOrigin(std::move(origin));
emplace(key, var);
}
void AnchoredSetVariable::set(const std::string &key,
const char *value, size_t offset) {
std::unique_ptr<VariableOrigin> origin(new VariableOrigin());
std::string *v = new std::string(value);
VariableValue *var = new VariableValue(&m_name, &key, v);
delete v;
origin->m_offset = offset;
origin->m_length = strlen(value);
var->addOrigin(std::move(origin));
emplace(key, var);
}
void AnchoredSetVariable::resolve(
std::vector<const VariableValue *> *l) {
for (const auto& x : *this) {

View File

@ -23,6 +23,7 @@
#include "modsecurity/modsecurity.h"
#include "modsecurity/transaction.h"
#include "src/utils/regex.h"
#include "modsecurity/string_view.hpp"
namespace modsecurity {
@ -75,6 +76,29 @@ void AnchoredVariable::set(const std::string &a, size_t offset) {
}
void AnchoredVariable::set(const char *a, size_t offset) {
std::unique_ptr<VariableOrigin> origin(new VariableOrigin());
m_offset = offset;
m_value.assign(a, strlen(a));
origin->m_offset = offset;
origin->m_length = m_value.size();
m_var->addOrigin(std::move(origin));
}
void AnchoredVariable::set(const bpstd::string_view &a, size_t offset) {
std::unique_ptr<VariableOrigin> origin(new VariableOrigin());
m_offset = offset;
m_value.assign(a.c_str(), a.size());
origin->m_offset = offset;
origin->m_length = m_value.size();
m_var->addOrigin(std::move(origin));
}
void AnchoredVariable::append(const std::string &a, size_t offset,
bool spaceSeparator) {
std::unique_ptr<VariableOrigin> origin(

View File

@ -444,12 +444,12 @@ std::string Lua::applyTransformations(lua_State *L, Transaction *t,
in.assign(newVar.c_str(), newVar.size());
tfn->execute(t, in, out);
newVar.assign(out.c_str(), out.size());
delete tfn;
} else {
ms_dbg_a(t, 1,
"SecRuleScript: Invalid transformation function: " \
+ std::string(name));
}
delete tfn;
}
return newVar;

View File

@ -24,8 +24,10 @@ namespace modsecurity {
namespace operators {
bool BeginsWith::evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &str, RuleMessage *ruleMessage) {
bool BeginsWith::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
std::string p(m_string->evaluate(transaction));
if (str.size() < p.size()) {

View File

@ -32,7 +32,9 @@ class BeginsWith : public Operator {
explicit BeginsWith(std::unique_ptr<RunTimeString> param)
: Operator("BeginsWith", std::move(param)) { }
bool evaluate(Transaction *transaction, RuleWithActions *rule, const std::string &str,
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};

View File

@ -21,10 +21,12 @@
namespace modsecurity {
namespace operators {
bool Contains::evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &input, RuleMessage *ruleMessage) {
bool Contains::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) {
std::string p(m_string->evaluate(transaction));
size_t offset = input.find(p);
size_t offset = input.to_string().find(p);
bool contains = offset != std::string::npos;

View File

@ -33,9 +33,11 @@ class Contains : public Operator {
public:
/** @ingroup ModSecurity_Operator */
explicit Contains(std::unique_ptr<RunTimeString> param)
: Operator("Contains", std::move(param)) { }
bool evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &str,
: Operator("Contains", std::move(param)) { };
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};

View File

@ -23,7 +23,7 @@
namespace modsecurity {
namespace operators {
bool ContainsWord::acceptableChar(const std::string& a, size_t pos) {
bool ContainsWord::acceptableChar(const bpstd::string_view &a, size_t pos) {
if (a.size() - 1 < pos) {
return false;
}
@ -36,37 +36,40 @@ bool ContainsWord::acceptableChar(const std::string& a, size_t pos) {
return true;
}
bool ContainsWord::evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &str, RuleMessage *ruleMessage) {
bool ContainsWord::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &inputView,
RuleMessage *ruleMessage) {
std::string paramTarget(m_string->evaluate(transaction));
std::string input = inputView.to_string();
if (paramTarget.empty()) {
return true;
}
if (str.empty()) {
if (input.empty()) {
return false;
}
if (str == paramTarget) {
if (input == paramTarget) {
return true;
}
size_t pos = str.find(paramTarget);
size_t pos = input.find(paramTarget);
while (pos != std::string::npos) {
if (pos == 0 && acceptableChar(str, paramTarget.size())) {
if (pos == 0 && acceptableChar(input, paramTarget.size())) {
logOffset(ruleMessage, 0, paramTarget.size());
return true;
}
if (pos + paramTarget.size() == str.size() &&
acceptableChar(str, pos - 1)) {
if (pos + paramTarget.size() == input.size() &&
acceptableChar(input, pos - 1)) {
logOffset(ruleMessage, pos, paramTarget.size());
return true;
}
if (acceptableChar(str, pos - 1) &&
acceptableChar(str, pos + paramTarget.size())) {
if (acceptableChar(input, pos - 1) &&
acceptableChar(input, pos + paramTarget.size())) {
logOffset(ruleMessage, pos, paramTarget.size());
return true;
}
pos = str.find(paramTarget, pos + 1);
pos = input.find(paramTarget, pos + 1);
}
return false;

View File

@ -32,12 +32,13 @@ class ContainsWord : public Operator {
explicit ContainsWord(std::unique_ptr<RunTimeString> param)
: Operator("ContainsWord", std::move(param)) { }
bool evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &str,
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
private:
static bool acceptableChar(const std::string& a, size_t pos);
static bool acceptableChar(const bpstd::string_view &a, size_t pos);
};
} // namespace operators

View File

@ -27,31 +27,33 @@ namespace modsecurity {
namespace operators {
bool DetectSQLi::evaluate(Transaction *t, RuleWithActions *rule,
const std::string& input, RuleMessage *ruleMessage) {
bool DetectSQLi::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) {
char fingerprint[8];
int issqli;
issqli = libinjection_sqli(input.c_str(), input.length(), fingerprint);
if (!t) {
if (!transaction) {
goto tisempty;
}
if (issqli) {
t->m_matched.push_back(fingerprint);
ms_dbg_a(t, 4, "detected SQLi using libinjection with " \
transaction->m_matched.push_back(fingerprint);
ms_dbg_a(transaction, 4, "detected SQLi using libinjection with " \
"fingerprint '" + std::string(fingerprint) + "' at: '" +
input + "'");
input.to_string() + "'");
if (rule && rule->hasCaptureAction()) {
t->m_collections.m_tx_collection->storeOrUpdateFirst(
transaction->m_collections.m_tx_collection->storeOrUpdateFirst(
"0", std::string(fingerprint));
ms_dbg_a(t, 7, "Added DetectSQLi match TX.0: " + \
ms_dbg_a(transaction, 7, "Added DetectSQLi match TX.0: " + \
std::string(fingerprint));
}
} else {
ms_dbg_a(t, 9, "detected SQLi: not able to find an " \
"inject on '" + input + "'");
ms_dbg_a(transaction, 9, "detected SQLi: not able to find an " \
"inject on '" + input.to_string() + "'");
}
tisempty:

View File

@ -32,8 +32,9 @@ class DetectSQLi : public Operator {
m_match_message.assign("detected SQLi using libinjection.");
}
bool evaluate(Transaction *t, RuleWithActions *rule,
const std::string& input,
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};

View File

@ -26,24 +26,26 @@ namespace modsecurity {
namespace operators {
bool DetectXSS::evaluate(Transaction *t, RuleWithActions *rule,
const std::string& input, RuleMessage *ruleMessage) {
bool DetectXSS::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) {
int is_xss;
is_xss = libinjection_xss(input.c_str(), input.length());
if (t) {
if (transaction) {
if (is_xss) {
ms_dbg_a(t, 5, "detected XSS using libinjection.");
ms_dbg_a(transaction, 5, "detected XSS using libinjection.");
if (rule && rule->hasCaptureAction()) {
t->m_collections.m_tx_collection->storeOrUpdateFirst(
transaction->m_collections.m_tx_collection->storeOrUpdateFirst(
"0", std::string(input));
ms_dbg_a(t, 7, "Added DetectXSS match TX.0: " + \
ms_dbg_a(transaction, 7, "Added DetectXSS match TX.0: " + \
std::string(input));
}
} else {
ms_dbg_a(t, 9, "libinjection was not able to " \
"find any XSS in: " + input);
ms_dbg_a(transaction, 9, "libinjection was not able to " \
"find any XSS in: " + input.to_string());
}
}
return is_xss != 0;

View File

@ -31,8 +31,9 @@ class DetectXSS : public Operator {
m_match_message.assign("detected XSS using libinjection.");
}
bool evaluate(Transaction *t, RuleWithActions *rule,
const std::string& input,
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};

View File

@ -23,16 +23,18 @@ namespace modsecurity {
namespace operators {
bool EndsWith::evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &str, RuleMessage *ruleMessage) {
bool EndsWith::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) {
bool ret = false;
std::string p(m_string->evaluate(transaction));
if (str.length() >= p.length()) {
ret = (0 == str.compare(str.length() - p.length(),
if (input.length() >= p.length()) {
ret = (0 == input.compare(input.length() - p.length(),
p.length(), p));
if (ret) {
logOffset(ruleMessage, str.length() - p.length(),
logOffset(ruleMessage, input.length() - p.length(),
p.size());
}
}

View File

@ -33,8 +33,10 @@ class EndsWith : public Operator {
: Operator("EndsWith", std::move(param)) {
m_couldContainsMacro = true;
}
bool evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &str,
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};

View File

@ -24,7 +24,10 @@ namespace modsecurity {
namespace operators {
bool Eq::evaluate(Transaction *transaction, const std::string &input) {
bool Eq::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) {
int p = 0;
int i = 0;
std::string pt(m_string->evaluate(transaction));
@ -35,7 +38,7 @@ bool Eq::evaluate(Transaction *transaction, const std::string &input) {
p = 0;
}
try {
i = std::stoi(input);
i = std::stoi(input.c_str());
} catch (...) {
i = 0;
}

View File

@ -31,7 +31,11 @@ class Eq : public Operator {
/** @ingroup ModSecurity_Operator */
explicit Eq(std::unique_ptr<RunTimeString> param)
: Operator("Eq", std::move(param)) { }
bool evaluate(Transaction *transaction, const std::string &input) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};
} // namespace operators

View File

@ -96,21 +96,24 @@ FuzzyHash::~FuzzyHash() {
}
bool FuzzyHash::evaluate(Transaction *t, const std::string &str) {
bool FuzzyHash::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
#ifdef WITH_SSDEEP
char result[FUZZY_MAX_RESULT];
struct fuzzy_hash_chunk *chunk = m_head;
if (fuzzy_hash_buf((const unsigned char*)str.c_str(),
str.size(), result)) {
ms_dbg_a(t, 4, "Problems generating fuzzy hash");
ms_dbg_a(transaction, 4, "Problems generating fuzzy hash");
return false;
}
while (chunk != NULL) {
int i = fuzzy_compare(chunk->data, result);
if (i >= m_threshold) {
ms_dbg_a(t, 4, "Fuzzy hash: matched " \
ms_dbg_a(transaction, 4, "Fuzzy hash: matched " \
"with score: " + std::to_string(i) + ".");
return true;
}

View File

@ -44,9 +44,12 @@ class FuzzyHash : public Operator {
m_head(NULL) { }
~FuzzyHash();
bool evaluate(Transaction *transaction, const std::string &std) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
bool init(const std::string &param, std::string *error) override;
bool init(const std::string &file, std::string *error) override;
private:
int m_threshold;
struct fuzzy_hash_chunk *m_head;

View File

@ -23,11 +23,13 @@
namespace modsecurity {
namespace operators {
bool Ge::evaluate(Transaction *transaction, const std::string &input) {
bool Ge::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
std::string p(m_string->evaluate(transaction));
std::string i = input;
bool ge = atoll(i.c_str()) >= atoll(p.c_str());
bool ge = atoll(str.c_str()) >= atoll(p.c_str());
return ge;
}

View File

@ -32,7 +32,11 @@ class Ge : public Operator {
: Operator("Ge", std::move(param)) {
m_couldContainsMacro = true;
}
bool evaluate(Transaction *transaction, const std::string &input) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};
} // namespace operators

View File

@ -34,16 +34,19 @@ namespace modsecurity {
namespace operators {
bool GeoLookup::evaluate(Transaction *trans, const std::string &exp) {
bool GeoLookup::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
using std::placeholders::_1;
using std::placeholders::_2;
bool ret = true;
if (trans) {
ret = Utils::GeoLookup::getInstance().lookup(exp, trans,
std::bind(&GeoLookup::debug, this, trans, _1, _2));
if (transaction) {
ret = Utils::GeoLookup::getInstance().lookup(str.c_str(), transaction,
std::bind(&GeoLookup::debug, this, transaction, _1, _2));
} else {
ret = Utils::GeoLookup::getInstance().lookup(exp, NULL,
ret = Utils::GeoLookup::getInstance().lookup(str.c_str(), NULL,
nullptr);
}

View File

@ -29,11 +29,15 @@ class GeoLookup : public Operator {
/** @ingroup ModSecurity_Operator */
GeoLookup()
: Operator("GeoLookup") { }
bool evaluate(Transaction *transaction, const std::string &exp) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
protected:
bool debug(Transaction *transaction, int x, const std::string &a) {
ms_dbg_a(transaction, x, a);
bool debug(Transaction *transaction, int x, const bpstd::string_view &str) {
ms_dbg_a(transaction, x, str.to_string());
return true;
}
};

View File

@ -23,7 +23,10 @@ namespace modsecurity {
namespace operators {
bool GsbLookup::evaluate(Transaction *transaction, const std::string &str) {
bool GsbLookup::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
/**
* @todo Implement the operator GeoLookup.
* Reference: https://github.com/SpiderLabs/ModSecurity/wiki/Reference-Manual#gsblookup

View File

@ -31,7 +31,10 @@ class GsbLookup : public Operator {
explicit GsbLookup(std::unique_ptr<RunTimeString> param)
: Operator("GsbLookup", std::move(param)) { }
bool evaluate(Transaction *transaction, const std::string &str) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};
} // namespace operators

View File

@ -23,10 +23,13 @@
namespace modsecurity {
namespace operators {
bool Gt::evaluate(Transaction *transaction, const std::string &input) {
bool Gt::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
std::string p(m_string->evaluate(transaction));
bool gt = atoll(input.c_str()) > atoll(p.c_str());
bool gt = atoll(str.c_str()) > atoll(p.c_str());
return gt;
}

View File

@ -33,7 +33,11 @@ class Gt : public Operator {
: Operator("Gt", std::move(param)) {
m_couldContainsMacro = true;
}
bool evaluate(Transaction *transaction, const std::string &input) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};
} // namespace operators

View File

@ -49,9 +49,12 @@ bool InspectFile::init(const std::string &param2, std::string *error) {
}
bool InspectFile::evaluate(Transaction *transaction, const std::string &str) {
bool InspectFile::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
if (m_isScript) {
return m_lua.run(transaction, str);
return m_lua.run(transaction, str.c_str());
} else {
FILE *in;
char buff[512];
@ -61,7 +64,7 @@ bool InspectFile::evaluate(Transaction *transaction, const std::string &str) {
openstr.append(m_param);
openstr.append(" ");
openstr.append(str);
openstr.append(str.c_str());
if (!(in = popen(openstr.c_str(), "r"))) {
return false;
}

View File

@ -35,8 +35,13 @@ class InspectFile : public Operator {
m_file(""),
m_isScript(false) { }
bool init(const std::string &param, std::string *error) override;
bool evaluate(Transaction *transaction, const std::string &str) override;
bool init(const std::string &file, std::string *error) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
private:
std::string m_file;
bool m_isScript;

View File

@ -37,8 +37,11 @@ bool IpMatch::init(const std::string &file, std::string *error) {
}
bool IpMatch::evaluate(Transaction *transaction, const std::string &input) {
return m_tree.contains(input);
bool IpMatch::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
return m_tree.contains(str.c_str());
}

View File

@ -34,7 +34,10 @@ class IpMatch : public Operator {
IpMatch(const std::string &n, std::unique_ptr<RunTimeString> param)
: Operator(n, std::move(param)) { }
bool evaluate(Transaction *transaction, const std::string &input) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
bool init(const std::string &file, std::string *error) override;

View File

@ -23,10 +23,13 @@
namespace modsecurity {
namespace operators {
bool Le::evaluate(Transaction *transaction, const std::string &input) {
bool Le::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
std::string p(m_string->evaluate(transaction));
bool le = atoll(input.c_str()) <= atoll(p.c_str());
bool le = atoll(str.c_str()) <= atoll(p.c_str());
return le;
}

View File

@ -34,7 +34,10 @@ class Le : public Operator {
m_couldContainsMacro = true;
}
bool evaluate(Transaction *transaction, const std::string &input) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};

View File

@ -22,10 +22,13 @@
namespace modsecurity {
namespace operators {
bool Lt::evaluate(Transaction *transaction, const std::string &input) {
bool Lt::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
std::string p(m_string->evaluate(transaction));
bool lt = atoll(input.c_str()) < atoll(p.c_str());
bool lt = atoll(str.c_str()) < atoll(p.c_str());
return lt;
}

View File

@ -34,7 +34,10 @@ class Lt : public Operator {
m_couldContainsMacro = true;
}
bool evaluate(Transaction *transaction, const std::string &input) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};
} // namespace operators

View File

@ -20,7 +20,10 @@
namespace modsecurity {
namespace operators {
bool NoMatch::evaluate(Transaction *transaction, const std::string &str) {
bool NoMatch::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
return false;
}

View File

@ -32,7 +32,10 @@ class NoMatch : public Operator {
NoMatch()
: Operator("NoMatch") { }
bool evaluate(Transaction *transaction, const std::string &str) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};
} // namespace operators

View File

@ -71,7 +71,7 @@ namespace operators {
bool Operator::evaluateInternal(Transaction *transaction,
RuleWithActions *rule, const std::string& a, RuleMessage *rm) {
RuleWithActions *rule, const bpstd::string_view &a, RuleMessage *rm) {
bool res = evaluate(transaction, rule, a, rm);
if (m_negation) {
@ -81,28 +81,6 @@ bool Operator::evaluateInternal(Transaction *transaction,
return res;
}
bool Operator::evaluateInternal(Transaction *transaction,
RuleWithActions *rule, const std::string& a) {
bool res = evaluate(transaction, rule, a);
if (m_negation) {
return !res;
}
return res;
}
bool Operator::evaluateInternal(Transaction *transaction,
const std::string& a) {
bool res = evaluate(transaction, a);
if (m_negation) {
return !res;
}
return res;
}
std::string Operator::resolveMatchMessage(Transaction *t,
std::string key, std::string value) {
@ -132,7 +110,10 @@ std::string Operator::resolveMatchMessage(Transaction *t,
}
bool Operator::evaluate(Transaction *transaction, const std::string& a) {
bool Operator::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) {
ms_dbg_a(transaction, 2, "Operator: " + m_op + \
" is not implemented or malfunctioning.");
return true;

View File

@ -24,6 +24,7 @@
#include "modsecurity/rule.h"
#include "modsecurity/rule_message.h"
#include "src/run_time_string.h"
#include "modsecurity/string_view.hpp"
namespace modsecurity {
namespace operators {
@ -107,26 +108,17 @@ class Operator {
return true;
}
virtual std::string resolveMatchMessage(Transaction *t,
std::string key, std::string value);
bool evaluateInternal(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view& a,
RuleMessage *ruleMessage);
bool evaluateInternal(Transaction *t, const std::string& a);
bool evaluateInternal(Transaction *t, RuleWithActions *rule,
const std::string& a);
bool evaluateInternal(Transaction *t, RuleWithActions *rule,
const std::string& a, RuleMessage *ruleMessage);
virtual bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage);
virtual bool evaluate(Transaction *transaction, const std::string &str);
virtual bool evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &str) {
return evaluate(transaction, str);
}
virtual bool evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &str, RuleMessage *ruleMessage) {
return evaluate(transaction, str);
}
static void logOffset(RuleMessage *ruleMessage, int offset, int len) {
if (ruleMessage) {
ruleMessage->m_reference.append("o"
@ -135,6 +127,10 @@ class Operator {
}
}
virtual std::string resolveMatchMessage(Transaction *t,
std::string key, std::string value);
std::string m_match_message;
bool m_negation;
std::string m_op;

View File

@ -83,8 +83,10 @@ void Pm::postOrderTraversal(acmp_btree_node_t *node) {
}
bool Pm::evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &input, RuleMessage *ruleMessage) {
bool Pm::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
int rc = -1;
ACMPT pt;
pt.parser = m_p;
@ -93,7 +95,7 @@ bool Pm::evaluate(Transaction *transaction, RuleWithActions *rule,
#ifdef MODSEC_MUTEX_ON_PM
pthread_mutex_lock(&m_lock);
#endif
rc = acmp_process_quick(&pt, &match, input.c_str(), input.length());
rc = acmp_process_quick(&pt, &match, str.c_str(), str.length());
#ifdef MODSEC_MUTEX_ON_PM
pthread_mutex_unlock(&m_lock);
#endif

View File

@ -41,8 +41,10 @@ class Pm : public Operator {
m_p = acmp_create(0);
}
~Pm();
bool evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &str,
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;

View File

@ -56,7 +56,7 @@ bool PmFromFile::init(const std::string &config, std::string *error) {
iss = new std::stringstream(client.content);
} else {
std::string err;
std::string resource = utils::find_resource(m_param, config, &err);
std::string resource = utils::find_resource(m_param, config.c_str(), &err);
iss = new std::ifstream(resource, std::ios::in);
if (((std::ifstream *)iss)->is_open() == false) {

View File

@ -202,11 +202,12 @@ void Rbl::furtherInfo(struct sockaddr_in *sin, const std::string &ipStr,
}
bool Rbl::evaluate(Transaction *t, RuleWithActions *rule,
const std::string& ipStr,
RuleMessage *ruleMessage) {
bool Rbl::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
struct addrinfo *info = NULL;
std::string host = Rbl::mapIpToAddress(ipStr, t);
std::string host = Rbl::mapIpToAddress(str.c_str(), transaction);
int rc = 0;
if (host.empty()) {
@ -219,20 +220,20 @@ bool Rbl::evaluate(Transaction *t, RuleWithActions *rule,
if (info != NULL) {
freeaddrinfo(info);
}
ms_dbg_a(t, 5, "RBL lookup of " + ipStr + " failed.");
ms_dbg_a(transaction, 5, "RBL lookup of " + str.to_string() + " failed.");
return false;
}
struct sockaddr *addr = info->ai_addr;
struct sockaddr_in *sin = (struct sockaddr_in *) addr;
furtherInfo(sin, ipStr, t, m_provider);
furtherInfo(sin, str.c_str(), transaction, m_provider);
freeaddrinfo(info);
if (rule && t && rule->hasCaptureAction()) {
t->m_collections.m_tx_collection->storeOrUpdateFirst(
"0", std::string(ipStr));
ms_dbg_a(t, 7, "Added RXL match TX.0: " + \
std::string(ipStr));
if (rule && transaction && rule->hasCaptureAction()) {
transaction->m_collections.m_tx_collection->storeOrUpdateFirst(
"0", std::string(str));
ms_dbg_a(transaction, 7, "Added RXL match TX.0: " + \
std::string(str));
}
return true;

View File

@ -76,8 +76,10 @@ class Rbl : public Operator {
m_provider = RblProvider::httpbl;
}
}
bool evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string& input,
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
std::string mapIpToAddress(const std::string &ipStr, Transaction *trans) const;

View File

@ -23,7 +23,10 @@ namespace modsecurity {
namespace operators {
bool Rsub::evaluate(Transaction *transaction, const std::string &str) {
bool Rsub::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) {
/**
* @todo Implement the operator Rsub.
* Reference: https://github.com/SpiderLabs/ModSecurity/wiki/Reference-Manual#rsub

View File

@ -32,7 +32,11 @@ class Rsub : public Operator {
/** @ingroup ModSecurity_Operator */
explicit Rsub(std::unique_ptr<RunTimeString> param)
: Operator("Rsub", std::move(param)) { }
bool evaluate(Transaction *transaction, const std::string &str) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};

View File

@ -29,7 +29,7 @@ namespace modsecurity {
namespace operators {
bool Rx::init(const std::string &arg, std::string *error) {
bool Rx::init(const std::string &file, std::string *error) {
if (m_string->m_containsMacro == false) {
m_re = new Regex(m_param);
}
@ -38,8 +38,10 @@ bool Rx::init(const std::string &arg, std::string *error) {
}
bool Rx::evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string& input, RuleMessage *ruleMessage) {
bool Rx::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) {
Regex *re;
if (m_param.empty() && !m_string->m_containsMacro) {
@ -54,8 +56,8 @@ bool Rx::evaluate(Transaction *transaction, RuleWithActions *rule,
}
std::vector<Utils::SMatchCapture> captures;
re->searchOneMatch(input, captures);
// FIXME: searchOneMatch should accept string_view.
re->searchOneMatch(input.c_str(), captures);
if (rule && rule->hasCaptureAction() && transaction) {
for (const Utils::SMatchCapture& capture : captures) {
const std::string capture_substring(input.substr(capture.m_offset,capture.m_length));

View File

@ -49,11 +49,12 @@ class Rx : public Operator {
}
}
bool evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string& input,
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
bool init(const std::string &arg, std::string *error) override;
bool init(const std::string &file, std::string *error) override;
private:
Regex *m_re;

View File

@ -37,7 +37,7 @@ bool RxGlobal::init(const std::string &arg, std::string *error) {
bool RxGlobal::evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string& input, RuleMessage *ruleMessage) {
const bpstd::string_view& input, RuleMessage *ruleMessage) {
Regex *re;
if (m_param.empty() && !m_string->m_containsMacro) {
@ -52,7 +52,7 @@ bool RxGlobal::evaluate(Transaction *transaction, RuleWithActions *rule,
}
std::vector<Utils::SMatchCapture> captures;
re->searchGlobal(input, captures);
re->searchGlobal(input.c_str(), captures);
if (rule && rule->hasCaptureAction() && transaction) {
for (const Utils::SMatchCapture& capture : captures) {

View File

@ -50,7 +50,7 @@ class RxGlobal : public Operator {
}
bool evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string& input,
const bpstd::string_view& input,
RuleMessage *ruleMessage) override;
bool init(const std::string &arg, std::string *error) override;

View File

@ -20,9 +20,12 @@
namespace modsecurity {
namespace operators {
bool StrEq::evaluate(Transaction *transaction, const std::string &str) {
bool StrEq::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
std::string pt(m_string->evaluate(transaction));
return !pt.compare(str);
return !pt.compare(str.to_string());
}

View File

@ -34,7 +34,10 @@ class StrEq : public Operator {
explicit StrEq(std::unique_ptr<RunTimeString> param)
: Operator("StrEq", std::move(param)) { }
bool evaluate(Transaction *transaction, const std::string &str) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};
} // namespace operators

View File

@ -24,9 +24,12 @@ namespace modsecurity {
namespace operators {
bool StrMatch::evaluate(Transaction *transaction, const std::string &input) {
bool StrMatch::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
std::string p(m_string->evaluate(transaction));
bool ret = input.find(p) != std::string::npos;
bool ret = str.find(p) != std::string::npos;
return ret;
}

View File

@ -34,7 +34,10 @@ class StrMatch : public Operator {
m_couldContainsMacro = true;
}
bool evaluate(Transaction *transaction, const std::string &input) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};
} // namespace operators

View File

@ -19,7 +19,9 @@ namespace modsecurity {
namespace operators {
bool UnconditionalMatch::evaluate(Transaction *transaction,
const std::string &input) {
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
return true;
}

View File

@ -31,7 +31,10 @@ class UnconditionalMatch : public Operator {
UnconditionalMatch()
: Operator("UnconditionalMatch") { }
bool evaluate(Transaction *transaction, const std::string &exp) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};
} // namespace operators

View File

@ -23,7 +23,7 @@
namespace modsecurity {
namespace operators {
bool ValidateByteRange::getRange(const std::string &rangeRepresentation,
bool ValidateByteRange::getRange(const bpstd::string_view &rangeRepresentation,
std::string *error) {
size_t pos = rangeRepresentation.find_first_of("-");
int start;
@ -31,9 +31,10 @@ bool ValidateByteRange::getRange(const std::string &rangeRepresentation,
if (pos == std::string::npos) {
try {
start = std::stoi(rangeRepresentation);
start = std::stoi(rangeRepresentation.c_str());
} catch(...) {
error->assign("Not able to convert '" + rangeRepresentation +
error->assign("Not able to convert '" + \
rangeRepresentation.to_string() +
"' into a number");
return false;
}
@ -42,19 +43,19 @@ bool ValidateByteRange::getRange(const std::string &rangeRepresentation,
}
try {
start = std::stoi(std::string(rangeRepresentation, 0, pos));
start = std::stoi(std::string(rangeRepresentation.c_str(), 0, pos));
} catch (...) {
error->assign("Not able to convert '" +
std::string(rangeRepresentation, 0, pos) +
std::string(rangeRepresentation.c_str(), 0, pos) +
"' into a number");
return false;
}
try {
end = std::stoi(std::string(rangeRepresentation, pos + 1,
end = std::stoi(std::string(rangeRepresentation.c_str(), pos + 1,
rangeRepresentation.length() - (pos + 1)));
} catch (...) {
error->assign("Not able to convert '" + std::string(rangeRepresentation,
error->assign("Not able to convert '" + std::string(rangeRepresentation.c_str(),
pos + 1, rangeRepresentation.length() - (pos + 1)) +
"' into a number");
return false;
@ -110,16 +111,18 @@ bool ValidateByteRange::init(const std::string &file,
}
bool ValidateByteRange::evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &input, RuleMessage *ruleMessage) {
bool ValidateByteRange::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
bool ret = true;
size_t count = 0;
for (int i = 0; i < input.length(); i++) {
int x = (unsigned char) input.at(i);
for (int i = 0; i < str.length(); i++) {
int x = (unsigned char) str.at(i);
if (!(table[x >> 3] & (1 << (x & 0x7)))) {
// debug(9, "Value " + std::to_string(x) + " in " +
// input + " ouside range: " + param);
// str + " ouside range: " + param);
logOffset(ruleMessage, i, 1);
count++;
}

View File

@ -37,10 +37,12 @@ class ValidateByteRange : public Operator {
}
~ValidateByteRange() override { }
bool evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &input,
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
bool getRange(const std::string &rangeRepresentation, std::string *error);
bool getRange(const bpstd::string_view &rangeRepresentation, std::string *error);
bool init(const std::string& file, std::string *error) override;
private:
std::vector<std::string> ranges;

View File

@ -43,25 +43,28 @@ bool ValidateDTD::init(const std::string &file, std::string *error) {
}
bool ValidateDTD::evaluate(Transaction *t, const std::string &str) {
bool ValidateDTD::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) {
xmlValidCtxtPtr cvp;
m_dtd = xmlParseDTD(NULL, (const xmlChar *)m_resource.c_str());
if (m_dtd == NULL) {
std::string err = std::string("XML: Failed to load DTD: ") \
+ m_resource;
ms_dbg_a(t, 4, err);
ms_dbg_a(transaction, 4, err);
return true;
}
if (t->m_xml->m_data.doc == NULL) {
ms_dbg_a(t, 4, "XML document tree could not "\
if (transaction->m_xml->m_data.doc == NULL) {
ms_dbg_a(transaction, 4, "XML document tree could not "\
"be found for DTD validation.");
return true;
}
if (t->m_xml->m_data.well_formed != 1) {
ms_dbg_a(t, 4, "XML: DTD validation failed because " \
if (transaction->m_xml->m_data.well_formed != 1) {
ms_dbg_a(transaction, 4, "XML: DTD validation failed because " \
"content is not well formed.");
return true;
}
@ -78,22 +81,23 @@ bool ValidateDTD::evaluate(Transaction *t, const std::string &str) {
cvp = xmlNewValidCtxt();
if (cvp == NULL) {
ms_dbg_a(t, 4, "XML: Failed to create a validation context.");
ms_dbg_a(transaction, 4,
"XML: Failed to create a validation context.");
return true;
}
/* Send validator errors/warnings to msr_log */
cvp->error = (xmlSchemaValidityErrorFunc)error_runtime;
cvp->warning = (xmlSchemaValidityErrorFunc)warn_runtime;
cvp->userData = t;
cvp->userData = transaction;
if (!xmlValidateDtd(cvp, t->m_xml->m_data.doc, m_dtd)) {
ms_dbg_a(t, 4, "XML: DTD validation failed.");
if (!xmlValidateDtd(cvp, transaction->m_xml->m_data.doc, m_dtd)) {
ms_dbg_a(transaction, 4, "XML: DTD validation failed.");
xmlFreeValidCtxt(cvp);
return true;
}
ms_dbg_a(t, 4, std::string("XML: Successfully validated " \
ms_dbg_a(transaction, 4, std::string("XML: Successfully validated " \
"payload against DTD: ") + m_resource);
xmlFreeValidCtxt(cvp);

View File

@ -46,7 +46,11 @@ class ValidateDTD : public Operator {
}
}
bool evaluate(Transaction *transaction, const std::string &str) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
bool init(const std::string &file, std::string *error) override;

View File

@ -22,7 +22,10 @@
namespace modsecurity {
namespace operators {
bool ValidateHash::evaluate(Transaction *transaction, const std::string &str) {
bool ValidateHash::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
/**
* @todo Implement the operator ValidateHash.
* Reference: https://github.com/SpiderLabs/ModSecurity/wiki/Reference-Manual#validateHash

View File

@ -31,7 +31,11 @@ class ValidateHash : public Operator {
/** @ingroup ModSecurity_Operator */
explicit ValidateHash(std::unique_ptr<RunTimeString> param)
: Operator("ValidateHash", std::move(param)) { }
bool evaluate(Transaction *transaction, const std::string &str) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};
} // namespace operators

View File

@ -39,8 +39,10 @@ bool ValidateSchema::init(const std::string &file, std::string *error) {
}
bool ValidateSchema::evaluate(Transaction *t,
const std::string &str) {
bool ValidateSchema::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
int rc;
m_parserCtx = xmlSchemaNewParserCtxt(m_resource.c_str());
@ -52,7 +54,7 @@ bool ValidateSchema::evaluate(Transaction *t,
if (m_err.empty() == false) {
err << m_err;
}
ms_dbg_a(t, 4, err.str());
ms_dbg_a(transaction, 4, err.str());
return true;
}
@ -75,7 +77,7 @@ bool ValidateSchema::evaluate(Transaction *t,
if (m_err.empty() == false) {
err << " " << m_err;
}
ms_dbg_a(t, 4, err.str());
ms_dbg_a(transaction, 4, err.str());
xmlSchemaFreeParserCtxt(m_parserCtx);
return true;
}
@ -86,23 +88,23 @@ bool ValidateSchema::evaluate(Transaction *t,
if (m_err.empty() == false) {
err << " " << m_err;
}
ms_dbg_a(t, 4, err.str());
ms_dbg_a(transaction, 4, err.str());
return true;
}
/* Send validator errors/warnings to msr_log */
xmlSchemaSetValidErrors(m_validCtx,
(xmlSchemaValidityErrorFunc)error_runtime,
(xmlSchemaValidityWarningFunc)warn_runtime, t);
(xmlSchemaValidityWarningFunc)warn_runtime, transaction);
if (t->m_xml->m_data.doc == NULL) {
ms_dbg_a(t, 4, "XML document tree could not be found for " \
if (transaction->m_xml->m_data.doc == NULL) {
ms_dbg_a(transaction, 4, "XML document tree could not be found for " \
"schema validation.");
return true;
}
if (t->m_xml->m_data.well_formed != 1) {
ms_dbg_a(t, 4, "XML: Schema validation failed because " \
if (transaction->m_xml->m_data.well_formed != 1) {
ms_dbg_a(transaction, 4, "XML: Schema validation failed because " \
"content is not well formed.");
return true;
}
@ -116,15 +118,15 @@ bool ValidateSchema::evaluate(Transaction *t,
}
*/
rc = xmlSchemaValidateDoc(m_validCtx, t->m_xml->m_data.doc);
rc = xmlSchemaValidateDoc(m_validCtx, transaction->m_xml->m_data.doc);
if (rc != 0) {
ms_dbg_a(t, 4, "XML: Schema validation failed.");
ms_dbg_a(transaction, 4, "XML: Schema validation failed.");
xmlSchemaFree(m_schema);
xmlSchemaFreeParserCtxt(m_parserCtx);
return true; /* No match. */
}
ms_dbg_a(t, 4, "XML: Successfully validated payload against " \
ms_dbg_a(transaction, 4, "XML: Successfully validated payload against " \
"Schema: " + m_resource);
xmlSchemaFree(m_schema);
xmlSchemaFreeParserCtxt(m_parserCtx);

View File

@ -58,7 +58,11 @@ class ValidateSchema : public Operator {
}
}
bool evaluate(Transaction *transaction, const std::string &str) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
bool init(const std::string &file, std::string *error) override;

View File

@ -68,8 +68,10 @@ int ValidateUrlEncoding::validate_url_encoding(const char *input,
}
bool ValidateUrlEncoding::evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &input, RuleMessage *ruleMessage) {
bool ValidateUrlEncoding::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) {
size_t offset = 0;
bool res = false;
@ -82,14 +84,15 @@ bool ValidateUrlEncoding::evaluate(Transaction *transaction, RuleWithActions *ru
case 1 :
/* Encoding is valid */
if (transaction) {
ms_dbg_a(transaction, 7, "Valid URL Encoding at '" +input + "'");
ms_dbg_a(transaction, 7, "Valid URL Encoding at '" + \
input.to_string() + "'");
}
res = false;
break;
case -2 :
if (transaction) {
ms_dbg_a(transaction, 7, "Invalid URL Encoding: Non-hexadecimal "
"digits used at '" + input + "'");
"digits used at '" + input.to_string() + "'");
logOffset(ruleMessage, offset, input.size());
}
res = true; /* Invalid match. */
@ -97,7 +100,7 @@ bool ValidateUrlEncoding::evaluate(Transaction *transaction, RuleWithActions *ru
case -3 :
if (transaction) {
ms_dbg_a(transaction, 7, "Invalid URL Encoding: Not enough " \
"characters at the end of input at '" + input + "'");
"characters at the end of input at '" + input.to_string() + "'");
logOffset(ruleMessage, offset, input.size());
}
res = true; /* Invalid match. */
@ -107,7 +110,7 @@ bool ValidateUrlEncoding::evaluate(Transaction *transaction, RuleWithActions *ru
if (transaction) {
ms_dbg_a(transaction, 7, "Invalid URL Encoding: Internal " \
"Error (rc = " + std::to_string(rc) + ") at '" +
input + "'");
input.to_string() + "'");
logOffset(ruleMessage, offset, input.size());
}
res = true;

View File

@ -31,8 +31,9 @@ class ValidateUrlEncoding : public Operator {
ValidateUrlEncoding()
: Operator("ValidateUrlEncoding") { }
bool evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &input,
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
static int validate_url_encoding(const char *input, uint64_t input_length,

View File

@ -113,8 +113,10 @@ int ValidateUtf8Encoding::detect_utf8_character(
return unicode_len;
}
bool ValidateUtf8Encoding::evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &str, RuleMessage *ruleMessage) {
bool ValidateUtf8Encoding::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
unsigned int i, bytes_left;
const char *str_c = str.c_str();
@ -128,7 +130,7 @@ bool ValidateUtf8Encoding::evaluate(Transaction *transaction, RuleWithActions *r
if (transaction) {
ms_dbg_a(transaction, 8, "Invalid UTF-8 encoding: "
"not enough bytes in character "
"at " + str + ". [offset \"" +
"at " + str.to_string() + ". [offset \"" +
std::to_string(i) + "\"]");
}
return true;
@ -137,7 +139,7 @@ bool ValidateUtf8Encoding::evaluate(Transaction *transaction, RuleWithActions *r
if (transaction) {
ms_dbg_a(transaction, 8, "Invalid UTF-8 encoding: "
"invalid byte value in character "
"at " + str + ". [offset \"" +
"at " + str.to_string() + ". [offset \"" +
std::to_string(i) + "\"]");
logOffset(ruleMessage, i, str.size());
}
@ -147,7 +149,7 @@ bool ValidateUtf8Encoding::evaluate(Transaction *transaction, RuleWithActions *r
if (transaction) {
ms_dbg_a(transaction, 8, "Invalid UTF-8 encoding: "
"overlong character detected "
"at " + str + ". [offset \"" +
"at " + str.to_string() + ". [offset \"" +
std::to_string(i) + "\"]");
logOffset(ruleMessage, i, str.size());
}
@ -157,7 +159,7 @@ bool ValidateUtf8Encoding::evaluate(Transaction *transaction, RuleWithActions *r
if (transaction) {
ms_dbg_a(transaction, 8, "Invalid UTF-8 encoding: "
"use of restricted character "
"at " + str + ". [offset \"" +
"at " + str.to_string() + ". [offset \"" +
std::to_string(i) + "\"]");
logOffset(ruleMessage, i, str.size());
}
@ -166,7 +168,7 @@ bool ValidateUtf8Encoding::evaluate(Transaction *transaction, RuleWithActions *r
case UNICODE_ERROR_DECODING_ERROR :
if (transaction) {
ms_dbg_a(transaction, 8, "Error validating UTF-8 decoding "
"at " + str + ". [offset \"" +
"at " + str.to_string() + ". [offset \"" +
std::to_string(i) + "\"]");
logOffset(ruleMessage, i, str.size());
}
@ -177,7 +179,7 @@ bool ValidateUtf8Encoding::evaluate(Transaction *transaction, RuleWithActions *r
if (rc <= 0) {
if (transaction) {
ms_dbg_a(transaction, 8, "Internal error during UTF-8 validation "
"at " + str + ". [offset \"" +
"at " + str.to_string() + ". [offset \"" +
std::to_string(i) + "\"]");
logOffset(ruleMessage, i, str.size());
}

View File

@ -38,8 +38,9 @@ class ValidateUtf8Encoding : public Operator {
ValidateUtf8Encoding()
: Operator("ValidateUtf8Encoding") { }
bool evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &str,
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
static int detect_utf8_character(const unsigned char *p_read,

View File

@ -119,8 +119,10 @@ bool VerifyCC::init(const std::string &param2, std::string *error) {
}
bool VerifyCC::evaluate(Transaction *t, RuleWithActions *rule,
const std::string& i, RuleMessage *ruleMessage) {
bool VerifyCC::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &i,
RuleMessage *ruleMessage) {
int offset = 0;
int target_length = i.length();
@ -139,18 +141,18 @@ bool VerifyCC::evaluate(Transaction *t, RuleWithActions *rule,
return false;
}
if (ret > 0) {
match = std::string(i, ovector[0], ovector[1] - ovector[0]);
match = std::string(i.to_string(), ovector[0], ovector[1] - ovector[0]);
int is_cc = luhnVerify(match.c_str(), match.size());
if (is_cc) {
if (t) {
if (transaction) {
if (rule && rule->hasCaptureAction()) {
t->m_collections.m_tx_collection->storeOrUpdateFirst(
transaction->m_collections.m_tx_collection->storeOrUpdateFirst(
"0", std::string(match));
ms_dbg_a(t, 7, "Added VerifyCC match TX.0: " + \
ms_dbg_a(transaction, 7, "Added VerifyCC match TX.0: " + \
std::string(match));
}
ms_dbg_a(t, 9, "CC# match \"" + m_param +
"\" at " + i + ". [offset " +
ms_dbg_a(transaction, 9, "CC# match \"" + m_param +
"\" at " + i.to_string() + ". [offset " +
std::to_string(offset) + "]");
}
return true;

View File

@ -35,10 +35,13 @@ class VerifyCC : public Operator {
m_pce(NULL) { }
~VerifyCC();
bool evaluate(Transaction *t, RuleWithActions *rule,
const std::string& input,
RuleMessage *ruleMessage) override;
bool init(const std::string &param, std::string *error) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
private:
pcre *m_pc;
pcre_extra *m_pce;

View File

@ -110,8 +110,10 @@ bool VerifyCPF::verify(const char *cpfnumber, int len) {
}
bool VerifyCPF::evaluate(Transaction *t, RuleWithActions *rule,
const std::string& input, RuleMessage *ruleMessage) {
bool VerifyCPF::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) {
std::list<SMatch> matches;
bool is_cpf = false;
int i;
@ -121,15 +123,15 @@ bool VerifyCPF::evaluate(Transaction *t, RuleWithActions *rule,
}
for (i = 0; i < input.size() - 1 && is_cpf == false; i++) {
matches = m_re->searchAll(input.substr(i, input.size()));
matches = m_re->searchAll(input.substr(i, input.size()).to_string());
for (const auto & m : matches) {
is_cpf = verify(m.str().c_str(), m.str().size());
if (is_cpf) {
logOffset(ruleMessage, m.offset(), m.str().size());
if (rule && t && rule->hasCaptureAction()) {
t->m_collections.m_tx_collection->storeOrUpdateFirst(
if (rule && transaction && rule->hasCaptureAction()) {
transaction->m_collections.m_tx_collection->storeOrUpdateFirst(
"0", m.str());
ms_dbg_a(t, 7, "Added VerifyCPF match TX.0: " + \
ms_dbg_a(transaction, 7, "Added VerifyCPF match TX.0: " + \
m.str());
}

View File

@ -46,8 +46,9 @@ class VerifyCPF : public Operator {
bool operator=(const VerifyCPF &a) = delete;
VerifyCPF(const VerifyCPF &a) = delete;
bool evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string& input,
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
bool verify(const char *ssnumber, int len);

View File

@ -112,8 +112,10 @@ invalid:
}
bool VerifySSN::evaluate(Transaction *t, RuleWithActions *rule,
const std::string& input, RuleMessage *ruleMessage) {
bool VerifySSN::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) {
std::list<SMatch> matches;
bool is_ssn = false;
int i;
@ -123,15 +125,15 @@ bool VerifySSN::evaluate(Transaction *t, RuleWithActions *rule,
}
for (i = 0; i < input.size() - 1 && is_ssn == false; i++) {
matches = m_re->searchAll(input.substr(i, input.size()));
matches = m_re->searchAll(input.substr(i, input.size()).to_string());
for (const auto & j : matches) {
is_ssn = verify(j.str().c_str(), j.str().size());
if (is_ssn) {
logOffset(ruleMessage, j.offset(), j.str().size());
if (rule && t && rule->hasCaptureAction()) {
t->m_collections.m_tx_collection->storeOrUpdateFirst(
if (rule && transaction && rule->hasCaptureAction()) {
transaction->m_collections.m_tx_collection->storeOrUpdateFirst(
"0", j.str());
ms_dbg_a(t, 7, "Added VerifySSN match TX.0: " + \
ms_dbg_a(transaction, 7, "Added VerifySSN match TX.0: " + \
j.str());
}

View File

@ -46,8 +46,9 @@ class VerifySSN : public Operator {
bool operator=(const VerifySSN &a) = delete;
VerifySSN(const VerifySSN &a) = delete;
bool evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string& input,
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;

View File

@ -78,8 +78,10 @@ bool VerifySVNR::verify(const char *svnrnumber, int len) {
}
bool VerifySVNR::evaluate(Transaction *t, RuleWithActions *rule,
const std::string& input, RuleMessage* ruleMessage) {
bool VerifySVNR::evaluate(Transaction *t,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage* ruleMessage) {
std::list<SMatch> matches;
bool is_svnr = false;
int i;
@ -89,7 +91,7 @@ bool VerifySVNR::evaluate(Transaction *t, RuleWithActions *rule,
}
for (i = 0; i < input.size() - 1 && is_svnr == false; i++) {
matches = m_re->searchAll(input.substr(i, input.size()));
matches = m_re->searchAll(input.substr(i, input.size()).to_string());
for (const auto & j : matches) {
is_svnr = verify(j.str().c_str(), j.str().size());

View File

@ -32,8 +32,9 @@ class VerifySVNR : public Operator {
bool operator=(const VerifySVNR &a) = delete;
VerifySVNR(const VerifySVNR &a) = delete;
bool evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string& input,
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
bool verify(const char *ssnumber, int len);

View File

@ -24,8 +24,10 @@ namespace modsecurity {
namespace operators {
bool Within::evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &str, RuleMessage *ruleMessage) {
bool Within::evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &str,
RuleMessage *ruleMessage) {
bool res = false;
size_t pos = 0;
std::string paramTarget(m_string->evaluate(transaction));
@ -34,7 +36,7 @@ bool Within::evaluate(Transaction *transaction, RuleWithActions *rule,
return true;
}
pos = paramTarget.find(str);
pos = paramTarget.find(str.c_str());
res = pos != std::string::npos;
if (res) {
logOffset(ruleMessage, pos, str.size());

View File

@ -33,8 +33,11 @@ class Within : public Operator {
: Operator("Within", std::move(param)) {
m_couldContainsMacro = true;
}
bool evaluate(Transaction *transaction, RuleWithActions *rule,
const std::string &str, RuleMessage *ruleMessage) override;
bool evaluate(Transaction *transaction,
RuleWithActions *rule,
const bpstd::string_view &input,
RuleMessage *ruleMessage) override;
};
} // namespace operators

View File

@ -41,6 +41,7 @@
#include "src/actions/block.h"
#include "src/variables/variable.h"
#include "src/rule_with_operator.h"
#include "modsecurity/string_view.hpp"
namespace modsecurity {
@ -68,8 +69,9 @@ RuleWithOperator::~RuleWithOperator() {
}
void RuleWithOperator::updateMatchedVars(Transaction *trans, const std::string &key,
const std::string &value) {
void RuleWithOperator::updateMatchedVars(Transaction *trans,
const std::string &key,
const bpstd::string_view &value) {
ms_dbg_a(trans, 9, "Matched vars updated.");
trans->m_variableMatchedVar.set(value, trans->m_variableOffset);
trans->m_variableMatchedVarName.set(key, trans->m_variableOffset);
@ -88,9 +90,9 @@ void RuleWithOperator::cleanMatchedVars(Transaction *trans) {
}
bool RuleWithOperator::executeOperatorAt(Transaction *trans, const std::string &key,
std::string value) {
bool RuleWithOperator::executeOperatorAt(Transaction *trans,
const std::string &key,
const bpstd::string_view &value) {
#if MSC_EXEC_CLOCK_ENABLED
clock_t begin = clock();
clock_t end;
@ -98,16 +100,13 @@ bool RuleWithOperator::executeOperatorAt(Transaction *trans, const std::string &
#endif
bool ret;
ms_dbg_a(trans, 9, "Target value: \"" + utils::string::limitTo(80,
utils::string::toHexIfNeeded(value)) \
ms_dbg_a(trans, 9, "Target value: \"" \
+ utils::string::limitTo(80,
utils::string::toHexIfNeeded(value.to_string())) \
+ "\" (Variable: " + key + ")");
ret = m_operator->evaluateInternal(trans, this, value, trans->messageGetLast());
if (ret == false) {
return false;
}
#if MSC_EXEC_CLOCK_ENABLED
end = clock();
elapsed_s = static_cast<double>(end - begin) / CLOCKS_PER_SEC;
@ -302,10 +301,9 @@ bool RuleWithOperator::evaluate(Transaction *trans) {
while (iter != transformationsResults.end()) {
bool ret;
auto &valueTemp = *iter;
// FIXME: this copy is not necessary.
std::string *valueAfterTrans = new std::string(valueTemp.getAfter()->c_str(), valueTemp.getAfter()->size());
bpstd::string_view view = *valueTemp.getAfter();
ret = executeOperatorAt(trans, key, *valueAfterTrans);
ret = executeOperatorAt(trans, key, view);
if (ret == true) {
trans->messageGetLast()->m_match = m_operator->resolveMatchMessage(trans,
@ -330,12 +328,12 @@ bool RuleWithOperator::evaluate(Transaction *trans) {
iter2++;
}
updateMatchedVars(trans, key, *valueAfterTrans);
updateMatchedVars(trans, key, view);
executeActionsIndependentOfChainedRuleResult(trans);
globalRet = true;
}
delete valueAfterTrans;
iter++;
}
delete v;

View File

@ -32,6 +32,7 @@
#include "src/rule_with_actions.h"
#include "src/variables/variable.h"
#include "src/operators/operator.h"
#include "modsecurity/string_view.hpp"
#ifdef __cplusplus
@ -68,11 +69,14 @@ class RuleWithOperator : public RuleWithActions {
inline void getFinalVars(variables::Variables *vars,
variables::Variables *eclusion, Transaction *trans);
bool executeOperatorAt(Transaction *trasn, const std::string &key,
std::string value);
bool executeOperatorAt(Transaction *transaction,
const std::string &key,
const bpstd::string_view &value);
static void updateMatchedVars(Transaction *transaction,
const std::string &key,
const bpstd::string_view &value);
static void updateMatchedVars(Transaction *trasn, const std::string &key,
const std::string &value);
static void cleanMatchedVars(Transaction *trasn);

View File

@ -19,6 +19,12 @@
*:others/mbedtls/sha1.c
//
// 3rd party string view
//
*:headers/modsecurity/string_view.hpp
//
// Code imported from ModSecurity v2...
//
@ -30,11 +36,10 @@ invalidScanfArgType_int:src/rules_set_properties.cc:102
redundantAssignment:src/operators/pm.cc:94
//
// ModSecurity v3 code...
//
unmatchedSuppression:src/utils/geo_lookup.cc:82
functionStatic:src/operators/geo_lookup.h:39
useInitializationList:src/utils/shared_files.h:87
unmatchedSuppression:src/utils/msc_tree.cc
functionStatic:headers/modsecurity/transaction.h:454
@ -54,8 +59,8 @@ syntaxError:src/transaction.cc:62
noConstructor:src/variables/variable.h:152
duplicateBranch:src/request_body_processor/multipart.cc:93
danglingTempReference:src/modsecurity.cc:204
knownConditionTrueFalse:src/operators/validate_url_encoding.cc:77
knownConditionTrueFalse:src/operators/verify_svnr.cc:88
knownConditionTrueFalse:src/operators/validate_url_encoding.cc:79
knownConditionTrueFalse:src/operators/verify_svnr.cc:90
noConstructor:src/actions/rule_id.h:33
functionStatic:src/actions/rule_id.h:35