For those that do not know, Cppcon is one of the largest (if not the largest) attended C++ conference held yearly in Denver, Colorado at the Gaylord Hotel. I landed at Denver's airpot on Tuesday around 1pm MDT and went directly to my first session. But before we get into that, let me give a few details about what you are going to read.
Anyways, let's get into it!
The first talk of the conference that I attended was by Elias Farhan. I was very excited to make it in time and hear his talk, Inside a Small Game Engine: An Architecture Tour in Modern C++. What I thought made this talk brilliant was that it was grounded in his experience in building a game called Soup Raiders. The talk is very useful for anyone who has programmedi a game before and spent time thinking about the architecture of a larger project (Total beginners may still also benefit watching the talk and then knowing they can revisit this talk later to learn ideas about abstraction). This talk was also particularly insightful for folks who have experience in using game engines like Godot, Unity3D, or Unreal, and otherwise may want to build or port their game to a custom game engine. Elias's blog has a good deal of content well worth reading. Elias walked us through many of the major components in games in his game engine with brilliant slides that have embedded demos running on the web. There's a really nice example in the talk discussing use of compile-time reflection for serializing data structures. Lewis Nicolle's DConf 2025 talk had also introduced a trick to serialize the whole gamestate structure and then produce a GUI (Lewis discussed a few other tricks at the D programming Language Symposium version of the talk as well.). Reflection was definitely an important theme at cppcon 2026, so it was brilliant to see some applications at the end of Elias's talk. Furthermore, Elias did a nice job discussing some difficulties and providing solutions using reflection for serializing data structures (e.g. serializing structs that have unions like glm::vec3). This will be a talk I look forward to rewatching again. While you wait for this talk to be published, Elias has given other talks including this cppcon 2024 talk on Rollback systems. for multiplayer games.
The second talk I attended Tuesday was by Greg Law Good boss, bad boss: how to be a good manager, and how to manage a bad one. I saw this as a continuation from Greg Laws excellent 2025 talk discussing the realities of being a CEO, challenges, and how to create a healthy workplace. Greg provides honest insights, examples, and lessons learned with actionable advice. Both this talk and his prior talk are useful for engineers in an organization as much as for those who are managing (whether at the CEO level or otherwise managing a technical team). Goodhart's law was one takeaway I did know the adage from Goodhart's law is:
"When a measure becomes a target, it ceases to be a good measure".
When Goodhart's Law was mentioned, the first thing that came to mind was a manager trying to measure developer productivity. I've had friends who have recounted tales at their company where games are played to hit the arbitrary metrics as opposed to focusing on the task at hand -- luckily I have not really been part of that (or otherwise remained oblivious and focused on the task at hand). Anyways, I have enjoyed going to at least 1 business track sessions since the track has been added to cppcon the past 2 years.
Later in the evening on Tuesday Cppcon hosted a screening of what I'll just refer to as the C++ movie, but it's officially called 'The Story of C++'. I had already watched it previously so I skipped the screening, but otherwise I recommend it to folks who enjoy programming to hear the story of the C++ language from many folks who have worked on and used the language or otherwise are part of computer science history. I spent the remaining of the evening chatting with folks and then went to finish my slides that I would give Wednesday for my talk on SDL 3.
Timur Doumler gave the keynote on Wednesday titled: How C++26 changes the way we write code. This is a continuation of Timur's series of talks How C++20 Changes the Way We Write Code - Timur Doumler - CppCon 2020 and How C++23 Changes the Way We Write Code - Timur Doumler - CppCon 2022. Each of these talks highlights what are (his) predicted to be the most impactful features in the new C++ standard. For C++ 26 the features that are highlighted in this talk are: std::simd, std::execution, Contracts, Reflection. In Timur's C++20 and C++23 the features were respectively: concepts, coroutines, modules, and then std::expected, std::mdspan, deducing this, and std::print.
Regarding std::simd, it seems the compiler support of std::simd has come a long way. There was a hackernews article at some point discussing earlier versions of std::simd not getting expected performance gains, but it seems folks are hard at work improving the support. The thing with reading anecdotes on performance however, is that you always have to measure yourself -- so I will have to do some benchmarking myself now that the libraries have been around for a bit. While you wait for Timur's YouTube video to be posted, I thought this presentation on implementing std::simd provides a good overview for those unfamiliar with std::simd and otherwise want some technical details and motivations: Implementing C++26 std::simd
Languages like D have had simd types for quite some time (yes, I know you will hear about D on occasion from me here -- and I am also aware we've had many simd libraries for C++ as well!). Other languages (e.g. Odin) have simd types as well, so I'm very happy that C++26 is providing a portable abstraction for data parallelism with simd now. That all said, I'm really excited to try the c++26 library more. Here's a 'hello world' example otherwise for you to get your feet wet if you have g++-16 or later.
// Compiled with: g++-16 simd.cpp -std=c++26 -o prog
#include <array>
#include <simd>
#include <print>
int main(){
// Try changing the size of the array, and you'll see
// this example still works!
constexpr std::array<int,8> values = {1,2,3,4,5,6,7,8};
std::simd::vec simd_values1 = values;
std::simd::vec simd_values2 = values;
auto result = simd_values1 + simd_values2;
std::println("Wow that was fast: {}",result);
return 0;
}
Next up on Timur's talk was std::execution, sometimes also called 'senders/receivers'. As I understand the motivation of senders/receivers in general is to enable concurrency without worrying as much about issues in regards to thread safety. Issues like deadlocks, race conditions should otherwise disappear. You can see this brief article by Lucian Radu Teodorescu for a nice introduction to std::execution. I need to actually write some code using senders and receivers before I comment further, but it seems like a cool form of concurrency that can work across various devices (e.g. GPU and CPU).
Concurrent programming otherwise is notoriously difficult at scale to get correct; primitives like std::thread and using std::mutex are susceptible to deadlock and race conditions if you are not careful. I have a whole YouTube series covering the basics of C++ concurrency. We do however need concurrency primitives for building higher level abstractions, so of course in C++ we want the ability to build our own abstractions from the ground up using concurrency primitives like mutex and thread. Other tools that exist in the standard library include already std::async (i.e. promises and futures) that are generally easier to use. Coroutines are another great option for concurrent programming, but I admittedly have not used coroutines much in C++ yet beyond some simple examples. I do however use fibers in D for game programming, and when I did some Unity3D programming, the C# coroutines there were incredibly easy to use and are an awesome way to model gameplay code.
Contracts was the next big topic for Timur's talk. I have not been following closely the papers on contracts or what got approved, but my understanding from the talk is 'contract_assert' is a proper keyword along with 'pre' and 'post' will be coming to C++26. 'pre' and 'post' will be written in source code in the header file so folks can see the interface. On top of the contracts, there's further control to: ignore, observe, enforce, and quick-enforce contracts. This seems to be quite a rich library, where many languages otherwise simply use assert. I was not aware of further capabilities like defining a contract violation handler otherwise (contract_violation). Timur made a nice analogy here to what happens 'when you still break the rules' and thus the motivation for the contract handler. Overall contracts look nice. I'm not sure which of the full features are part of C++26 or if some are otherwise being proposed as part of C++29, but again, I think they will be useful. One of the nice thing about contracts that has received ancedote evidence of a benefit is that for LLM's the LLM can have an idea of the specification. I think languages that have contracts will be important (And Andrei's keynote had some thoughts on specifications being important in the future). C++ continues to evolve and having contracts in the language should at the least be very useful in human and AI-assisted engineering for code that you own. I remain optimistic that we are yet going to need even more computer scientists in the future who will be able to at the least specify correct programs even if the day-to-day task changes in the future.
The final of the four impactful features Timur highlighted were static reflection. Static reflection was highlighted last year in Herb Sutter's keynote (Note: Herb was unfortunately not feeling well this year, so I hope he is feeling better now!). D's metaprogramming and awesome compile-time reflection has been one of my favorite features. As a brief introduction, static reflection (or sometimes called 'compile-time reflection') allows you to inspect and understand the structure of a program at compile-time. In my 2024 ACCU talk I discussed how learning D helps my C++ and vice versa and I highlighted where D helped me understand concepts in C++. D further taught me metaprogramming and I still often write metaprograms in D before porting them over to C++. Now, I am curious to see how I can do some of the things like static reflection in D and compare them to C++. There's all sorts of cool things I've done like generate getters/setters for a class based on which fields had user-defined attributes on them. So while I have not dived deeply into C++ reflection yet, I may have to do an update of my 2024 ACCU talk to show some more examples of languages like D and C++ side-by-side. I think reflection was probably the biggest theme at Cppcon 2026, so some of the talks that I missed should otherwise be good resources for myself and others in the future..
Here's a 'hello world' to reflection in C++26 otherwise that you can try in godbolt or g++-16 or later.
// Compiled with: g++-16 reflection.cpp -freflection -std=c++26 -o prog
#include <meta>
#include <print>
struct Test{
int a;
float b;
};
// Consteval must be solved at compile-time, and with reflection
// we need to do our work at compile-time.
// Here's an example of counting the 'member variables' of Test
consteval int CountFields(const std::meta::info info){
int result={0};
constexpr std::meta::access_context ctx = std::meta::access_context::current();
auto fields = members_of(info, ctx);
for(std::meta::info f : fields){
if(is_nonstatic_data_member(f)){
result++;
}
}
return result;
}
int main(){
// Generate 'metadata' for 'Test' at compile-time
constexpr std::meta::info info = ^^Test;
constexpr int fields = CountFields(info);
std::println("Test has: {} fields",fields);
return 0;
}
Note: In C++26, the ability to create 'skip tags' are a super useful feature to figuring out how to reflect over data structures. 'Skip tags' appear to be the equivalent to 'user defined attributes' in D, I believe we can then use in C++26 std::meta::annotations to serve the same purpose of gathering data. I finally put together that in D, the empty struct we use (and similar in C++) is to give the compiler some symbol at compile-time for lookups, I also assume that compiler later eliminates that symbol. So at the least, doing things like serializing data structures or generating functions based on member fields will be some fun things you can do.
One last cool thing Timur showed off regarding compile-time for reflection at the end of his talk was that there is also debugger support for debugging this stuff at compile-time -- awesome!
The second talk I attended was Turbocharging Native Code Performance: Compiler Optimizations, Profile-guided Optimizations, and Beyond by Eric Brumer. Unfortunately I only made it into the talk ~30 minutes in, but when I walked into the room, Eric said some wise words along:
"short story, if you want faster code, upgrade your compiler".
Note: I generally would agree with that advice as that has held true over time.
I caught the tail end otherwise of the first section of talk talking about fun compiler optimizations like Scalar Replacement of Aggregates (SROA) and views of machine code generation to see how well compilers are generating code. The second portion of this talk was about profile-guided optimizations (PGO) or sometimes called 'feedback-driven optimization'. I worked briefly on this type of stuff briefly with LLVM during my graduate student years, so this was a great talk to see what else was going on. SPGO is 'sampling-based' profile-guided optimizations and there is a nice tutorial referenced here from Microsoft on SPGO from Eric. My understanding is SPGO uses the hardware performance counters to gather their information. If you've used profilers like perf, (or used the perf system calls) you can see some examples of the performance counters. One really neat example (around 46 minutes into the talk) was on 'speculative devirtualization'. This is pretty cool stuff to see how spgo (pronounced as 's'-po'-'go') could speed up the task about 30%. I remember again trying to look at things like function splitting or figuring out where 'virtual calls' tended to go to see if PGO could help with optimizations. This talk reminded me that I need to update and perhaps post in the next year or so my LLVM slides and revisit some of this world, so many fun projects yet to work on! I'll end that SPGO Eric explained is PGO without instrumentation. I'll have to check this out, along with whatever autoFDO and other projects are up to.
I gave my talk towards the end of the conference day titled Graphics Programming with SDL 3 Part 2. This is a direct follow up to my talk from Cppcon 2025 - SDL Graphics Programming Part 1. I would recommend watching part 1 first, or otherwise going to my SDL3 C++ Playlist that will walk you through all of this code. What is new about 'part 2' of this talk, is that I provide an introduction into shaders with SDL 3.4. I recommend watching it, and I'll probably have more video tutorials on my YouTube before the talk is published anyway. I had a great turnout for the talk, and I look forward to seeing what folks build! I personally think that having access to shaders is a real game changer for folks getting into graphics programming with the 2D API. Note: The way I introduce the topic is through some reverse engineering with renderdoc.
Note: I have since started recording the programming companion episodes (showing each line of code typed) based on this talk on my YouTube channel: The SDL 3.4 lessons with custom shaders begin here.
For Thursday I started my day with the keynote by Laurie Kirk - The Address is Not The Place: Object Residency in C++26. This was a brilliant talk, and I was very happy that it landed on Thursday prior to my Back to Basics talk on Computer Systems. The talk gives a crash course on systems, but dives deeper into telling us how the abstractions in our operating system and hardware make it a bit difficult for us to actually nail down 'where is the data'.
In Laurie's words 'The operating system is constantly lying to us'.
That quote is not actually far off. To help us understand this, Laurie gave us a crash course on UMA (Uniform Memory Architecture) and NUMA (Non-uniform memory access) before advancing us forward to new styles of memory. There were a lot of really nice diagrams showing us how to think of main memory with the different 'nodes' on memory (often this omitted or oversimplified in beginner courses, but for understandable reasons). When I teach my students about the nice abstraction virtual memory gives us, I will now be thinking a bit more about how I should discuss more about RAM. Perhaps doing some fun microbenchmarks like Laurie provided will be good exercises. For an introduction to NUMA, there are some nice resources available on the What is NUMA linux page.
One thing that I thought was interesting was the 'underrated' nature of annotations in code. Laurie talks about this being a potential place where we can make improvements and presented some work alongside this during the talk. Something I was curious about years ago was [[likely]] and [[unlikely]] for branches (note: this shows up after an hour or so in the talk). If we go to the previous days talk regarding SPGO, that's kind of what those tools are doing with data to to feed into optimizers at compile-time. Annotations are interesting because they can (depending on the language) give explicit control to the software engineer to at least inform the compiler what decisions to make. One catch with annotations however is just like comments -- those annotations have to be kept up to date. This made me wonder if (similar to comments) we need tooling that checks the 'age' of comments/annotations and if this is something LLM's could be useful for, perhaps even as part of the annotation (though let's be honest, that would probably be some ugly code!).
The second talk I was able to attend was by Steve Sorkin When Zero Cost Abstractions Aren't Zero Cost. This was a great talk and discussed the sometimes 'hidden' cost of abstractions. The point was not necessarily to avoid using abstractions, but otherwise to figure out what the costs were and understand the trade-offs when these exist. Sometimes the trade-offs might include tings like readability, maintenance, plasticity, and of course performance. From my own experience, the simplest and clearest code tends to be the thing that I am most likely to revisit and optimize later. I popped open a few of his examples during the talk that were linked in Godbolt to explore the assembly myself. I recommend folks watch Steve's talk and follow along and learn with him the costs. One other thing that I like doing too, is to use some abstraction (e.g. ranges) and then explore over time in godbolt (by selecting different compilers) to see how the generated assembly improves. So sometimes it is best to use the thing that makes your code very readable, and then over time the compiler may end up getting you close or exactly at zero-cost for the final generated assembly (of course, you might pay in compile-time, but you get my point that code generation tends to get better over time -- so just use the nice abstraction).
I overachieved today and made it to a 3rd talk, Alex Dathskovsky The Biggest Misconception of Computer Science. The talk was a nice bridging of what we often learn at university in two separate courses: systems and algorithms. The talk had very nice synergy with my talk (which came right after) regarding discussing systems topics like pipelining, out-of-order execution, and other fundamentals everyone should know. One of the unique courses I developed while at Northeastern University in 2019 was a 'Computer Systems and Algorithms' course which served as a bridge course for students entering a masters computer science program. What was special about that course is that algorithms and computer science are introduced together rather than in separate classrooms. I think this is really helpful, and I wonder why not teach a two-semester sequence that combines both of these topics, rather than two separate courses that may not have synergy (Note: I am currently teaching a two-semester systems sequence at Yale which is quite unique, and I think will prepare our students well for understanding how to connect theory and practice). Regardless, I thought Alex did a really nice job, and I'd recommend it to students who have just finished their systems or algorithms course to otherwise help 'connect' topics together. In fact, I would recommend folks watch my Back to Basics: Computer Systems talk first, and then watch Alex's, because he goes a little further into some topics that I only briefly introduce (including branch predictors, simd, branchless programming, parallelism). I was very happy to have sat in on this talk that I unfortunately missed earlier at NDC Toronto 2026.
I unfortunately missed Michelle D'Souza's talk which likely would have been complementary, but I'll otherwise link her great C++ North 2025 talk Michelle D'Souza - Gotta Cache 'Em All: Optimize Your C++ Code By Utilizing Your Cache!
This was my talk! I'll link to it when it was posted. The main idea was that there are three pictures I need folks to understand: 1.) The compilation process, 2.) The program stack 3.) A basic CPU. If you're able to understand those three pictures in-depth, you're going to have a good foundation to grow in any domain of programming.
I made it to Jessica Ding's talk on Incremental Modernization: Refactoring Legacy OOP Application Code using Type Erasure and Functional C++. I think the main emphasis of things that I took away was on writing pure functions. This was a really nice talk discussing some of the benefits of using functional programming (or otherwise techniques for functional style things) to help modernize legacy codebases. 'pure' functions were highlighted. To make a function pure, it was demonstrated to use nodiscard (to signal intent), and otherwise avoid mutation/side-effects. Again, the benefits of pure functions are they're easy to test, and can enable a lot more concurrency. I thought when Jessica discussed this, it was neat to also talk about how pure functions much more easily can be turned into pipelines. 'Referential Transparency' is the term that was brought up, and lead into 'railway-oriented programming', I had not heard of this term previously, but I found this article as a nice first hit on a google search to explain more beyond Jessica's talk on Railroad oriented programming . __attribute__(pure) was something I did not know about that may be available. This talk also covers other important concepts like type erasure. Each topic is presented with nice 'trade-offs' along the way.
For my final talk, I had the pleasure of giving it together with Chris Croft-White! The talk was Code You Didn't Write: Understanding Large and Unfamiliar Codebases. Chris really gets credit for driving a lot of the material for the new stuff with this talk. We had previously given a version of this talk (and I gave it at a few meetups prior) titled: Understanding large and unfamiliar codebases. This years talk modernized a bit, discussing some of the challenges with, well, code you did not write (whether it be LLM or just yourself a few years ago). There are some handy tools, case studies, and just realities of 'being human' that we each discuss throughout the talk. In fact, as I'm updating my markdown to html transpiler in order to publish this post...I can relate that there is a lot of code from a year ago that I had trouble remembering (luckily I had at least some comments and another blog post to refer to--ha!).
I attended Tom Tesch's talk In Pursuit of a 6,000 FPS Game Boy Emulator. This is the third part in his trilogy of talks Blazing Trails: Building the World's Fastest GameBoy Emulator in Modern C++ - Tom Tesch CppCon 2024 and Tom Tesch - Building the World's Fastest GameBoy Emulator in Modern C++. One of the other key resources he cites is The Ultimate Game Boy Talk. I'll paraphrase one of the big takeaways:
"The best way to understand a computer is to build something".
One thing that Tom highlights regarding performance that I think is important for folks to be aware of is Link-Time Optimization (LTO). There are a few variations of link-time optimization, and 'thinLTO' that I learned about at the same time as PGO during my graduate student days. I think it was great that Tom mentioned this, it's another one of those things I always forget to tell folks about (and I'm very guilty of only running -O2 on projects and forgetting these other flags sometimes...). I thought there was an interesting case study on modulo operations and signed integer operations (around slides 100 or ~40 minutes). I would recommend folks watch the trilogy in order who are interested in building gameboy emulators, you'll learn quite a bit and find a lot of neat tools packed into Tom's talks (i.e. There's all sorts of gems in Tom's slides, like this cool asm emulator that I think is great for any learner doing assembly). Also, the other reason to go to Tom's talks is he will make you laugh. We really had a fun time during his session, and it was a nice way to close out the GameDev track.
Andre's keynote -- abstraction is king was one of the takeaways. I spent most of the time listening rather than typing out my notes here. One thing I will mention is that I think the proof-based languages that Andre mentioned are going to have there day. It was about 15 or so years ago where program synthesis was a pretty hot area. With research it tends to go in cycles where sometimes these ideas take about 10-15 years to come to fruition before they make their way into industry (Note: This is why it's incredibly important to fund basic research, returns on research far exceed the cost of the actual research in many cases.). I'd recommend folks go watch Andrei's talk, it should make you think.
As mentioned, I was able to write many of these notes while watching the sessions. The sessions this year were all high quality, and I could not make a fraction of the sessions I would have liked too. Given the number of sessions I attended (and gave), it's nearly half of a semesters worth of content crammed into a full week, I truly do learn a lot from these conferences. The best part of the conference of course is spending time with others. It was wonderful to see so many familiar faces and make new friends. I always feel a bit guilty I did not get to spend more time with some folks, but that's why we all have to come back next year :)