Dynamic languages typically aren't compiled, though. So either a language would have some kind of VM of its own (which is typically implemented in C, and hence can be implemented in CIL), or else they have some form of JIT compilation, which can use CIL as a target.
If you bothered to read why DLR was created, you will see why CIL wasn't enough.
Or why Java following the same linr of thought had to follow DLR changes to the CLR and introduce invokedynamic byte code and its related infrastructure.
I know why DLR was created. I work on a team that has one of the guys who was working on it, and specifically on IronPython.
My point is that they are two different layers in the stack. CIL and JVM are lower level. DLR is a higher level layer. Said higher level can be implemented on any kind of lower level that's powerful enough - for example, you could have a kind of DLR directly on top of native code. All that matters for the lower level is that it's flexible enough to permit something like DLR to be implemented on top of it. CIL is undeniably flexible enough for that.
I remember reading some articles that justified DLR as CIL not having enough semantics that allowed to properly implement optimization algorithms commonly used in dynamic languages, like method lookup and call site caches.
Then again, maybe I understood it wrongly back then and I surely don't have the knowledge of your team.
Yes, that's right. But it's kinda what I meant. CIL is really roughly the level of C, plus some strongly typed object oriented stuff on top. It doesn't really offer anything useful for a dynamic language directly. But you can use it to implement a dynamic language VM with all those optimizations - just like C was used to write Parrot VM. DLR is to CLR as Parrot is to native code.