为什么C用于驱动程序开发而不是C#?

时间:2010-10-14 07:05:35

标签: c# c driver

  

可能重复:
  C# driver development?

为什么我们使用C进行设备驱动程序开发而不是C#?

7 个答案:

答案 0 :(得分:14)

因为C#程序无法在内核模式下运行(Ring 0)。

答案 1 :(得分:6)

主要原因是C比C#更适合低级(接近硬件)开发。 C被设计为便携式汇编代码的一种形式。而且,很多时候使用C#可能很困难或不安全。关键时刻是在ring-0或内核模式下运行驱动程序。大多数应用程序不打算在此模式下运行,包括.NET运行时。

虽然理论上可以做到,但很多时候C更适合这项任务。一些原因是对产生的机器代码进行更严格的控制,并且在直接使用硬件时更接近处理器几乎总是更好。

答案 2 :(得分:2)

因为C#是一种高级语言,它无法直接与处理器通信。 C代码直接编译成处理器可以理解的本机代码。

答案 3 :(得分:2)

忽略C#的一些面向对象语言(如C#)的托管语言限制,通常会在开发驱动程序时妨碍我们。驱动程序开发 - 实际上是在硬件中读取和操作位 - 通常具有严格的时序约束,并且使用在其他类型的编程中避免的编程实践,例如忙等待和取消引用从整数常量值设置的指针。设备驱动程序通常实际上是用C和内联汇编的混合编写的(或者使用C编译器通常不会发出指令的其他一些方法)。单独的低级锁定机制(用汇编编写)足以使C#难以使用。 C#具有许多锁定功能,但是当你挖掘它们时它们处于线程级别。驱动程序需要能够阻止中断以及其他线程来执行某些任务。

面向对象的语言也倾向于一遍又一遍地分配和释放(通过垃圾收集)大量内存。但是,在中断处理程序中,您访问堆分配功能的能力受到严格限制。这是因为堆分配可能会触发垃圾收集(昂贵),因为您必须避免和处理中断代码和尝试同时分配的非中断代码。没有对这段代码,编译器的输出以及管理代码(VM或可能本地编译且仅使用库)的任何限制,你可能最终会遇到一些非常奇怪的错误。

托管语言必须由某人管理。这种管理可能依赖于功能底层的操作系统。这为许多(但不是全部)驱动程序使用托管代码产生了引导问题。

完全有可能在C#中编写设备驱动程序。如果您正在驾驶一个串行设备,例如GPS设备,那么它可能是微不足道的(尽管您将使用较低的UART芯片或USB驱动程序,可能是用C或汇编编写的)因为它可以完成作为申请。如果您正在编写以太网卡(不用于网络引导),那么(理论上)可能会在某些部分使用C#,但您可能会严重依赖于使用其他语言编写的库和/或使用操作系统的用户空间驱动程序功能。

C用于驱动程序,因为它具有相对可预测的输出。如果您对处理器有一点了解,可以在C中编写一些代码,为该处理器编译,并且可以很好地猜测它的装配是什么样的。您还将了解这些指令的确定性。他们中的任何一个都不会让你感到惊讶并启动垃圾收集器或调用析构函数(或最终确定)。

答案 4 :(得分:1)

只是为了达林迪米特罗夫的回答。是的C#程序无法在内核模式下运行。

但他们为什么不能呢?

在Patrick Dussud撰写的interview中,他介绍了在Vista开发过程中尝试将CLR包含在低级*中的尝试。他们遇到的问题是,CLR依赖于操作系统安全库,后者依赖于UI级别。他们无法为Vista解决这个问题。除了奇点,我不知道有任何其他的努力。

*请注意,虽然“低级别”可能不足以在C#中编写驱动程序,但至少是必要的。

答案 5 :(得分:0)

这是诚实的事实。倾向于擅长硬件或硬件接口的人不是非常复杂的程序员。他们倾向于坚持像C这样的简单语言。否则,框架就会发展到允许像C ++甚至C#这样的语言在内核级别使用。整个操作系统都是用C ++编写的(ECOS)。所以,恕我直言,这主要是传统。

现在,一些合法的论据,反对在驱动程序/内核等要求严格的代码中使用更复杂的语言。有可见性方面。 C#和C ++编译器在幕后做了很多工作。无害的赋值语句可能隐藏一堆代码(运算符覆盖,属性)。例外的成本可能不清楚。垃圾收集使对象/内存的生命周期不明确。所有使编程更容易的功能,也可以自行解决。

然后该语言需要生态系统。如果所需的功能包含太多组件,则单独的大小可能会成为一个因素。如果语言中的原语往往很重(为了有用的软件抽象),这就是驱动程序和内核可能不愿意承担的负担。

答案 6 :(得分:-1)

C语言支持更多与其他外围设备接口的语言。所以C用于开发系统软件。唯一的问题是需要管理内存。这是开发人员的噩梦。但在C#中,内存管理可以轻松自动完成(c和C之间有很多差异# ,尝试谷歌搜索)。