mirror of
https://github.com/zeek/zeek.git
synced 2025-10-07 00:58:19 +00:00
Merge remote-tracking branch 'origin/topic/vern/when-lambda'
* origin/topic/vern/when-lambda: explicitly provide the frame for evaluating a "when" timeout expression attempt to make "when" btest deterministic tests for new "when" semantics/errors update existing test suite usage of "when" statements to include captures update uses of "when" in base scripts to include captures captures for "when" statements update Triggers to IntrusivePtr's and simpler AST traversal introduce IDSet type, migrate associated "ID*" types to "const ID*" logic (other than in profiling) for assignments that yield separate values option for internal use to mark a function type as allowing non-expression returns removed some now-obsolete profiling functionality minor commenting clarifications
This commit is contained in:
commit
3d9d6e953b
56 changed files with 931 additions and 255 deletions
31
src/Expr.cc
31
src/Expr.cc
|
@ -4586,7 +4586,8 @@ void CallExpr::ExprDescribe(ODesc* d) const
|
|||
args->Describe(d);
|
||||
}
|
||||
|
||||
LambdaExpr::LambdaExpr(std::unique_ptr<function_ingredients> arg_ing, IDPList arg_outer_ids)
|
||||
LambdaExpr::LambdaExpr(std::unique_ptr<function_ingredients> arg_ing, IDPList arg_outer_ids,
|
||||
StmtPtr when_parent)
|
||||
: Expr(EXPR_LAMBDA)
|
||||
{
|
||||
ingredients = std::move(arg_ing);
|
||||
|
@ -4594,7 +4595,7 @@ LambdaExpr::LambdaExpr(std::unique_ptr<function_ingredients> arg_ing, IDPList ar
|
|||
|
||||
SetType(ingredients->id->GetType());
|
||||
|
||||
CheckCaptures();
|
||||
CheckCaptures(when_parent);
|
||||
|
||||
// Install a dummy version of the function globally for use only
|
||||
// when broker provides a closure.
|
||||
|
@ -4639,7 +4640,7 @@ LambdaExpr::LambdaExpr(std::unique_ptr<function_ingredients> arg_ing, IDPList ar
|
|||
id->SetConst();
|
||||
}
|
||||
|
||||
void LambdaExpr::CheckCaptures()
|
||||
void LambdaExpr::CheckCaptures(StmtPtr when_parent)
|
||||
{
|
||||
auto ft = type->AsFuncType();
|
||||
const auto& captures = ft->GetCaptures();
|
||||
|
@ -4663,6 +4664,8 @@ void LambdaExpr::CheckCaptures()
|
|||
std::set<const ID*> outer_is_matched;
|
||||
std::set<const ID*> capture_is_matched;
|
||||
|
||||
auto desc = when_parent ? "\"when\" statement" : "lambda";
|
||||
|
||||
for ( const auto& c : *captures )
|
||||
{
|
||||
auto cid = c.id.get();
|
||||
|
@ -4675,7 +4678,11 @@ void LambdaExpr::CheckCaptures()
|
|||
|
||||
if ( capture_is_matched.count(cid) > 0 )
|
||||
{
|
||||
ExprError(util::fmt("%s listed multiple times in capture", cid->Name()));
|
||||
auto msg = util::fmt("%s listed multiple times in capture", cid->Name());
|
||||
if ( when_parent )
|
||||
when_parent->Error(msg);
|
||||
else
|
||||
ExprError(msg);
|
||||
continue;
|
||||
}
|
||||
|
||||
|
@ -4690,13 +4697,25 @@ void LambdaExpr::CheckCaptures()
|
|||
|
||||
for ( auto id : outer_ids )
|
||||
if ( outer_is_matched.count(id) == 0 )
|
||||
ExprError(util::fmt("%s is used inside lambda but not captured", id->Name()));
|
||||
{
|
||||
auto msg = util::fmt("%s is used inside %s but not captured", id->Name(), desc);
|
||||
if ( when_parent )
|
||||
when_parent->Error(msg);
|
||||
else
|
||||
ExprError(msg);
|
||||
}
|
||||
|
||||
for ( const auto& c : *captures )
|
||||
{
|
||||
auto cid = c.id.get();
|
||||
if ( cid && capture_is_matched.count(cid) == 0 )
|
||||
ExprError(util::fmt("%s is captured but not used inside lambda", cid->Name()));
|
||||
{
|
||||
auto msg = util::fmt("%s is captured but not used inside %s", cid->Name(), desc);
|
||||
if ( when_parent )
|
||||
when_parent->Error(msg);
|
||||
else
|
||||
ExprError(msg);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue