Latest snapshot of devd. This one adds re-matching and string

expansion.
This commit is contained in:
Warner Losh 2002-12-18 07:08:01 +00:00
parent e4ceb70f7a
commit 5102ef8416
Notes: svn2git 2020-12-20 02:59:44 +00:00
svn path=/head/; revision=108014
2 changed files with 89 additions and 17 deletions

View File

@ -30,7 +30,6 @@
// TODO list: // TODO list:
// o rewrite the main loop: // o rewrite the main loop:
// - expand variables
// - find best match // - find best match
// - execute it. // - execute it.
// o need to insert the event_proc structures in order of priority. // o need to insert the event_proc structures in order of priority.
@ -46,10 +45,12 @@ __FBSDID("$FreeBSD$");
#include <sys/param.h> #include <sys/param.h>
#include <sys/types.h> #include <sys/types.h>
#include <ctype.h>
#include <dirent.h> #include <dirent.h>
#include <errno.h> #include <errno.h>
#include <err.h> #include <err.h>
#include <fcntl.h> #include <fcntl.h>
#include <regex.h>
#include <stdlib.h> #include <stdlib.h>
#include <stdio.h> #include <stdio.h>
#include <string.h> #include <string.h>
@ -103,13 +104,14 @@ public:
class match : public eps class match : public eps
{ {
public: public:
match(const char *var, const char *re); match(config &, const char *var, const char *re);
virtual ~match(); virtual ~match();
virtual bool do_match(config &); virtual bool do_match(config &);
virtual bool do_action(config &) { return true; } virtual bool do_action(config &) { return true; }
private: private:
string _var; string _var;
string _re; string _re;
regex_t _regex;
}; };
class action : public eps class action : public eps
@ -155,10 +157,11 @@ public:
void pop_var_table(); void pop_var_table();
void set_variable(const char *var, const char *val); void set_variable(const char *var, const char *val);
const string &get_variable(const string &var); const string &get_variable(const string &var);
const string &expand_string(const string &var); const string expand_string(const string &var);
protected: protected:
void parse_one_file(const char *fn); void parse_one_file(const char *fn);
void parse_files_in_dir(const char *dirname); void parse_files_in_dir(const char *dirname);
void expand_one(const char *&src, char *&dst, char *eod);
private: private:
vector<string> _dir_list; vector<string> _dir_list;
string _pidfile; string _pidfile;
@ -224,30 +227,35 @@ action::~action()
} }
bool bool
action::do_action(config &) action::do_action(config &c)
{ {
// this is lame because we don't expand variables.
// xxx // xxx
::system(_cmd.c_str()); ::system(c.expand_string(_cmd).c_str());
return (true); return (true);
} }
match::match(const char *var, const char *re) match::match(config &c, const char *var, const char *re)
: _var(var), _re(re) : _var(var), _re(re)
{ {
// nothing string pattern = "^";
pattern.append(c.expand_string(_re));
pattern.append("$");
regcomp(&_regex, pattern.c_str(), REG_EXTENDED | REG_NOSUB);
} }
match::~match() match::~match()
{ {
// nothing regfree(&_regex);
} }
bool bool
match::do_match(config &) match::do_match(config &c)
{ {
// XXX string value = c.get_variable(_var);
return false; bool retval;
retval = (regexec(&_regex, value.c_str(), 0, NULL, 0) == 0);
return retval;
} }
const string var_list::bogus = "_$_$_$_$_B_O_G_U_S_$_$_$_$_"; const string var_list::bogus = "_$_$_$_$_B_O_G_U_S_$_$_$_$_";
@ -411,10 +419,74 @@ config::get_variable(const string &var)
return (var_list::nothing); return (var_list::nothing);
} }
const string & // Hey script |<idz, here's a routine chock-full-o-buffer-overflows.
config::expand_string(const string &) // XXX
// imp should learn how to make effective use of the string class for the shit.
void
config::expand_one(const char *&src, char *&dst, char *)
{ {
return var_list::bogus; int count;
const char *var;
char buffer[1024];
string varstr;
// $$ -> $
if (*src == '$') {
*dst++ = *src++;
return;
}
// $(foo) -> $(foo)
// Not sure if I want to support this or not, so for now we just pass it through.
if (*src == '(') {
*dst++ = '$';
count = 1;
while (count > 0) {
if (*src == ')')
count--;
else if (*src == '(')
count++;
*dst++ = *src++;
}
return;
}
// ${^A-Za-z] -> $\1
if (!isalpha(*src)) {
*dst++ = '$';
*dst++ = *src++;
return;
}
// $var -> replace with value
var = src++;
while (*src && isalpha(*src) || isdigit(*src) || *src == '_' || *src == '-')
src++;
memcpy(buffer, var, src - var);
buffer[src - var] = '\0';
varstr = get_variable(buffer);
strcpy(dst, varstr.c_str());
dst += strlen(dst);
}
const string
config::expand_string(const string &s)
{
const char *src;
char *dst;
char buffer[1024];
src = s.c_str();
dst = buffer;
while (*src) {
if (*src == '$')
expand_one(++src, dst, buffer + sizeof(buffer));
else
*dst++ = *src++;
}
*dst++ = '\0';
return (buffer);
} }
@ -524,7 +596,7 @@ new_action(const char *cmd)
eps * eps *
new_match(const char *var, const char *re) new_match(const char *var, const char *re)
{ {
eps *e = new match(var, re); eps *e = new match(cfg, var, re);
free(const_cast<char *>(var)); free(const_cast<char *>(var));
free(const_cast<char *>(re)); free(const_cast<char *>(re));
return (e); return (e);

View File

@ -93,7 +93,7 @@ device-name { return DEVICE_NAME; }
action { return ACTION; } action { return ACTION; }
match { return MATCH; } match { return MATCH; }
nomatch { return NOMATCH; } nomatch { return NOMATCH; }
[A-Za-z][A-Za-z0-9-]* { [A-Za-z][A-Za-z0-9_-]* {
yylval.str = strdup(yytext); yylval.str = strdup(yytext);
return ID; return ID;
} }