That is surely not the case for C#, contrary to most JVM implementations, on the CLR CIL is always jitted before execution since .NET 1.0, and this not taking into account AOT scenarios like NGEN (since .NET 1.0), and everything that came later as AOT toolchains.
The only .NET implementations that interpret CIL were the .NET Compact and Micro frameworks due to hardware limitations, nowadays mostly gone as .NET workloads, and alternative implementations like Mono.
You’re correct, where I got confused is the lazy per-method JIT and the tiers of JIT optimization. My understanding is that dotnet only compiles on first function call, or when it has to for things like generics. So, some code is never compiled if it’s never executed. And then, functions will be re-JIT at higher optimization levels under certain conditions later. You certainly know more about this than me, but yes I was wrong about conditional JIT.
The only .NET implementations that interpret CIL were the .NET Compact and Micro frameworks due to hardware limitations, nowadays mostly gone as .NET workloads, and alternative implementations like Mono.