Skip to content

Commit

Permalink
Fix inconsistency with $$ in hooks.
Browse files Browse the repository at this point in the history
Fixes #1914

`$$` says it refers to the pre-conversion value, but that's not true
within a hook. This fixes that so that `$$` always refers to the
pre-conversion value.
  • Loading branch information
evantypanski committed Nov 20, 2024
1 parent d9c025d commit 9d9f2e9
Show file tree
Hide file tree
Showing 5 changed files with 20 additions and 6 deletions.
2 changes: 1 addition & 1 deletion spicy/toolchain/src/compiler/codegen/codegen.cc
Original file line number Diff line number Diff line change
Expand Up @@ -636,7 +636,7 @@ hilti::declaration::Function* CodeGen::compileHook(const type::Unit& unit, const
params.push_back(builder()->parameter("__excpt", builder()->typeString(), hilti::parameter::Kind::In));
}
else if ( original_field_type ) {
params.push_back(builder()->parameter("__dd", field->itemType()->type(), hilti::parameter::Kind::In));
params.push_back(builder()->parameter("__dd", field->ddType()->type(), hilti::parameter::Kind::In));

// Pass on captures for fields of type regexp, which are the only
// ones that have it (for vector of regexps, it wouldn't be clear what
Expand Down
2 changes: 1 addition & 1 deletion spicy/toolchain/src/compiler/codegen/parser-builder.cc
Original file line number Diff line number Diff line change
Expand Up @@ -2470,7 +2470,7 @@ void ParserBuilder::newValueForField(const production::Meta& meta, Expression* v
if ( field->emitHook() ) {
beforeHook();

Expressions args = {value};
Expressions args = {dd};

if ( field->originalType()->type()->isA<hilti::type::RegExp>() && ! field->isContainer() ) {
if ( state().captures )
Expand Down
5 changes: 1 addition & 4 deletions spicy/toolchain/src/compiler/resolver.cc
Original file line number Diff line number Diff line change
Expand Up @@ -267,18 +267,15 @@ struct VisitorPass2 : visitor::MutatingPostOrder {
if ( n->unitFieldIndex() && ! n->dd() ) {
auto unit_field = context()->lookup(n->unitFieldIndex())->as<type::unit::item::Field>();

QualifiedType* dd = nullptr;
QualifiedType* dd = unit_field->ddType();

if ( n->hookType() == declaration::hook::Type::ForEach ) {
dd = unit_field->ddType();
if ( ! dd || ! dd->isResolved() )
return;

// Validator will catch if the type is not a container.
dd = dd->type()->elementType();
}
else
dd = unit_field->itemType();

if ( dd && dd->isResolved() ) {
auto dd_ = QualifiedType::createExternal(context(), dd->type(), dd->constness());
Expand Down
3 changes: 3 additions & 0 deletions tests/Baseline/spicy.types.unit.dd-hook-type/output
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
### BTest baseline data generated by btest-diff. Do not edit. Use "btest -U/-u" to update. Requires BTest >= 0.63.
True
True
14 changes: 14 additions & 0 deletions tests/spicy/types/unit/dd-hook-type.spicy
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
# @TEST-EXEC: echo '00' | spicy-driver -d %INPUT >output
# @TEST-EXEC: btest-diff output

module DDConsistency;

public type Data = unit {
x: uint8 &convert=($$ + 5) &requires=($$ < 50) {
print $$ < 50; # Should print True since it got through the requires
}

y: uint8 &convert=($$ == 48) &requires=($$ < 50) {
print $$ == 48; # Should succeed compiling since $$ is uint8 still
}
};

0 comments on commit 9d9f2e9

Please # to comment.