mirror of
https://github.com/zeek/zeek.git
synced 2025-10-08 17:48:21 +00:00
Allow named table constructors. Addresses #983.
This commit is contained in:
parent
29740d3d6e
commit
bcf5c41786
5 changed files with 117 additions and 14 deletions
50
src/Expr.cc
50
src/Expr.cc
|
@ -3461,12 +3461,25 @@ bool RecordConstructorExpr::DoUnserialize(UnserialInfo* info)
|
|||
}
|
||||
|
||||
TableConstructorExpr::TableConstructorExpr(ListExpr* constructor_list,
|
||||
attr_list* arg_attrs)
|
||||
attr_list* arg_attrs, BroType* arg_type)
|
||||
: UnaryExpr(EXPR_TABLE_CONSTRUCTOR, constructor_list)
|
||||
{
|
||||
if ( IsError() )
|
||||
return;
|
||||
|
||||
if ( arg_type )
|
||||
{
|
||||
if ( ! arg_type->IsTable() )
|
||||
{
|
||||
Error("bad table constructor type", arg_type);
|
||||
SetError();
|
||||
return;
|
||||
}
|
||||
|
||||
SetType(arg_type->Ref());
|
||||
}
|
||||
else
|
||||
{
|
||||
if ( constructor_list->Exprs().length() == 0 )
|
||||
SetType(new TableType(new TypeList(base_type(TYPE_ANY)), 0));
|
||||
else
|
||||
|
@ -3480,8 +3493,43 @@ TableConstructorExpr::TableConstructorExpr(ListExpr* constructor_list,
|
|||
type->AsTableType()->IsSet() )
|
||||
SetError("values in table(...) constructor do not specify a table");
|
||||
}
|
||||
}
|
||||
|
||||
attrs = arg_attrs ? new Attributes(arg_attrs, type, false) : 0;
|
||||
|
||||
type_list* indices = type->AsTableType()->Indices()->Types();
|
||||
expr_list& cle = constructor_list->Exprs();
|
||||
|
||||
// check and promote all index expressions in ctor list
|
||||
loop_over_list(cle, i)
|
||||
{
|
||||
if ( cle[i]->Tag() != EXPR_ASSIGN )
|
||||
continue;
|
||||
|
||||
Expr* idx_expr = cle[i]->AsAssignExpr()->Op1();
|
||||
|
||||
if ( idx_expr->Tag() != EXPR_LIST )
|
||||
continue;
|
||||
|
||||
expr_list& idx_exprs = idx_expr->AsListExpr()->Exprs();
|
||||
|
||||
if ( idx_exprs.length() != indices->length() )
|
||||
continue;
|
||||
|
||||
loop_over_list(idx_exprs, j)
|
||||
{
|
||||
Expr* idx = idx_exprs[j];
|
||||
|
||||
if ( check_and_promote_expr(idx, (*indices)[j]) )
|
||||
{
|
||||
if ( idx != idx_exprs[j] )
|
||||
idx_exprs.replace(j, idx);
|
||||
continue;
|
||||
}
|
||||
|
||||
ExprError("inconsistent types in table constructor");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Val* TableConstructorExpr::Eval(Frame* f) const
|
||||
|
|
15
src/Expr.h
15
src/Expr.h
|
@ -58,6 +58,7 @@ class Stmt;
|
|||
class Frame;
|
||||
class ListExpr;
|
||||
class NameExpr;
|
||||
class AssignExpr;
|
||||
class CallExpr;
|
||||
class EventExpr;
|
||||
|
||||
|
@ -177,6 +178,17 @@ public:
|
|||
return (NameExpr*) this;
|
||||
}
|
||||
|
||||
const AssignExpr* AsAssignExpr() const
|
||||
{
|
||||
CHECK_TAG(tag, EXPR_ASSIGN, "ExprVal::AsAssignExpr", expr_name)
|
||||
return (const AssignExpr*) this;
|
||||
}
|
||||
AssignExpr* AsAssignExpr()
|
||||
{
|
||||
CHECK_TAG(tag, EXPR_ASSIGN, "ExprVal::AsAssignExpr", expr_name)
|
||||
return (AssignExpr*) this;
|
||||
}
|
||||
|
||||
void Describe(ODesc* d) const;
|
||||
|
||||
bool Serialize(SerialInfo* info) const;
|
||||
|
@ -760,7 +772,8 @@ protected:
|
|||
|
||||
class TableConstructorExpr : public UnaryExpr {
|
||||
public:
|
||||
TableConstructorExpr(ListExpr* constructor_list, attr_list* attrs);
|
||||
TableConstructorExpr(ListExpr* constructor_list, attr_list* attrs,
|
||||
BroType* arg_type = 0);
|
||||
~TableConstructorExpr() { Unref(attrs); }
|
||||
|
||||
Attributes* Attrs() { return attrs; }
|
||||
|
|
|
@ -545,16 +545,15 @@ expr:
|
|||
case TYPE_RECORD:
|
||||
$$ = new RecordConstructorExpr($4, ctor_type);
|
||||
break;
|
||||
|
||||
case TYPE_TABLE:
|
||||
if ( ctor_type->IsTable() )
|
||||
{
|
||||
$1->Error("constructor type not implemented");
|
||||
YYERROR;
|
||||
}
|
||||
$$ = new TableConstructorExpr($4, 0, ctor_type);
|
||||
else
|
||||
$$ = new SetConstructorExpr($4, 0, ctor_type);
|
||||
|
||||
break;
|
||||
|
||||
case TYPE_VECTOR:
|
||||
default:
|
||||
$1->Error("constructor type not implemented");
|
||||
|
|
19
testing/btest/Baseline/language.named-table-ctors/out
Normal file
19
testing/btest/Baseline/language.named-table-ctors/out
Normal file
|
@ -0,0 +1,19 @@
|
|||
{
|
||||
[1] = one,
|
||||
[5] = five,
|
||||
[3] = three
|
||||
}
|
||||
{
|
||||
[[min=<uninitialized>, max=5]] = max5,
|
||||
[[min=<uninitialized>, max=2]] = max2
|
||||
}
|
||||
{
|
||||
[test, 1] = test1,
|
||||
[cool, 2] = cool2
|
||||
}
|
||||
{
|
||||
[two] = 2.0,
|
||||
[one] = 1.0,
|
||||
[three] = 3.0
|
||||
}
|
||||
0
|
24
testing/btest/language/named-table-ctors.bro
Normal file
24
testing/btest/language/named-table-ctors.bro
Normal file
|
@ -0,0 +1,24 @@
|
|||
# @TEST-EXEC: bro -b %INPUT >out
|
||||
# @TEST-EXEC: btest-diff out
|
||||
|
||||
type MyRec: record {
|
||||
min: count &optional;
|
||||
max: count;
|
||||
};
|
||||
|
||||
type FooTable: table[count] of string;
|
||||
type FooTableRec: table[MyRec] of string;
|
||||
type FooTableComp: table[string, count] of string;
|
||||
type FooTableY: table[string] of double;
|
||||
|
||||
global mytable: FooTable = FooTable([1] = "one", [5] = "five", [3] = "three");
|
||||
global mytablerec: FooTableRec = FooTableRec([[$max=5]] = "max5", [[$max=2]] = "max2");
|
||||
global mytablecomp: FooTableComp = FooTableComp(["test", 1] = "test1", ["cool",
|
||||
2] = "cool2");
|
||||
global mytabley: FooTableY = FooTableY(["one"] = 1, ["two"] = 2, ["three"] = 3) &default=0;
|
||||
|
||||
print mytable;
|
||||
print mytablerec;
|
||||
print mytablecomp;
|
||||
print mytabley;
|
||||
print mytabley["test"];
|
Loading…
Add table
Add a link
Reference in a new issue