Looks for external resources in the same path of the rule

This commit is contained in:
Felipe Zimmerle 2015-10-06 09:21:30 -03:00
parent 5cc9e94505
commit e54ef72051
17 changed files with 96 additions and 27 deletions

View File

@ -23,7 +23,8 @@ namespace ModSecurity {
namespace operators {
bool IpMatchFromFile::init(const char **error) {
bool IpMatchFromFile::init(const std::string &file,
const char **error) {
std::string e("");
bool res = false;

View File

@ -29,7 +29,7 @@ class IpMatchFromFile : public IpMatch {
IpMatchFromFile(std::string op, std::string param, bool negation)
: IpMatch(op, param, negation) { }
bool init(const char **error) override;
bool init(const std::string& file, const char **error) override;
};
} // namespace operators

View File

@ -40,7 +40,10 @@ class Operator {
std::string param;
bool negation;
virtual bool init(const char **error) { return true; }
virtual bool init(const std::string &file, const char **error) {
return true;
}
virtual bool evaluate(Assay *assay);
virtual bool evaluate(Assay *assay, const std::string &str);
static Operator *instantiate(std::string op);

View File

@ -19,12 +19,13 @@
#include "operators/operator.h"
#include "utils/https_client.h"
#include "src/utils.h"
namespace ModSecurity {
namespace operators {
bool PmFromFile::init(const char **error) {
bool PmFromFile::init(const std::string &config, const char **error) {
std::istream *iss;
if (param.compare(0, 8, "https://") == 0) {
@ -36,7 +37,8 @@ bool PmFromFile::init(const char **error) {
}
iss = new std::stringstream(client.content);
} else {
iss = new std::ifstream(param, std::ios::in);
std::string resource = find_resource(param, config);
iss = new std::ifstream(resource, std::ios::in);
if (((std::ifstream *)iss)->is_open() == false) {
*error = std::string("Failed to open file: " + param).c_str();

View File

@ -31,7 +31,7 @@ class PmFromFile : public Pm {
PmFromFile(std::string op, std::string param, bool negation)
: Pm(op, param, negation) { }
bool init(const char **error) override;
bool init(const std::string &file, const char **error) override;
};

View File

@ -30,6 +30,7 @@ bool Rx::evaluate(Assay *assay, const std::string& input) {
SMatch match;
if (regex_search(input, &match, *m_re) && match.size() >= 1) {
std::cout << "wheee" << std::endl;
// this->matched.push_back(match.match);
return true;
}

View File

@ -83,7 +83,8 @@ bool ValidateByteRange::getRange(const std::string &rangeRepresentation,
}
bool ValidateByteRange::init(const char **error) {
bool ValidateByteRange::init(const std::string &file,
const char **error) {
size_t pos = param.find_first_of(",");
if (pos == std::string::npos) {

View File

@ -38,7 +38,7 @@ class ValidateByteRange : public Operator {
bool evaluate(Assay *assay, const std::string &input) override;
bool getRange(const std::string &rangeRepresentation, const char **error);
bool init(const char **error) override;
bool init(const std::string& file, const char **error) override;
private:
std::vector<std::string> ranges;
char table[32];

View File

@ -90,7 +90,9 @@ int Driver::addSecRule(Rule *rule) {
* by other rule
*/
if (rule->rule_id == 0) {
parserError << "Rules must have an ID." << std::endl;
parserError << "Rules must have an ID. File: ";
parserError << rule->m_fileName << " at line: ";
parserError << std::to_string(rule->m_lineNumber) << std::endl;
return false;
}
for (int i = 0; i < ModSecurity::Phases::NUMBER_OF_PHASES; i++) {

View File

@ -351,7 +351,7 @@ op:
{
Operator *op = Operator::instantiate($1);
const char *error = NULL;
if (op->init(&error) == false) {
if (op->init(driver.ref.back(), &error) == false) {
driver.error(@0, error);
YYERROR;
}
@ -361,7 +361,7 @@ op:
{
Operator *op = Operator::instantiate("\"@rx " + $1 + "\"");
const char *error = NULL;
if (op->init(&error) == false) {
if (op->init(driver.ref.back(), &error) == false) {
driver.error(@0, error);
YYERROR;
}
@ -375,7 +375,9 @@ expression:
Rule *rule = new Rule(
/* op */ $3,
/* variables */ $2,
/* actions */ $4
/* actions */ $4,
/* file name */ driver.ref.back(),
/* line number */ @0.end.line
);
if (driver.addSecRule(rule) == false) {
@ -387,7 +389,9 @@ expression:
Rule *rule = new Rule(
/* op */ $3,
/* variables */ $2,
/* actions */ NULL
/* actions */ NULL,
/* file name */ driver.ref.back(),
/* line number */ @0.end.line
);
if (driver.addSecRule(rule) == false) {
@ -399,7 +403,9 @@ expression:
Rule *rule = new Rule(
/* op */ NULL,
/* variables */ NULL,
/* actions */ $2
/* actions */ $2,
/* file name */ driver.ref.back(),
/* line number */ @0.end.line
);
driver.addSecAction(rule);
}
@ -508,7 +514,14 @@ expression:
/* Debug log: end */
| CONFIG_DIR_GEO_DB
{
GeoLookup::getInstance().setDataBase($1);
std::string file = ModSecurity::find_resource($1, driver.ref.back());
if (GeoLookup::getInstance().setDataBase(file) == false) {
std::stringstream ss;
ss << "Failed to load the GeoDB from: ";
ss << file;
driver.error(@0, ss.str());
YYERROR;
}
}
/* Body limits */
| CONFIG_DIR_REQ_BODY_LIMIT

View File

@ -98,7 +98,7 @@ CONFIG_SEC_REMOTE_RULES (?i:SecRemoteRules)
CONFIG_SEC_REMOTE_RULES_FAIL_ACTION (?i:SecRemoteRulesFailAction)
DICT_ELEMENT [^ \|\t]+
DICT_ELEMENT [^ \t]+
OPERATOR (?i:(?:@inspectFile|@fuzzyHash|@validateByteRange|@validateDTD|@validateHash|@validateSchema|@verifyCC|@verifyCPF|@verifySSN|@gsbLookup|@rsub)|(?:\!{0,1})(?:@within|@containsWord|@contains|@endsWith|@eq|@ge|@gt|@ipMatchF|@ipMatch|@ipMatchFromFile|@le|@lt|@pmf|@pm|@pmFromFile|@rbl|@rx|@streq|@strmatch|@beginsWith))
@ -143,17 +143,20 @@ CONFIG_VALUE_PATH [0-9A-Za-z_/\.\-\*]+
AUDIT_PARTS [ABCDEFHJKIZ]+
CONFIG_VALUE_NUMBER [0-9]+
FREE_TEXT ([^\"]|([^\\]\\\"))+
FREE_TEXT ([^\"]|(\\\"))+
FREE_TEXT_NEW_LINE [^\"|\n]+
FREE_TEXT_QUOTE ([^\']|([^\\]\\\'))+
FREE_TEXT_SPACE [^ \t]+
FREE_TEXT_SPACE_COMMA [^, \t]+
FREE_TEXT_SPACE_COMMA_QUOTE [^, \t\"]+
VAR_FREE_TEXT_QUOTE ([^\']|([^\\]\\\'))+
VAR_FREE_TEXT_SPACE_COMMA [^, \t\"]+
VAR_FREE_TEXT_SPACE [^ \t\"]+
SOMETHING ["]{1}[^@]{1}([^"]|([^\\"]\\\"))*["]{1}
CONFIG_DIR_UNICODE_MAP_FILE (?i:SecUnicodeMapFile)
%x EXPECTING_OPERATOR COMMENT
@ -266,14 +269,14 @@ CONFIG_DIR_UNICODE_MAP_FILE (?i:SecUnicodeMapFile)
{CONFIG_DIR_SEC_MARKER}[ ]{FREE_TEXT_NEW_LINE} { return yy::seclang_parser::make_CONFIG_DIR_SEC_MARKER(strchr(yytext, ' ') + 1, *driver.loc.back()); }
<EXPECTING_OPERATOR>{
["][^@]{FREE_TEXT}["] { BEGIN(INITIAL); return yy::seclang_parser::make_FREE_TEXT(yytext, *driver.loc.back()); }
{SOMETHING} { BEGIN(INITIAL); return yy::seclang_parser::make_FREE_TEXT(yytext, *driver.loc.back()); }
["]{OPERATOR}[ ]{FREE_TEXT}["] { BEGIN(INITIAL); return yy::seclang_parser::make_OPERATOR(yytext, *driver.loc.back()); }
["]{OPERATORNOARG}[\t ]*["] { BEGIN(INITIAL); return yy::seclang_parser::make_OPERATOR(yytext, *driver.loc.back()); }
}
{ACTION} { return yy::seclang_parser::make_ACTION(yytext, *driver.loc.back()); }
{ACTION_PHASE} { return yy::seclang_parser::make_ACTION_PHASE(yytext, *driver.loc.back()); }
{ACTION_SKIP_AFTER}:{FREE_TEXT} { return yy::seclang_parser::make_ACTION_SKIP_AFTER(strchr(yytext, ':') + 1, *driver.loc.back()); }
{ACTION_SKIP_AFTER}:{FREE_TEXT_SPACE_COMMA_QUOTE} { return yy::seclang_parser::make_ACTION_SKIP_AFTER(strchr(yytext, ':') + 1, *driver.loc.back()); }
{ACTION_AUDIT_LOG} { return yy::seclang_parser::make_ACTION_AUDIT_LOG(yytext, *driver.loc.back()); }
{ACTION_SEVERITY}:{ACTION_SEVERITY_VALUE} { return yy::seclang_parser::make_ACTION_SEVERITY(yytext + 9, *driver.loc.back()); }

View File

@ -82,12 +82,15 @@ Rule::Rule(std::string marker)
m_unconditional(false),
m_secmarker(true),
m_marker(marker),
m_referenceCount(0) { }
m_referenceCount(0),
m_fileName(""),
m_lineNumber(0) { }
Rule::Rule(Operator *_op,
std::vector<Variable *> *_variables,
std::vector<Action *> *actions)
: chained(false),
std::vector<Action *> *actions,
std::string fileName,
int lineNumber): chained(false),
chainedRule(NULL),
variables(_variables),
op(_op),
@ -96,7 +99,9 @@ Rule::Rule(Operator *_op,
m_unconditional(false),
m_secmarker(false),
m_marker(""),
m_referenceCount(0) {
m_referenceCount(0),
m_fileName(fileName),
m_lineNumber(lineNumber) {
if (actions != NULL) {
for (Action *a : *actions) {
if (a->action_kind == Action::ConfigurationKind) {

View File

@ -33,7 +33,10 @@ class Rule {
public:
Rule(operators::Operator *_op,
std::vector<Variables::Variable *> *_variables,
std::vector<actions::Action *> *_actions);
std::vector<actions::Action *> *_actions,
std::string fileName,
int lineNumber
);
explicit Rule(std::string marker);
~Rule();
@ -67,6 +70,8 @@ class Rule {
std::string m_marker;
bool m_secmarker;
std::string m_fileName;
int m_lineNumber;
private:
bool m_unconditional;

View File

@ -1040,5 +1040,38 @@ std::vector<std::string> expandEnv(const std::string& var, int flags)
}
std::string get_path(const std::string& file) {
size_t found;
found = file.find_last_of("/\\");
if (found > 0) {
return file.substr(0, found);
}
return std::string("");
}
std::string find_resource(const std::string& resource, const std::string& config) {
std::ifstream *iss = NULL;
// Trying absolute or relative to the current dir.
iss = new std::ifstream(resource, std::ios::in);
if (iss->is_open()) {
iss->close();
return resource;
}
// Trying the same path of the configuration file.
std::string f = get_path(config) + "/" + resource;
iss = new std::ifstream(f, std::ios::in);
if (iss->is_open()) {
iss->close();
return f;
}
return std::string("");
}
} // namespace ModSecurity

View File

@ -48,6 +48,8 @@ namespace ModSecurity {
std::string limitTo(int amount, const std::string &str);
std::string toHexIfNeeded(const std::string &str);
std::vector<std::string> expandEnv(const std::string& var, int flags);
std::string find_resource(const std::string& file,
const std::string& param);
} // namespace ModSecurity
#define SRC_UTILS_H_

View File

@ -1,7 +1,5 @@
include "owasp-modsecurity-crs-orig/modsecurity_crs_10_setup.conf"
#include "owasp-modsecurity-crs-orig/rules/*.conf"
#include owasp-modsecurity-crs-orig/rules/RESPONSE-51-DATA-LEAKAGES-SQL.conf
include owasp-modsecurity-crs-orig/rules/REQUEST-01-COMMON-EXCEPTIONS.conf
include owasp-modsecurity-crs-orig/rules/REQUEST-10-IP-REPUTATION.conf
include owasp-modsecurity-crs-orig/rules/REQUEST-11-METHOD-ENFORCEMENT.conf

View File

@ -51,7 +51,7 @@ void perform_unit_test(UnitTest *t, ModSecurityTestResults<UnitTest>* res) {
if (t->type == "op") {
Operator *op = Operator::instantiate("\"@" + t->name + \
" " + t->param + "\"");
op->init(&error);
op->init(t->filename, &error);
int ret = op->evaluate(NULL, t->input);
if (ret != t->ret) {
t->obtained = ret;