mirror of
https://github.com/zeek/zeek.git
synced 2025-10-02 06:38:20 +00:00
change vector constructors to require direct type equivalence for non-arithmetics
This commit is contained in:
parent
c1e5389929
commit
47152e38c4
5 changed files with 63 additions and 12 deletions
|
@ -3977,7 +3977,7 @@ VectorConstructorExpr::VectorConstructorExpr(ListExprPtr constructor_list, TypeP
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( auto t = merge_type_list(op->AsListExpr()) )
|
if ( auto t = maximal_type(op->AsListExpr()) )
|
||||||
SetType(make_intrusive<VectorType>(std::move(t)));
|
SetType(make_intrusive<VectorType>(std::move(t)));
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
|
23
src/Type.cc
23
src/Type.cc
|
@ -63,6 +63,11 @@ const char* type_name(TypeTag t)
|
||||||
return type_names[int(t)];
|
return type_names[int(t)];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Given two types, returns the "merge", in which promotable types
|
||||||
|
// are promoted to the maximum of the two. Returns nil (and generates
|
||||||
|
// an error message) if the types are incompatible.
|
||||||
|
static TypePtr merge_types(const TypePtr& t1, const TypePtr& t2);
|
||||||
|
|
||||||
Type::Type(TypeTag t, bool arg_base_type)
|
Type::Type(TypeTag t, bool arg_base_type)
|
||||||
: tag(t), internal_tag(to_internal_type_tag(tag)), is_network_order(zeek::is_network_order(t)),
|
: tag(t), internal_tag(to_internal_type_tag(tag)), is_network_order(zeek::is_network_order(t)),
|
||||||
base_type(arg_base_type)
|
base_type(arg_base_type)
|
||||||
|
@ -2673,7 +2678,7 @@ TypePtr merge_types(const TypePtr& arg_t1, const TypePtr& arg_t2)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
TypePtr merge_type_list(detail::ListExpr* elements)
|
TypePtr maximal_type(detail::ListExpr* elements)
|
||||||
{
|
{
|
||||||
TypeList* tl_type = elements->GetType()->AsTypeList();
|
TypeList* tl_type = elements->GetType()->AsTypeList();
|
||||||
const auto& tl = tl_type->GetTypes();
|
const auto& tl = tl_type->GetTypes();
|
||||||
|
@ -2690,7 +2695,21 @@ TypePtr merge_type_list(detail::ListExpr* elements)
|
||||||
return t;
|
return t;
|
||||||
|
|
||||||
for ( size_t i = 1; t && i < tl.size(); ++i )
|
for ( size_t i = 1; t && i < tl.size(); ++i )
|
||||||
t = merge_types(t, tl[i]);
|
{
|
||||||
|
auto& tl_i = tl[i];
|
||||||
|
|
||||||
|
if ( t == tl_i )
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if ( BothArithmetic(t->Tag(), tl_i->Tag()) )
|
||||||
|
t = merge_types(t, tl_i);
|
||||||
|
|
||||||
|
else if ( t->Tag() == TYPE_ENUM && tl_i->Tag() == TYPE_ENUM )
|
||||||
|
t = merge_enum_types(t.get(), tl_i.get());
|
||||||
|
|
||||||
|
else if ( ! same_type(t, tl_i) )
|
||||||
|
t = nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
if ( ! t )
|
if ( ! t )
|
||||||
reporter->Error("inconsistent types in list");
|
reporter->Error("inconsistent types in list");
|
||||||
|
|
13
src/Type.h
13
src/Type.h
|
@ -923,15 +923,10 @@ extern Type* flatten_type(Type* t);
|
||||||
// Returns the "maximum" of two type tags, in a type-promotion sense.
|
// Returns the "maximum" of two type tags, in a type-promotion sense.
|
||||||
extern TypeTag max_type(TypeTag t1, TypeTag t2);
|
extern TypeTag max_type(TypeTag t1, TypeTag t2);
|
||||||
|
|
||||||
// Given two types, returns the "merge", in which promotable types
|
// Given a list of expressions, returns the maximal type consistent across
|
||||||
// are promoted to the maximum of the two. Returns nil (and generates
|
// all of them, or nil if this cannot be done. "Maximal" incorporates
|
||||||
// an error message) if the types are incompatible.
|
// notions of arithmetic coercion, but otherwise requires type-equivalence.
|
||||||
TypePtr merge_types(const TypePtr& t1, const TypePtr& t2);
|
TypePtr maximal_type(detail::ListExpr* elements);
|
||||||
|
|
||||||
// Given a list of expressions, returns a (ref'd) type reflecting
|
|
||||||
// a merged type consistent across all of them, or nil if this
|
|
||||||
// cannot be done.
|
|
||||||
TypePtr merge_type_list(detail::ListExpr* elements);
|
|
||||||
|
|
||||||
// Given an expression, infer its type when used for an initialization.
|
// Given an expression, infer its type when used for an initialization.
|
||||||
TypePtr init_type(const detail::ExprPtr& init);
|
TypePtr init_type(const detail::ExprPtr& init);
|
||||||
|
|
|
@ -3,3 +3,13 @@
|
||||||
[11, 5, , 107, , , 1046]
|
[11, 5, , 107, , , 1046]
|
||||||
[-2, -4, , -7, , -18, -999]
|
[-2, -4, , -7, , -18, -999]
|
||||||
[, -1, 11, 15]
|
[, -1, 11, 15]
|
||||||
|
[connT
|
||||||
|
{
|
||||||
|
return (T);
|
||||||
|
}, connF
|
||||||
|
{
|
||||||
|
return (F);
|
||||||
|
}, connMaybe
|
||||||
|
{
|
||||||
|
return (c$id$orig_p < c$id$resp_p);
|
||||||
|
}]
|
||||||
|
|
|
@ -51,3 +51,30 @@ event zeek_init()
|
||||||
|
|
||||||
print d;
|
print d;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type recursive: record {
|
||||||
|
placeholder: bool;
|
||||||
|
};
|
||||||
|
|
||||||
|
redef record recursive += { rec: table[count] of recursive &optional; };
|
||||||
|
|
||||||
|
function connT(c: connection, r: recursive): bool
|
||||||
|
{
|
||||||
|
return T;
|
||||||
|
}
|
||||||
|
|
||||||
|
function connF(c: connection, r: recursive): bool
|
||||||
|
{
|
||||||
|
return F;
|
||||||
|
}
|
||||||
|
|
||||||
|
function connMaybe(c: connection, r: recursive): bool
|
||||||
|
{
|
||||||
|
return c$id$orig_p < c$id$resp_p;
|
||||||
|
}
|
||||||
|
|
||||||
|
event zeek_init()
|
||||||
|
{
|
||||||
|
local v = vector(connT, connF, connMaybe);
|
||||||
|
print v;
|
||||||
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue