Commit 7b3ec506 authored by Alastair Robertson's avatar Alastair Robertson

Add binops, predicates and maps

parent bfdff36c
#include "ast.h"
#include "parser.tab.hh"
namespace ebpf {
namespace bpftrace {
......@@ -14,13 +15,31 @@ void Variable::print_ast(std::ostream &out, unsigned int depth) const
{
std::string indent(depth, ' ');
out << indent << "var: " << ident << std::endl;
if (vargs != nullptr) {
if (vargs) {
for (Expression *expr : *vargs) {
expr->print_ast(out, depth+1);
}
}
}
void Binop::print_ast(std::ostream &out, unsigned int depth) const
{
std::string indent(depth, ' ');
std::string opstr;
switch (op) {
case ebpf::bpftrace::Parser::token::EQ:
opstr = "==";
break;
default:
std::cerr << "Bad binop: " << op << std::endl;
break;
}
out << indent << opstr << std::endl;
left->print_ast(out, depth+1);
right->print_ast(out, depth+1);
}
void ExprStatement::print_ast(std::ostream &out, unsigned int depth) const
{
std::string indent(depth, ' ');
......@@ -38,7 +57,11 @@ void AssignStatement::print_ast(std::ostream &out, unsigned int depth) const
void Probe::print_ast(std::ostream &out, unsigned int depth) const
{
std::string indent(depth, ' ');
out << indent << "Probe" << std::endl;
out << indent << type << ":" << attach_point << std::endl;
out << indent << " pred" << std::endl;
if (pred) {
pred->print_ast(out, depth+2);
}
for (Statement *stmt : *stmts) {
stmt->print_ast(out, depth+1);
}
......
......@@ -34,6 +34,14 @@ public:
ExpressionList *vargs;
};
class Binop : public Expression {
public:
Binop(Expression *left, int op, Expression *right) : left(left), right(right), op(op) { }
void print_ast(std::ostream &out, unsigned int depth = 0) const override;
Expression *left, *right;
int op;
};
class Statement : public Node {
};
using StatementList = std::vector<Statement *>;
......@@ -56,11 +64,14 @@ public:
class Probe : public Node {
public:
Probe(std::string &type, std::string &attach_point, StatementList *stmts)
: type(type), attach_point(attach_point), stmts(stmts) { }
: type(type), attach_point(attach_point), pred(nullptr), stmts(stmts) { }
Probe(std::string &type, std::string &attach_point, Expression *pred, StatementList *stmts)
: type(type), attach_point(attach_point), pred(pred), stmts(stmts) { }
void print_ast(std::ostream &out, unsigned int depth = 0) const override;
std::string type;
std::string attach_point;
Expression *pred;
StatementList *stmts;
};
using ProbeList = std::vector<Probe *>;
......
......@@ -32,7 +32,17 @@ using namespace ebpf::bpftrace;
";" { return Parser::make_SEMI(loc); }
"{" { return Parser::make_LBRACE(loc); }
"}" { return Parser::make_RBRACE(loc); }
"[" { return Parser::make_LBRACKET(loc); }
"]" { return Parser::make_RBRACKET(loc); }
"," { return Parser::make_COMMA(loc); }
"=" { return Parser::make_ASSIGN(loc); }
"/" { return Parser::make_FSLASH(loc); }
"==" { return Parser::make_EQ(loc); }
"!=" { return Parser::make_NE(loc); }
"<=" { return Parser::make_LE(loc); }
">=" { return Parser::make_GE(loc); }
"<" { return Parser::make_LT(loc); }
">" { return Parser::make_GT(loc); }
. { driver.error(loc, std::string("invalid character: ")+std::string(yytext)); exit(1); }
......
......@@ -35,14 +35,23 @@ class Node;
void yyerror(ebpf::bpftrace::Driver &driver, const char *s);
%}
%define api.token.prefix {TOK_}
%token
END 0 "end of file"
COLON ":"
SEMI ";"
LBRACE "{"
RBRACE "}"
ASSIGN "="
END 0 "end of file"
COLON ":"
SEMI ";"
LBRACE "{"
RBRACE "}"
LBRACKET "["
RBRACKET "]"
COMMA ","
ASSIGN "="
FSLASH "/"
EQ "=="
NE "!="
LE "<="
GE ">="
LT "<"
GT ">"
;
%token <std::string> IDENT "identifier"
......@@ -58,6 +67,8 @@ void yyerror(ebpf::bpftrace::Driver &driver, const char *s);
%printer { yyoutput << %%; } <*>;
%left EQ NE LE GE LT GT
%start program
%%
......@@ -69,7 +80,8 @@ probes : probes probe { $$ = $1; $1->push_back($2); }
| probe { $$ = new ast::ProbeList; $$->push_back($1); }
;
probe : IDENT ":" IDENT block { $$ = new ast::Probe($1, $3, $4); }
probe : IDENT ":" IDENT block { $$ = new ast::Probe($1, $3, $4); }
| IDENT ":" IDENT "/" expr "/" block { $$ = new ast::Probe($1, $3, $5, $7); }
;
block : "{" stmts "}" { $$ = $2; }
......@@ -83,8 +95,14 @@ stmt : expr { $$ = new ast::ExprStatement($1); }
| var "=" expr { $$ = new ast::AssignStatement($1, $3); }
;
expr : INT { $$ = new ast::Integer($1); }
| var { $$ = $1; }
expr : INT { $$ = new ast::Integer($1); }
| var { $$ = $1; }
| expr EQ expr { $$ = new ast::Binop($1, token::EQ, $3); }
| expr NE expr { $$ = new ast::Binop($1, token::NE, $3); }
| expr LE expr { $$ = new ast::Binop($1, token::LE, $3); }
| expr GE expr { $$ = new ast::Binop($1, token::GE, $3); }
| expr LT expr { $$ = new ast::Binop($1, token::LT, $3); }
| expr GT expr { $$ = new ast::Binop($1, token::GT, $3); }
;
var : IDENT { $$ = new ast::Variable($1); }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment