学习嵌入式C语言要掌握到什么程度?

姓名:李鸿彬

学号:16040520011

转载自https://www.zhihu.com/question/29590155,有删节

【嵌牛导读】学习C语言,尤其是对于嵌入式底层工程师来说,我们要学习的不仅仅是C语言的基本语法,更重要的是如何通过C语言这个工具,去理解我们的计算机系统、CPU架构。

【嵌牛鼻子】一个sizeof(int)引发的思考 自增运算符带来的思考 代码分析 

【嵌牛提问】1)程序到底是如何编译、链接、和运行的?

2)运行时各种代码段、数据段、BSS段、堆栈在内存中如何分布,如何管理的?

3)程序在不同的平台(ARM、X86)、裸机环境或有OS的环境(linux、uc/os等)有何不同?

4)静态链接与动态链接的过程有何差异,为什么要使用动态链接?共享库?

5)不同的开发平台、IDE、编译器,C语言的编程有何差异和不一样的地方,如何做到跨平台、增强程序的可移植性和鲁棒性?

6)各种变量名、函数名、数组名、指针的本质是什么?编译器是如何处理的?

【嵌牛正文】

搞懂了这些语言背后计算机系统知识,还远远不够,还要去学习操作系统相关的知识:进程、线程、中断、内存管理

对于嵌入式开发来说,还要学习ARM等处理器架构知识、GCC编译器对C标准的各种扩展,各种生僻的用法,否则你去看linux内核代码、驱动代码,总感觉“怪怪的”,好像哪里不对,跟平时的C语言不太一样,感觉自己学的是一门假C语言......

C语言的精华是内存、存储管理。各种隐藏很深的bug其实也跟内存有关:内存越界、内存泄露、野指针等等,一个不经意的疏漏,就可能阴沟里翻船。就是有多年工作经验的工程师也不敢保证自己写的代码一定没有问题。C语言默认大家都是大牛、计算机专家,可惜现实中往往太多挖坑小能手,太多猪一样的队友。如何养成良好的编程习惯,避免各种bug,也是C语言进阶学习的一个重点。

为了测试一下你对C语言的掌握程度,下面的几个测试题,可以自我测试一下,检测一下自己的C语言水平,是否达到嵌入式工程师(尤其是内核驱动工程师)的要求:

1)你对以下C语言的基本概念是否掌握?是否能用一句话概括出来?

标识符、关键字、预定义标识符、分隔符、语法检查、语义检查、表达式、语句、左值、对象、结合性、左结合右结合、未定义行为

2)一个sizeof(int)引发的思考

•sizeof是函数吗?是关键字?预定义标识符?后两者有何区别?•在32位和64位的Windows7系统下,结果分别是多少?•在32位和64位X86CPU系统下,结果分别是多少?•在8位、16位、32位ARM系统环境下运行结果分别是多少?•在TurboC、keil、GCC-32、GCC-64开发环境下,结果是多少?•使用gcc–m32生成一个32位代码,运行在64位环境下,结果?使用gcc–m64生成一个64位代码,运行在32位环境下,结果?

3)自增运算符带来的思考

下面一段程序,在不同的编译器上编译,结果是多少,一样吗?为什么?

i=1,j=2;printf(“%d\n”,i++*i++);i+++j;

4)代码分析

使用tc、C-free、GCC、VC++6.0、visual studio分别编译下面代码,会出现什么问题?

intmain(){inti;//定义一个变量inta[0];printf("hello world!\n");intj;for(intk=0;k<10;k++);return0;}

5)在linux环境下,运行下面代码,会出现什么问题?

int*data_copy(int*p){intbuffer[8192*1024];memcpy(buffer,p,8192*1024);returnbuffer;}

6)下面是linux内核代码的一部分(摘自Linux4.4内核),你能看懂多少?

#define stamp(fmt, args...) pr_debug("%s:%i: " fmt "\n", __func__, __LINE__, ## args)#define container_of(ptr, type, member) ({ \const typeof(((type *)0)->member) * __mptr = (ptr); \(type *)((char *)__mptr - offsetof(type, member)); })structurb{…structusb_iso_packet_descriptoriso_frame_desc[0];}urb->transfer_flags&=~(URB_DIR_MASK|URB_DMA_MAP_SINGLE|URB_DMA_MAP_PAGE);

你可能感兴趣的:(学习嵌入式C语言要掌握到什么程度?)