深刻理解C指针chap7

CERT组织
地址空间布局随机化(Address Space Layout Randominzation):会把应用程序的数据区域随机放置在内存中,这些数据区域包括代码,栈和堆。
数据执行保护(Data Execution Prevention)数组

  • 7.1 指针的声明和初始化
    • 不恰当的指针声明
      • 不要有歧义
      • 用类型定义代替宏定义(类型定义容许编译器检查做用域范围)。
      define PINT int*   
      	PINT ptr1,ptr2;
      	```//换成
      typedef int* PINT; PINT ptr1,ptr2;
       
    • 使用指针前未初始化
      在初始化指针以前就使用指针会致使运行时错误,称为野指针
    • 处理未初始化的指针
      • 老是用NULL来初始化指针
      if(pi == NULL){
      	   // 不该该解引pi
      	}else{
      	   // 能够使用pi
      	}
      • 用assert函数
        assert(pi != NULL);
      • 用第三方工具
  • 7.2 指针的使用问题
    • 覆写对象边界之外的内存就会致使缓冲区溢出。(溢出在应用程序的地址空间内;举出发生在栈帧的元素上;)
      • 访问数组元素时没有检查索引值
      • 对数组指针作指针算术运算时不够当心
      • 用gets这样的函数从标准输入读取字符串
      • 误用strcpy和strcat这样的函数
    • 7.2.1 测试NULL
    float *vector = malloc(20 * sizeof(float));
    	if(vector == NULL){//malloc分配内存失败}
    • 错误使用解引操做
    • 迷途指针
    • 越过数组边界访问内存
    • 错误计算数组长度
    • 错误使用sizeof操做符
    int buffer[20];
    • 必定要匹配指针类型
    int num = 2147483647;  
    	int *pi = #  
    	short *ps = (short*)pi;  
    	//将一个整数指针赋值给一个短整数指针
    • 有界指针
    • 字符串的安全问题
    • 指针算术运算和结构体
    • 函数指针问题
      • if(getSystemStatus == 0)//把函数的地址与0做比较,而不是调用函数后的返回值与0比较。只用函数名自己时返回的是函数的地址。
      • 若是函数类型和函数指针的类型不一样,不要把函数赋给函数指针
      int (*fptrCompute)(int,int);  
      	int add(int n1,int n2, int n3){return n1+n2+n3;}  
      	fptrCompute = add;  
      	fptrCompute(2,5);  
      	//试图只用两个参数调用add函数,而该函数指望的是三个参数,能编译,但输出不肯定。
  • 7.3 内存释放问题
    • 重复释放
      避免的方法:释放指针后老是将其置为NULL,大部分堆管理器都会忽略后续对空指针的释放。free(name);name=NULL
    • 消除敏感数据
      • 覆写敏感数据
      int userID;  
      	char *securityQuestion;
      memset(name,0,sizeof(name));
      	userID = 0;
      	memset(securityQuestion,0,sizeof(securityQuestion));
      • name为指针,应该在释放内存以前将其清空
      ...  
      memset(name,0,sizeof(name));
      free(name);```
  • 7.4 使用静态分析工具
    • GCC编译器的 -Wall选项能够启用编译器警告。
相关文章
相关标签/搜索