@matt
Objective-C provides late binding and dynamic typing with AOT compilation. 15 years ago, I wrote a compiler that implemented a Smalltalk dialect on the same object model. It had three execution modes!
- An AST interpreter.
- A JIT, which worked method at a time (so was fairly fast if you just edited a method and recompiled).
- A ‘just too late’ compiler that, when a process exited, did an AOT compilation of all of the code and dumped it in a .so, so the next time the program started it got all of the last run’s code with a single dlopen call.
Startup times were on the order of 200ms on a 1.2GHz Celeron M.
This still gave a Smalltalk-like programming environment: you could open a class browser, replace methods, add instance variables to classes, and so on. While you were editing, things ran a bit slower (though I broke the JIT for a couple of months and used the AST interpreter without noticing) but they worked and were then fast the next run of the program.
The goal was to integrate it with CoreObject, the persistent object store for Étoilé. With that, it would have been trivial to restart the program without losing state, so we could have done the same thing that Sudden Termination does on macOS: when none of the windows for a program are active, quietly restart it so that you pick up new object layout and so on.
I mostly gave up the approach because, without something like CHERI, it’s hard to give end-user-programming environments access to C libraries without giving them myriad ways of crashing themselves. So I had to go and build CHERI before I could come back to solving the fun problem.