Adds support to macro expansion in setvar action

This commit is contained in:
Felipe Zimmerle
2015-08-07 00:43:16 -03:00
parent e12d95b10d
commit 5fdb5b7d2e
7 changed files with 306 additions and 9 deletions

View File

@@ -20,6 +20,7 @@
#include "modsecurity/assay.h"
#include "src/rule.h"
#include "src/macro_expansion.h"
namespace ModSecurity {
namespace actions {
@@ -94,6 +95,7 @@ void SetVar::dump() {
bool SetVar::evaluate(Rule *rule, Assay *assay) {
std::string targetValue;
variableName = MacroExpansion::expand(variableName, assay);
int value = 0;
try {
std::string *resolvedValue =
@@ -111,14 +113,16 @@ bool SetVar::evaluate(Rule *rule, Assay *assay) {
try {
pre = stoi(predicate);
} catch (...) {
/* perform a macro expansion. */
pre = 0;
try {
pre = stoi(MacroExpansion::expand(predicate, assay));
} catch (...) {
pre = 0;
}
}
switch (operation) {
case setOperation:
/* perform a macro expansion. */
targetValue = predicate;
targetValue = MacroExpansion::expand(predicate, assay);
break;
case sumAndSetOperation:
targetValue = std::to_string(value + pre);

View File

@@ -1374,8 +1374,9 @@ std::string* Assay::resolve_variable_first(std::string var) {
std::string* Assay::resolve_variable_first(const std::string collectionName,
std::string var) {
for (auto &a : collections) {
if (a.first == collectionName) {
auto range = a.second->equal_range(collectionName + ":" + var);
if (tolower(a.first) == tolower(collectionName)) {
auto range = a.second->equal_range(toupper(collectionName)
+ ":" + var);
for (auto it = range.first; it != range.second; ++it) {
return &it->second;
}
@@ -1391,8 +1392,8 @@ void Assay::setCollection(const std::string& collectionName,
ModSecurityStringVariables *collection;
try {
collection = collections.at(collectionName);
collection->storeOrUpdateVariable(collectionName + ":"
collection = collections.at(toupper(collectionName));
collection->storeOrUpdateVariable(toupper(collectionName) + ":"
+ variableName, targetValue);
} catch (...) {
debug(9, "don't know any collection named: "

View File

@@ -14,10 +14,43 @@
*/
#include "src/macro_expansion.h"
#include "modsecurity/assay.h"
namespace ModSecurity {
MacroExpansion::MacroExpansion() {
MacroExpansion::MacroExpansion() { }
std::string MacroExpansion::expand(const std::string& input, Assay *assay) {
std::string res(input);
size_t pos = res.find("%{");
while (pos != std::string::npos) {
size_t start = pos;
size_t end = res.find("}%");
if (end == std::string::npos) {
return res;
}
std::string variable(res, start + 2, end - (start + 2));
std::string *variableValue;
size_t collection = variable.find(".");
if (collection == std::string::npos) {
variableValue = assay->resolve_variable_first(variable);
} else {
std::string col = std::string(variable, 0, collection);
std::string var = std::string(variable, collection + 1,
variable.length() - (collection + 1));
variableValue = assay->resolve_variable_first(col, var);
}
res.erase(start, end + 2);
if (variableValue != NULL) {
res.insert(start, *variableValue);
}
pos = res.find("%{");
}
return res;
}
} // namespace ModSecurity

View File

@@ -19,6 +19,7 @@
#include <vector>
#include "modsecurity/modsecurity.h"
#include "modsecurity/assay.h"
#ifndef SRC_MACRO_EXPANSION_H_
#define SRC_MACRO_EXPANSION_H_
@@ -29,6 +30,8 @@ namespace ModSecurity {
class MacroExpansion {
public:
MacroExpansion();
static std::string expand(const std::string& input, Assay *assay);
};

View File

@@ -112,6 +112,16 @@ std::string tolower(std::string str) {
return value;
}
std::string toupper(std::string str) {
std::locale loc;
std::string value;
for (std::string::size_type i=0; i < str.length(); ++i) {
value.assign(value + std::toupper(str[i], loc));
}
return value;
}
const char SAFE[256] = {
/* 0 1 2 3 4 5 6 7 8 9 A B C D E F */

View File

@@ -32,6 +32,7 @@ namespace ModSecurity {
void chomp(std::string *str);
std::string uri_decode(const std::string & sSrc);
std::string tolower(std::string str);
std::string toupper(std::string str);
double cpu_seconds(void);
int js_decode_nonstrict_inplace(unsigned char *input, int64_t input_len);
static unsigned char x2c(unsigned char *what);