From c4399579dfff6bb7f082cf54ad61784dbce678f0 Mon Sep 17 00:00:00 2001 From: Ocean Date: Fri, 30 May 2025 18:21:25 +0800 Subject: [PATCH 1/2] Support Isolated Declgen with Plugin API Issue:https://gitee.com/openharmony/arkcompiler_ets_frontend/issues/IC906D Reason: In the hope of speeding up compiler process Description: 1. generate decl file with error info 2. carry out some isolated declaration specific check 3. do not parse import path in import statement 4. carry some type deduction for the return type of function Signed-off-by: Ocean --- ets2panda/BUILD.gn | 4 +- ets2panda/CMakeLists.txt | 3 +- ets2panda/bindings/native/src/bridges.cpp | 8 +- .../bindings/src/Es2pandaNativeModule.ts | 3 +- ets2panda/bindings/src/driver_helper.ts | 6 +- ets2panda/compiler/core/compilerImpl.cpp | 66 +-------- ets2panda/compiler/core/compilerImpl.h | 2 +- .../ets/insertOptionalParametersAnnotation.h | 3 +- ets2panda/declgen_ets2ts/BUILD.gn | 1 + ets2panda/declgen_ets2ts/CMakeLists.txt | 1 + ets2panda/declgen_ets2ts/declgenEts2Ts.cpp | 13 +- ets2panda/declgen_ets2ts/declgenEts2Ts.h | 10 +- .../isolatedDeclgenChecker.cpp} | 128 ++++++++---------- .../isolatedDeclgenChecker.h} | 18 ++- .../isolated_declgen.yaml | 16 +-- ets2panda/declgen_ets2ts/main.cpp | 34 +---- .../build_system/src/build/base_mode.ts | 1 + ets2panda/ir/astNode.cpp | 7 - ets2panda/ir/astNode.h | 1 - ets2panda/ir/base/classProperty.cpp | 5 - ets2panda/ir/base/scriptFunction.cpp | 5 +- ets2panda/ir/base/scriptFunction.h | 11 -- ets2panda/ir/srcDump.cpp | 4 +- ets2panda/ir/srcDump.h | 7 +- ets2panda/parser/ETSparser.cpp | 6 +- ets2panda/public/CMakeLists.txt | 1 + ets2panda/public/es2panda_lib.cpp | 7 +- ets2panda/public/es2panda_lib.h | 2 +- ets2panda/public/public.h | 3 - ...eturn_type_with_import_symbol-expected.txt | 26 ---- ...tion_return_type_with_literal-expected.txt | 16 --- ...ion_return_type_with_variable-expected.txt | 16 --- .../isolated_interface-expected.txt | 36 ----- .../isolated_namespace-expected.txt | 25 ---- ets2panda/test/unit/CMakeLists.txt | 1 + ets2panda/test/unit/declgen/CMakeLists.txt | 90 ++++++++++++ ...eturn_type_with_import_symbol-expected.txt | 7 + ...nction_return_type_with_import_symbol.ets} | 6 +- .../test_ets2ts_isolated_class-expected.txt | 18 +++ .../test_ets2ts_isolated_class.ets} | 0 .../test_ets2ts_isolated_enum-expected.txt | 11 ++ .../test_ets2ts_isolated_enum.ets} | 14 +- ...ction_with_optional_parameter-expected.txt | 2 + ...ated_function_with_optional_parameter.ets} | 0 ...est_ets2ts_isolated_interface-expected.txt | 14 ++ .../test_ets2ts_isolated_interface.ets} | 2 +- .../test_ets2ts_isolated_module-expected.txt | 6 + .../test_ets2ts_isolated_module.ets} | 23 +++- ...est_ets2ts_isolated_namespace-expected.txt | 5 + .../test_ets2ts_isolated_namespace.ets} | 0 .../declgen/test_ets2ts_isolated_declgen.cpp} | 60 ++++++-- ets2panda/test/unit/declgen/util.cpp | 83 ++++++++++++ .../declgen/util.h} | 40 +++--- ets2panda/test/unit/sizeof_node_test.cpp | 3 +- ets2panda/util/diagnostic.cpp | 4 +- ets2panda/util/diagnostic.h | 2 +- ets2panda/util/diagnosticEngine.cpp | 2 +- ets2panda/util/options.yaml | 4 - ets2panda/varbinder/ETSBinder.cpp | 9 +- 59 files changed, 477 insertions(+), 424 deletions(-) rename ets2panda/{checker/IsolatedDeclgenChecker.cpp => declgen_ets2ts/isolatedDeclgenChecker.cpp} (75%) rename ets2panda/{checker/IsolatedDeclgenChecker.h => declgen_ets2ts/isolatedDeclgenChecker.h} (90%) rename ets2panda/{util/diagnostic => declgen_ets2ts}/isolated_declgen.yaml (88%) delete mode 100644 ets2panda/test/isolated_declgen/infer_function_return_type_with_import_symbol-expected.txt delete mode 100644 ets2panda/test/isolated_declgen/infer_function_return_type_with_literal-expected.txt delete mode 100644 ets2panda/test/isolated_declgen/infer_function_return_type_with_variable-expected.txt delete mode 100644 ets2panda/test/isolated_declgen/isolated_interface-expected.txt delete mode 100644 ets2panda/test/isolated_declgen/isolated_namespace-expected.txt create mode 100644 ets2panda/test/unit/declgen/CMakeLists.txt create mode 100644 ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_infer_function_return_type_with_import_symbol-expected.txt rename ets2panda/test/{isolated_declgen/infer_function_return_type_with_import_symbol.ets => unit/declgen/ets2ts_isolated/test_ets2ts_infer_function_return_type_with_import_symbol.ets} (99%) create mode 100644 ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_class-expected.txt rename ets2panda/test/{isolated_declgen/isolated_class.ets => unit/declgen/ets2ts_isolated/test_ets2ts_isolated_class.ets} (100%) create mode 100644 ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_enum-expected.txt rename ets2panda/test/{isolated_declgen/isolated_function_with_optional_parameter-expected.txt => unit/declgen/ets2ts_isolated/test_ets2ts_isolated_enum.ets} (80%) create mode 100644 ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_function_with_optional_parameter-expected.txt rename ets2panda/test/{isolated_declgen/isolated_function_with_optional_parameter.ets => unit/declgen/ets2ts_isolated/test_ets2ts_isolated_function_with_optional_parameter.ets} (100%) create mode 100644 ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_interface-expected.txt rename ets2panda/test/{isolated_declgen/isolated_interface.ets => unit/declgen/ets2ts_isolated/test_ets2ts_isolated_interface.ets} (99%) create mode 100644 ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_module-expected.txt rename ets2panda/test/{isolated_declgen/infer_function_return_type_with_variable.ets => unit/declgen/ets2ts_isolated/test_ets2ts_isolated_module.ets} (63%) create mode 100644 ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_namespace-expected.txt rename ets2panda/test/{isolated_declgen/isolated_namespace.ets => unit/declgen/ets2ts_isolated/test_ets2ts_isolated_namespace.ets} (100%) rename ets2panda/test/{isolated_declgen/infer_function_return_type_with_literal.ets => unit/declgen/test_ets2ts_isolated_declgen.cpp} (31%) create mode 100644 ets2panda/test/unit/declgen/util.cpp rename ets2panda/test/{isolated_declgen/isolated_class-expected.txt => unit/declgen/util.h} (43%) diff --git a/ets2panda/BUILD.gn b/ets2panda/BUILD.gn index dec0dc9a48..fa9389bddc 100644 --- a/ets2panda/BUILD.gn +++ b/ets2panda/BUILD.gn @@ -59,7 +59,6 @@ libes2panda_sources = [ "checker/ETSAnalyzerHelpers.cpp", "checker/ETSAnalyzerUnreachable.cpp", "checker/ETSchecker.cpp", - "checker/IsolatedDeclgenChecker.cpp", "checker/JSchecker.cpp", "checker/TSAnalyzer.cpp", "checker/TSAnalyzerUnreachable.cpp", @@ -1095,6 +1094,7 @@ ark_gen("gen") { # libes2panda does not include bytecode optimizer, because it is used in # libarkruntime, and conflict with JIT setup ensues libes2panda_public_sources = [ + "declgen_ets2ts/isolatedDeclgenChecker.cpp", "declgen_ets2ts/declgenEts2Ts.cpp", "public/${LIB_NAME}.cpp", "util/generateBin.cpp", @@ -1243,9 +1243,9 @@ ark_gen("es2panda_diagnostic_gen") { "util/diagnostic/semantic.yaml", "util/diagnostic/warning.yaml", "util/diagnostic/fatal.yaml", - "util/diagnostic/isolated_declgen.yaml", "declgen_ets2ts/declgen_ets2ts_error.yaml", "declgen_ets2ts/declgen_ets2ts_warning.yaml", + "declgen_ets2ts/isolated_declgen.yaml", "util/diagnostic/arktsconfig_error.yaml", ] template_files = [ "diagnostic.h.erb" ] diff --git a/ets2panda/CMakeLists.txt b/ets2panda/CMakeLists.txt index 10cf792e94..4a9b9f39e1 100644 --- a/ets2panda/CMakeLists.txt +++ b/ets2panda/CMakeLists.txt @@ -144,8 +144,8 @@ panda_gen( ${DIAGNOSTIC_DIR}/fatal.yaml ${CMAKE_CURRENT_SOURCE_DIR}/declgen_ets2ts/declgen_ets2ts_error.yaml ${CMAKE_CURRENT_SOURCE_DIR}/declgen_ets2ts/declgen_ets2ts_warning.yaml + ${CMAKE_CURRENT_SOURCE_DIR}/declgen_ets2ts/isolated_declgen.yaml ${DIAGNOSTIC_DIR}/arktsconfig_error.yaml - ${DIAGNOSTIC_DIR}/isolated_declgen.yaml TARGET_NAME es2panda_diagnostic_gen TEMPLATES diagnostic.h.erb SOURCE ${DIAGNOSTIC_DIR} @@ -537,7 +537,6 @@ set(ES2PANDA_LIB_SRC checker/TSAnalyzer.cpp checker/TSAnalyzerUnreachable.cpp checker/JSchecker.cpp - checker/IsolatedDeclgenChecker.cpp checker/typeChecker/TypeChecker.cpp checker/ets/aliveAnalyzer.cpp checker/ets/etsWarningAnalyzer.cpp diff --git a/ets2panda/bindings/native/src/bridges.cpp b/ets2panda/bindings/native/src/bridges.cpp index 2757d4b9ef..19790f849e 100644 --- a/ets2panda/bindings/native/src/bridges.cpp +++ b/ets2panda/bindings/native/src/bridges.cpp @@ -37,13 +37,13 @@ KNativePointer impl_CreateContextFromString(KNativePointer configPtr, KStringPtr TS_INTEROP_3(CreateContextFromString, KNativePointer, KNativePointer, KStringPtr, KStringPtr) KInt impl_GenerateTsDeclarationsFromContext(KNativePointer contextPtr, KStringPtr &outputDeclEts, KStringPtr &outputEts, - KBoolean exportAll) + KBoolean exportAll, KBoolean isolated) { auto context = reinterpret_cast(contextPtr); - return static_cast(GetPublicImpl()->GenerateTsDeclarationsFromContext(context, outputDeclEts.data(), - outputEts.data(), exportAll != 0)); + return static_cast(GetPublicImpl()->GenerateTsDeclarationsFromContext( + context, outputDeclEts.data(), outputEts.data(), exportAll != 0, isolated != 0)); } -TS_INTEROP_4(GenerateTsDeclarationsFromContext, KInt, KNativePointer, KStringPtr, KStringPtr, KBoolean) +TS_INTEROP_5(GenerateTsDeclarationsFromContext, KInt, KNativePointer, KStringPtr, KStringPtr, KBoolean, KBoolean) KNativePointer impl_CreateContextFromFile(KNativePointer configPtr, KStringPtr &filenamePtr) { diff --git a/ets2panda/bindings/src/Es2pandaNativeModule.ts b/ets2panda/bindings/src/Es2pandaNativeModule.ts index 210ad83e1c..0c0838479a 100644 --- a/ets2panda/bindings/src/Es2pandaNativeModule.ts +++ b/ets2panda/bindings/src/Es2pandaNativeModule.ts @@ -65,7 +65,8 @@ export class Es2pandaNativeModule { config: KPtr, outputDeclEts: String, outputEts: String, - exportAll: KBoolean + exportAll: KBoolean, + isolated: KBoolean ): KPtr { throw new Error('Not implemented'); } diff --git a/ets2panda/bindings/src/driver_helper.ts b/ets2panda/bindings/src/driver_helper.ts index 29f82f3d01..5b43299469 100644 --- a/ets2panda/bindings/src/driver_helper.ts +++ b/ets2panda/bindings/src/driver_helper.ts @@ -76,9 +76,11 @@ export class DriverHelper { global.destroyCfg(); } - public generateTsDecl(declOutPath: string, etsOutPath: string, exportAll: boolean): void { + public generateTsDecl(declOutPath: string, etsOutPath: string, exportAll: boolean, isolated: boolean): void { let exportAll_: KBoolean = exportAll ? 1 : 0; - global.es2panda._GenerateTsDeclarationsFromContext(this._cfg.peer, declOutPath, etsOutPath, exportAll_); + let isolated_: KBoolean = isolated ? 1 : 0; + global.es2panda._GenerateTsDeclarationsFromContext(this._cfg.peer, declOutPath, etsOutPath, + exportAll_, isolated_); } } diff --git a/ets2panda/compiler/core/compilerImpl.cpp b/ets2panda/compiler/core/compilerImpl.cpp index af038f7485..244b3ea4f3 100644 --- a/ets2panda/compiler/core/compilerImpl.cpp +++ b/ets2panda/compiler/core/compilerImpl.cpp @@ -14,7 +14,6 @@ */ #include "compilerImpl.h" -#include #include "es2panda.h" #include "ast_verifier/ASTVerifier.h" @@ -35,10 +34,7 @@ #include "compiler/lowering/phase.h" #include "compiler/lowering/scopesInit/scopesInitPhase.h" #include "compiler/lowering/checkerPhase.h" -#include "compiler/lowering/resolveIdentifiers.h" -#include "compiler/lowering/ets/insertOptionalParametersAnnotation.h" #include "evaluate/scopedDebugInfoPlugin.h" -#include "generated/isa.h" #include "parser/parserImpl.h" #include "parser/JSparser.h" #include "parser/ASparser.h" @@ -111,7 +107,7 @@ static bool CheckOptionsBeforePhase(const util::Options &options, const parser:: } void HandleGenerateDecl(const parser::Program &program, util::DiagnosticEngine &diagnosticEngine, - const std::string &outputPath, bool isIsolatedDeclgen) + const std::string &outputPath) { std::ofstream outFile(outputPath); if (!outFile.is_open()) { @@ -119,13 +115,7 @@ void HandleGenerateDecl(const parser::Program &program, util::DiagnosticEngine & lexer::SourcePosition()); return; } - std::string result; - if (!isIsolatedDeclgen) { - result = program.Ast()->DumpDecl(); - } else { - result = program.Ast()->IsolatedDumpDecl(); - } - + std::string result = program.Ast()->DumpDecl(); result.erase(0, result.find_first_not_of('\n')); outFile << result; @@ -148,68 +138,26 @@ static bool CheckOptionsAfterPhase(const util::Options &options, const parser::P return options.GetExitAfterPhase() == name; } -static bool DoIsolatedDeclgenCheck(const util::Options &options, const std::string &phaseName, - checker::IsolatedDeclgenChecker &isolatedDeclgenChecker, - public_lib::Context &context) -{ - if (!options.IsGenerateDeclEnableIsolated()) { - return true; - } - if (phaseName == compiler::ResolveIdentifiers::NAME) { - isolatedDeclgenChecker.CheckBeforeChecker(); - if (context.diagnosticEngine->IsAnyError()) { - return false; - } - } - - if (phaseName == compiler::CheckerPhase::NAME) { - isolatedDeclgenChecker.CheckAfterChecker(); - if (context.diagnosticEngine->IsAnyError()) { - return false; - } - } - - return true; -} - static bool RunVerifierAndPhases(public_lib::Context &context, parser::Program &program) { - auto &options = const_cast(*context.config->options); + const auto &options = *context.config->options; const auto verifierEachPhase = options.IsAstVerifierEachPhase(); ast_verifier::ASTVerifier verifier(context, program); - checker::IsolatedDeclgenChecker isolatedDeclgenChecker(*context.diagnosticEngine, program); - if (options.IsGenerateDeclEnableIsolated()) { - options.SetGenerateDeclEnabled(true); - } - bool skipPhase = false; while (auto phase = context.phaseManager->NextPhase()) { const auto name = std::string {phase->Name()}; - skipPhase = options.GetSkipPhases().count(name) > 0 || - (options.IsGenerateDeclEnableIsolated() && - phase->Name() == compiler::InsertOptionalParametersAnnotation::NAME); - if (skipPhase) { + if (options.GetSkipPhases().count(name) > 0) { continue; } - if (options.IsGenerateDeclEnableIsolated() && name == "plugins-after-check") { - return false; - } - if (CheckOptionsBeforePhase(options, program, name) || !phase->Apply(&context, &program) || CheckOptionsAfterPhase(options, program, name)) { return false; } - if (!DoIsolatedDeclgenCheck(options, name, isolatedDeclgenChecker, context)) { - return false; - } - - if (!options.IsGenerateDeclEnableIsolated()) { - verifier.IntroduceNewInvariants(phase->Name()); - } - if (verifierEachPhase || options.HasVerifierPhase(phase->Name())) { + if (verifier.IntroduceNewInvariants(phase->Name()); + verifierEachPhase || options.HasVerifierPhase(phase->Name())) { verifier.Verify(phase->Name()); } @@ -225,7 +173,7 @@ static bool RunVerifierAndPhases(public_lib::Context &context, parser::Program & } else { path = options.GetGenerateDeclPath(); } - HandleGenerateDecl(program, *context.diagnosticEngine, path, options.IsGenerateDeclEnableIsolated()); + HandleGenerateDecl(program, *context.diagnosticEngine, path); } } diff --git a/ets2panda/compiler/core/compilerImpl.h b/ets2panda/compiler/core/compilerImpl.h index 6c669d5e00..02ac0514b2 100644 --- a/ets2panda/compiler/core/compilerImpl.h +++ b/ets2panda/compiler/core/compilerImpl.h @@ -26,7 +26,7 @@ namespace ark::es2panda::compiler { class CompileQueue; void HandleGenerateDecl(const parser::Program &program, util::DiagnosticEngine &diagnosticEngine, - const std::string &outputPath, bool isIsolatedDeclgen); + const std::string &outputPath); class CompilationUnit { public: diff --git a/ets2panda/compiler/lowering/ets/insertOptionalParametersAnnotation.h b/ets2panda/compiler/lowering/ets/insertOptionalParametersAnnotation.h index 1e8a0440a1..780d43d514 100644 --- a/ets2panda/compiler/lowering/ets/insertOptionalParametersAnnotation.h +++ b/ets2panda/compiler/lowering/ets/insertOptionalParametersAnnotation.h @@ -22,10 +22,9 @@ namespace ark::es2panda::compiler { class InsertOptionalParametersAnnotation : public PhaseForDeclarations { public: - static constexpr std::string_view NAME = "InsertOptionalParametersAnnotation"; std::string_view Name() const override { - return NAME; + return "InsertOptionalParametersAnnotation"; } bool PerformForModule(public_lib::Context *ctx, parser::Program *program) override; diff --git a/ets2panda/declgen_ets2ts/BUILD.gn b/ets2panda/declgen_ets2ts/BUILD.gn index 165a35a81f..8de1df605d 100644 --- a/ets2panda/declgen_ets2ts/BUILD.gn +++ b/ets2panda/declgen_ets2ts/BUILD.gn @@ -16,6 +16,7 @@ import("//build/ohos.gni") ohos_executable("declgen_ets2ts") { sources = [ + "isolatedDeclgenChecker.cpp", "declgenEts2Ts.cpp", "main.cpp", ] diff --git a/ets2panda/declgen_ets2ts/CMakeLists.txt b/ets2panda/declgen_ets2ts/CMakeLists.txt index 6d0687fa1d..994c760889 100644 --- a/ets2panda/declgen_ets2ts/CMakeLists.txt +++ b/ets2panda/declgen_ets2ts/CMakeLists.txt @@ -14,6 +14,7 @@ set(DECLGEN_ETS2TS_SRC main.cpp declgenEts2Ts.cpp + isolatedDeclgenChecker.cpp ) set(DECLGEN_ETS2TS_INCLUDE_DIRS diff --git a/ets2panda/declgen_ets2ts/declgenEts2Ts.cpp b/ets2panda/declgen_ets2ts/declgenEts2Ts.cpp index 6dd04a3916..ebdc7c56d6 100644 --- a/ets2panda/declgen_ets2ts/declgenEts2Ts.cpp +++ b/ets2panda/declgen_ets2ts/declgenEts2Ts.cpp @@ -14,8 +14,8 @@ */ #include "declgenEts2Ts.h" -#include +#include "isolatedDeclgenChecker.h" #include "checker/types/ets/etsTupleType.h" #include "generated/diagnostic.h" #include "ir/base/classProperty.h" @@ -700,8 +700,8 @@ void TSDeclGen::ProcessFunctionReturnType(const checker::Signature *sig) } std::string typeStr = sig->ReturnType()->ToString(); - if (declgenOptions_.isIsolatedDeclgen && typeStr.find(ERROR_TYPE) != std::string::npos) { - typeStr = sig->Function()->GetIsolatedDeclgenReturnType(); + if (declgenOptions_.isolated && typeStr.find(ERROR_TYPE) != std::string::npos) { + typeStr = isolatedDeclgenChecker_->Check(const_cast(sig->Function())); OutDts(typeStr); SplitUnionTypes(typeStr); return; @@ -2062,7 +2062,12 @@ bool WriteToFile(const std::string &path, const std::string &content, checker::E bool GenerateTsDeclarations(checker::ETSChecker *checker, const ark::es2panda::parser::Program *program, const DeclgenOptions &declgenOptions) { - TSDeclGen declBuilder(checker, program); + declgen::IsolatedDeclgenChecker isolatedDeclgenChecker(checker->DiagnosticEngine(), *program); + if (declgenOptions.isolated) { + isolatedDeclgenChecker.Check(); + } + + TSDeclGen declBuilder(checker, &isolatedDeclgenChecker, program); declBuilder.SetDeclgenOptions(declgenOptions); if ((declBuilder.GetDeclgenOptions().outputDeclEts.empty() && !declBuilder.GetDeclgenOptions().outputEts.empty()) || diff --git a/ets2panda/declgen_ets2ts/declgenEts2Ts.h b/ets2panda/declgen_ets2ts/declgenEts2Ts.h index fda8c826a1..81f29c2a6b 100644 --- a/ets2panda/declgen_ets2ts/declgenEts2Ts.h +++ b/ets2panda/declgen_ets2ts/declgenEts2Ts.h @@ -22,12 +22,13 @@ #include "libpandabase/utils/arena_containers.h" #include "util/options.h" #include "util/diagnosticEngine.h" +#include "isolatedDeclgenChecker.h" namespace ark::es2panda::declgen_ets2ts { struct DeclgenOptions { bool exportAll = false; - bool isIsolatedDeclgen = false; + bool isolated = false; std::string outputDeclEts; std::string outputEts; }; @@ -38,8 +39,10 @@ bool GenerateTsDeclarations(checker::ETSChecker *checker, const ark::es2panda::p class TSDeclGen { public: - TSDeclGen(checker::ETSChecker *checker, const ark::es2panda::parser::Program *program) + TSDeclGen(checker::ETSChecker *checker, declgen::IsolatedDeclgenChecker *isolatedDeclgenChecker, + const ark::es2panda::parser::Program *program) : checker_(checker), + isolatedDeclgenChecker_(isolatedDeclgenChecker), program_(program), diagnosticEngine_(checker->DiagnosticEngine()), allocator_(SpaceType::SPACE_TYPE_COMPILER, nullptr, true), @@ -95,9 +98,9 @@ private: const checker::Signature *GetFuncSignature(const checker::ETSFunctionType *etsFunctionType, const ir::MethodDefinition *methodDef); - void SplitUnionTypes(std::string &unionTypeString); void GenType(const checker::Type *checkerType); void GenFunctionType(const checker::ETSFunctionType *functionType, const ir::MethodDefinition *methodDef = nullptr); + void SplitUnionTypes(std::string &unionTypeString); void ProcessFunctionReturnType(const checker::Signature *sig); bool ProcessTSQualifiedName(const ir::ETSTypeReference *typeReference); void ProcessETSTypeReferenceType(const ir::ETSTypeReference *typeReference, @@ -289,6 +292,7 @@ private: std::stringstream outputDts_; std::stringstream outputTs_; checker::ETSChecker *checker_ {}; + declgen::IsolatedDeclgenChecker *isolatedDeclgenChecker_ {}; const ark::es2panda::parser::Program *program_ {}; util::DiagnosticEngine &diagnosticEngine_; ArenaAllocator allocator_; diff --git a/ets2panda/checker/IsolatedDeclgenChecker.cpp b/ets2panda/declgen_ets2ts/isolatedDeclgenChecker.cpp similarity index 75% rename from ets2panda/checker/IsolatedDeclgenChecker.cpp rename to ets2panda/declgen_ets2ts/isolatedDeclgenChecker.cpp index ed623f5cb4..052a88c503 100644 --- a/ets2panda/checker/IsolatedDeclgenChecker.cpp +++ b/ets2panda/declgen_ets2ts/isolatedDeclgenChecker.cpp @@ -13,11 +13,13 @@ * limitations under the License. */ -#include "checker/IsolatedDeclgenChecker.h" +#include "isolatedDeclgenChecker.h" + +#include "es2panda.h" #include "clang.h" #include "utils/logger.h" -namespace ark::es2panda::checker { +namespace ark::es2panda::declgen { using AstNodePtr = ir::AstNode *; void IsolatedDeclgenChecker::LogError(const diagnostic::DiagnosticKind &diagnostic, @@ -27,23 +29,28 @@ void IsolatedDeclgenChecker::LogError(const diagnostic::DiagnosticKind &diagnost diagnosticEngine_.LogDiagnostic(diagnostic, diagnosticParams, pos); } +static bool IsUnionTypeWithError(const checker::Type *type) +{ + if (type == nullptr || !type->IsUnionType()) { + return false; + } + + return type->ToString().find(ERROR_TYPE) != std::string::npos; +} + void IsolatedDeclgenChecker::Check(ir::ClassProperty *ast) { if (ast->Parent()->IsAnnotationUsage()) { return; } - if (ast->TypeAnnotation() == nullptr) { - LogError(diagnostic::PROPERTY_MUST_HAVE_EXPLICIT_TYPE_ANNOTATION_WITH_ISOLATED_DECL, {}, ast->Start()); + if (ast->IsPrivate()) { + return; } -} - -void IsolatedDeclgenChecker::Check(ir::ObjectExpression *ast) -{ - for (auto property : ast->Properties()) { - if (property->IsSpreadElement()) { - LogError(diagnostic::OBJECTS_THAT_CONTAIN_SPREAD_ASSIGNMENTS_CANNOT_BE_INFERRED_WITH_ISOLATED_DECL, {}, - property->Start()); - } + if (ast->TypeAnnotation() != nullptr) { + return; + } + if (ast->TsType()->IsTypeError() || IsUnionTypeWithError(ast->TsType())) { + LogError(diagnostic::PROPERTY_MUST_HAVE_EXPLICIT_TYPE_ANNOTATION_WITH_ISOLATED_DECL, {}, ast->Start()); } } @@ -76,9 +83,30 @@ void IsolatedDeclgenChecker::Check(ir::ArrayExpression *ast) } } +static std::string GetETSTypeReferenceName(ir::ETSTypeReference *typeRef) +{ + if (typeRef == nullptr) { + return ""; + } + auto *part = typeRef->Part(); + if (part == nullptr) { + return ""; + } + if (part->Name()->IsIdentifier()) { + return part->Name()->AsIdentifier()->Name().Mutf8(); + } + if (part->Name()->IsTSQualifiedName()) { + return part->Name()->AsTSQualifiedName()->Name().Mutf8(); + } + return ""; +} + void IsolatedDeclgenChecker::Check(ir::ETSParameterExpression *ast) { - if (ast->TypeAnnotation() == nullptr) { + if (ast->TypeAnnotation() != nullptr) { + return; + } + if (ast->TsType()->IsTypeError() || IsUnionTypeWithError(ast->TsType())) { LogError(diagnostic::PARAMETER_MUST_HAVE_EXPLICIT_TYPE_ANNOTATION_WITH_ISOLATED_DECL, {}, ast->Start()); } } @@ -87,57 +115,57 @@ void IsolatedDeclgenChecker::Check(ir::ExportDefaultDeclaration *ast) { auto *decl = ast->Decl(); if (decl == nullptr) { - LogError(diagnostic::DEFAULT_EXPORTS__CANNOT_BE_INFERRED_WITH_ISOLATED_DECL, {}, ast->Start()); + LogError(diagnostic::DEFAULT_EXPORTS_CANNOT_BE_INFERRED_WITH_ISOLATED_DECL, {}, ast->Start()); return; } if (decl->IsClassDeclaration()) { auto *classDecl = decl->AsClassDeclaration(); if (classDecl == nullptr) { - LogError(diagnostic::DEFAULT_EXPORTS__CANNOT_BE_INFERRED_WITH_ISOLATED_DECL, {}, ast->Start()); + LogError(diagnostic::DEFAULT_EXPORTS_CANNOT_BE_INFERRED_WITH_ISOLATED_DECL, {}, ast->Start()); } return; } if (decl->IsTSInterfaceDeclaration()) { auto *interfaceDecl = decl->AsTSInterfaceDeclaration(); if (interfaceDecl == nullptr) { - LogError(diagnostic::DEFAULT_EXPORTS__CANNOT_BE_INFERRED_WITH_ISOLATED_DECL, {}, ast->Start()); + LogError(diagnostic::DEFAULT_EXPORTS_CANNOT_BE_INFERRED_WITH_ISOLATED_DECL, {}, ast->Start()); } return; } if (decl->IsTSEnumDeclaration()) { auto *enumDecl = decl->AsTSEnumDeclaration(); if (enumDecl == nullptr) { - LogError(diagnostic::DEFAULT_EXPORTS__CANNOT_BE_INFERRED_WITH_ISOLATED_DECL, {}, ast->Start()); + LogError(diagnostic::DEFAULT_EXPORTS_CANNOT_BE_INFERRED_WITH_ISOLATED_DECL, {}, ast->Start()); } return; } if (decl->IsFunctionDeclaration()) { auto *funcDecl = decl->AsFunctionDeclaration(); if (funcDecl == nullptr) { - LogError(diagnostic::DEFAULT_EXPORTS__CANNOT_BE_INFERRED_WITH_ISOLATED_DECL, {}, ast->Start()); + LogError(diagnostic::DEFAULT_EXPORTS_CANNOT_BE_INFERRED_WITH_ISOLATED_DECL, {}, ast->Start()); } return; } if (decl->IsClassProperty()) { auto *classProperty = decl->AsClassProperty(); if (classProperty == nullptr) { - LogError(diagnostic::DEFAULT_EXPORTS__CANNOT_BE_INFERRED_WITH_ISOLATED_DECL, {}, ast->Start()); + LogError(diagnostic::DEFAULT_EXPORTS_CANNOT_BE_INFERRED_WITH_ISOLATED_DECL, {}, ast->Start()); } return; } - LogError(diagnostic::DEFAULT_EXPORTS__CANNOT_BE_INFERRED_WITH_ISOLATED_DECL, {}, ast->Start()); + LogError(diagnostic::DEFAULT_EXPORTS_CANNOT_BE_INFERRED_WITH_ISOLATED_DECL, {}, ast->Start()); } -std::string GetLiteralType(const ir::Literal *literal) +static std::string GetLiteralType(const ir::Literal *literal) { if (literal->IsStringLiteral()) { - return "String"; + return "string"; } if (literal->IsNumberLiteral()) { - return "Number"; + return "number"; } if (literal->IsBooleanLiteral()) { - return "Boolean"; + return "boolean"; } return ""; } @@ -170,15 +198,8 @@ std::string IsolatedDeclgenChecker::ProcessIdentifierArgument(ir::Identifier *id } if (decl->IsLetOrConstDecl()) { - return decl->Node() - ->AsClassProperty() - ->TypeAnnotation() - ->AsETSTypeReference() - ->Part() - ->Name() - ->AsIdentifier() - ->Name() - .Mutf8(); + auto *typeAnnotationRef = decl->Node()->AsClassProperty()->TypeAnnotation()->AsETSTypeReference(); + return GetETSTypeReferenceName(typeAnnotationRef); } LogError(diagnostic::FUNCTION_MUST_HAVE_AN_EXPLICIT_RETURN_TYPE_ANNOTATION_WITH_ISOLATED_DECL, {}, returnStatement->Start()); @@ -206,7 +227,7 @@ std::string IsolatedDeclgenChecker::ProcessNewClassInstanceExpressionArgument( returnStatement->Start()); return ""; } - return classType->AsETSTypeReference()->Part()->Name()->AsIdentifier()->Name().Mutf8(); + return GetETSTypeReferenceName(classType->AsETSTypeReference()); } std::string IsolatedDeclgenChecker::InferReturnTypeForArgument(ir::ReturnStatement *returnStatement) @@ -281,9 +302,9 @@ std::string IsolatedDeclgenChecker::Check(ir::ScriptFunction *ast) return returnTypeStr; } -void IsolatedDeclgenChecker::CheckBeforeChecker() +void IsolatedDeclgenChecker::Check() { - program_.Ast()->TransformChildrenRecursively( + const_cast(program_).Ast()->TransformChildrenRecursively( [&](ir::AstNode *ast) -> AstNodePtr { if (ast->IsClassProperty()) { Check(ast->AsClassProperty()); @@ -300,10 +321,6 @@ void IsolatedDeclgenChecker::CheckBeforeChecker() return ast; } - if (ast->IsObjectExpression()) { - Check(ast->AsObjectExpression()); - return ast; - } if (ast->IsExportDefaultDeclaration()) { Check(ast->AsExportDefaultDeclaration()); return ast; @@ -311,31 +328,6 @@ void IsolatedDeclgenChecker::CheckBeforeChecker() return ast; }, - "CheckIsolatedDeclBeforeChecker"); -} - -void IsolatedDeclgenChecker::CheckAfterChecker() -{ - program_.Ast()->TransformChildrenRecursively( - [&](ir::AstNode *ast) -> AstNodePtr { - if (!ast->IsScriptFunction()) { - return ast; - } - - auto *scriptFunction = ast->AsScriptFunction(); - auto *returnType = scriptFunction->Signature()->ReturnType(); - if (returnType == nullptr) { - return ast; - } - std::string returnTypeStr = Check(scriptFunction); - if (returnType->ToString().find(ERROR_TYPE) == std::string::npos) { - scriptFunction->SetIsolatedDeclgenReturnType(returnType->ToString()); - return ast; - } - scriptFunction->SetIsolatedDeclgenReturnType(returnTypeStr); - - return ast; - }, - "CheckIsolatedDeclAfterChecker"); + "CheckIsolatedDecl"); } -} // namespace ark::es2panda::checker \ No newline at end of file +} // namespace ark::es2panda::declgen \ No newline at end of file diff --git a/ets2panda/checker/IsolatedDeclgenChecker.h b/ets2panda/declgen_ets2ts/isolatedDeclgenChecker.h similarity index 90% rename from ets2panda/checker/IsolatedDeclgenChecker.h rename to ets2panda/declgen_ets2ts/isolatedDeclgenChecker.h index eef54b0232..3769b90ea1 100644 --- a/ets2panda/checker/IsolatedDeclgenChecker.h +++ b/ets2panda/declgen_ets2ts/isolatedDeclgenChecker.h @@ -19,10 +19,10 @@ #include "macros.h" #include "checker/checker.h" -namespace ark::es2panda::checker { +namespace ark::es2panda::declgen { class IsolatedDeclgenChecker { public: - explicit IsolatedDeclgenChecker(util::DiagnosticEngine &diagnosticEngine, parser::Program &program) + explicit IsolatedDeclgenChecker(util::DiagnosticEngine &diagnosticEngine, const parser::Program &program) : diagnosticEngine_(diagnosticEngine), program_(program) { } @@ -31,18 +31,16 @@ public: NO_COPY_SEMANTIC(IsolatedDeclgenChecker); NO_MOVE_SEMANTIC(IsolatedDeclgenChecker); - void CheckBeforeChecker(); - void CheckAfterChecker(); + void Check(); + std::string Check(ir::ScriptFunction *ast); + +private: void Check(ir::ClassProperty *ast); - void Check(ir::ObjectExpression *ast); void Check(ir::ArrayExpression *ast); void Check(ir::ETSParameterExpression *ast); void Check(ir::ExportDefaultDeclaration *ast); - std::string Check(ir::ScriptFunction *ast); - -private: std::string InferReturnTypeForArgument(ir::ReturnStatement *returnStatement); std::string ProcessLiteralArgument(ir::Literal *literal, ir::ReturnStatement *returnStatement); @@ -56,8 +54,8 @@ private: private: util::DiagnosticEngine &diagnosticEngine_; - parser::Program &program_; + const parser::Program &program_; }; -} // namespace ark::es2panda::checker +} // namespace ark::es2panda::declgen #endif // ES2PANDA_CHECKER_ISOLATED_DECLGEN_CHECKER_H \ No newline at end of file diff --git a/ets2panda/util/diagnostic/isolated_declgen.yaml b/ets2panda/declgen_ets2ts/isolated_declgen.yaml similarity index 88% rename from ets2panda/util/diagnostic/isolated_declgen.yaml rename to ets2panda/declgen_ets2ts/isolated_declgen.yaml index fb9d9d2c32..bfde0c6897 100644 --- a/ets2panda/util/diagnostic/isolated_declgen.yaml +++ b/ets2panda/declgen_ets2ts/isolated_declgen.yaml @@ -23,26 +23,22 @@ isolated_declgen: id: 3 message: Property must have an explicit type annotation when using isolated declaration. -- name: OBJECTS_THAT_CONTAIN_SPREAD_ASSIGNMENTS_CANNOT_BE_INFERRED_WITH_ISOLATED_DECL - id: 4 - message: Objects that contain spread assignments cannot be inferred with isolated declaration. - - name: ONLY_CONST_ARRAYS_CAN_BE_INFERRED_WITH_ISOLATED_DECL - id: 5 + id: 4 message: Only const arrays can be inferred with isolated declaration. - name: DECLARATION_EMIT_FOR_THIS_PARAMETER_REQUIRES_IMPLICITLY_ADD_UNDEFINED_TO_ITS_TYPE_NOT_ALLOWED_IN_ISOLATED_DECL - id: 6 + id: 5 message: Declaration emit for this parameter requires implicitly adding undefined to its type, which is not allowed in isolated declaration. -- name: DEFAULT_EXPORTS__CANNOT_BE_INFERRED_WITH_ISOLATED_DECL - id: 7 +- name: DEFAULT_EXPORTS_CANNOT_BE_INFERRED_WITH_ISOLATED_DECL + id: 6 message: Cannot use array creation expression with type parameter. - name: FUNCTION_MUST_HAVE_AN_EXPLICIT_RETURN_TYPE_ANNOTATION_WITH_ISOLATED_DECL - id: 8 + id: 7 message: Function must have an explicit return type annotation when using isolated declaration. - name: METHOD_MUST_HAVE_AN_EXPLICIT_RETURN_TYPE_ANNOTATION_WITH_ISOLATED_DECL - id: 9 + id: 8 message: Method must have an explicit return type annotation when using isolated declaration. \ No newline at end of file diff --git a/ets2panda/declgen_ets2ts/main.cpp b/ets2panda/declgen_ets2ts/main.cpp index d55467fc90..792a7ae7a9 100644 --- a/ets2panda/declgen_ets2ts/main.cpp +++ b/ets2panda/declgen_ets2ts/main.cpp @@ -13,10 +13,10 @@ * limitations under the License. */ -#include #include "public/es2panda_lib.h" #include "public/public.h" #include "declgenEts2Ts.h" +#include "isolatedDeclgenChecker.h" namespace ark::es2panda::declgen_ets2ts { @@ -26,7 +26,6 @@ static void PrintUsage() std::cerr << " --export-all Treat all top level statements as exported\n"; std::cerr << " --output-dets=[FILE] Path to output .d.ets file\n"; std::cerr << " --output-ets=[FILE] Path to output .ets file\n"; - std::cerr << " --generate-decl:enable-isolated Generate isolated decl\n"; std::cerr << " --help Print this message and exit. Default: false\n"; std::cerr << "Tail arguments:\n"; std::cerr << "input: input file\n"; @@ -68,21 +67,11 @@ static DeclgenOptions ParseOptions(Span args) std::strchr(args[i], '=') != nullptr) { std::string arg = args[i]; options.outputEts = arg.substr(std::strlen("--output-ets=")); - } else if (std::strcmp(args[i], "--generate-decl:enable-isolated") == 0) { - options.isIsolatedDeclgen = true; } } return options; } -static void DestroyContextAndConfig(const es2panda_Impl *impl, es2panda_Context *ctx, es2panda_Config *cfg, - const char **newArgv) -{ - impl->DestroyContext(ctx); - impl->DestroyConfig(cfg); - delete[] newArgv; -} - static int Run(int argc, const char **argv) { Span args(argv, static_cast(argc)); @@ -107,31 +96,16 @@ static int Run(int argc, const char **argv) auto *ctxImpl = reinterpret_cast(ctx); auto *checker = reinterpret_cast(ctxImpl->checker); - auto *isolatedDeclgenChecker = reinterpret_cast(ctxImpl->isolatedDeclgenChecker); - impl->ProceedToState(ctx, ES2PANDA_STATE_BOUND); - if (declgenOptions.isIsolatedDeclgen) { - isolatedDeclgenChecker->CheckBeforeChecker(); - if (ctxImpl->diagnosticEngine->IsAnyError()) { - DestroyContextAndConfig(impl, ctx, cfg, newArgv); - return 1; - } - } - impl->ProceedToState(ctx, ES2PANDA_STATE_CHECKED); - if (declgenOptions.isIsolatedDeclgen) { - isolatedDeclgenChecker->CheckAfterChecker(); - if (ctxImpl->diagnosticEngine->IsAnyError()) { - DestroyContextAndConfig(impl, ctx, cfg, newArgv); - return 1; - } - } int res = 0; if (!GenerateTsDeclarations(checker, ctxImpl->parserProgram, declgenOptions)) { res = 1; } - DestroyContextAndConfig(impl, ctx, cfg, newArgv); + impl->DestroyContext(ctx); + impl->DestroyConfig(cfg); + delete[] newArgv; return res; } diff --git a/ets2panda/driver/build_system/src/build/base_mode.ts b/ets2panda/driver/build_system/src/build/base_mode.ts index 99fad43361..ea4dfca989 100644 --- a/ets2panda/driver/build_system/src/build/base_mode.ts +++ b/ets2panda/driver/build_system/src/build/base_mode.ts @@ -174,6 +174,7 @@ export abstract class BaseMode { arkts.generateTsDeclarationsFromContext( declEtsOutputPath, etsOutputPath, + false, false ); // Generate 1.0 declaration files & 1.0 glue code this.logger.printInfo('declaration files generated'); diff --git a/ets2panda/ir/astNode.cpp b/ets2panda/ir/astNode.cpp index 9d920eeac2..3acbcae47c 100644 --- a/ets2panda/ir/astNode.cpp +++ b/ets2panda/ir/astNode.cpp @@ -238,13 +238,6 @@ std::string AstNode::DumpDecl() const return dumper.Str(); } -std::string AstNode::IsolatedDumpDecl() const -{ - ir::SrcDumper dumper {this, true, true}; - dumper.Run(); - return dumper.Str(); -} - void AstNode::SetOriginalNode(AstNode *originalNode) noexcept { originalNode_ = originalNode; diff --git a/ets2panda/ir/astNode.h b/ets2panda/ir/astNode.h index c8f07a0c75..355b707e69 100644 --- a/ets2panda/ir/astNode.h +++ b/ets2panda/ir/astNode.h @@ -524,7 +524,6 @@ public: std::string DumpJSON() const; std::string DumpEtsSrc() const; std::string DumpDecl() const; - std::string IsolatedDumpDecl() const; virtual void Dump(ir::AstDumper *dumper) const = 0; virtual void Dump(ir::SrcDumper *dumper) const = 0; diff --git a/ets2panda/ir/base/classProperty.cpp b/ets2panda/ir/base/classProperty.cpp index 0ec31492bc..d6864b9d4d 100644 --- a/ets2panda/ir/base/classProperty.cpp +++ b/ets2panda/ir/base/classProperty.cpp @@ -14,7 +14,6 @@ */ #include "classProperty.h" -#include #include "checker/ETSchecker.h" #include "checker/TSchecker.h" @@ -179,10 +178,6 @@ void ClassProperty::DumpCheckerTypeForDeclGen(ir::SrcDumper *dumper) const } auto typeStr = TsType()->ToString(); - if (TsType()->IsTypeError() && dumper->IsIsolatedDeclgen() && typeAnnotation_ != nullptr) { - typeStr = typeAnnotation_->AsETSTypeReference()->Part()->Name()->AsIdentifier()->Name().Mutf8(); - } - dumper->Add(": "); dumper->Add(typeStr); diff --git a/ets2panda/ir/base/scriptFunction.cpp b/ets2panda/ir/base/scriptFunction.cpp index 0eb77cd6c8..396d22d082 100644 --- a/ets2panda/ir/base/scriptFunction.cpp +++ b/ets2panda/ir/base/scriptFunction.cpp @@ -182,8 +182,7 @@ void ScriptFunction::DumpCheckerTypeForDeclGen(ir::SrcDumper *dumper) const return; } - auto typeStr = dumper->IsIsolatedDeclgen() ? GetIsolatedDeclgenReturnType() : Signature()->ReturnType()->ToString(); - + auto typeStr = Signature()->ReturnType()->ToString(); dumper->Add(": "); dumper->Add(typeStr); @@ -297,8 +296,8 @@ void ScriptFunction::CopyTo(AstNode *other) const otherImpl->preferredReturnType_ = preferredReturnType_; otherImpl->lang_ = lang_; otherImpl->returnStatements_ = returnStatements_; - otherImpl->isolatedDeclGenInferType_ = isolatedDeclGenInferType_; JsDocAllowed>::CopyTo(other); } + } // namespace ark::es2panda::ir diff --git a/ets2panda/ir/base/scriptFunction.h b/ets2panda/ir/base/scriptFunction.h index 5651635642..c301d7d459 100644 --- a/ets2panda/ir/base/scriptFunction.h +++ b/ets2panda/ir/base/scriptFunction.h @@ -355,16 +355,6 @@ public: checker::Type *Check(checker::TSChecker *checker) override; checker::VerifiedType Check(checker::ETSChecker *checker) override; - void SetIsolatedDeclgenReturnType(std::string type) noexcept - { - isolatedDeclGenInferType_ = std::move(type); - } - - [[nodiscard]] std::string GetIsolatedDeclgenReturnType() const noexcept - { - return isolatedDeclGenInferType_; - } - void Accept(ASTVisitorT *v) override { v->Accept(this); @@ -394,7 +384,6 @@ private: checker::Type *preferredReturnType_ {}; es2panda::Language lang_; ArenaVector returnStatements_; - std::string isolatedDeclGenInferType_; }; } // namespace ark::es2panda::ir diff --git a/ets2panda/ir/srcDump.cpp b/ets2panda/ir/srcDump.cpp index 0002996a89..534ded77c3 100644 --- a/ets2panda/ir/srcDump.cpp +++ b/ets2panda/ir/srcDump.cpp @@ -31,9 +31,7 @@ SrcDumper::SrcDumper(const ir::AstNode *node) node->Dump(this); } -SrcDumper::SrcDumper(const ir::AstNode *node, bool isDeclgen, bool isIsolatedDeclgen) - : isDeclgen_(isDeclgen), isIsolatedDeclgen_(isIsolatedDeclgen) - +SrcDumper::SrcDumper(const ir::AstNode *node, bool isDeclgen) : isDeclgen_(isDeclgen) { node->Dump(this); } diff --git a/ets2panda/ir/srcDump.h b/ets2panda/ir/srcDump.h index f218ace82d..9d5ebd3440 100644 --- a/ets2panda/ir/srcDump.h +++ b/ets2panda/ir/srcDump.h @@ -42,7 +42,7 @@ using NodeVariant = class SrcDumper { public: explicit SrcDumper(const ir::AstNode *node); - explicit SrcDumper(const ir::AstNode *node, bool isDeclgen, bool isIsolatedDeclgen = false); + explicit SrcDumper(const ir::AstNode *node, bool isDeclgen); void Add(const std::string &str); void Add(int32_t i); @@ -60,10 +60,6 @@ public: void Endl(size_t num = 1); bool IsDeclgen() const; - bool IsIsolatedDeclgen() const - { - return isIsolatedDeclgen_; - } void DumpVariant(NodeVariant &node); void DumpNode(const std::string &key); @@ -98,7 +94,6 @@ private: std::stringstream ss_; std::string indent_; bool isDeclgen_ = false; - bool isIsolatedDeclgen_ = false; bool isIndirectDepPhase_ = false; std::unordered_map unExportNode_; diff --git a/ets2panda/parser/ETSparser.cpp b/ets2panda/parser/ETSparser.cpp index e5fdd5ac3e..130a3dc80d 100644 --- a/ets2panda/parser/ETSparser.cpp +++ b/ets2panda/parser/ETSparser.cpp @@ -139,11 +139,7 @@ void ETSParser::ParseProgram(ScriptKind kind) if ((GetContext().Status() & ParserStatus::IN_PACKAGE) != 0) { GetContext().Status() &= ~ParserStatus::IN_PACKAGE; } - - if (!GetOptions().IsGenerateDeclEnableIsolated()) { - AddExternalSource(ParseSources(true)); - } - + AddExternalSource(ParseSources(true)); GetProgram()->SetAst(script); } diff --git a/ets2panda/public/CMakeLists.txt b/ets2panda/public/CMakeLists.txt index 12227ac6fe..59a10c7855 100644 --- a/ets2panda/public/CMakeLists.txt +++ b/ets2panda/public/CMakeLists.txt @@ -624,6 +624,7 @@ add_custom_target(gen_yamls DEPENDS es2panda_options_gen es2panda_keywords ${ES2 set(ES2PANDA_PUBLIC_SOURCES ${LIB_NAME}.cpp ../declgen_ets2ts/declgenEts2Ts.cpp + ../declgen_ets2ts/isolatedDeclgenChecker.cpp ../util/generateBin.cpp ../util/options.cpp ../util/plugin.cpp diff --git a/ets2panda/public/es2panda_lib.cpp b/ets2panda/public/es2panda_lib.cpp index 68c404993f..29368792ee 100644 --- a/ets2panda/public/es2panda_lib.cpp +++ b/ets2panda/public/es2panda_lib.cpp @@ -325,7 +325,6 @@ __attribute__((unused)) static es2panda_Context *CreateContext(es2panda_Config * res->parser = new parser::ETSParser(res->parserProgram, *cfg->options, *cfg->diagnosticEngine, parser::ParserStatus::NO_OPTS); res->checker = new checker::ETSChecker(*res->diagnosticEngine); - res->isolatedDeclgenChecker = new checker::IsolatedDeclgenChecker(*res->diagnosticEngine, *(res->parserProgram)); res->analyzer = new checker::ETSAnalyzer(res->checker); res->checker->SetAnalyzer(res->analyzer); @@ -997,7 +996,8 @@ extern "C" es2panda_AstNode **AllDeclarationsByNameFromProgram([[maybe_unused]] extern "C" __attribute__((unused)) int GenerateTsDeclarationsFromContext(es2panda_Context *ctx, const char *outputDeclEts, - const char *outputEts, bool exportAll) + const char *outputEts, bool exportAll, + bool isolated) { auto *ctxImpl = reinterpret_cast(ctx); auto *checker = reinterpret_cast(ctxImpl->checker); @@ -1006,6 +1006,7 @@ extern "C" __attribute__((unused)) int GenerateTsDeclarationsFromContext(es2pand declgenOptions.exportAll = exportAll; declgenOptions.outputDeclEts = outputDeclEts ? outputDeclEts : ""; declgenOptions.outputEts = outputEts ? outputEts : ""; + declgenOptions.isolated = isolated; return ark::es2panda::declgen_ets2ts::GenerateTsDeclarations(checker, ctxImpl->parserProgram, declgenOptions) ? 0 : 1; @@ -1019,7 +1020,7 @@ extern "C" __attribute__((unused)) int GenerateStaticDeclarationsFromContext(es2 if (ctxImpl->state != ES2PANDA_STATE_CHECKED) { return 1; } - compiler::HandleGenerateDecl(*ctxImpl->parserProgram, *ctxImpl->diagnosticEngine, outputPath, false); + compiler::HandleGenerateDecl(*ctxImpl->parserProgram, *ctxImpl->diagnosticEngine, outputPath); return ctxImpl->diagnosticEngine->IsAnyError() ? 1 : 0; } diff --git a/ets2panda/public/es2panda_lib.h b/ets2panda/public/es2panda_lib.h index b331f56829..b5511c4ac5 100644 --- a/ets2panda/public/es2panda_lib.h +++ b/ets2panda/public/es2panda_lib.h @@ -252,7 +252,7 @@ struct CAPI_EXPORT es2panda_Impl { const char *name, size_t *declsLen); int (*GenerateTsDeclarationsFromContext)(es2panda_Context *context, const char *outputDeclEts, - const char *outputEts, bool exportAll); + const char *outputEts, bool exportAll, bool isolated); void (*InsertETSImportDeclarationAndParse)(es2panda_Context *context, es2panda_Program *program, es2panda_AstNode *importDeclaration); int (*GenerateStaticDeclarationsFromContext)(es2panda_Context *context, const char *outputPath); diff --git a/ets2panda/public/public.h b/ets2panda/public/public.h index fdb18d9ca6..2b543e3148 100644 --- a/ets2panda/public/public.h +++ b/ets2panda/public/public.h @@ -25,7 +25,6 @@ #include "compiler/core/compileQueue.h" #include "parser/ETSparser.h" #include "checker/checker.h" -#include "checker/IsolatedDeclgenChecker.h" #include "compiler/core/emitter.h" namespace ark::es2panda::util { @@ -174,8 +173,6 @@ struct Context { parser::Program *parserProgram = nullptr; parser::ParserImpl *parser = nullptr; checker::Checker *checker = nullptr; - checker::IsolatedDeclgenChecker *isolatedDeclgenChecker = nullptr; - checker::SemanticAnalyzer *analyzer = nullptr; compiler::Emitter *emitter = nullptr; pandasm::Program *program = nullptr; diff --git a/ets2panda/test/isolated_declgen/infer_function_return_type_with_import_symbol-expected.txt b/ets2panda/test/isolated_declgen/infer_function_return_type_with_import_symbol-expected.txt deleted file mode 100644 index 1804ab1e7b..0000000000 --- a/ets2panda/test/isolated_declgen/infer_function_return_type_with_import_symbol-expected.txt +++ /dev/null @@ -1,26 +0,0 @@ -/** - * Copyright (c) 2025 Huawei Device Co., Ltd. - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -import A from "./infer_function_return_type_with_literal.ets"; - -import B from "./infer_function_return_type_with_literal.ets"; - -import C from "./infer_function_return_type_with_literal.ets"; - -export declare let b: A; - -export default declare let d: int; - -export declare function foo(a: int, c: C): A | Array | Array | Array | B | Number | String; \ No newline at end of file diff --git a/ets2panda/test/isolated_declgen/infer_function_return_type_with_literal-expected.txt b/ets2panda/test/isolated_declgen/infer_function_return_type_with_literal-expected.txt deleted file mode 100644 index 0580538547..0000000000 --- a/ets2panda/test/isolated_declgen/infer_function_return_type_with_literal-expected.txt +++ /dev/null @@ -1,16 +0,0 @@ -/** - * Copyright (c) 2025 Huawei Device Co., Ltd. - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - - export declare function foo(a: int): Int|Boolean|String; \ No newline at end of file diff --git a/ets2panda/test/isolated_declgen/infer_function_return_type_with_variable-expected.txt b/ets2panda/test/isolated_declgen/infer_function_return_type_with_variable-expected.txt deleted file mode 100644 index 6eced86611..0000000000 --- a/ets2panda/test/isolated_declgen/infer_function_return_type_with_variable-expected.txt +++ /dev/null @@ -1,16 +0,0 @@ -/** - * Copyright (c) 2025 Huawei Device Co., Ltd. - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - - export declare function foo(a: int): String|B|Int|A; \ No newline at end of file diff --git a/ets2panda/test/isolated_declgen/isolated_interface-expected.txt b/ets2panda/test/isolated_declgen/isolated_interface-expected.txt deleted file mode 100644 index 029658ebdd..0000000000 --- a/ets2panda/test/isolated_declgen/isolated_interface-expected.txt +++ /dev/null @@ -1,36 +0,0 @@ -/** - * Copyright (c) 2025 Huawei Device Co., Ltd. - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -export declare interface User { - set id(id: number): void; - - get id(): double; - set name(name: string): void; - - get name(): String; - set age(age: number | undefined): void; - - get age(): Double|undefined; - get apiUrl(): String; - -} - -export declare interface Animal { - set name(name: string): void; - - get name(): String; - makeSound(): void; - -} \ No newline at end of file diff --git a/ets2panda/test/isolated_declgen/isolated_namespace-expected.txt b/ets2panda/test/isolated_declgen/isolated_namespace-expected.txt deleted file mode 100644 index c5d5aa7784..0000000000 --- a/ets2panda/test/isolated_declgen/isolated_namespace-expected.txt +++ /dev/null @@ -1,25 +0,0 @@ -/** - * Copyright (c) 2025 Huawei Device Co., Ltd. - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - - export declare namespace MathOperations { - - let PI: double; - - function add(a: number, b: number): double; - - function subtract(a: number, b: number): double; - - -} \ No newline at end of file diff --git a/ets2panda/test/unit/CMakeLists.txt b/ets2panda/test/unit/CMakeLists.txt index 07663a9a29..c84184cf5f 100644 --- a/ets2panda/test/unit/CMakeLists.txt +++ b/ets2panda/test/unit/CMakeLists.txt @@ -16,6 +16,7 @@ if(NOT PANDA_REGRESSION_TESTS) endif() add_subdirectory(cfg) +add_subdirectory(declgen) add_subdirectory(dynamic) add_subdirectory(lowerings) add_subdirectory(public) diff --git a/ets2panda/test/unit/declgen/CMakeLists.txt b/ets2panda/test/unit/declgen/CMakeLists.txt new file mode 100644 index 0000000000..30dc08da1c --- /dev/null +++ b/ets2panda/test/unit/declgen/CMakeLists.txt @@ -0,0 +1,90 @@ +# Copyright (c) 2025 Huawei Device Co., Ltd. +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +if (PANDA_ENABLE_ADDRESS_SANITIZER OR PANDA_ENABLE_THREAD_SANITIZER) + return() +endif() + +set(COMMON_SOURCE_FILES + "util.cpp" +) + +set(DECLGEN_PLUGIN_TESTS + "test_ets2ts_isolated_declgen cpp" +) + +set(ETS2TS_ISOLATED_TESTS + "./ets2ts_isolated/test_ets2ts_isolated_class.ets" + "./ets2ts_isolated/test_ets2ts_isolated_enum.ets" + "./ets2ts_isolated/test_ets2ts_isolated_module.ets" + "./ets2ts_isolated/test_ets2ts_isolated_namespace.ets" + "./ets2ts_isolated/test_ets2ts_isolated_interface.ets" + "./ets2ts_isolated/test_ets2ts_isolated_function_with_optional_parameter.ets" + "./ets2ts_isolated/test_ets2ts_infer_function_return_type_with_import_symbol.ets" +) + +foreach(TEST_DATA IN ITEMS ${DECLGEN_PLUGIN_TESTS}) + string(REPLACE " " ";" TEST_DATA_ELEM "${TEST_DATA}") + list(GET TEST_DATA_ELEM 0 TEST_NAME) + list(GET TEST_DATA_ELEM 1 EXTENSION) + + panda_add_executable(${TEST_NAME} ${TEST_NAME}.${EXTENSION} ${COMMON_SOURCE_FILES} OUTPUT_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}) + panda_add_sanitizers(TARGET ${TEST_NAME} SANITIZERS ${PANDA_SANITIZERS_LIST}) + + panda_target_include_directories(${TEST_NAME} + PRIVATE ${ES2PANDA_PATH} + PRIVATE ${PANDA_ROOT}/libpandafile + PRIVATE ${PANDA_ROOT}/assembler + PRIVATE ${OUTPUT_DIR} + PUBLIC ${CMAKE_CURRENT_BINARY_DIR} + PUBLIC ${CMAKE_CURRENT_SOURCE_DIR} + PUBLIC ${CMAKE_SOURCE_DIR}/libpandabase + PUBLIC ${CMAKE_SOURCE_DIR}/runtime + PUBLIC ${CMAKE_BINARY_DIR}/libpandabase + PUBLIC ${CMAKE_BINARY_DIR}/libpandafile/include + ${CMAKE_BINARY_DIR} + ) + panda_target_link_libraries(${TEST_NAME} es2panda-public arkassembler arkbase arkfile) +endforeach() + +add_custom_target(es2panda-declgen-plugin-test) + +set(ETS2TS "ets2ts_isolated") +foreach(TEST_DATA IN ITEMS ${DECLGEN_PLUGIN_TESTS}) + string(REPLACE " " ";" TEST_DATA_ELEM "${TEST_DATA}") + list(GET TEST_DATA_ELEM 0 TEST_NAME) + list(GET TEST_DATA_ELEM 1 EXTENSION) + foreach(TEST_ETS_FILE IN ITEMS ${ETS2TS_ISOLATED_TESTS}) + cmake_path(SET PATH_ITEM "${TEST_ETS_FILE}") + cmake_path(GET PATH_ITEM STEM FILE_NAME) + add_custom_target(es2panda-declgen-plugin-test-compile-${FILE_NAME} + COMMAND ${CMAKE_COMMAND} -E env + LD_LIBRARY_PATH=${CMAKE_LIBRARY_OUTPUT_DIRECTORY} ${PANDA_RUN_PREFIX} + ${CMAKE_CURRENT_BINARY_DIR}/${TEST_NAME} $ + --extension=ets --ets-unnamed --output="${CMAKE_CURRENT_BINARY_DIR}/${FILE_NAME}.abc" + "${CMAKE_CURRENT_SOURCE_DIR}/${TEST_ETS_FILE}" > "${CMAKE_CURRENT_BINARY_DIR}/${FILE_NAME}.out" 2>&1 + ) + message(STATUS "${CMAKE_CURRENT_BINARY_DIR}/${FILE_NAME}.abc") + add_dependencies(es2panda-declgen-plugin-test-compile-${FILE_NAME} es2panda ${TEST_NAME} es2panda-lib) + add_dependencies(es2panda-declgen-plugin-test es2panda-declgen-plugin-test-compile-${FILE_NAME}) + + add_custom_target(es2panda-declgen-plugin-test-expected-${FILE_NAME} + COMMAND ${CMAKE_COMMAND} -E compare_files + "${CMAKE_CURRENT_BINARY_DIR}/${FILE_NAME}.d.ets" "${CMAKE_CURRENT_SOURCE_DIR}/${ETS2TS}/${FILE_NAME}-expected.txt" + ) + add_dependencies(es2panda-declgen-plugin-test-expected-${FILE_NAME} es2panda-declgen-plugin-test-compile-${FILE_NAME} es2panda-lib) + add_dependencies(es2panda-declgen-plugin-test es2panda-declgen-plugin-test-expected-${FILE_NAME}) + endforeach() +endforeach() + +add_dependencies(es2panda_tests es2panda-declgen-plugin-test) \ No newline at end of file diff --git a/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_infer_function_return_type_with_import_symbol-expected.txt b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_infer_function_return_type_with_import_symbol-expected.txt new file mode 100644 index 0000000000..f4ecd41313 --- /dev/null +++ b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_infer_function_return_type_with_import_symbol-expected.txt @@ -0,0 +1,7 @@ +import A from "./infer_function_return_type_with_literal"; +import B from "./infer_function_return_type_with_literal"; +import C from "./infer_function_return_type_with_literal"; +export declare let b: A; +declare let d: number; +export default d; +export declare function foo(a: number, c: C): A | Array | Array | Array | B | number | string; diff --git a/ets2panda/test/isolated_declgen/infer_function_return_type_with_import_symbol.ets b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_infer_function_return_type_with_import_symbol.ets similarity index 99% rename from ets2panda/test/isolated_declgen/infer_function_return_type_with_import_symbol.ets rename to ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_infer_function_return_type_with_import_symbol.ets index 6acccddadf..96ef59e9df 100644 --- a/ets2panda/test/isolated_declgen/infer_function_return_type_with_import_symbol.ets +++ b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_infer_function_return_type_with_import_symbol.ets @@ -43,8 +43,4 @@ export function foo(a: int, c: C) } return "hello"; -} - - - - +} \ No newline at end of file diff --git a/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_class-expected.txt b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_class-expected.txt new file mode 100644 index 0000000000..4ad14cb500 --- /dev/null +++ b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_class-expected.txt @@ -0,0 +1,18 @@ +export declare interface I0 { + I0Method(a: string): string; +} +export declare interface I1 { + I1Method(a: number): number; +} +export declare class Base { + public get a(): number; + public set a(value: number); + public constructor(a: number); +} +export declare class Derived extends Base implements I0, I1 { + public I0Method(a: string): string; + public I1Method(a: number): number; + public get b(): number; + public set b(value: number); + public constructor(a: number, b: number); +} diff --git a/ets2panda/test/isolated_declgen/isolated_class.ets b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_class.ets similarity index 100% rename from ets2panda/test/isolated_declgen/isolated_class.ets rename to ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_class.ets diff --git a/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_enum-expected.txt b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_enum-expected.txt new file mode 100644 index 0000000000..ae0a088911 --- /dev/null +++ b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_enum-expected.txt @@ -0,0 +1,11 @@ +export declare enum Direction { + Up = 0, + Down = 1, + Left = 2, + Right = 3, +} +export declare enum Message { + Success = "SUCCESS", + Failure = "FAILURE", + Pending = "PENDING", +} diff --git a/ets2panda/test/isolated_declgen/isolated_function_with_optional_parameter-expected.txt b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_enum.ets similarity index 80% rename from ets2panda/test/isolated_declgen/isolated_function_with_optional_parameter-expected.txt rename to ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_enum.ets index 5276a1c1bd..045fe8db94 100644 --- a/ets2panda/test/isolated_declgen/isolated_function_with_optional_parameter-expected.txt +++ b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_enum.ets @@ -12,7 +12,15 @@ * See the License for the specific language governing permissions and * limitations under the License. */ +export enum Direction { + Up, + Down, + Left, + Right +} -export declare function greet(name: string, age?: number): String; - -export declare function multiply(x: number, gensym%%_1?: number): double; \ No newline at end of file +export enum Message { + Success = "SUCCESS", + Failure = "FAILURE", + Pending = "PENDING" +} \ No newline at end of file diff --git a/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_function_with_optional_parameter-expected.txt b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_function_with_optional_parameter-expected.txt new file mode 100644 index 0000000000..602c65d87e --- /dev/null +++ b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_function_with_optional_parameter-expected.txt @@ -0,0 +1,2 @@ +export declare function greet(name: string, age?: number): string; +export declare function multiply(x: number, y?: number): number; diff --git a/ets2panda/test/isolated_declgen/isolated_function_with_optional_parameter.ets b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_function_with_optional_parameter.ets similarity index 100% rename from ets2panda/test/isolated_declgen/isolated_function_with_optional_parameter.ets rename to ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_function_with_optional_parameter.ets diff --git a/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_interface-expected.txt b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_interface-expected.txt new file mode 100644 index 0000000000..40f1e96753 --- /dev/null +++ b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_interface-expected.txt @@ -0,0 +1,14 @@ +export declare interface User { + get id(): number; + set id(value: number); + get name(): string; + set name(value: string); + get age(): number | undefined; + set age(value: number | undefined); + get apiUrl(): string; +} +export declare interface Animal { + get name(): string; + set name(value: string); + makeSound(): void; +} diff --git a/ets2panda/test/isolated_declgen/isolated_interface.ets b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_interface.ets similarity index 99% rename from ets2panda/test/isolated_declgen/isolated_interface.ets rename to ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_interface.ets index 828c677385..1b27d21ef4 100644 --- a/ets2panda/test/isolated_declgen/isolated_interface.ets +++ b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_interface.ets @@ -12,7 +12,7 @@ * See the License for the specific language governing permissions and * limitations under the License. */ - + export interface User { id: number; name: string; diff --git a/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_module-expected.txt b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_module-expected.txt new file mode 100644 index 0000000000..a6f0fc49ca --- /dev/null +++ b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_module-expected.txt @@ -0,0 +1,6 @@ +import * as np from "./infer_function_return_type_with_literal"; +import { B, C0 as C } from "./hello"; +export declare let b: np.A; +declare let d: number; +export default d; +export declare function foo(a: number, c: C): Array | Array | Array | B | np.A | number | string; diff --git a/ets2panda/test/isolated_declgen/infer_function_return_type_with_variable.ets b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_module.ets similarity index 63% rename from ets2panda/test/isolated_declgen/infer_function_return_type_with_variable.ets rename to ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_module.ets index 4a19a2de33..cc1bb38b39 100644 --- a/ets2panda/test/isolated_declgen/infer_function_return_type_with_variable.ets +++ b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_module.ets @@ -13,20 +13,33 @@ * limitations under the License. */ -class A {} -class B {} +import * as np from "./infer_function_return_type_with_literal.ets" +import {B, C0 as C} from "./hello.ets" -export function foo(a: int) +export let b: np.A = new np.A + +export default let d: int = 1 + +export function foo(a: int, c: C) { if (a < 0) { return 1; } if (a == 0) { - return new A; + return b; } - if (a > 0) { + if (a == 1) { return new B; } + if (a == 2) { + return ["hello", "arkts"]; + } + if (a == 3) { + return [0, 1, 2]; + } + if (a == 4) { + return [true, false, false, true]; + } return "hello"; } \ No newline at end of file diff --git a/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_namespace-expected.txt b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_namespace-expected.txt new file mode 100644 index 0000000000..d0ac8cfd8a --- /dev/null +++ b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_namespace-expected.txt @@ -0,0 +1,5 @@ +export declare namespace MathOperations { + const PI: number; + function add(a: number, b: number): number; + function subtract(a: number, b: number): number; +} diff --git a/ets2panda/test/isolated_declgen/isolated_namespace.ets b/ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_namespace.ets similarity index 100% rename from ets2panda/test/isolated_declgen/isolated_namespace.ets rename to ets2panda/test/unit/declgen/ets2ts_isolated/test_ets2ts_isolated_namespace.ets diff --git a/ets2panda/test/isolated_declgen/infer_function_return_type_with_literal.ets b/ets2panda/test/unit/declgen/test_ets2ts_isolated_declgen.cpp similarity index 31% rename from ets2panda/test/isolated_declgen/infer_function_return_type_with_literal.ets rename to ets2panda/test/unit/declgen/test_ets2ts_isolated_declgen.cpp index 00375f7d6e..51a6f716d1 100644 --- a/ets2panda/test/isolated_declgen/infer_function_return_type_with_literal.ets +++ b/ets2panda/test/unit/declgen/test_ets2ts_isolated_declgen.cpp @@ -12,18 +12,58 @@ * See the License for the specific language governing permissions and * limitations under the License. */ - -export function foo(a: int) + +#include +#include +#include + +#include "os/library_loader.h" + +#include "public/es2panda_lib.h" +#include "./util.h" + +// NOLINTBEGIN + +static es2panda_Impl *impl = nullptr; + +int main(int argc, char **argv) { - if (a < 0) { - return 1; + if (argc < MIN_ARGC) { + return INVALID_ARGC_ERROR_CODE; } - if (a == 0) { - return "hello"; + + if (GetImpl() == nullptr) { + return NULLPTR_IMPL_ERROR_CODE; } - if (a > 0) { - return true; + impl = GetImpl(); + std::cout << "LOAD SUCCESS" << std::endl; + + const char **args = const_cast(&(argv[1])); + auto config = impl->CreateConfig(argc - 1, args); + auto context = impl->CreateContextFromFile(config, argv[argc - 1]); + if (context == nullptr) { + std::cerr << "FAILED TO CREATE CONTEXT" << std::endl; + return NULLPTR_CONTEXT_ERROR_CODE; } - + + impl->ProceedToState(context, ES2PANDA_STATE_PARSED); + CheckForErrors("PARSE", context); + + impl->ProceedToState(context, ES2PANDA_STATE_BOUND); + CheckForErrors("BOUND", context); + + impl->ProceedToState(context, ES2PANDA_STATE_CHECKED); + CheckForErrors("CHECKED", context); + std::string declName = GetDeclPrefix(argv[argc - 1]) + ".d.ets"; + int result = impl->GenerateTsDeclarationsFromContext(context, declName.c_str(), "dump.ets", false, true); + if (result != 0) { + std::cerr << "FAILED TO GENERATE DECLARATIONS" << std::endl; + return result; + } + + impl->DestroyConfig(config); + return 0; -} \ No newline at end of file +} + +// NOLINTEND diff --git a/ets2panda/test/unit/declgen/util.cpp b/ets2panda/test/unit/declgen/util.cpp new file mode 100644 index 0000000000..ed872305b2 --- /dev/null +++ b/ets2panda/test/unit/declgen/util.cpp @@ -0,0 +1,83 @@ +/** + * Copyright (c) 2025 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "util.h" +#include +#include +#include +#include +#include +#include +#include "macros.h" + +static es2panda_Impl *g_implPtr = nullptr; + +es2panda_Impl *GetImpl() +{ + if (g_implPtr != nullptr) { + return g_implPtr; + } + + std::string soName = ark::os::library_loader::DYNAMIC_LIBRARY_PREFIX + std::string("es2panda-public") + + ark::os::library_loader::DYNAMIC_LIBRARY_SUFFIX; + auto libraryRes = ark::os::library_loader::Load(soName); + if (!libraryRes.HasValue()) { + std::cout << "Error in load lib" << std::endl; + return nullptr; + } + + auto library = std::move(libraryRes.Value()); + auto getImpl = ark::os::library_loader::ResolveSymbol(library, "es2panda_GetImpl"); + if (!getImpl.HasValue()) { + std::cout << "Error in load func get g_implPtr" << std::endl; + return nullptr; + } + + auto getImplFunc = reinterpret_cast(getImpl.Value()); + if (getImplFunc != nullptr) { + g_implPtr = const_cast(getImplFunc(ES2PANDA_LIB_VERSION)); + return g_implPtr; + } + return nullptr; +} + +void CheckForErrors(const std::string &stateName, es2panda_Context *context) +{ + if (g_implPtr->ContextState(context) == ES2PANDA_STATE_ERROR) { + std::cout << "PROCEED TO " << stateName << " ERROR" << std::endl; + std::cout << g_implPtr->ContextErrorMessage(context) << std::endl; + } else { + std::cout << "PROCEED TO " << stateName << " SUCCESS" << std::endl; + } +} + +std::string GetDeclPrefix(const char *etsSrcName) +{ + if (etsSrcName == nullptr) { + return ""; + } + std::string_view etsSrc(etsSrcName); + auto pos = etsSrc.find_last_of('/'); + if (pos != std::string_view::npos) { + etsSrc = etsSrc.substr(pos + 1); + } + std::cout << "ETS SRC: " << etsSrc << std::endl; + pos = etsSrc.find_last_of('.'); + if (pos != std::string_view::npos) { + etsSrc = etsSrc.substr(0, pos); + } + std::cout << "ETS SRC PREFIX: " << etsSrc << std::endl; + return std::string(etsSrc); +} \ No newline at end of file diff --git a/ets2panda/test/isolated_declgen/isolated_class-expected.txt b/ets2panda/test/unit/declgen/util.h similarity index 43% rename from ets2panda/test/isolated_declgen/isolated_class-expected.txt rename to ets2panda/test/unit/declgen/util.h index 5ee4f26785..d4c678d9ad 100644 --- a/ets2panda/test/isolated_declgen/isolated_class-expected.txt +++ b/ets2panda/test/unit/declgen/util.h @@ -13,30 +13,34 @@ * limitations under the License. */ -export declare interface I0 { - I0Method(a: string): String; +#ifndef ES2PANDA_TEST_UNIT_DECLGEN_PLUGIN_UTIL_H +#define ES2PANDA_TEST_UNIT_DECLGEN_PLUGIN_UTIL_H -} +#include +#include +#include +#include +#include -export declare interface I1 { - I1Method(a: double): double; +#include "os/library_loader.h" -} +#include "public/es2panda_lib.h" -export declare class Base { - public a: double; +constexpr int MIN_ARGC = 3; - public constructor(a: double); +// error code number +constexpr int NULLPTR_IMPL_ERROR_CODE = 2; +constexpr int PROCEED_ERROR_CODE = 3; +constexpr int TEST_ERROR_CODE = 4; +constexpr int INVALID_ARGC_ERROR_CODE = 5; +constexpr int NULLPTR_CONTEXT_ERROR_CODE = 6; -} +es2panda_Impl *GetImpl(); +void CheckForErrors(const std::string &stateName, es2panda_Context *context); -export declare class Derived extends Base implements I0, I1 { - public I0Method(a: string): String; +es2panda_AstNode *GetETSGlobalClass(es2panda_Context *ctx, es2panda_AstNode *rootNode); - public I1Method(a: double): double; +// CC-OFFNXT(G.NAM.01) false positive +std::string GetDeclPrefix(const char *etsSrcName); - public b: double; - - public constructor(a: double, b: double); - -} \ No newline at end of file +#endif \ No newline at end of file diff --git a/ets2panda/test/unit/sizeof_node_test.cpp b/ets2panda/test/unit/sizeof_node_test.cpp index 428a6010b7..1d94f3d732 100644 --- a/ets2panda/test/unit/sizeof_node_test.cpp +++ b/ets2panda/test/unit/sizeof_node_test.cpp @@ -281,8 +281,7 @@ size_t SizeOfNodeTest::SizeOf() sizeof(node->signature_) + sizeof(node->preferredReturnType_) + Align(sizeof(node->lang_)) + - sizeof(node->returnStatements_) + - sizeof(node->isolatedDeclGenInferType_); + sizeof(node->returnStatements_); // clang-format on } diff --git a/ets2panda/util/diagnostic.cpp b/ets2panda/util/diagnostic.cpp index 40b71f1e63..8104e2ad61 100644 --- a/ets2panda/util/diagnostic.cpp +++ b/ets2panda/util/diagnostic.cpp @@ -166,12 +166,12 @@ const char *DiagnosticTypeToString(DiagnosticType type) return "Declgen ets2ts error"; case DiagnosticType::DECLGEN_ETS2TS_WARNING: return "Declgen ets2ts warning"; + case DiagnosticType::ISOLATED_DECLGEN: + return "Isolated declgen error"; case DiagnosticType::ARKTS_CONFIG_ERROR: return "ArkTS config error"; case DiagnosticType::SUGGESTION: return "SUGGESTION"; - case DiagnosticType::ISOLATED_DECLGEN: - return "Isolated declgen error"; default: ES2PANDA_UNREACHABLE(); } diff --git a/ets2panda/util/diagnostic.h b/ets2panda/util/diagnostic.h index cb4c70a256..40584dac1c 100644 --- a/ets2panda/util/diagnostic.h +++ b/ets2panda/util/diagnostic.h @@ -50,9 +50,9 @@ enum DiagnosticType { PLUGIN_WARNING, DECLGEN_ETS2TS_ERROR, DECLGEN_ETS2TS_WARNING, + ISOLATED_DECLGEN, ARKTS_CONFIG_ERROR, SUGGESTION, - ISOLATED_DECLGEN, COUNT, INVALID = COUNT }; diff --git a/ets2panda/util/diagnosticEngine.cpp b/ets2panda/util/diagnosticEngine.cpp index 131ca76cf8..dbd74ca4e8 100644 --- a/ets2panda/util/diagnosticEngine.cpp +++ b/ets2panda/util/diagnosticEngine.cpp @@ -114,8 +114,8 @@ bool DiagnosticEngine::IsError(DiagnosticType type) const case DiagnosticType::SEMANTIC: case DiagnosticType::PLUGIN_ERROR: case DiagnosticType::DECLGEN_ETS2TS_ERROR: - case DiagnosticType::ARKTS_CONFIG_ERROR: case DiagnosticType::ISOLATED_DECLGEN: + case DiagnosticType::ARKTS_CONFIG_ERROR: return true; case DiagnosticType::WARNING: case DiagnosticType::DECLGEN_ETS2TS_WARNING: diff --git a/ets2panda/util/options.yaml b/ets2panda/util/options.yaml index 3dab3459f6..5cf3fc0cae 100644 --- a/ets2panda/util/options.yaml +++ b/ets2panda/util/options.yaml @@ -182,10 +182,6 @@ options: type: std::string default: "" description: Output path for generated static declaration files - - name: enable-isolated - type: bool - default: false - description: Whether to enable isolated declaration file generation - name: thread type: int diff --git a/ets2panda/varbinder/ETSBinder.cpp b/ets2panda/varbinder/ETSBinder.cpp index 0f9ae6db10..b2303e9097 100644 --- a/ets2panda/varbinder/ETSBinder.cpp +++ b/ets2panda/varbinder/ETSBinder.cpp @@ -154,10 +154,7 @@ void ETSBinder::LookupTypeReference(ir::Identifier *ident, bool allowDynamicName return; } - if (!GetContext()->config->options->IsGenerateDeclEnableIsolated()) { - ThrowUnresolvableType(ident->Start(), name); - } - + ThrowUnresolvableType(ident->Start(), name); CreateDummyVariable(this, ident); } @@ -1001,10 +998,8 @@ varbinder::Variable *ETSBinder::FindStaticBinding(Span r if (result != nullptr) { return result; } - if (!GetContext()->config->options->IsGenerateDeclEnableIsolated()) { - ThrowError(importPath->Start(), diagnostic::DEFAULT_IMPORT_NOT_FOUND); - } + ThrowError(importPath->Start(), diagnostic::DEFAULT_IMPORT_NOT_FOUND); return nullptr; } -- Gitee From 4995a2550abd7808c4c0b8949f11cf39f7829749 Mon Sep 17 00:00:00 2001 From: xuxinjie4 Date: Mon, 2 Jun 2025 00:13:57 +0800 Subject: [PATCH 2/2] Fix log decl bug Issue: https://gitee.com/openharmony/arkcompiler_ets_frontend/issues/ICBVWC?from=project-issue Signed-off-by: xuxinjie4 --- .../compiler/ets/external_local_interface.ets | 18 +++++++++++++++ .../ets/external_local_interface_decl.ets | 22 +++++++++++++++++++ .../srcdumper/srcdumper-ets-ignored.txt | 1 + ets2panda/varbinder/varbinder.cpp | 13 +++++++++++ 4 files changed, 54 insertions(+) create mode 100644 ets2panda/test/ast/compiler/ets/external_local_interface.ets create mode 100644 ets2panda/test/ast/compiler/ets/external_local_interface_decl.ets diff --git a/ets2panda/test/ast/compiler/ets/external_local_interface.ets b/ets2panda/test/ast/compiler/ets/external_local_interface.ets new file mode 100644 index 0000000000..b17d69c20e --- /dev/null +++ b/ets2panda/test/ast/compiler/ets/external_local_interface.ets @@ -0,0 +1,18 @@ +/* + * Copyright (c) 2025 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +import {foo} from "./external_local_interface_decl" + + diff --git a/ets2panda/test/ast/compiler/ets/external_local_interface_decl.ets b/ets2panda/test/ast/compiler/ets/external_local_interface_decl.ets new file mode 100644 index 0000000000..891e84f1a8 --- /dev/null +++ b/ets2panda/test/ast/compiler/ets/external_local_interface_decl.ets @@ -0,0 +1,22 @@ +/* + * Copyright (c) 2025 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +export function foo() { + interface A{ + s:string + } + + let a:A = {s:""} +} \ No newline at end of file diff --git a/ets2panda/test/test-lists/srcdumper/srcdumper-ets-ignored.txt b/ets2panda/test/test-lists/srcdumper/srcdumper-ets-ignored.txt index 42b02135c1..cff206ab65 100644 --- a/ets2panda/test/test-lists/srcdumper/srcdumper-ets-ignored.txt +++ b/ets2panda/test/test-lists/srcdumper/srcdumper-ets-ignored.txt @@ -159,6 +159,7 @@ runtime/ets/import_declare_type_alias.ets ast/compiler/ets/import_type_without_export.ets ast/compiler/ets/type_binding_01.ets ast/compiler/ets/type_binding_02.ets +ast/compiler/ets/external_local_interface.ets # FailKind.ES2PANDA_FAIL runtime/ets/StringFasta.ets diff --git a/ets2panda/varbinder/varbinder.cpp b/ets2panda/varbinder/varbinder.cpp index 0504029b7b..d08635be49 100644 --- a/ets2panda/varbinder/varbinder.cpp +++ b/ets2panda/varbinder/varbinder.cpp @@ -470,6 +470,19 @@ void VarBinder::VisitScriptFunction(ir::ScriptFunction *func) } if (!BuildInternalName(func)) { + if (func->Body() == nullptr) { + return; + } + auto stmt = func->Body()->AsBlockStatement()->Statements(); + auto scopeCtx = LexicalScope::Enter(this, funcScope); + std::function doNode = [&](ir::AstNode *node) { + if (node->IsTSInterfaceDeclaration() || node->IsClassDeclaration() || node->IsTSEnumDeclaration() || + node->IsAnnotationDeclaration() || node->IsTSTypeAliasDeclaration()) { + ResolveReference(node); + } + node->Iterate([&](ir::AstNode *child) { doNode(child); }); + }; + doNode(func->Body()); return; } -- Gitee