日期:2014-05-16  浏览次数:20697 次

初探Linux kernel之喝凉水系列二

初探Linux kernel之喝凉水系列二
2011年03月03日
  今天来介绍一下内核开发和应用程序开发的差别:
  l         内核编程时不能访问C库(因为Linux下很多C库函数是对Linux系统调用的封装,自身怎么可以调用自身呢?)
  l         内核编程时必须使用GNU C。
  l         内核编程时缺乏像用户空间那样的内存保护机制。
  l         内核编程时浮点数很难使用。
  l         内核只有一个很小的定长堆栈。
  l         由于内核支持异步中断、抢占和SMP,因此必须时刻注意同步和并发。
  l         要考虑可移植性的重要性。
  下面对这几点进行描述。
  1、首先就是内核不能访问C库的问题,你想啊Linux下很多C库函数是对Linux系统调用的封装,自身怎么可以调用自身呢?这里的系统调用学过OS的应该都清楚,是系统应用给用户提供的编程接口,注意这里的对象是用户。注意啦,程序员也是分等级的,在kernel级别的编程(这里指纯kernel编程),你已经看不到系统调用,此时你的职责可能就是为系统添加一个系统调用(后边会讲到),且C库是应用层对底层系调(系统调用,为了便于我打字,后边可能会多次出现)的封装,从逻辑的角度你也该明白了吧。那么问题就出来了,没有c库怎么办,还谈什么模块化,难不成都自己写?这就是接下来的问题。
  2、既然kernel不能调用C库,那么它就得拥有自己独立的c语言库,这样才能高内聚低耦合,并且提升其安全性,所以就用了GNU C 。短小精悍效率高,毕竟是专才专用。这里需要注意一点,内核中没有实现printf(); 但是有功能更为强大的printk();其实也谈不上功能强大(因为printf() 本身就很强大,尤其是在调试时,这里也显出了printk的优势),它和printf() 的显著区别就是printk() 允许通过指定一个标志来设置优先级。Syslog会根据这个优先级标志来决定什么地方显示这条系统消息。如:
  printk( KERN_ERR  “This is an error!”); // 不理解吧,我也不理解,后边内核调试时肯定还会将这东西,不怕。
  3、内核编程时缺乏像用户空间那样的内存保护机制。你在做什么?内核好不好,这是一个OS的核心部分,控制着整个系统的运转,自然要有处理协调整个系统的权利,在内核coding的东西就是OS核心的一部分,是给别人或者自己在OS的上一层用的。既然你是把握这一切的,且又是在硬件基础上的第一层抽象,另外还把握着全局,内存的控制自然也不能束缚你,就像在公司工作一样,领导要在可能的范围内尽可能的下放权力,下属才能发挥他的极致,估计kernel也是这样,内存访问,包括其他的内核结构都不对出于内核的你进行束缚,当然也没有进行相应的保护机制。因为这是的内核是你的,你没必要傻逼到写程序让自己的系统崩溃吧,哈哈。这也留了一个问题,就是在coding过程中要斟酌好啊。
  4、内核编程时浮点数很难使用。这里你需要知道的是在用户空间的进程进行浮点操作时,kernel会完成从整数到浮点数的模式转换,一般是通过捕获陷阱并作相应的处理的实现的。(陷阱可以算是一种特殊的异常,是从用户态进入内核态的途径,后边会进一步介绍。)
  与用户空间不同的是,kernel并不能完美的支持浮点操作,因为自身不能陷入自身。在kernel中使用浮点数时,除了要人工保存和恢复浮点寄存器,还有很多琐碎的事要做。直截了的说就是:不要在kernel中使用浮点数!!!
  5、内核只有一个很小的定长堆栈。在x86上,kernel的栈是在编译时配置的,可为4k或者8k,且每个处理器都有自己的栈。为什么这么小呢?大了不可以么?我的理解是,现在都在追求微内核,这是一方面原因,还有就是内核也是一个软件,只不过是包含了硬件抽象且富含大量系统管理功能的进程,而其他功能的进程(系统调用,其他内核进程),在调度是,存在内核抢占和代替内核执行的情况,这是要将要执行的进程的上下文切换过来,当然这些数据都会出现在栈里边,你想如果栈很大,那么操作时内存访问地址会很长,访问时占内存且费时间,会降低效率,所以要尽可能的小且灵活……
  6、由于内核支持异步中断、抢占和SMP,因此必须时刻注意同步和并发。这不仅仅是linux kernel ,是所有现有的多进程/多线程并发OS都要注意的,包括多线程编程也一样,你就把kernel 想成是一个多线程的执行程序就OK了,不难理解。
  7、要考虑可移植性的重要性。这个更不用多说了,因为这是linux的一个灰常显著的特征,大到企业的服务器,小到嵌入式的android ,IP camera ……等很多东西不同平台构架的cpu …… 应该是目前跑的平台最多的OS了,所以他的内核要有足够的可移植性,似乎有点java的感觉,哈哈,毕竟我是学java出身的啊……
  OK,未完待续……
  其他相关请关注:http://blog.csdn.net/dreambegin 博客更新。