Skip to content

Binary size #71

Description

@LDemetrios

So this is pretty much expected, isn't it. Not only the compiled projects are slow (which we talked about in the other issue), their binary is also about 20 times bigger than wasm->chicory coupling.

The other issue talks about how generics will improve the binary size compared to monomorphisation, and that is probably true, but I wouldn't treat it as a primary solution, I expect monomorphed version to be significantly faster than generic one (unless we get Valhalla, of course). So here are a few places to cut the size.

  • String constants. Really.
    • For example, this code:
    NEW java.lang.RuntimeException
    DUP
    LDC "Unreachable code reached"
    INVOKESPECIAL java.lang.RuntimeException.<init>(Ljava/lang/String;):V
    
    is repeated in a lot of places. So why not create a org.rustlang.Unreachable extending RuntimeException? I suspect there might be more cases like this.
    • Type names. As far as I see, Pointer methods take a lot of String arguments. It might go away if you just reduce Pointer usage, but still. I might be wrong on this, I am only reader here, but I don't see why those have to be Strings, because all I could find is either using them for equality, and using them for obtaining some typeinfo like "is it zero-size", "is it built-in" etc, which might be encoded into something less weighty, like bitmaps. I would propose interning: enumerate them with longs and use longs to carry those type names. You can then:
      • Simply store a file with typename list in classpath, and resolve only when needed. I imagine, they repeat across files a lot.
      • Use LDC with dynamic descriptor to load those strings by long identifiers
      • Introduce a dedicated type descriptor class and create with by LDC-descriptor, but the parameters are said unique id and bitmaps.
      • Probably something even smarter I didn't think of
  • And speaking of LDC, there are sure a lot of PointerCodecs. Each of them an empty constructor, two methods -- encode and decode into/from bytes -- and implements RustCopy with a call to that empty constructor. And I am pretty sure those encode-decode methods are generated automatically based on the type layout, right? So I would think about creating a metafactory that creates those classes when needed. Honestly I don't know, might be difficult to do on earlier jdks without classfile api, but I assume the code can be accurately plucked from the stdlib and downgraded to lower bytecode versions.
  • ... and speaking of LDC, there are sure a lot of Closures. From what I see, they usually implement some functional interface, rustcopy and that's it. Plus, call is usually (or always) just a wrapper to call some Mono method. So I would think about writing an alternative to lambda metafactory (stdlib one won't cooperate with RustCopy), and use INDY to create them. I assume the same can be done about TraitObjectCarrier and other interfaces that have ridiculously many implementations.

Activity

  1. LDemetrios commented on Oct 1, 2026

    @LDemetrios
    Author

    I also apologize for a lot of probably impolite "I would" in those issues, I'm majoring in compiler development, so naturally the question of how I would do something crosses my mind a lot xD

  2. IntegralPilot commented on Oct 2, 2026

    @IntegralPilot
    Owner

    Thank you! The reason I have been inactive the last few days is because I have been working locally on aggressively optimising the compiler output (and it's getting really good, almost ready to upload/share, it is DRAMATICALLY better in terms of both size and runtime and significantly reduces allocations and max RSS during running).

    is repeated in a lot of places. So why not create a org.rustlang.Unreachable extending RuntimeException? I suspect there might be more cases like this.

    Unreachable is UB so I think aconst_null; athrow is best here because it's even smaller (the old way it was is tech debt from when the compiler would keep unintentionally calling it so I needed a nice way to tell), thanks for the suggestion! I applied it now onto of my working changes and it saves 523 KB in the Typst release JAR (taking it from 88.31 MB to 87.78 MB). I believe current main is ~750MB so my WIP changes do make a big impact, hopefully I can upload soon (I'm targeting getting it down to ~50MB first).

    Pointer methods take a lot of String arguments. It might go away if you just reduce Pointer usage ... which might be encoded into something less weighty, like bitmaps

    Good idea, thank you! My current focus is aggressively dropping down the pointer usage. It is currently reduced quite a lot on my WIP stuff. I think from ~20GB in allocations when rendering Typst hello world on main is now ~1.2GB. Though to be clear allocations in JFR =/= RSS or memory usage, because most pointers are not active at the same time and they often die very early in Eden space. It is my goal to eventually get it near 0. I will look into that since it could be a really good idea for those pointers we do have to use currently.

    And speaking of LDC, there are sure a lot of PointerCodecs / ... and speaking of LDC, there are sure a lot of Closures

    I have been cutting them down a LOT in my WIP work by aggressively merging them where possible (better than InDy I think, but if you'd like me to try InDy I can).

    I also apologize for a lot of probably impolite "I would" in those issues, I'm majoring in compiler development, so naturally the question of how I would do something crosses my mind a lot xD

    That's so fine, I don't take it as rude at all! It is good to have input from someone who is taking formal classes on this / more experienced, I really appreciate it! :)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions