home.social

#aoco2025 — Public Fediverse posts

Live and recent posts from across the Fediverse tagged #aoco2025, aggregated by home.social.

  1. [ ] Day 3 of Study Notes: You can’t fool the optimiser

    My notes focus on reproducing and verifying Matt Godbolt’s teaching within a local development environment

    This post specifically compares Tail Recursion vs. Standard Recursion.

    Read more here: gapry.github.io/2026/01/31/Adv

  2. [ ] Day 2 of Study Notes

    My notes focus on reproducing and verifying Matt Godbolt’s teaching within a local development environment

    Additionally, I have extended the discussion by implementing a manual PoC in assembly

    Read more here: gapry.github.io/2026/01/31/Adv

  3. [] Day 1 of Study Notes

    While the original uses , I wanted to replicate the analysis locally.

    In this post, I have used , , llvm-objdump and to analyze.

    Read more here: gapry.github.io/2026/01/01/Adv

  4. [#Compiler] Day 1 of #AoCO2025 Study Notes

    While the original uses #CompilerExplorer, I wanted to replicate the analysis locally.

    In this post, I have used #gcc, #clang, llvm-objdump and #LLDB to analyze.

    Read more here: gapry.github.io/2026/01/01/Adv

  5. [#Compiler] Day 1 of #AoCO2025 Study Notes

    While the original uses #CompilerExplorer, I wanted to replicate the analysis locally.

    In this post, I have used #gcc, #clang, llvm-objdump and #LLDB to analyze.

    Read more here: gapry.github.io/2026/01/01/Adv

  6. Day 25 of Advent of Compiler Optimisations!

    We've reached the end of this journey through compiler magic—from simple arithmetic tricks to mind-bending loop transformations. Thank you for following along! Whether you celebrate Christmas or just enjoy a good compiler optimisation, I hope you've discovered something that made you see your code differently.

    Read more: xania.org/202512/25-thank-you
    Watch: youtu.be/N1sRfYwzmso

    #AoCO2025

  7. Day 24 of Advent of Compiler Optimisations!

    A simple loop that sums integers from 0 to n. GCC cleverly unrolls it to process two numbers at once. But clang? The loop completely disappears—replaced by a few multiplies and shifts that compute the answer directly. How does it recognise this pattern and transform O(n) code into O(1)?

    Read more: xania.org/202512/24-cunning-cl
    Watch: youtu.be/V9dy34slaxA

    #AoCO2025

  8. Day 23 of Advent of Compiler Optimisations!

    Switch statements compile to jump tables, right? Well... sometimes. But what happens when your five-case switch becomes pure arithmetic? Or when checking for whitespace turns into a single mysterious constant and some bit manipulation? Turns out compilers have a whole bag of tricks beyond the textbook answer.

    Read more: xania.org/202512/23-switching-
    Watch: youtu.be/aSljdPafBAw

    #AoCO2025

  9. Day 22 of Advent of Compiler Optimisations!

    Comparing a string_view against "ABCDEFG" should call memcmp, right? Watch what Clang actually generates — no function call at all, just a handful of inline instructions using some rather cunning tricks. How does it compare 7 bytes so efficiently when they don't fit in a single register?

    Read more: xania.org/202512/22-memory-cun
    Watch: youtu.be/kXmqwJoaapg

    #AoCO2025

  10. Day 21 of Advent of Compiler Optimisations!

    Summing an array of integers? The compiler vectorises it beautifully, processing 8 at a time with SIMD. Switch to floats and... the compiler refuses to vectorise, doing each add one by one. Same loop, same code structure — why does the compiler treat floats so differently?

    Read more: xania.org/202512/21-vectorisin
    Watch: youtu.be/lUTvi_96-D8

    #AoCO2025

  11. Day 20 of Advent of Compiler Optimisations!

    Loop over 65,536 integers doing comparisons — that's 65,536 iterations, right? Wrong! With the right flags, the compiler processes 8 integers per iteration using SIMD instructions. Same number of assembly instructions, 8× the throughput. What's the trick that makes this possible?

    Read more: xania.org/202512/20-simd-city
    Watch: youtu.be/d68x8TF7XJs

    #AoCO2025

  12. Day 19 of Advent of Compiler Optimisations!

    Recursive functions need to call themselves over and over — that must mean unbounded stack growth, right? Wrong! When a function ends by calling another function (even itself), the compiler can replace the call with a simple jump. Recursion becomes iteration, no stack overhead at all. How does this transformation work?

    Read more: xania.org/202512/19-tail-call-
    Watch: youtu.be/J1vtP0QDLLU

    #AoCO2025

  13. Day 18 of Advent of Compiler Optimisations!

    You have a function with a fast path and a slow path. Inline it everywhere? Massive code bloat. Don't inline? You miss the fast path performance gains. It's an impossible choice—or is it? The compiler finds a way to get the performance benefits of inlining without paying the full code size cost. But how?

    Read more: xania.org/202512/18-partial-in
    Watch: youtu.be/STZb5K5sPDs

    #AoCO2025

  14. Day 17 of Advent of Compiler Optimisations!

    A function that handles both upper and lower case conversion. Call it with upper=true and the compiler inlines it — but something remarkable happens. The inlined code doesn't just avoid the function call overhead. Half the function completely vanishes! How does copy-pasting code make it disappear?

    Read more: xania.org/202512/17-inlining-t
    Watch: youtu.be/JFHfFTvMPp0

    #AoCO2025

  15. Day 16 of Advent of Compiler Optimisations!

    Pass a function two separate arguments, or pack them in a struct — which is faster? The answer might surprise you: sometimes the struct version is MORE efficient! Eight char arguments as separate parameters spill to the stack, but pack them in a struct and they fit in a single register. How does the compiler pull this off?

    Read more: xania.org/202512/16-calling-co
    Watch: youtu.be/Yaw8AMoP4sI

    #AoCO2025

  16. Day 15 of Advent of Compiler Optimisations!

    Two nearly identical loops: one accumulates ints into an int, the other accumulates ints into a long. You'd expect similar assembly—just different register sizes, right? Wrong! One loop writes to memory on every iteration, the other keeps everything in registers. Same algorithm, wildly different performance. What's going on?

    Read more: xania.org/202512/15-aliasing-i
    Watch: youtu.be/PPJtJzT2U04

    #AoCO2025

  17. Day 14 of Advent of Compiler Optimisations! 🎄

    Yesterday we saw the compiler beautifully hoist strlen() out of our loop. Today? Add a single global counter and watch that optimisation vanish—strlen gets called EVERY iteration! But why would incrementing an unrelated variable break loop-invariant code motion? The answer involves a surprising rule about char* in the C++ standard.

    Read more: xania.org/202512/14-licm-when-
    Watch: youtu.be/OwFNblEEAXo

    #AoCO2025

  18. Day 13 of Advent of Compiler Optimisations!

    You're calling a function inside a loop, but its result never changes between iterations. Does the compiler spot this and hoist it out? Turns out the answer depends on which compiler you use! Clang pulls off the optimisation beautifully, but gcc stumbles—even with explicit hints. What's going on?

    Read more: xania.org/202512/13-licking-li
    Watch: youtu.be/dIwaqJG0WDo

    #AoCO2025

  19. Day 12 of Advent of Compiler Optimisations!

    Your loop checks the same condition every iteration, even though it never changes. Seems wasteful, right? The compiler thinks so too—and its solution is something that sounds completely backwards. Making your code bigger to make it faster? What's the trick?

    Read more: xania.org/202512/12-loop-unswi
    Watch: youtu.be/-VCrYshE7iQ

    #AoCO2025

  20. Day 11 of Advent of Compiler Optimisations!

    A clever loop that counts set bits using the "clear bottom bit" trick: value &= value - 1. Works great, generates tight assembly. But change one compiler flag to target a slightly newer CPU and something extraordinary happens to your loop. The compiler spots a pattern you didn't even know was there. What replaces your careful bit manipulation?

    Read more: xania.org/202512/11-pop-goes-t
    Watch: youtu.be/Hu0vu1tpZnc

    #AoCO2025

  21. Day 10 of Advent of Compiler Optimisations!

    A simple loop summing 8 values — but tell the compiler the count is fixed at compile time and watch what happens. The code transforms in surprising ways. What does "unrolling" actually look like in assembly, and when does the compiler decide it's worth it? Try changing the count and see how the strategy changes!

    Read more: xania.org/202512/10-loop-unrol
    Watch: youtu.be/HvF3tF2efEA

    #AoCO2025

  22. Day 9 of Advent of Compiler Optimisations!

    Loop with `i * i` inside? Surely the compiler replaces that expensive multiply with clever addition tricks — like manually tracking an accumulator. But no! The compiler keeps the multiply because it enables something more valuable. Why is "more expensive per iteration" sometimes faster overall? The answer lies in how modern CPUs actually execute code.

    Read more: xania.org/202512/09-induction-
    Watch: youtu.be/vZk7Br6Vh1U

    #AoCO2025

  23. Day 8 of Advent of Compiler Optimisations!

    Which loop style is fastest—index-based for, pointer while, range-for, or std::accumulate? I compared four different ways to sum a vector. The compiler generates identical assembly for three of them! But one approach forces an extra calculation. Can you guess which? 🔄

    Read more: xania.org/202512/08-going-loopy
    Watch: youtu.be/FB8Hgj3TpJM

    #AoCO2025

  24. Day 7 of Advent of Compiler Optimisations!

    Converting numbers to ASCII requires dividing by 10 repeatedly. But division is slow, so what does the compiler actually generate? Turns out: no division instructions at all! Instead, a mysterious constant (0xcccccccd) appears along with multiply and shift operations. How does this produce exact results for all inputs?

    Read more: xania.org/202512/07-division-a
    Watch: youtu.be/V9Pvv1tkocM

    #AoCO2025

  25. Day 6 of Advent of Compiler Optimisations!

    Divide by 512—that's just a shift right by 9, right? But look at the generated code: extra instructions appear! The compiler seems to be doing unnecessary work. Or is it? Turns out there's a subtle difference between what you asked for and what you probably meant. One keyword fixes everything.

    Read more: xania.org/202512/06-dividing-t
    Watch: youtu.be/7Rtk0qOX9zs

    #AoCO2025

  26. Day 5 of Advent of Compiler Optimisations!

    x86 has LEA for multiplication tricks, but what does ARM bring to the party? Meet the barrel shifter—a hardware feature that lets many instructions shift their second operand. The compiler exploits this to turn multiplications into shifted adds, all in a single instruction. Different architectures, different superpowers!

    Read more: xania.org/202512/05-barrel-shi
    Watch: youtu.be/TZubUyr2UEY

    #AoCO2025

  27. If you have even the slightest curiosity about optimising compilers and aren't already following @mattgodbolt's Advent of Compiler Optimisations, you absolutely should.

    #AoCO2025

  28. Day 4 of Advent of Compiler Optimisations!

    Multiply by 2, 3, 4, 16, 25—which ones use the actual multiply instruction? Spoiler: fewer than you think! The compiler has a bag of tricks for avoiding multiplication, using shifts, adds, and that versatile LEA instruction. But when you outsmart it with your own shift-and-add... it un-optimises you right back!

    Read more: xania.org/202512/04-multiplyin
    Watch: youtu.be/1X88od0miHs

    #AoCO2025

  29. Day 3 of Advent of Compiler Optimisations!

    Four completely different ways to add two numbers—direct addition, a while loop, recursive calls—yet they all compile to the exact same single instruction. The compiler's pattern recognition sees through the obfuscation and finds the canonical form underneath. How does it know?

    Read more: xania.org/202512/03-more-addin
    Watch: youtu.be/wHg9lYPMvvE

    #AoCO2025

  30. Day 2 of Advent of Compiler Optimisations!

    How do you add two integers on x86-64? You might expect `add`, but the compiler has other ideas—it uses an instruction designed for calculating memory addresses instead! Why would it choose this unusual approach, and what advantages does it bring? The answer reveals something fascinating about x86's quirky architecture.

    Read more: xania.org/202512/02-adding-int
    Watch: youtu.be/BOvg0sGJnes

    #AoCO2025