.NET Memory Performance Analysis
This document aims to help folks who develop applications in .NET with how to think about memory performance analysis and finding the right approaches to perform such analysis if they need to. In this context .NET includes .NET Framework and .NET Core. In order to get the latest memory improvements in both the garbage collector and the rest of the framework I strongly encourage you to be on .NET Core if you are not already, because that’s where the active development happens.
When I was writing this document I intended to introduce concepts like concurrent GC or pinning as needed by the explanation of the analysis. So as you read it, you’ll gradually come across them. If you already kind of knew what they are and are looking for explanation on a specific concept here are the links to them
This Goes to Eleven - Decimating Array.Sort with AVX2
Let’s get in the ring and show what AVX/AVX2 intrinsics can really do for a non-trivial problem, and even discuss potential improvements that future CoreCLR versions could bring to the table.
Everyone needs to sort arrays, once in a while, and many algorithms we take for granted rely on doing so. We think of it as a solved problem and that nothing can be further done about it in 2020, except for waiting for newer, marginally faster machines to pop-up. However, that is not the case, and while I’m not the first to have thoughts about it; or the best at implementing it, if you join me in this rather long journey, we’ll end up with a replacement function for Array.Sort, written in pure C# that outperforms CoreCLR’s C++2 code by a factor north of 10x on most modern Intel CPUs, and north of 11x on my laptop. Sounds interesting? If so, down the rabbit hole we go…
Very well done.
Analysing .NET start-up time with Flamegraphs
Recently I gave a talk at the NYAN Conference called ‘From ‘dotnet run’ to ‘hello world’: In the talk I demonstrate how you can use PerfView to analyse where the .NET Runtime is spending it’s time during start-up:
Research based on the .NET Runtime
Over the last few years, I’ve come across more and more research papers based, in some way, on the ‘Common Language Runtime’ (CLR). So armed with Google Scholar and ably assisted by Semantic Scholar, I put together the list below.
"Stubs" in the .NET Runtime
‘Stubs’, as they’re known in the runtime (sometimes ‘Thunks’), provide a level of indirection throughout the source code, there’s almost 500 mentions of them!
This post will explore what they are, how they work and why they’re needed.
.NET Internals Cookbook
In this series I answer various .NET questions. Some of them are asked during interviews, some of them I see on the internet, some of them are completely made up. The goal is to provide short answer with links to references if needed. This is by no means a .NET tutorial or experts reference, this is just a bunch of useful answers to refresh your knowledge.
Some of this gets pretty deep actually.
Is C# a low-level language?
Specifically, what happens when translating a C++ raytracer and trying to make it fast.
I started by simply porting the un-obfuscated C++ code line-by-line to C#. Turns out that this was pretty straight forward, I guess the story about C# being C++++ is true after all!!
An Exhausting List of Differences Between VB.NET & C#
Before I joined Microsoft I might have vaguely held that idea too and used it in arguments to push back against detractors or reassure someone. I understand its allure. It’s easy to grasp and very easy to repeat. But, working on Roslyn–the complete from-the-ground-up rewrite of both VB and C#–for 5 years, I came to understand how unequivocally false this idea really is. I worked with a team of developers and testers to re-implement from scratch every inch of both languages as well as their tooling in a huge multi-project solution with millions of lines of code written in both. And with so many developers switching back and forth between them, and a high bar for compatibility with the outputs and experiences of previous versions, and the need to faithfully represent every detailed nuance throughout a massive API surface area I got to be intimately familiar with the differences.
This list is not exhaustive. It’s exhausting. It’s not all the differences there are, it’s not even all the differences I’ve ever known, it’s just the differences I can remember off the top of my head until such time as I become too tired to go on; until I’m exhausted. If I or others run into or remember other differences I’ll gladly update this list after the fact.
"Stack Walking" in the .NET Runtime
The CLR makes heavy use of a technique known as stack walking (or stack crawling). This involves iterating the sequence of call frames for a particular thread, from the most recent (the thread’s current function) back down to the base of the stack.
The rest of this post will explore what it is, how it works and why so many parts of the runtime need to be involved.
Announcing .NET Core 3 Preview 1 and Open Sourcing Windows Desktop Frameworks
Today, we are excited to announce that are open sourcing WPF, Windows Forms, and WinUI, so the three major Windows UX technologies will be open sourced. For the first time ever, the community will be able to see the development of WPF, Windows Forms, and WinUI happen in the open and we will take contributions for these frameworks on .NET Core. The first wave of code will be available in GitHub today and more will appear over the next few months.
Fuzzing the .NET JIT Compiler
I recently came across the excellent ‘Fuzzlyn’ project, created as part of the ‘Language-Based Security’ course at Aarhus University. As per the project description Fuzzlyn is a: … fuzzer which utilizes Roslyn to generate random C# programs
Announcing F# 4.5
The first thing you may notice about F# 4.5 is that it’s higher than F# 4.1.
Performance Improvements in .NET Core 2.1
Back before .NET Core 2.0 shipped, I wrote a post highlighting various performance improvements in .NET Core 2.0 when compared with .NET Core 1.1 and the .NET Framework. As .NET Core 2.1 is in its final stages of being released, I thought it would be a good time to have some fun and take a tour through some of the myriad of performance improvements that have found their way into this release.
How we doubled Mono’s Float Speed
I decided to look at what was going on, and document possible areas for improvement. As a result of this benchmark, and looking into this problem, we identified three areas of improvement:
Taking a look at the ECMA-335 Standard for .NET
The rest of this post will take a look at the standard, exploring the contents and investigating what we can learn from it (hint: lots of low-level details and information about .NET internals)
How generics were added to .NET
Before we dive into the technical details, let’s start with a quick history lesson, courtesy of Don Syme who worked on adding generics to .NET and then went on to design and implement F#, which is a pretty impressive set of achievements!
There are some significant differences between the Rotor source code and the real .NET framework. Most notably the JIT and GC are completely different implementations (due to licensing issues, listen to DotNetRocks show 360 - Ted Neward and Joel Pobar on Rotor 2.0 for more info). However, the Rotor source does give us an accurate idea about how other core parts of the CLR are implemented, such as the Type-System, Debugger, AppDomains and the VM itself. It’s interesting to compare the Rotor source with the current CoreCLR source and see how much of the source code layout and class names have remained the same.
Announcing .NET Core 2.1 Preview 1
.NET Core 2.1 Roadmap
We have been thinking of .NET Core 2.1 as a feedback-oriented release after the more foundational .NET Core 2.0 release. The following improvements are based on some of the most common feedback.
Resources for Learning about .NET Internals
I wouldn’t recommend reading through the entire list, at least not in one go, your brain will probably melt. Picks some posts/topics that interest you and start with those.
.NET Instrumentation via MSIL bytecode injection
In this article we will explore the internals of the .NET framework with the purpose of providing an innovative method to instrument .NET programs at runtime.