Using a custom VariableMatch* implementation

Delay the variable name resolution till last minute.

Fix one of the issues raised in #2376
This commit is contained in:
Felipe Zimmerle 2020-11-22 11:04:24 -03:00 committed by Felipe Zimmerle
parent 97762dc1bc
commit eec1f00bea
15 changed files with 710 additions and 26 deletions

View File

@ -1,6 +1,9 @@
v3.x.y - YYYY-MMM-DD (to be released)
-------------------------------------
- Using a custom VariableMatch* implementation
[#2428 - @zimmerle, @martinhsv]
- Avoids to cleanup GeoIp on ModSecurity destructor
[#2041 - @zimmerle, @jptosso, @victorhora]
- Fix memory leak of RuleMessages objects

View File

@ -0,0 +1,85 @@
/*
* ModSecurity, http://www.modsecurity.org/
* Copyright (c) 2015 - 2020 Trustwave Holdings, Inc. (http://www.trustwave.com/)
*
* You may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* If any of the files related to licensing are missing or if you have any
* other questions related to licensing please contact Trustwave Holdings, Inc.
* directly using the email address security@modsecurity.org.
*
*/
#ifdef __cplusplus
#include <vector>
#include <utility>
#include "modsecurity/string_view.hpp"
#endif
#include "modsecurity/variable_value.h"
#ifndef HEADERS_MODSECURITY_ANCHORED_SET_VARIABLE_MATCH_VARS_H_
#define HEADERS_MODSECURITY_ANCHORED_SET_VARIABLE_MATCH_VARS_H_
#ifdef __cplusplus
namespace modsecurity {
class Transaction;
namespace Utils {
class Regex;
}
namespace variables {
class KeyExclusions;
}
class AnchoredVariableMatchVars {
public:
explicit AnchoredVariableMatchVars(Transaction *t)
: m_name("MATCHED_VARS"),
m_transaction(t)
{ }
AnchoredVariableMatchVars(const AnchoredVariableMatchVars &a) = delete;
AnchoredVariableMatchVars &operator= (const AnchoredVariableMatchVars &a) = delete;
void set(std::shared_ptr<const VariableValue> v) noexcept {
m_vvs.push_back(v);
}
void unset() noexcept {
m_vvs.clear();
}
void resolve(VariableValues *l,
const variables::KeyExclusions &ke) const noexcept;
void resolve(const std::string &key,
VariableValues *l) const noexcept;
void resolveRegularExpression(const Utils::Regex *r,
VariableValues *l,
const variables::KeyExclusions &ke) const noexcept;
std::unique_ptr<std::string> resolveFirst(const std::string &key) const noexcept;
private:
std::vector<std::shared_ptr<const VariableValue>> m_vvs;
const std::string m_name;
const Transaction *m_transaction;
};
} // namespace modsecurity
#endif
#endif // HEADERS_MODSECURITY_ANCHORED_SET_VARIABLE_MATCH_VARS_H_

View File

@ -0,0 +1,85 @@
/*
* ModSecurity, http://www.modsecurity.org/
* Copyright (c) 2015 - 2020 Trustwave Holdings, Inc. (http://www.trustwave.com/)
*
* You may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* If any of the files related to licensing are missing or if you have any
* other questions related to licensing please contact Trustwave Holdings, Inc.
* directly using the email address security@modsecurity.org.
*
*/
#ifdef __cplusplus
#include <vector>
#include <utility>
#include "modsecurity/string_view.hpp"
#endif
#include "modsecurity/variable_value.h"
#ifndef HEADERS_MODSECURITY_ANCHORED_SET_VARIABLE_MATCH_VARS_NAMES_H_
#define HEADERS_MODSECURITY_ANCHORED_SET_VARIABLE_MATCH_VARS_NAMES_H_
#ifdef __cplusplus
namespace modsecurity {
class Transaction;
namespace Utils {
class Regex;
}
namespace variables {
class KeyExclusions;
}
class AnchoredVariableMatchVarsNames {
public:
explicit AnchoredVariableMatchVarsNames(Transaction *t)
: m_name("MATCHED_VARS_NAMES"),
m_transaction(t)
{ }
AnchoredVariableMatchVarsNames(const AnchoredVariableMatchVarsNames &a) = delete;
AnchoredVariableMatchVarsNames &operator= (const AnchoredVariableMatchVarsNames &a) = delete;
void set(std::shared_ptr<const VariableValue> v) noexcept {
m_vvs.push_back(v);
}
void unset() noexcept {
m_vvs.clear();
}
void resolve(VariableValues *l,
const variables::KeyExclusions &ke) const noexcept;
void resolve(const std::string &key,
VariableValues *l) const noexcept;
void resolveRegularExpression(const Utils::Regex *r,
VariableValues *l,
const variables::KeyExclusions &ke) const noexcept;
std::unique_ptr<std::string> resolveFirst(const std::string &key) const noexcept;
private:
std::vector<std::shared_ptr<const VariableValue>> m_vvs;
const std::string m_name;
const Transaction *m_transaction;
};
} // namespace modsecurity
#endif
#endif // HEADERS_MODSECURITY_ANCHORED_SET_VARIABLE_MATCH_VARS_NAMES_H_

View File

@ -0,0 +1,92 @@
/*
* ModSecurity, http://www.modsecurity.org/
* Copyright (c) 2015 - 2020 Trustwave Holdings, Inc. (http://www.trustwave.com/)
*
* You may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* If any of the files related to licensing are missing or if you have any
* other questions related to licensing please contact Trustwave Holdings, Inc.
* directly using the email address security@modsecurity.org.
*
*/
#ifdef __cplusplus
#include <ctime>
#include <fstream>
#include <iomanip>
#include <iostream>
#include <list>
#include <map>
#include <sstream>
#include <string>
#include <unordered_map>
#include <utility>
#include <vector>
#include <memory>
#include <cstring>
#include "modsecurity/string_view.hpp"
#endif
#include "modsecurity/variable_value.h"
#ifndef HEADERS_MODSECURITY_ANCHORED_VARIABLE_NAME_H_
#define HEADERS_MODSECURITY_ANCHORED_VARIABLE_NAME_H_
#ifdef __cplusplus
namespace modsecurity {
class Transaction;
class AnchoredVariableMatchVarName {
public:
AnchoredVariableMatchVarName()
: m_name("MATCHED_VAR_NAME")
{ }
AnchoredVariableMatchVarName(const AnchoredVariableMatchVarName &a) = delete;
AnchoredVariableMatchVarName &operator= (const AnchoredVariableMatchVarName &a) = delete;
void set(std::shared_ptr<const VariableValue> v) noexcept {
m_vv = v;
}
void unset() noexcept {
m_vv = nullptr;
}
void evaluate(VariableValues *l) const noexcept {
if (!m_vv) {
return;
}
const VariableValue *var = new VariableValue(
std::unique_ptr<std::string>(new std::string(m_vv->getName())),
&m_name
);
l->push_back(std::unique_ptr<const VariableValue>(var));
}
std::unique_ptr<std::string> resolveFirst() const noexcept {
if (m_vv) {
return std::unique_ptr<std::string>(new std::string(m_vv->getName()));
}
return std::unique_ptr<std::string>(new std::string(""));
}
private:
std::shared_ptr<const VariableValue> m_vv;
const std::string m_name;
};
} // namespace modsecurity
#endif
#endif // HEADERS_MODSECURITY_ANCHORED_VARIABLE_NAME_H_

View File

@ -42,6 +42,9 @@ typedef struct Rules_t RulesSet;
#endif
#include "modsecurity/anchored_set_variable.h"
#include "modsecurity/anchored_set_variable_match_vars_names.h"
#include "modsecurity/anchored_set_variable_match_vars.h"
#include "modsecurity/anchored_variable_match_var_name.h"
#include "modsecurity/anchored_variable.h"
#include "modsecurity/intervention.h"
#include "modsecurity/collection/collections.h"
@ -136,7 +139,7 @@ class TransactionAnchoredVariables {
m_variableFullRequestLength(t, "FULL_REQUEST_LENGTH"),
m_variableInboundDataError(t, "INBOUND_DATA_ERROR"),
m_variableMatchedVar(t, "MATCHED_VAR"),
m_variableMatchedVarName(t, "MATCHED_VAR_NAME"),
m_variableMatchedVarName(),
m_variableMultipartBoundaryQuoted(t, "MULTIPART_BOUNDARY_QUOTED"),
m_variableMultipartBoundaryWhiteSpace(t,
"MULTIPART_BOUNDARY_WHITESPACE"),
@ -195,8 +198,8 @@ class TransactionAnchoredVariables {
m_variableFilesTmpContent(t, "FILES_TMP_CONTENT"),
m_variableMultipartFileName(t, "MULTIPART_FILENAME"),
m_variableMultipartName(t, "MULTIPART_NAME"),
m_variableMatchedVarsNames(t, "MATCHED_VARS_NAMES"),
m_variableMatchedVars(t, "MATCHED_VARS"),
m_variableMatchedVarsNames(t),
m_variableMatchedVars(t),
m_variableFiles(t, "FILES"),
m_variableRequestCookies(t, "REQUEST_COOKIES"),
m_variableRequestHeaders(t, "REQUEST_HEADERS"),
@ -220,7 +223,7 @@ class TransactionAnchoredVariables {
AnchoredVariable m_variableFullRequestLength;
AnchoredVariable m_variableInboundDataError;
AnchoredVariable m_variableMatchedVar;
AnchoredVariable m_variableMatchedVarName;
AnchoredVariableMatchVarName m_variableMatchedVarName;
AnchoredVariable m_variableMultipartBoundaryQuoted;
AnchoredVariable m_variableMultipartBoundaryWhiteSpace;
AnchoredVariable m_variableMultipartCrlfLFLines;
@ -276,8 +279,8 @@ class TransactionAnchoredVariables {
AnchoredSetVariable m_variableFilesTmpContent;
AnchoredSetVariable m_variableMultipartFileName;
AnchoredSetVariable m_variableMultipartName;
AnchoredSetVariable m_variableMatchedVarsNames;
AnchoredSetVariable m_variableMatchedVars;
AnchoredVariableMatchVarsNames m_variableMatchedVarsNames;
AnchoredVariableMatchVars m_variableMatchedVars;
AnchoredSetVariable m_variableFiles;
AnchoredSetVariable m_variableRequestCookies;
AnchoredSetVariable m_variableRequestHeaders;

View File

@ -35,8 +35,11 @@ MAINTAINERCLEANFILES = \
pkginclude_HEADERS = \
../headers/modsecurity/anchored_set_variable.h \
../headers/modsecurity/anchored_variable.h \
../headers/modsecurity/anchored_set_variable.h \
../headers/modsecurity/anchored_set_variable_match_vars.h \
../headers/modsecurity/anchored_set_variable_match_vars_names.h \
../headers/modsecurity/anchored_variable.h \
../headers/modsecurity/anchored_variable_match_var_name.h \
../headers/modsecurity/audit_log.h \
../headers/modsecurity/debug_log.h \
../headers/modsecurity/intervention.h \
@ -272,6 +275,8 @@ libmodsecurity_la_SOURCES = \
parser/driver.cc \
transaction.cc \
anchored_set_variable.cc \
anchored_set_variable_match_vars.cc \
anchored_set_variable_match_vars_names.cc \
anchored_variable.cc \
audit_log/audit_log.cc \
audit_log/writer/writer.cc \

View File

@ -0,0 +1,101 @@
/*
* ModSecurity, http://www.modsecurity.org/
* Copyright (c) 2015 - 2020 Trustwave Holdings, Inc. (http://www.trustwave.com/)
*
* You may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* If any of the files related to licensing are missing or if you have any
* other questions related to licensing please contact Trustwave Holdings, Inc.
* directly using the email address security@modsecurity.org.
*
*/
#include <string>
#include <vector>
#include "modsecurity/anchored_set_variable_match_vars.h"
#include "modsecurity/modsecurity.h"
#include "modsecurity/transaction.h"
#include "src/utils/regex.h"
#include "src/variables/variable.h"
namespace modsecurity {
void AnchoredVariableMatchVars::resolve(VariableValues *l,
const variables::KeyExclusions &ke) const noexcept
{
for (const auto& x : m_vvs) {
if (ke.toOmit(x->getName())) {
ms_dbg_a(m_transaction, 7, "Excluding key: " + x->getName()
+ " from target value.");
continue;
}
const VariableValue *var = new VariableValue(
&m_name,
std::unique_ptr<std::string>(new std::string(x->getName())),
std::unique_ptr<std::string>(new std::string(x->getValue()))
);
l->insert(l->begin(), std::unique_ptr<const VariableValue>(var));
}
}
void AnchoredVariableMatchVars::resolve(const std::string &key,
VariableValues *l) const noexcept
{
for (const auto& x : m_vvs) {
if (key != x->getName()) {
continue;
}
const VariableValue *var = new VariableValue(
&m_name,
std::unique_ptr<std::string>(new std::string(x->getName())),
std::unique_ptr<std::string>(new std::string(x->getValue()))
);
l->insert(l->begin(), std::unique_ptr<const VariableValue>(var));
}
}
void AnchoredVariableMatchVars::resolveRegularExpression(const Utils::Regex *r,
VariableValues *l,
const variables::KeyExclusions &ke) const noexcept
{
for (const auto& x : m_vvs) {
int ret = Utils::regex_search(x->getName(), *r);
if (ret <= 0) {
continue;
}
if (ke.toOmit(x->getName())) {
ms_dbg_a(m_transaction, 7, "Excluding key: " + x->getName()
+ " from target value.");
continue;
}
const VariableValue *var = new VariableValue(
&m_name,
std::unique_ptr<std::string>(new std::string(x->getName())),
std::unique_ptr<std::string>(new std::string(x->getValue()))
);
l->insert(l->begin(), std::unique_ptr<const VariableValue>(var));
}
}
std::unique_ptr<std::string> AnchoredVariableMatchVars::resolveFirst(const std::string &key) const noexcept
{
for (const auto& x : m_vvs) {
if (key != x->getName()) {
continue;
}
return std::unique_ptr<std::string>(new std::string(x->getValue()));
}
return std::unique_ptr<std::string>();
}
} // namespace modsecurity

View File

@ -0,0 +1,100 @@
/*
* ModSecurity, http://www.modsecurity.org/
* Copyright (c) 2015 - 2020 Trustwave Holdings, Inc. (http://www.trustwave.com/)
*
* You may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* If any of the files related to licensing are missing or if you have any
* other questions related to licensing please contact Trustwave Holdings, Inc.
* directly using the email address security@modsecurity.org.
*
*/
#include <string>
#include "modsecurity/anchored_set_variable_match_vars_names.h"
#include "modsecurity/modsecurity.h"
#include "modsecurity/transaction.h"
#include "src/utils/regex.h"
#include "src/variables/variable.h"
namespace modsecurity {
void AnchoredVariableMatchVarsNames::resolve(VariableValues *l,
const variables::KeyExclusions &ke) const noexcept
{
for (const auto& x : m_vvs) {
if (ke.toOmit(x->getName())) {
ms_dbg_a(m_transaction, 7, "Excluding key: " + x->getName()
+ " from target value.");
continue;
}
const VariableValue *var = new VariableValue(
&m_name,
std::unique_ptr<std::string>(new std::string(x->getName())),
std::unique_ptr<std::string>(new std::string(x->getName()))
);
l->insert(l->begin(), std::unique_ptr<const VariableValue>(var));
}
}
void AnchoredVariableMatchVarsNames::resolve(const std::string &key,
VariableValues *l) const noexcept
{
for (const auto& x : m_vvs) {
if (key != x->getName()) {
continue;
}
const VariableValue *var = new VariableValue(
&m_name,
std::unique_ptr<std::string>(new std::string(x->getName())),
std::unique_ptr<std::string>(new std::string(x->getName()))
);
l->insert(l->begin(), std::unique_ptr<const VariableValue>(var));
}
}
void AnchoredVariableMatchVarsNames::resolveRegularExpression(const Utils::Regex *r,
VariableValues *l,
const variables::KeyExclusions &ke) const noexcept
{
for (const auto& x : m_vvs) {
int ret = Utils::regex_search(x->getName(), *r);
if (ret <= 0) {
continue;
}
if (ke.toOmit(x->getName())) {
ms_dbg_a(m_transaction, 7, "Excluding key: " + x->getName()
+ " from target value.");
continue;
}
const VariableValue *var = new VariableValue(
&m_name,
std::unique_ptr<std::string>(new std::string(x->getName())),
std::unique_ptr<std::string>(new std::string(x->getName()))
);
l->insert(l->begin(), std::unique_ptr<const VariableValue>(var));
}
}
std::unique_ptr<std::string> AnchoredVariableMatchVarsNames::resolveFirst(const std::string &key) const noexcept
{
for (const auto& x : m_vvs) {
if (key != x->getName()) {
continue;
}
return std::unique_ptr<std::string>(new std::string(x->getName()));
}
return std::unique_ptr<std::string>();
}
} // namespace modsecurity

View File

@ -19,7 +19,7 @@
#include <string>
#include <vector>
#include "../headers/modsecurity/anchored_variable.h"
#include "modsecurity/anchored_variable.h"
#include "modsecurity/modsecurity.h"
#include "modsecurity/transaction.h"
#include "src/utils/regex.h"

View File

@ -79,17 +79,14 @@ RuleWithOperator::~RuleWithOperator() {
void RuleWithOperator::updateMatchedVars(Transaction *trans,
const VariableValue *v,
std::shared_ptr<const VariableValue> v,
const bpstd::string_view &value) {
// FIXME: Memory leak.
const std::string *key = new std::string(v->getName());
ms_dbg_a(trans, 9, "Matched vars updated.");
trans->m_variableMatchedVar.set(value, trans->m_variableOffset);
trans->m_variableMatchedVarName.set(*key, trans->m_variableOffset);
trans->m_variableMatchedVarName.set(v);
trans->m_variableMatchedVars.set(*key, value, trans->m_variableOffset);
trans->m_variableMatchedVarsNames.set(*key, *key, trans->m_variableOffset);
trans->m_variableMatchedVars.set(v);
trans->m_variableMatchedVarsNames.set(v);
}
@ -354,7 +351,7 @@ bool RuleWithOperator::evaluate(Transaction *trans) const {
iter2++;
}
updateMatchedVars(trans, v, view);
updateMatchedVars(trans, vv, view);
executeActionsIndependentOfChainedRuleResult(trans);
globalRet = true;

View File

@ -82,7 +82,7 @@ class RuleWithOperator : public RuleWithActions {
const bpstd::string_view &value) const;
static void updateMatchedVars(Transaction *transaction,
const VariableValue *v,
std::shared_ptr<const VariableValue> v,
const bpstd::string_view &value);
static void cleanMatchedVars(Transaction *trasn);

View File

@ -42,7 +42,7 @@ redundantAssignment:src/operators/pm.cc:94
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:438
functionStatic:headers/modsecurity/transaction.h:441
duplicateBranch:src/audit_log/audit_log.cc:223
unreadVariable:src/request_body_processor/multipart.cc:435
stlcstrParam:src/audit_log/writer/parallel.cc:145

View File

@ -2,7 +2,7 @@
{
"enabled":1,
"version_min":300000,
"title":"Testing Variables :: MATCHED_VARS (1/2)",
"title":"Testing Variables :: MATCHED_VARS (1/4)",
"client":{
"ip":"200.249.12.31",
"port":123
@ -43,7 +43,7 @@
{
"enabled":1,
"version_min":300000,
"title":"Testing Variables :: MATCHED_VARS (2/2)",
"title":"Testing Variables :: MATCHED_VARS (2/4)",
"client":{
"ip":"200.249.12.31",
"port":123
@ -81,6 +81,92 @@
"SecRule MATCHED_VARS \"@contains asdf\" \"\"",
"SecRule MATCHED_VARS \"@contains value\" \"id:29\""
]
},
{
"enabled":1,
"version_min":300000,
"title":"Testing Variables :: MATCHED_VARS (3/4)",
"client":{
"ip":"200.249.12.31",
"port":123
},
"server":{
"ip":"200.249.12.31",
"port":80
},
"request":{
"headers":{
"Host":"localhost",
"User-Agent":"curl/7.38.0",
"Accept":"*/*"
},
"uri":"/?keyI=value&keyII=other_value",
"method":"GET"
},
"response":{
"headers":{
"Date":"Mon, 13 Jul 2015 20:02:41 GMT",
"Last-Modified":"Sun, 26 Oct 2014 22:33:37 GMT",
"Content-Type":"text/html"
},
"body":[
"no need."
]
},
"expected":{
"debug_log":"Target value: \"other_value\" \\(Variable: MATCHED_VARS:ARGS:keyII\\)",
"http_code": 302,
"error_log": "whee MATCHED_VARS:ARGS:keyII test"
},
"rules":[
"SecRuleEngine On",
"SecRule ARGS:keyI \"@contains value\" \"chain,id:28,deny,status:302\"",
"SecRule ARGS:keyII \"@contains other_value\" \"chain\"",
"SecRule MATCHED_VARS:ARGS:keyII \"@contains other_value\" \"msg:'whee %{MATCHED_VARS_NAMES}% test'\""
]
},
{
"enabled":1,
"version_min":300000,
"title":"Testing Variables :: MATCHED_VARS (4/4)",
"client":{
"ip":"200.249.12.31",
"port":123
},
"server":{
"ip":"200.249.12.31",
"port":80
},
"request":{
"headers":{
"Host":"localhost",
"User-Agent":"curl/7.38.0",
"Accept":"*/*"
},
"uri":"/?keyI=value&keyII=other_value",
"method":"GET"
},
"response":{
"headers":{
"Date":"Mon, 13 Jul 2015 20:02:41 GMT",
"Last-Modified":"Sun, 26 Oct 2014 22:33:37 GMT",
"Content-Type":"text/html"
},
"body":[
"no need."
]
},
"expected":{
"debug_log":"Target value: \"other_value\" \\(Variable: MATCHED_VARS:ARGS:keyII\\)",
"http_code": 302,
"error_log": "whee MATCHED_VARS:ARGS:keyII test"
},
"rules":[
"SecRuleEngine On",
"SecRule ARGS:keyI \"@contains value\" \"chain,id:28,deny,status:302\"",
"SecRule ARGS:keyII \"@contains other_value\" \"chain\"",
"SecRule MATCHED_VARS:/ARGS:.*II/ \"@contains other_value\" \"msg:'whee %{MATCHED_VARS_NAMES}% test'\""
]
}
]

View File

@ -2,7 +2,7 @@
{
"enabled":1,
"version_min":300000,
"title":"Testing Variables :: MATCHED_VARS_NAMES (1/2)",
"title":"Testing Variables :: MATCHED_VARS_NAMES (1/5)",
"client":{
"ip":"200.249.12.31",
"port":123
@ -43,7 +43,7 @@
{
"enabled":1,
"version_min":300000,
"title":"Testing Variables :: MATCHED_VARS_NAMES (2/2)",
"title":"Testing Variables :: MATCHED_VARS_NAMES (2/5)",
"client":{
"ip":"200.249.12.31",
"port":123
@ -81,6 +81,133 @@
"SecRule MATCHED_VARS_NAMES \"@contains asdf\" \"\"",
"SecRule MATCHED_VARS_NAMES \"@contains value\" \"id:29\""
]
},
{
"enabled":1,
"version_min":300000,
"title":"Testing Variables :: MATCHED_VARS_NAMES (3/5)",
"client":{
"ip":"200.249.12.31",
"port":123
},
"server":{
"ip":"200.249.12.31",
"port":80
},
"request":{
"headers":{
"Host":"localhost",
"User-Agent":"curl/7.38.0",
"Accept":"*/*"
},
"uri":"/?keyI=value&keyII=other_value",
"method":"GET"
},
"response":{
"headers":{
"Date":"Mon, 13 Jul 2015 20:02:41 GMT",
"Last-Modified":"Sun, 26 Oct 2014 22:33:37 GMT",
"Content-Type":"text/html"
},
"body":[
"no need."
]
},
"expected":{
"debug_log":"Target value: \"ARGS:keyI\" \\(Variable: MATCHED_VARS_NAMES:ARGS:keyI\\)"
},
"rules":[
"SecRuleEngine On",
"SecRule ARGS:keyI \"@contains value\" \"chain,id:28,pass\"",
"SecRule ARGS:keyII \"@contains other_value\" \"chain\"",
"SecRule MATCHED_VARS_NAMES \"@contains asdf\" \"\"",
"SecRule MATCHED_VARS_NAMES:ARGS:keyI \"@contains value\" \"id:29\""
]
},
{
"enabled":1,
"version_min":300000,
"title":"Testing Variables :: MATCHED_VARS_NAMES (4/5)",
"client":{
"ip":"200.249.12.31",
"port":123
},
"server":{
"ip":"200.249.12.31",
"port":80
},
"request":{
"headers":{
"Host":"localhost",
"User-Agent":"curl/7.38.0",
"Accept":"*/*"
},
"uri":"/?keyI=value&keyII=other_value",
"method":"GET"
},
"response":{
"headers":{
"Date":"Mon, 13 Jul 2015 20:02:41 GMT",
"Last-Modified":"Sun, 26 Oct 2014 22:33:37 GMT",
"Content-Type":"text/html"
},
"body":[
"no need."
]
},
"expected":{
"debug_log":"Target value: \"ARGS:keyI\" \\(Variable: MATCHED_VARS_NAMES:ARGS:keyI\\)",
"http_code": 302
},
"rules":[
"SecRuleEngine On",
"SecRule ARGS:keyI \"@contains value\" \"chain,id:28,deny,status:302\"",
"SecRule ARGS:keyII \"@contains other_value\" \"chain\"",
"SecRule MATCHED_VARS_NAMES:/^ARGS:.*eyI$/ \"@contains ARGS:keyI\" \"\""
]
},
{
"enabled":1,
"version_min":300000,
"title":"Testing Variables :: MATCHED_VARS_NAMES (5/5)",
"client":{
"ip":"200.249.12.31",
"port":123
},
"server":{
"ip":"200.249.12.31",
"port":80
},
"request":{
"headers":{
"Host":"localhost",
"User-Agent":"curl/7.38.0",
"Accept":"*/*"
},
"uri":"/?keyI=value&keyII=other_value",
"method":"GET"
},
"response":{
"headers":{
"Date":"Mon, 13 Jul 2015 20:02:41 GMT",
"Last-Modified":"Sun, 26 Oct 2014 22:33:37 GMT",
"Content-Type":"text/html"
},
"body":[
"no need."
]
},
"expected":{
"debug_log":"Target value: \"ARGS:keyI\" \\(Variable: MATCHED_VARS_NAMES:ARGS:keyI\\)",
"http_code": 302,
"error_log": "whee MATCHED_VARS_NAMES:ARGS:keyI test"
},
"rules":[
"SecRuleEngine On",
"SecRule ARGS:keyI \"@contains value\" \"chain,id:28,deny,status:302\"",
"SecRule ARGS:keyII \"@contains other_value\" \"chain\"",
"SecRule MATCHED_VARS_NAMES:/^ARGS:.*eyI$/ \"@contains ARGS:keyI\" \"msg:'whee %{MATCHED_VARS_NAMES}% test'\""
]
}
]

View File

@ -35,9 +35,9 @@
},
"rules":[
"SecRuleEngine On",
"SecRule ARGS:keyI \"@contains value\" \"chain,id:28,pass\"",
"SecRule ARGS:keyII \"@contains other_value\" \"chain\"",
"SecRule MATCHED_VAR_NAME \"@contains asdf\" \"\""
"SecRule ARGS:keyI \"@contains value\" \"id:28,pass\"",
"SecRule ARGS:keyII \"@contains other_value\" \"id:29,pass\"",
"SecRule MATCHED_VAR_NAME \"@contains asdf\" \"id:30,pass\""
]
},
{