How to add optimization layer for ORC JIT to optimize ir contains `gc.statepoint`

Hi, I’m building my ORC JIT engine’s optimization layer based on this tutorial: 2. Building a JIT: Adding Optimizations – An introduction to ORC Layers — LLVM 19.0.0git documentation

My own language has a custom relocation gc, which may moving things around during collection, so I’ve made my own gc strategy and running the RwriteStatepointsForGC pass during code generation. However, I found that running other passes after RwriteStatepointsForGC may create new ir instructions that are not considered by RwriteStatepointsForGC, which may result in missing relocation instructions.

So I wonder how to implement optimization layer of my JIT engine to make sure IR produced are not missing may relocation, and can still do some optimization everytime it runs the layer? Basically I have two thoughts:

  1. During compile stage, don’t run RwriteStatepointsForGC pass. When running JIT, everytime the optimization layer is involved, run some optimization passes and store the ir before running RwriteStatepointsForGC pass. Next turn we can start optimization again from the stored ir.
  2. Write a custom pass which do the opposite job as RwriteStatepointsForGC pass, run it everytime we enter the optimization layer to restore the ir.

Which one is better and is there any other way to implement the optimization layer?