5 ms·
Makes me wonder why the C compiler (gcc?) isn't clever enough here and is not inlining all that non-sense. At least I would expect SufficientlySmartCompiler™ to
by skratlo 12y ago
Makes me wonder why the C compiler (gcc?) isn't clever enough here and is not inlining all that non-sense. At least I would expect SufficientlySmartCompiler™ to do so. Doing the inline by hand just proves how dark is the age we're living in.
- masklinn 12y ago> Makes me wonder why the C compiler (gcc?) isn't clever enough here and is not inlining all that non-sense. There's an indirection through a function pointer (ci->me). The manual optimisation is there to see whether the function pointer matches a baseline pointer, and apply that baseline directly instead of invoking the "generic" dispatch machinery (which involves setting new callframes & al) If you look at the whole function, there's a few special case before that which statically dispatch the case of a comparison between numbers or strings, so here we're in the "general" case and one last optimisation available is to see whether equality has been overridden at all.
- chrisseaton 12y agoPeople are often confused about how a JIT can be faster than a static compiler - this is a great example of why that can be the case. A dynamic compiler would be able to speculatively inline through the function pointer, where in a static compiler that is not tractable with what we currently know about compilers.
- gsg 12y agoThat's not really true - it's just (possibly partial) defunctionalisation. The problem isn't that we don't know how to do it, but that the necessary whole program architecture has various drawbacks. See Stalin and MLton for examples of a static compiler performing such analyses.
- chrisseaton 12y agoConsider the case of a program which applies a processing function to pixels in an image. Which processing function to run depends a command line parameter. How would whole program analysis help you know which function you are going to use? But a JIT will see you keep calling the same function and inline it. Not even profile directed feedback will help you if each time you run the program you use a different function. I know Stalin and MLton but not the research you mention - can you point me at any papers?
- gsg 12y agoIt's true that whole program compilation doesn't cover speculation (and many other cases of dynamicism, like running code that you download or construct at runtime). But it does allow inlining through a function pointer as in the OP, which you suggested is impossible for a static compiler. The classic paper on defunctionalisation is Reynolds' "Definitional Interpreters for Higher-Order Programming Languages". There's also a huge whack of papers at http://mlton.org/References http://mlton.org/References, some of which go into MLton's compilation strategy (I don't remember which ones to point you at, though).
- syncsynchalt 12y agoThere's no inline being done in this fix. The equality method has a check for a particular function pointer, and if found executes a fast path. By using a #define to alias another name to that same function pointer, it hits the same fast path. The equality method can't be inlined because ruby is a dynamic language and eql? can be redefined.