swiftlang / swift

The Swift Programming Language
https://swift.org
Apache License 2.0
67.29k stars 10.33k forks source link

Recursive generics cause infinite recursion #70625

Open nickolas-pohilets opened 8 months ago

nickolas-pohilets commented 8 months ago

Description

Recursive generics cause infinite recursion when deserialising .swiftmodule file.

Reproduction

// badaboom.swift
protocol Tree: AnyObject {}
class TreeBase<Child: Tree> {}
final class AlphaTree: TreeBase<BetaTree>, Tree {}
final class BetaTree: TreeBase<AlphaTree>, Tree {}
# DEBUG_BUILD_DIR=.../swift-project/build/Ninja+cmark-DebugAssert+llvm-RelWithDebInfoAssert+swift-DebugAssert+stdlib-DebugAssert/swift-macosx-arm64
SDKROOT=/Applications/Xcode-15.0.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk \
    $DEBUG_BUILD_DIR/bin/swiftc \
        -target arm64-apple-macosx10.13 \
        -F /Applications/Xcode-15.1.app/Contents/Developer/Platforms/MacOSX.platform/Developer/Library/Frameworks \
        -toolchain-stdlib-rpath \
        -Xlinker \
        -rpath \
        -Xlinker /Applications/Xcode-15.1.app/Contents/Developer/Platforms/MacOSX.platform/Developer/Library/Frameworks \
        -Xlinker \
        -rpath \
        -Xlinker /usr/lib/swift \
        -Xlinker \
        -headerpad_max_install_names \
        -swift-version 4 \
        -parse-as-library \
        -F $DEBUG_BUILD_DIR/lib \
        -Xlinker \
        -rpath \
        -Xlinker $DEBUG_BUILD_DIR/lib \
        badaboom.swift \
        -Xfrontend \
        -disable-availability-checking \
        -g \
        -Onone \
        -o ./badaboom.out \
        -module-name main

Stack dump

Please submit a bug report (https://swift.org/contributing/#reporting-bugs) and include the crash backtrace.
Stack dump:
0.  Program arguments: $DEBUG_BUILD_DIR/bin/swift-frontend -frontend -merge-modules -emit-module /var/folders/f6/qllm_pk56m56tdvyx0g_4d3m0000gp/T/badaboom-a1ac7a.swiftmodule -parse-as-library -disable-diagnostic-passes -disable-sil-perf-optzns -target arm64-apple-macosx10.13 -Xllvm -aarch64-use-tbi -enable-objc-interop -sdk /Applications/Xcode-15.0.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk -F /Applications/Xcode-15.1.app/Contents/Developer/Platforms/MacOSX.platform/Developer/Library/Frameworks -F $DEBUG_BUILD_DIR/lib -g -swift-version 4 -Onone -disable-availability-checking -enable-anonymous-context-mangled-names -external-plugin-path /Applications/Xcode-15.0.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/usr/lib/swift/host/plugins#/Applications/Xcode-15.0.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/usr/bin/swift-plugin-server -external-plugin-path /Applications/Xcode-15.0.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/usr/local/lib/swift/host/plugins#/Applications/Xcode-15.0.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/usr/bin/swift-plugin-server -external-plugin-path /Applications/Xcode-15.0.app/Contents/Developer/Platforms/MacOSX.platform/Developer/usr/lib/swift/host/plugins#/Applications/Xcode-15.0.app/Contents/Developer/Platforms/MacOSX.platform/Developer/usr/bin/swift-plugin-server -external-plugin-path /Applications/Xcode-15.0.app/Contents/Developer/Platforms/MacOSX.platform/Developer/usr/local/lib/swift/host/plugins#/Applications/Xcode-15.0.app/Contents/Developer/Platforms/MacOSX.platform/Developer/usr/bin/swift-plugin-server -plugin-path $DEBUG_BUILD_DIR/lib/swift/host/plugins -plugin-path $DEBUG_BUILD_DIR/local/lib/swift/host/plugins -target-sdk-version 14.0 -dwarf-version=4 -emit-module-doc-path /var/folders/f6/qllm_pk56m56tdvyx0g_4d3m0000gp/T/main-091c70.swiftdoc -emit-module-source-info-path /var/folders/f6/qllm_pk56m56tdvyx0g_4d3m0000gp/T/main-091c70.swiftsourceinfo -module-name main -o /var/folders/f6/qllm_pk56m56tdvyx0g_4d3m0000gp/T/main-091c70.swiftmodule
1.  Swift version 5.11-dev (LLVM 8be112bb7e107a9, Swift df858a5ab96c574)
2.  Compiling with effective version 4.1.50
3.  While evaluating request ExecuteSILPipelineRequest(Run pipelines { Non-Diagnostic Mandatory Optimizations, Serialization, Rest of Onone } on SIL for main)
4.  While running pass #1 SILModuleTransform "SerializeSILPass".
5.  While reading from module 'main', builder version '5.11(4.1.50)/Swift version 5.11-dev (LLVM 8be112bb7e107a9, Swift df858a5ab96c574)', built from source, non-resilient, loaded from '/var/folders/f6/qllm_pk56m56tdvyx0g_4d3m0000gp/T/badaboom-a1ac7a.swiftmodule'
6.  While deserializing decl @ 124968 (CLASS_DECL) in 'main'
7.      ...decl is named 'AlphaTree'
8.  While deserializing decl @ 125436 (CLASS_DECL) in 'main'
9.      ...decl is named 'BetaTree'
10. While deserializing decl @ 124968 (CLASS_DECL) in 'main'
11.     ...decl is named 'AlphaTree'
12. While deserializing decl @ 125436 (CLASS_DECL) in 'main'
13.     ...decl is named 'BetaTree'
14. While deserializing decl @ 124968 (CLASS_DECL) in 'main'
15.     ...decl is named 'AlphaTree'
...
2684.   While deserializing decl @ 125436 (CLASS_DECL) in 'main'
2685.       ...decl is named 'BetaTree'
2686.   While deserializing decl @ 124968 (CLASS_DECL) in 'main'
2687.       ...decl is named 'AlphaTree'
<unknown>:0: error: unable to execute command: Segmentation fault: 11
<unknown>:0: error: merge-module command failed due to signal 11 (use -v to see invocation)

Expected behavior

No crash. Ideally code should not be rejected as invalid, but if this is not possible, compilation error would be better than crash.

Environment

Swift version 5.11-dev (LLVM 8be112bb7e107a9, Swift df858a5ab96c574) Target: arm64-apple-macosx10.13

Additional information

No response

xymus commented 1 month ago

Sorry for the late answer, I was just made aware of this issue. It fails under a merge-module job. These have been deprecated a few years ago as they were prone to this find of failures.

It looks like the command line may be using the old driver written in C++, only the new driver written in Swift supports the new build mode emit-module-separately that replaces merge-module.

@nickolas-pohilets Was this seen only when building Swift locally? Can you make sure that you also build the new driver? There's a --swift-driver flag for build-script, but it may be on by default at this time.