From dcffd378e16b39474d86f171886361eb70c6f06e Mon Sep 17 00:00:00 2001 From: WebFreak001 Date: Mon, 4 Dec 2023 11:54:11 +0100 Subject: [PATCH] support casts in initializers rework of #710, reuses the existing type construction Co-authored-by: ryuukk --- dsymbol/src/dsymbol/conversion/first.d | 25 +++++++++++++++++++++++-- tests/tc_casts/expected1.txt | 8 ++++++++ tests/tc_casts/expected2.txt | 0 tests/tc_casts/file.d | 26 ++++++++++++++++++++++++++ tests/tc_casts/run.sh | 8 ++++++++ 5 files changed, 65 insertions(+), 2 deletions(-) create mode 100644 tests/tc_casts/expected1.txt create mode 100644 tests/tc_casts/expected2.txt create mode 100644 tests/tc_casts/file.d create mode 100755 tests/tc_casts/run.sh diff --git a/dsymbol/src/dsymbol/conversion/first.d b/dsymbol/src/dsymbol/conversion/first.d index 600d542f..26f366f0 100644 --- a/dsymbol/src/dsymbol/conversion/first.d +++ b/dsymbol/src/dsymbol/conversion/first.d @@ -1133,9 +1133,10 @@ private: auto lookup = l ? l : TypeLookupsAllocator.instance.make!TypeLookup(TypeLookupKind.varOrFunType); lookup.breadcrumbs.insert(TYPEOF_SYMBOL_NAME); - scope (exit) - lookup.breadcrumbs.insert(TYPEOF_END_SYMBOL_NAME); scope visitor = new InitializerVisitor(lookup, appendForeach, this); + scope (exit) + if (!visitor.isCast) + lookup.breadcrumbs.insert(TYPEOF_END_SYMBOL_NAME); if (l is null) lookups.insert(lookup); @@ -1586,6 +1587,25 @@ class InitializerVisitor : ASTVisitor on = false; } + override void visit(const CastExpression expression) + { + if (expression.type) + { + if (lookup.breadcrumbs.empty || lookup.breadcrumbs.back != TYPEOF_SYMBOL_NAME) + return; + + isCast = true; + lookup.breadcrumbs.popBack(); + TypeLookups none; + fp.addTypeToLookups(none, expression.type, lookup); + } + else + { + // we don't care about non-type casts (e.g. `cast()` or `cast(const)`) yet + expression.accept(this); + } + } + override void dynamicDispatch(const ExpressionNode expression) { on = true; @@ -1599,6 +1619,7 @@ class InitializerVisitor : ASTVisitor bool on = false; const bool appendForeach; FirstPass fp; + bool isCast; } class ArgumentListVisitor : ASTVisitor diff --git a/tests/tc_casts/expected1.txt b/tests/tc_casts/expected1.txt new file mode 100644 index 00000000..52a22649 --- /dev/null +++ b/tests/tc_casts/expected1.txt @@ -0,0 +1,8 @@ +identifiers +alignof k +init k +inside_c v +mangleof k +sizeof k +stringof k +tupleof k diff --git a/tests/tc_casts/expected2.txt b/tests/tc_casts/expected2.txt new file mode 100644 index 00000000..e69de29b diff --git a/tests/tc_casts/file.d b/tests/tc_casts/file.d new file mode 100644 index 00000000..3fa9bce2 --- /dev/null +++ b/tests/tc_casts/file.d @@ -0,0 +1,26 @@ +struct A +{ + struct B + { + struct C + { + int inside_c; + } + int inside_b; + } + int inside_a; +} + +unittest +{ + auto from_cast = cast(A.B.C) nonExist; + from_cast. +} + +unittest +{ + struct A {} + + auto from_cast = cast(A.B.C) nonExist; + from_cast. +} diff --git a/tests/tc_casts/run.sh b/tests/tc_casts/run.sh new file mode 100755 index 00000000..bacdbad1 --- /dev/null +++ b/tests/tc_casts/run.sh @@ -0,0 +1,8 @@ +set -e +set -u + +../../bin/dcd-client $1 file.d -c159 > actual1.txt +diff actual1.txt expected1.txt --strip-trailing-cr + +../../bin/dcd-client $1 file.d -c239 > actual2.txt +diff actual2.txt expected2.txt --strip-trailing-cr