Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

"cc65 compatibility" #29

Closed
johnwbyrd opened this issue Mar 26, 2021 · 8 comments
Closed

"cc65 compatibility" #29

johnwbyrd opened this issue Mar 26, 2021 · 8 comments
Labels
enhancement New feature or request p2

Comments

@johnwbyrd
Copy link
Member

Whenever I've brought up feature requests for a new compiler online, the near to first request that comes up is "cc65 compatibility."

On its face, this seems like a sensible request, but the deeper that you think about it, the less sensible this request becomes. ABI compatibility? All the #pragma's? How about all the predefined macros? Read and write cc65 library files? Support cl65 linker scripts?

I'd like to break out "cc65 compatibility," which I think is an abstract notion, into a smaller set of specific and measurable features.

1. ca65 compatibility. More specifically, a version of llvm-mc that's capable of emulating ca65, to the point where it can compile and link all the assembly code from the cc65 sdk. This is not necessarily the same as complete ca65 emulation, whatever that is. In practice, people could use the cc65 compiler to generate assembly code, and then pass their assembly through llvm-mc and our linker, to receive ELF introspection and real-time debugging and other things that we can do.

2. ABI compatibility. More, specifically, a version of llvm-mos that observes this [https://github.com/cc65/wiki/wiki/Parameter-passing-and-calling-conventions](calling convention). I'm a bit worried about even making this available, because all comparisons of llvm-mos to cc65 that use such a convention, will cause llvm-mos to look slow and embarrassing. A great part of llvm-mos's benefits is the control it has over the register allocator, which would all go away if the ABI were compatible. Thoughts?

3. clang-cc65 compatibility. Considering all the command line flags, #pragmas, and constants that cc65 assumes to exist, and all of which are deviations from ANSI C, I'm going to flat out state that we should not bother. Honestly, I'd be more tempted to simply give such users a Python script that simply strips all the cc65-specific #pragma's from their source code, converts all the asm commands to clang form, and just give them a header file in the SDK that sets all the cc65-specific constants. If that.

The end goal, of whatever we call cc65 compatibility, is to get people to leave cc65 alone and to proceed to use a more performant compiler. To that end, I think we might be able to get ahead of the problem, by publishing a few benchmarks of our own, comparing cc65's performance to llvm-mos. Interestingly, implementing item 1 above makes it straightforward to try these benchmarks ourselves.

In the pessimal case, our answer to the question of cc65 compatibility is "if it's C99, we can compile it." In a more optimal case, perhaps I can work on item 1, once some higher priority items are dealt with.

@johnwbyrd
Copy link
Member Author

johnwbyrd commented Mar 26, 2021

4. o65 to ELF object file converter. We could just skip the whole business, and provide a command line tool to permit cc65 object files to be converted into an ELF compatible format. The resultant code would not be ABI compatible with llvm-mos, but it would work regardless of how you generated those object files. Again though, a good bit of pain for not a great deal of long term reward.

http://www.6502.org/users/andre/o65/fileformat.html

@mysterymath
Copy link
Contributor

mysterymath commented Mar 31, 2021

Of these, (2) seems like the one that would provide the most utility: the ability to mix existing cc65 libraries, ASM code, and linker scripts with llvm-mos generated code, without trying to port code written using compiler-specific extensions/linker scripts.

At the end of the day, either ld65 or lld will be making the binary (or binary-shaped ELF file), and the nature of "cc65 compatibility" would depend pretty strongly on which linker they're thinking to use.

If we want ld65 to be able to link code generated with clang/LLVM together with cc65 or ca65 code, then we'd need to be able to produce an object file format that ld65 is capable of ingesting, and we'd need to be able to have our code play nice with the cc65 ABI. Ideally, we'd have a sort of "cloister"; we'd reserve a zero page region for use with the new compiler, and any internal functions would use a better, faster calling convention, be LTOed together, etc. We'd probably want an in-C calling convention annotation to say "make this function here or this call here use the cc65 ABI for its arguments".

For the integration the other way around, we'd need lld to be able to read cc65's object file format and incorporate it into the link. In that case, the cc65 code would be the cloister: we'd reserve temporaries and so forth for it, probably sharing the same stack pointer though. All of the cc65 code would use the same cc65 calling convention; and we'd annotate any LLVM calls to that code with a "cc65 ABI" annotation, causing them to set things up on cc65's soft stack. Similarly, any LLVM functions that need to be called from within the cloister would use the cc65 ABI to get their arguments.

Supporting the cc65 calling convention as a C annotation ([clang::mos_cc65] void foo().... or something) is the common piece between the two, but it's doubtful how useful it would be on its own without linker support. It seems like the LLVM cloister in ld65 would be more useful for folks with existing cc65 projects, so I'd start with that one.

It looks like cc65 is willing to both import and export the o65 object format, which is reasonably well documented, so that might be a natural way to go. If we could convert that to/from llvm-mos ELF, then the compatibility would work both ways. The o65 is also a pretty good candidate for a file format that allows practical dynamic linking and relocating to be done on real 6502 hardware, so we may want to support it independently of this feature.

I don't think it's an enormous amount of work necessarily, but I doubt it would ever be particularly easy to use. The only way around having to modifying the cc65 linker scripts to build the cloister would be to make the cloisters as minimal as possible (i.e., basically just the stack pointer and the zero page locations already reserved by cc65), which as you mentioned would produce fairly bad performance. The cc65 in LLVM direction would have bad performance just because cc65 sux. The other way around might not actually be all that bad, if we can take advantage of all of the temporary locations that cc65 reserves for its own use. We'd really want to do an on-paper prototype here to see exactly what an integration would entail.

@mysterymath mysterymath added the enhancement New feature or request label Jun 16, 2021
@oliverschmidt
Copy link

4. o65 to ELF object file converter. We could just skip the whole business, and provide a command line tool to permit cc65 object files to be converted into an ELF compatible format. The resultant code would not be ABI compatible with llvm-mos, but it would work regardless of how you generated those object files. Again though, a good bit of pain for not a great deal of long term reward.

http://www.6502.org/users/andre/o65/fileformat.html

This seems to be a misunderstanding. The ld65 linker is able to produce an o65 file as OUTPUT file. BTW: ld65 only supports a subset of what o65 files can contain/express. The object files created by ca65 and consumed by ld65 as INPUT files have nothing to do whatsoever with o65 files.

@oliverschmidt
Copy link

I'm not sure if my comments acctually fit here - but I was explicitly encouraged to participate here...

From my POV the question is (way) more broader, it's how llvm-mos and cc65 are positioned. It's what "we" advise someone to use for which scenarion / use case. Maybe we come up with answers that don't ask for compatibility at all.

I imagine it might help when I briefly describe how I believe people are using cc65 what interested them:

First, there's a surprisingly large number of cc65 users not interested in the the C compiler at all. They are only using the ca65 assembler and the ld65 linker. ca65 is a full-fledged, feature-rich macro assembler (the code generated by the cc65 C compiler doesn't make any use of that). However, I tend to believe that ca65 user rather favor it over other 65xx assemblers because of the separated ld65 linker. Using so-called linker config files the user can make ld65 do a lot of interesting things. In general it's about being able to define in a pretty flexible way what code/data segments are placed where in one or multiple output files and - totally independent from that placement - what absolute addresses should be assumed for that code/data segments at runtime. This is obligatory for e.g. generating ROMs for whatever use case.

Second, there are of course the users writing C code. I'd separate them in three subgroups:

The first (I think by far smallest) subgroup is "only" interested in writing (parts of) their business logic in C rather than 65xx assembly. Beside the so-called runtime library they don't make use of any library code coming with cc65. The runtime library contains functions not called explictly by the user's C code but functions called implicitly by the code generated by the C compiler. The C compiler is very closely tied to the runtime library.

The second (I think largest) subgroup wants to write C programs for "their" target machine (like e.g. the C64). Often they don't know (anymore) how to do things directly on that machine. They usually rely on the C library (and other libraries coming with cc65) on doing the right thing when they use console I/O or disk I/O. Please note that I personally have no insight to which extend people have created their own cc65-based libraries to be used by others, not even talking about how popular those libraries actually are!

The third (I think rather small) subgroup wants to write C programs for multiple target machines (like e.g. the Apple II and the ATARI). They additionally rely on the libraries that come with with cc65 to behave as similiar as possible on as many as possible targets. machines.

While for the assembly programmers mostly the flexibility of ld65 is interesting, for the C programmers some rather out-of-the-box features are interesting too. I personally see here primarily support for "structured" output files like (CONVERTed) GEOS VLIR files and ATARI XEX files. BTW: The o65 files mentioned above only play a rather marginal role for cc65 from my POV.

Okay, so the first question for me is to ask: Which of those cc65 users should rather use llvm-mos? I might be totally wrong but I guess you're not after the assembly programmers using only ca65 and ld65.

Looking at the C programmers I presume that the first group not looking for libraries coming with the C compiler may be convinced quickly to use llvm-mos if it outperforms cc65 regarding the generated code speed and/or size. I presume they only need an at least somewhat capable (inline-)assembler to create the necessary glue code to have the C code "do something".

I guess the from llvm-mos perspective problematic/challanging users are C programmers relying on mature libraries for one or even multiple targets.

Another perspective on the topic is that I personally believe that most code using cc65 is written at some point in time as a (most of the time) fun project. Those projects are at some point considered final and then left alone. I don't see many cc65-based projects being worked on over a longer time. So I personally don't see a big win in the ability to migrate exsisting projects from cc65 to llvm-mos.

The result from all I wrote so far is that I don't think that "cc65 compatibility" in itself is desirable feature. But maybe "cc65 compatibility" is desirable as means to reach other desirable goals.

As I already wrote in the Usenet I think it is desirable to not re-create all library FUNCTIONALITY for all targets coming with cc65 from scratch once more. So the from my POV primary/only question is how to leverage the exsisting cc65 library functionality.

So after this (too) long preamble...

The cc65 libraries are nearly completely written in hand-crafted, manually heavily optimized 65xx assembly. For cc65 that was the obvious way to go as it was clear that the C compiler always creates inferior 65xx code. But is that still (and supposed to stay) true for llvm-mos? Maybe it's desirable/necessary to have as much library code as possible written in C in oder to allow llvm-mos to optimize the overall code. In that case the only thing I personally see is to look VERY closely at the cc65 library code and (try to) recreate it in C.

If it should however be desirable to have some/the library code written in 65xx assembly then it might make sense to evaluate if it makes sense to have llvm-mos generate code that's compatible with the cc65 ABI enough to allow to call into unchanged cc65 libraries. In that case one would have to choose between processing the library source code with something different than ca65 and converting the ca65 output. Please note that the library source code tends to not make heavy use of ca65 features.

@johnwbyrd
Copy link
Member Author

Thank you for commenting Oliver, your comments are always welcome here and I'm very glad that you're contributing your thoughts and opinions.

I can speak to the assembler portion of things, a bit. llvm-mos has support for assembler variants, of which ca65 might theoretically become one. I recall that the cc65 libraries use the assembler macro functionality in the source code, in a few places, but the library code doesn't exercise all of ca65's features. So it seems possible to convince llvm-mos to compile ca65 assembly files to ELF, in the cc65 calling convention, with llvm-mos style relocations. Then it'd be up to Daniel et al to convince llvm-mos to follow the cc65 calling conventions.

Not a trivial project I think, but possible.

@oliverschmidt
Copy link

Yep, the question likely isn't if it's feasible but if it's desirable.

Maybe it makes sense as a short/mid term solution to have sort of a jump-start. Being able to "do things" with llvm-mos might create the momentum necessary to grow the contributor community. And that community might then bring up individuals creating "native" llvm-mos libraries. This is supposed to be possible in a continuous step-by-step approach.

@mysterymath
Copy link
Contributor

mysterymath commented Oct 19, 2021

Oliver, thanks for the detailed and well-reasoned look at this issue.

As you've mentioned, I'd agree we can treat the assembly language and C portions of this somewhat separately. Regarding the C portions.

The first (I think by far smallest) subgroup is "only" interested in writing (parts of) their business logic in C rather than 65xx assembly.

While I'd agree that currently this group is relatively small, one of our major goals is to increase its size. My present soft goal is to generate code that is no more than twice as slow as expertly hand-optimized assembly; hopefully this is around the sweet spot where you can start trusting a compiler to do a relatively good job writing most of an application outside it's very innermost loops. As this is a hobby platform, a sizeable group of folks just really enjoy writing 6502 assembly, so there are limits to how big this group can grow. I myself am mainly in this group though, which has definitely influenced my thoughts about code generation.

The cc65 libraries are nearly completely written in hand-crafted, manually heavily optimized 65xx assembly. For cc65 that was the obvious way to go as it was clear that the C compiler always creates inferior 65xx code. But is that still (and supposed to stay) true for llvm-mos? Maybe it's desirable/necessary to have as much library code as possible written in C in order to allow llvm-mos to optimize the overall code. In that case the only thing I personally see is to look VERY closely at the cc65 library code and (try to) recreate it in C.

Yep, for the minimum libcalls and C library functions we needed to get LLVM's test suite working, absolutely everything is written in C, well past the point of absurdity. Not because I think the compiler will ever be able to reliably match or beat a human at these innermost routines, but rather because once you write them in assembly, you lose the pressure that they place on the code generator.

Eventually, our libcalls should probably be written in assembly to maximize the performance of the C code that uses them, but the advantages will steadily decrease as the code generator improves. Accordingly, given the choice of adding optimization or rewriting a libcall, I'd always take the former, since it generalizes to other similar code; this policy would result in libcalls being rewritten once all available optimization opportunities are exhausted.

We'd probably never want to rewrite things like printf; for sufficiently large routines, better algorithms provide more bang for your buck than micro-optimization, and one of the real advantages of C is that it's easier to quickly write and compare approaches. For example, we really should be using double-dabble in our printf to convert from integers to strings, and it's really easy to write a C double dabble to replace the div/mod by 10 currently in our printf. This adds up; there's only so many hours in the day, and we could write a better C printf in the same time it'd take to write a worse assembly one.

So, overall, I'd agree that the benefits we'd get from ABI compatibility with cc65 is suspect, especially relative to the work involved. The folks most likely to benefit from better code generation are the most likely ones to be directly accessing hardware registers; the onus would then be on us to develop/port the OS calls and hardware registers that performance-conscious (and usually high-knowledge) developers would need.

Low-knowledge and performance-insensitive developers should likely continue using cc65, since they'd benefit greatly from the scope of its libraries. No matter how good we make "cc65 compatibility," I have doubts that it could ever be easy to mix llvm-mos and cc65 code together, and unless it's really really easy, we wouldn't have much to offer that group. Even if it were, it'd ring something like a BASIC accelerator, which is usually a nice to have, compared to the folks would consider llvm-mos's code gen abilities a barrier to entry for they type of projects they might like to write with it.

Accordingly, I think it's reasonable to close this issue, at least until we get new information about something specific someone's trying to do with cc65/llvm-mos that bucks this model of our userbase.

EDIT: By the end of this post, I relized I had forgotten the CA65 compatibility angle, which I'm not really inclined to speak on; I just haven't written enough 6502 assembly to have good opinions. The proposal above is to close the C ABI portion of this, and if we want to keep asm compatibility open, to create a separate issue for that.

@johnwbyrd, WDYT?

@mysterymath mysterymath added the p2 label Mar 3, 2022
@mysterymath
Copy link
Contributor

Closing as won'tfix; issues created along these lines should be more specific.

@mysterymath mysterymath closed this as not planned Won't fix, can't repro, duplicate, stale Oct 17, 2022
mysterymath pushed a commit that referenced this issue Feb 27, 2024
…(#80904)"

This reverts commit b1ac052.

This commit breaks coroutine splitting for non-swift calling convention
functions. In this example:

```ll
; ModuleID = 'repro.ll'
source_filename = "stdlib/test/runtime/test_llcl.mojo"
target datalayout = "e-m:e-p270:32:32-p271:32:32-p272:64:64-i64:64-i128:128-f80:128-n8:16:32:64-S128"
target triple = "x86_64-unknown-linux-gnu"

@0 = internal constant { i32, i32 } { i32 trunc (i64 sub (i64 ptrtoint (ptr @craSH to i64), i64 ptrtoint (ptr getelementptr inbounds ({ i32, i32 }, ptr @0, i32 0, i32 1) to i64)) to i32), i32 64 }

define dso_local void @af_suspend_fn(ptr %0, i64 %1, ptr %2) #0 {
  ret void
}

define dso_local void @craSH(ptr %0) #0 {
  %2 = call token @llvm.coro.id.async(i32 64, i32 8, i32 0, ptr @0)
  %3 = call ptr @llvm.coro.begin(token %2, ptr null)
  %4 = getelementptr inbounds { ptr, { ptr, ptr }, i64, { ptr, i1 }, i64, i64 }, ptr poison, i32 0, i32 0
  %5 = call ptr @llvm.coro.async.resume()
  store ptr %5, ptr %4, align 8
  %6 = call { ptr, ptr, ptr } (i32, ptr, ptr, ...) @llvm.coro.suspend.async.sl_p0p0p0s(i32 0, ptr %5, ptr @ctxt_proj_fn, ptr @af_suspend_fn, ptr poison, i64 -1, ptr poison)
  ret void
}

define dso_local ptr @ctxt_proj_fn(ptr %0) #0 {
  ret ptr %0
}

; Function Attrs: nomerge nounwind
declare { ptr, ptr, ptr } @llvm.coro.suspend.async.sl_p0p0p0s(i32, ptr, ptr, ...) #1

; Function Attrs: nounwind
declare token @llvm.coro.id.async(i32, i32, i32, ptr) #2

; Function Attrs: nounwind
declare ptr @llvm.coro.begin(token, ptr writeonly) #2

; Function Attrs: nomerge nounwind
declare ptr @llvm.coro.async.resume() #1

attributes #0 = { "target-features"="+adx,+aes,+avx,+avx2,+bmi,+bmi2,+clflushopt,+clwb,+clzero,+crc32,+cx16,+cx8,+f16c,+fma,+fsgsbase,+fxsr,+invpcid,+lzcnt,+mmx,+movbe,+mwaitx,+pclmul,+pku,+popcnt,+prfchw,+rdpid,+rdpru,+rdrnd,+rdseed,+sahf,+sha,+sse,+sse2,+sse3,+sse4.1,+sse4.2,+sse4a,+ssse3,+vaes,+vpclmulqdq,+wbnoinvd,+x87,+xsave,+xsavec,+xsaveopt,+xsaves" }
attributes #1 = { nomerge nounwind }
attributes #2 = { nounwind }
```

This verifier crashes after the `coro-split` pass with

```
cannot guarantee tail call due to mismatched parameter counts
  musttail call void @af_suspend_fn(ptr poison, i64 -1, ptr poison)
LLVM ERROR: Broken function
PLEASE submit a bug report to https://github.com/llvm/llvm-project/issues/ and include the crash backtrace.
Stack dump:
0.      Program arguments: opt ../../../reduced.ll -O0
 #0 0x00007f1d89645c0e __interceptor_backtrace.part.0 /build/gcc-11-XeT9lY/gcc-11-11.4.0/build/x86_64-linux-gnu/libsanitizer/asan/../../../../src/libsanitizer/sanitizer_common/sanitizer_common_interceptors.inc:4193:28
 #1 0x0000556d94d254f7 llvm::sys::PrintStackTrace(llvm::raw_ostream&, int) /home/ubuntu/modular/third-party/llvm-project/llvm/lib/Support/Unix/Signals.inc:723:22
 #2 0x0000556d94d19a2f llvm::sys::RunSignalHandlers() /home/ubuntu/modular/third-party/llvm-project/llvm/lib/Support/Signals.cpp:105:20
 #3 0x0000556d94d1aa42 SignalHandler(int) /home/ubuntu/modular/third-party/llvm-project/llvm/lib/Support/Unix/Signals.inc:371:36
 #4 0x00007f1d88e42520 (/lib/x86_64-linux-gnu/libc.so.6+0x42520)
 #5 0x00007f1d88e969fc __pthread_kill_implementation ./nptl/pthread_kill.c:44:76
 #6 0x00007f1d88e969fc __pthread_kill_internal ./nptl/pthread_kill.c:78:10
 #7 0x00007f1d88e969fc pthread_kill ./nptl/pthread_kill.c:89:10
 #8 0x00007f1d88e42476 gsignal ./signal/../sysdeps/posix/raise.c:27:6
 #9 0x00007f1d88e287f3 abort ./stdlib/abort.c:81:7
 #10 0x0000556d8944be01 std::vector<llvm::json::Value, std::allocator<llvm::json::Value>>::size() const /usr/include/c++/11/bits/stl_vector.h:919:40
 #11 0x0000556d8944be01 bool std::operator==<llvm::json::Value, std::allocator<llvm::json::Value>>(std::vector<llvm::json::Value, std::allocator<llvm::json::Value>> const&, std::vector<llvm::json::Value, std::allocator<llvm::json::Value>> const&) /usr/include/c++/11/bits/stl_vector.h:1893:23
 #12 0x0000556d8944be01 llvm::json::operator==(llvm::json::Array const&, llvm::json::Array const&) /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/Support/JSON.h:572:69
 #13 0x0000556d8944be01 llvm::json::operator==(llvm::json::Value const&, llvm::json::Value const&) (.cold) /home/ubuntu/modular/third-party/llvm-project/llvm/lib/Support/JSON.cpp:204:28
 #14 0x0000556d949ed2bd llvm::report_fatal_error(char const*, bool) /home/ubuntu/modular/third-party/llvm-project/llvm/lib/Support/ErrorHandling.cpp:82:70
 #15 0x0000556d8e37e876 llvm::SmallVectorBase<unsigned int>::size() const /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/ADT/SmallVector.h:91:32
 #16 0x0000556d8e37e876 llvm::SmallVectorTemplateCommon<llvm::DiagnosticInfoOptimizationBase::Argument, void>::end() /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/ADT/SmallVector.h:282:41
 #17 0x0000556d8e37e876 llvm::SmallVector<llvm::DiagnosticInfoOptimizationBase::Argument, 4u>::~SmallVector() /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/ADT/SmallVector.h:1215:24
 #18 0x0000556d8e37e876 llvm::DiagnosticInfoOptimizationBase::~DiagnosticInfoOptimizationBase() /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/IR/DiagnosticInfo.h:413:7
 #19 0x0000556d8e37e876 llvm::DiagnosticInfoIROptimization::~DiagnosticInfoIROptimization() /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/IR/DiagnosticInfo.h:622:7
 #20 0x0000556d8e37e876 llvm::OptimizationRemark::~OptimizationRemark() /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/IR/DiagnosticInfo.h:689:7
 #21 0x0000556d8e37e876 operator() /home/ubuntu/modular/third-party/llvm-project/llvm/lib/Transforms/Coroutines/CoroSplit.cpp:2213:14
 #22 0x0000556d8e37e876 emit<llvm::CoroSplitPass::run(llvm::LazyCallGraph::SCC&, llvm::CGSCCAnalysisManager&, llvm::LazyCallGraph&, llvm::CGSCCUpdateResult&)::<lambda()> > /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/Analysis/OptimizationRemarkEmitter.h:83:12
 #23 0x0000556d8e37e876 llvm::CoroSplitPass::run(llvm::LazyCallGraph::SCC&, llvm::AnalysisManager<llvm::LazyCallGraph::SCC, llvm::LazyCallGraph&>&, llvm::LazyCallGraph&, llvm::CGSCCUpdateResult&) /home/ubuntu/modular/third-party/llvm-project/llvm/lib/Transforms/Coroutines/CoroSplit.cpp:2212:13
 #24 0x0000556d8c36ecb1 llvm::detail::PassModel<llvm::LazyCallGraph::SCC, llvm::CoroSplitPass, llvm::AnalysisManager<llvm::LazyCallGraph::SCC, llvm::LazyCallGraph&>, llvm::LazyCallGraph&, llvm::CGSCCUpdateResult&>::run(llvm::LazyCallGraph::SCC&, llvm::AnalysisManager<llvm::LazyCallGraph::SCC, llvm::LazyCallGraph&>&, llvm::LazyCallGraph&, llvm::CGSCCUpdateResult&) /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/IR/PassManagerInternal.h:91:3
 #25 0x0000556d91c1a84f llvm::PassManager<llvm::LazyCallGraph::SCC, llvm::AnalysisManager<llvm::LazyCallGraph::SCC, llvm::LazyCallGraph&>, llvm::LazyCallGraph&, llvm::CGSCCUpdateResult&>::run(llvm::LazyCallGraph::SCC&, llvm::AnalysisManager<llvm::LazyCallGraph::SCC, llvm::LazyCallGraph&>&, llvm::LazyCallGraph&, llvm::CGSCCUpdateResult&) /home/ubuntu/modular/third-party/llvm-project/llvm/lib/Analysis/CGSCCPassManager.cpp:90:12
 #26 0x0000556d8c3690d1 llvm::detail::PassModel<llvm::LazyCallGraph::SCC, llvm::PassManager<llvm::LazyCallGraph::SCC, llvm::AnalysisManager<llvm::LazyCallGraph::SCC, llvm::LazyCallGraph&>, llvm::LazyCallGraph&, llvm::CGSCCUpdateResult&>, llvm::AnalysisManager<llvm::LazyCallGraph::SCC, llvm::LazyCallGraph&>, llvm::LazyCallGraph&, llvm::CGSCCUpdateResult&>::run(llvm::LazyCallGraph::SCC&, llvm::AnalysisManager<llvm::LazyCallGraph::SCC, llvm::LazyCallGraph&>&, llvm::LazyCallGraph&, llvm::CGSCCUpdateResult&) /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/IR/PassManagerInternal.h:91:3
 #27 0x0000556d91c2162d llvm::ModuleToPostOrderCGSCCPassAdaptor::run(llvm::Module&, llvm::AnalysisManager<llvm::Module>&) /home/ubuntu/modular/third-party/llvm-project/llvm/lib/Analysis/CGSCCPassManager.cpp:278:18
 #28 0x0000556d8c369035 llvm::detail::PassModel<llvm::Module, llvm::ModuleToPostOrderCGSCCPassAdaptor, llvm::AnalysisManager<llvm::Module>>::run(llvm::Module&, llvm::AnalysisManager<llvm::Module>&) /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/IR/PassManagerInternal.h:91:3
 #29 0x0000556d9457abc5 llvm::PassManager<llvm::Module, llvm::AnalysisManager<llvm::Module>>::run(llvm::Module&, llvm::AnalysisManager<llvm::Module>&) /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/IR/PassManager.h:247:20
 #30 0x0000556d8e30979e llvm::CoroConditionalWrapper::run(llvm::Module&, llvm::AnalysisManager<llvm::Module>&) /home/ubuntu/modular/third-party/llvm-project/llvm/lib/Transforms/Coroutines/CoroConditionalWrapper.cpp:19:74
 #31 0x0000556d8c365755 llvm::detail::PassModel<llvm::Module, llvm::CoroConditionalWrapper, llvm::AnalysisManager<llvm::Module>>::run(llvm::Module&, llvm::AnalysisManager<llvm::Module>&) /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/IR/PassManagerInternal.h:91:3
 #32 0x0000556d9457abc5 llvm::PassManager<llvm::Module, llvm::AnalysisManager<llvm::Module>>::run(llvm::Module&, llvm::AnalysisManager<llvm::Module>&) /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/IR/PassManager.h:247:20
 #33 0x0000556d89818556 llvm::SmallPtrSetImplBase::isSmall() const /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/ADT/SmallPtrSet.h:196:33
 #34 0x0000556d89818556 llvm::SmallPtrSetImplBase::~SmallPtrSetImplBase() /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/ADT/SmallPtrSet.h:84:17
 #35 0x0000556d89818556 llvm::SmallPtrSetImpl<llvm::AnalysisKey*>::~SmallPtrSetImpl() /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/ADT/SmallPtrSet.h:321:7
 #36 0x0000556d89818556 llvm::SmallPtrSet<llvm::AnalysisKey*, 2u>::~SmallPtrSet() /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/ADT/SmallPtrSet.h:427:7
 #37 0x0000556d89818556 llvm::PreservedAnalyses::~PreservedAnalyses() /home/ubuntu/modular/third-party/llvm-project/llvm/include/llvm/IR/Analysis.h:109:7
 #38 0x0000556d89818556 llvm::runPassPipeline(llvm::StringRef, llvm::Module&, llvm::TargetMachine*, llvm::TargetLibraryInfoImpl*, llvm::ToolOutputFile*, llvm::ToolOutputFile*, llvm::ToolOutputFile*, llvm::StringRef, llvm::ArrayRef<llvm::PassPlugin>, llvm::ArrayRef<std::function<void (llvm::PassBuilder&)>>, llvm::opt_tool::OutputKind, llvm::opt_tool::VerifierKind, bool, bool, bool, bool, bool, bool, bool) /home/ubuntu/modular/third-party/llvm-project/llvm/tools/opt/NewPMDriver.cpp:532:10
 #39 0x0000556d897e3939 optMain /home/ubuntu/modular/third-party/llvm-project/llvm/tools/opt/optdriver.cpp:737:27
 #40 0x0000556d89455461 main /home/ubuntu/modular/third-party/llvm-project/llvm/tools/opt/opt.cpp:25:33
 #41 0x00007f1d88e29d90 __libc_start_call_main ./csu/../sysdeps/nptl/libc_start_call_main.h:58:16
 #42 0x00007f1d88e29e40 call_init ./csu/../csu/libc-start.c:128:20
 #43 0x00007f1d88e29e40 __libc_start_main ./csu/../csu/libc-start.c:379:5
 #44 0x0000556d897b6335 _start (/home/ubuntu/modular/.derived/third-party/llvm-project/build-relwithdebinfo-asan/bin/opt+0x150c335)
Aborted (core dumped)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request p2
Projects
None yet
Development

No branches or pull requests

3 participants