华为C&C语言安全编程规范_V3.1.docx
《华为C&C语言安全编程规范_V3.1.docx》由会员分享,可在线阅读,更多相关《华为C&C语言安全编程规范_V3.1.docx(47页珍藏版)》请在淘文阁 - 分享文档赚钱的网站上搜索。
1、华为C&C+语言安全编程规范Huawei C&C+ Secure Coding StandardV3.1华为技术有限公司 版权所有 侵权必究目录0 前言目的适用范围 攻击者思维安全编码基本思想外部数据定义术语定义1 基础要求1.1 变量规则1.1.1:指针变量、表示资源描述符的变量、BOOL变量声明必须赋予初值规则1.1.2:指向资源句柄或描述符的变量,在资源释放后立即赋予新值规则1.1.3:类的成员变量必须在构造函数中赋予初值规则1.1.4:严禁对指针变量进行sizeof操作建议1.1.1:尽量使用const建议1.1.2:全局变量的访问如果涉及多个线程,必须加锁 建议1.1.3:同一个函数
2、内,局部变量所占用的空间不要过大1.2 断言(ASSERT)规则1.2.1:断言必须使用宏定义,禁止直接调用assert函数规则1.2.2:运行时可能会导致的错误,严禁使用断言规则1.2.3:严禁在断言内改变运行环境建议1.2.1:不要将多条语句放在同一个断言中1.3 函数规则1.3.1:数组作为函数参数时,必须同时将其长度作为函数的参数规则1.3.2:严禁对公共接口API函数的参数进行ASSERT操作规则1.3.3:不对内容进行修改的指针型参数,定义为const建议1.3.1:谨慎使用不可重入函数建议1.3.2:字符串或指针作为函数参数时,请检查参数是否为NULL建议1.3.3:在函数的开始
3、处对参数进行ASSERT操作(API除外)1.4 循环规则1.4.1:循环必须有退出条件1.5 异常机制规则1.5.1:禁用C+异常机制1.6 类规则1.6.1:如果有构造函数,则必须有析构函数规则1.6.2:构造函数内不能做任何有可能失败的操作规则1.6.3:严禁在构造函数中创建线程规则1.6.4:严禁出现 delete this操作规则1.6.5:如果类的公共接口中返回类的私有数据地址,则必须加const类型建议1.6.1:尽量避免定义public成员1.7 安全退出规则1.7.1:禁用atexit函数规则1.7.2:严禁调用kill、TerminateProcess函数终止其他进程规则1
4、.7.3:禁用pthread_exit、ExitThread函数建议1.7.1:禁用exit、ExitProcess函数(main函数除外)建议1.7.2:禁用abort函数2 字符串/数组操作规则2.1:确保有足够的存储空间规则2.2:对字符串进行存储操作,确保字符串有0结束符规则2.3:外部数据作为数组索引时必须确保在数组大小范围内规则2.4:外部输入作为内存操作相关函数的复制长度时,需要校验其合法性规则2.5:调用格式化函数时,禁止format参数由外部可控规则2.6:调用格式化函数时,format中参数的类型与个数必须与实际参数类型一致3 正确使用安全函数规则3.1:正确设置安全函数中
5、的destMax参数规则3.2:禁止不正确地重定义或封装安全函数规则3.3:禁止用宏重命名安全函数规则3.4:禁止自定义安全函数规则3.5:必须检查安全函数返回值,并进行正确的处理4 整数规则4.1:整数之间运算时必须严格检查,确保不会出现溢出、反转、除0规则4.2:整型表达式比较或赋值为一种更大类型之前必须用这种更大类型对它进行求值规则4.3:禁止对有符号整数进行位操作符运算规则4.4:禁止整数与指针间的互相转化规则4.5:禁止对指针进行逻辑或位运算(&、|、!、name, name) = 0) break;p = p-next;UnLock();return p;19. 性能敏感的代码,请
6、考虑采用原子操作或者无锁算法。相关指南:CERT.CON43-C. Do not allow data races in multithreaded code MITRE.CWE-366, Race condition within a thread建议1.1.3:同一个函数内,局部变量所占用的空间不要过大1. #define MAX_BUFF 0x10000002. int Foo()3. 4.char buffMAX_BUFF = 0;5.6. 程序在运行期间,函数内的局部变量保存在栈中,栈的大小是有限的。如果申请过大的静态数组,可能导致出现运行出错。 建议在申请静态数组的时候,大小不超过
7、0x1000。 下面的代码,bu申请过大,导致栈空间不够,程序发生stackoverow异常。相关指南:CERT.MEM05-C. Avoid large stack allocations1.2 断言(ASSERT)断言是一种除错机制,用于验证代码是否符合编码人员的预期。编码人员在开发期间应该对函数的参数、代码中间执行结果合理地使用断言机制,确保程序的缺陷尽量在测试阶段被发现。 断言被触发后,说明程序出现了不应该出现的严重错误,程序会立即提示错误,并终止执行。 断言必须用宏进行定义,只在调试版本有效,最终发布版本不允许出现assert函数,例如:1. #include 2. #ifdef D
8、EBUG3. #define ASSERT(f) assert(f)4. #else5. #define ASSERT(f) (void)0)6. #endif下面的函数VerifyUser,上层调用者会保证传进来的参数是合法的字符串,不可能出现传递非法参数的情况。因此,在该函数的开头,加上4个ASSERT进行校验。1. BOOL VerifyUser(const char *userName, const char *password)2. 3. ASSERT(userName != NULL);4. ASSERT(strlen(userName) 0);5. ASSERT(password
9、 != NULL);6. ASSERT(strlen(password) 0);7. .8. 以下的switch,由于不可能出现default的情况,所以在default处直接调用ASSERT:1. enum 2. COLOR_RED = 1,3. COLOR_GREEN,4. COLOR_BLUE5. ;6. .7. switch (color) 8. case COLOR_RED:9. .10. case COLOR_GREEN:11. .12. case COLOR_BLUE:13. .14. default: 15. ASSERT(0);16.17. 以下代码,SendMsg是CMsg
10、类的成员函数,socketID是成员变量,在调用SendMsg的时候必须保证socketID已经被初始化,因此在此处用ASSERT判断socketID的合法性。1. CMsg:CMsg()2. 3. socketID = INVALID_SOCKET;4. 5. int CMsg:SendMsg(const char *msg, int len)6. 7. ASSERT(socketID != INVALID_SOCKET);8. .9. ret = send(socketID, msg, len, 0);10. .11. 在linux内核中定义ASSERT宏,可以采用如下方式:1. #ifd
11、ef DEBUG2. #define ASSERT(f) BUG_ON(!(f)3. #else4. #define ASSERT(f) (void)0)5. #endif相关指南:CERT.MSC11-C. Incorporate diagnostic tests using assertions规则1.2.1:断言必须使用宏定义,禁止直接调用系统提供的assert()断言只能在调试版使用,断言被触发后,程序会立即退出,因此严禁在正式发布版本使用断言,请通过编译选项进行控制。 错误用法如:1. int Foo(int *array, int size)2. 3. assert(array !
12、= NULL);4. .5. 规则1.2.2:运行时可能会导致的错误,严禁使用断言1. FILE *fp = fopen(path, r);2. ASSERT(fp != NULL);/文件有可能打开失败3. char *str = (char *)malloc(MAX_LINE);4. ASSERT(str != NULL);/内存有可能分配失败5. ReadLine(fp, str);6. char *p = strstr(str, age=);7. ASSERT(p != NULL);/文件中不一定存在该字符串8. int age = atoi(p+4);9. ASSERT(age 0)
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 华为C&C 语言安全编程规范_V3.1 华为 amp 语言 安全 编程 规范 _V3
限制150内