SEI CERT C++ Coding Standard 学习及翻译计划
稍微说说
最近在网上浏览到卡内基梅隆大学 (CMU) 软件工程研究所 (SEI) 发布的安全编码规范。SEI CERT
的规则都是为了确保 C/C++ 编程开发软件系统的安全性、可靠性和稳固性,比如消除一些未定义行为或者可利用漏洞。大致浏览了一下,很多规则相对比较基础,有些规则相对比较隐晦,示例代码很丰富简洁明了,文后还有一些实际漏洞的案例介绍等。规范的内容组织得也非常清晰,一方面是学习一下安全编码,另一方面也作为平时积累和查漏补缺的过程。
在此,记录一下自己对这份规范的蹩脚翻译,保留了原文英文,以备后用。顺便也提升一下阅读英文技术手册的能力,为了打工恰饭。
更新目录
Rule 01. Declarations and Initialization (DCL) 声明和初始化 (DCL)
- DCL50-CPP. Do not define a C-style variadic function
- DCL51-CPP. Do not declare or define a reserved identifier
- DCL52-CPP. Never qualify a reference type with const or volatile
- DCL53-CPP. Do not write syntactically ambiguous declarations
- DCL54-CPP. Overload allocation and deallocation functions as a pair in the same scope
- DCL55-CPP. Avoid information leakage when passing a class object across a trust boundary
- DCL56-CPP. Avoid cycles during initialization of static objects
- DCL57-CPP. Do not let exceptions escape from destructors or deallocation functions
- DCL58-CPP. Do not modify the standard namespaces
- DCL59-CPP. Do not define an unnamed namespace in a header file
- DCL60-CPP. Obey the one-definition rule
The following rules from the SEI CERT C Coding Standard also apply in C++:
Rule 02. Expressions (EXP) 表达式 (EXP)
- EXP50-CPP. Do not depend on the order of evaluation for side effects
- EXP51-CPP. Do not delete an array through a pointer of the incorrect type
- EXP52-CPP. Do not rely on side effects in unevaluated operands
- EXP53-CPP. Do not read uninitialized memory
- EXP54-CPP. Do not access an object outside of its lifetime
- EXP55-CPP. Do not access a cv-qualified object through a cv-unqualified type
- EXP56-CPP. Do not call a function with a mismatched language linkage
- EXP57-CPP. Do not cast or delete pointers to incomplete classes
- EXP58-CPP. Pass an object of the correct type to va_start
- EXP59-CPP. Use offsetof() on valid types and members
- EXP60-CPP. Do not pass a nonstandard-layout type object across execution boundaries
- EXP61-CPP. A lambda object must not outlive any of its reference captured objects
- EXP62-CPP. Do not access the bits of an object representation that are not part of the object’s value representation
- EXP63-CPP. Do not rely on the value of a moved-from object
The following rules from the SEI CERT C Coding Standard also apply in C++:
- EXP34-C. Do not dereference null pointers
- EXP35-C. Do not modify objects with temporary lifetime
- EXP36-C. Do not cast pointers into more strictly aligned pointer types
- EXP37-C. Call functions with the correct number and type of arguments
- EXP39-C. Do not access a variable through a pointer of an incompatible type
- EXP42-C. Do not compare padding data
- EXP45-C. Do not perform assignments in selection statements
- EXP46-C. Do not use a bitwise operator with a Boolean-like operand
- EXP47-C. Do not call va_arg with an argument of the incorrect type
Rule 03. Integers (INT) 整型 (INT)
The following rules from the SEI CERT C Coding Standard also apply in C++:
- INT30-C. Ensure that unsigned integer operations do not wrap
- INT31-C. Ensure that integer conversions do not result in lost or misinterpreted data
- INT32-C. Ensure that operations on signed integers do not result in overflow
- INT33-C. Ensure that division and remainder operations do not result in divide-by-zero errors
- INT34-C. Do not shift an expression by a negative number of bits or by greater than or equal to the number of bits that exist in the operand
- INT35-C. Use correct integer precisions
- INT36-C. Converting a pointer to integer or integer to pointer
Rule 04. Containers (CTR) 容器 (CTR) —— 2020.06.24 完成
- CTR50-CPP. 保证容器索引和迭代器在有效范围内
- CTR51-CPP. 使用有效的引用,指针,迭代器来引用容器的元素
- CTR52-CPP. 确保库函数不要溢出
- CTR53-CPP. 使用有效的迭代器范围
- CTR54-CPP. 不要相减不是指向同一个容器的迭代器
- CTR55-CPP. 不要使用对迭代器使用加法运算如果结果会溢出
- CTR56-CPP. 不要在多态对象上使用指针运算
- CTR57-CPP. 提供一个有效排序的谓词
- CTR58-CPP. 谓词函数对象不应该是 mutable
The following rules from the SEI CERT C Coding Standard also apply in C++:
Rule 05. Characters and Strings (STR) 字符和字符串 (STR) —— 2021.11.20 完成
- STR50-CPP. 确保有足够的空间来存储字符串的字符数据和空终终止符
- STR51-CPP. 不用试图以空指针创建 str::string
- STR52-CPP. 使用合法的引用, 指针和迭代器来引用 basic_string 的元素
- STR53-CPP. 元素访问的范围检查
The following rules from the SEI CERT C Coding Standard also apply in C++:
- STR30-C. Do not attempt to modify string literals
- STR31-C. Guarantee that storage for strings has sufficient space for character data and the null terminator
- STR32-C. Do not pass a non-null-terminated character sequence to a library function that expects a string
- STR34-C. Cast characters to unsigned char before converting to larger integer sizes
- STR37-C. Arguments to character-handling functions must be representable as an unsigned char
- STR38-C. Do not confuse narrow and wide character strings and functions
Rule 06. Memory Management (MEM) 内存分配 (MEM) —— 2021.11.16 完成
- MEM50-CPP. 不要访问被释放的内存
- MEM51-CPP. 正确地释放动态分配的资源
- MEM52-CPP. 检测并处理内存分配错误
- MEM53-CPP. 不要访问被释放的内存
- MEM54-CPP. 为 placement new 提供足够内存容量的正确对齐的指针
- MEM55-CPP. 遵守替换动态内存管理的要求
- MEM56-CPP. 不要在不相关的智能指针中存放一个已有所属的指针值
- MEM57-CPP. 避免对超出默认对齐的对象使用默认 new 操作符
The following rules from the SEI CERT C Coding Standard also apply in C++:
Rule 07. Input Output (FIO) 输入输出 (FIO)
The following rules from the SEI CERT C Coding Standard also apply in C++:
- FIO30-C. Exclude user input from format strings
- FIO32-C. Do not perform operations on devices that are only appropriate for files
- FIO34-C. Distinguish between characters read from a file and EOF or WEOF
- FIO37-C. Do not assume that fgets() or fgetws() returns a nonempty string when successful
- FIO38-C. Do not copy a FILE object
- FIO39-C. Do not alternately input and output from a stream without an intervening flush or positioning call
- FIO40-C. Reset strings on fgets() or fgetws() failure
- FIO41-C. Do not call getc(), putc(), getwc(), or putwc() with a stream argument that has side effects
- FIO42-C. Close files when they are no longer needed
- FIO44-C. Only use values for fsetpos() that are returned from fgetpos()
- FIO45-C. Avoid TOCTOU race conditions while accessing files
- FIO46-C. Do not access a closed file
- FIO47-C. Use valid format strings
Rule 08. Exceptions and Error Handling (ERR) 异常及错误处理 (ERR)
- ERR50-CPP. Do not abruptly terminate the program
- ERR51-CPP. Handle all exceptions
- ERR52-CPP. Do not use setjmp() or longjmp()
- ERR53-CPP. Do not reference base classes or class data members in a constructor or destructor function-try-block handler
- ERR54-CPP. Catch handlers should order their parameter types from most derived to least derived
- ERR55-CPP. Honor exception specifications
- ERR56-CPP. Guarantee exception safety
- ERR57-CPP. Do not leak resources when handling exceptions
- ERR58-CPP. Handle all exceptions thrown before main() begins executing
- ERR59-CPP. Do not throw an exception across execution boundaries
- ERR60-CPP. Exception objects must be nothrow copy constructible
- ERR61-CPP. Catch exceptions by lvalue reference
- ERR62-CPP. Detect errors when converting a string to a number
The following rules from the SEI CERT C Coding Standard also apply in C++:
- ERR30-C. Set errno to zero before calling a library function known to set errno, and check errno only after the function returns a value indicating failure
- ERR32-C. Do not rely on indeterminate values of errno
- ERR33-C. Detect and handle standard library errors
- ERR34-C. Detect errors when converting a string to a number
Rule 09. Object Oriented Programming (OOP) 面向对象编程 (OOP)
- OOP50-CPP. Do not invoke virtual functions from constructors or destructors
- OOP51-CPP. Do not slice derived objects
- OOP52-CPP. Do not delete a polymorphic object without a virtual destructor
- OOP53-CPP. Write constructor member initializers in the canonical order
- OOP54-CPP. Gracefully handle self-copy assignment
- OOP55-CPP. Do not use pointer-to-member operators to access nonexistent members
- OOP56-CPP. Honor replacement handler requirements
- OOP57-CPP. Prefer special member functions and overloaded operators to C Standard Library functions
- OOP58-CPP. Copy operations must not mutate the source object
Rule 10. Concurrency (CON) 并发 (CON)
- CON50-CPP. Do not destroy a mutex while it is locked
- CON51-CPP. Ensure actively held locks are released on exceptional conditions
- CON52-CPP. Prevent data races when accessing bit-fields from multiple threads
- CON53-CPP. Avoid deadlock by locking in a predefined order
- CON54-CPP. Wrap functions that can spuriously wake up in a loop
- CON55-CPP. Preserve thread safety and liveness when using condition variables
- CON56-CPP. Do not speculatively lock a non-recursive mutex that is already owned by the calling thread
The following rules from the SEI CERT C Coding Standard also apply in C++:
Rule 49. Miscellaneous (MSC) 杂项 (MSC)
- MSC50-CPP. Do not use std::rand() for generating pseudorandom numbers
- MSC51-CPP. Ensure your random number generator is properly seeded
- MSC52-CPP. Value-returning functions must return a value from all exit paths
- [MSC53-CPP. Do not return from a function declared [noreturn]]
- MSC54-CPP. A signal handler must be a plain old function
The following rules from the SEI CERT C Coding Standard also apply in C++:
- MSC30-C. Do not use the rand() function for generating pseudorandom numbers
- MSC32-C. Properly seed pseudorandom number generators
- MSC33-C. Do not pass invalid data to the asctime() function
- MSC37-C. Ensure that control never reaches the end of a non-void function
- MSC38-C. Do not treat a predefined identifier as an object if it might only be implemented as a macro
- MSC39-C. Do not call va_arg() on a va_list that has an indeterminate value
- MSC40-C. Do not violate constraints
- MSC41-C. Never hard code sensitive information
- FLP30-C. Do not use floating-point variables as loop counters
- FLP32-C. Prevent or detect domain and range errors in math functions
- FLP34-C. Ensure that floating-point conversions are within range of the new type
- FLP36-C. Preserve precision when converting integral values to floating-point type
- FLP37-C. Do not use object representations to compare floating-point values
- ENV30-C. Do not modify the object referenced by the return value of certain functions
- ENV31-C. Do not rely on an environment pointer following an operation that may invalidate it
- ENV32-C. All exit handlers must return normally
- ENV33-C. Do not call system()
- ENV34-C. Do not store pointers returned by certain functions
- SIG31-C. Do not access shared objects in signal handlers
- SIG34-C. Do not call signal() from within interruptible signal handlers
- SIG35-C. Do not return from a computational exception signal handler
- PRE30-C. Do not create a universal character name through concatenation
- PRE31-C. Avoid side effects in arguments to unsafe macros
- PRE32-C. Do not use preprocessor directives in invocations of function-like macros
关于 SEI CERT
规范
SEI CERT
的规则都是为了确保 C/C++ 编程开发软件系统的安全性、可靠性和稳固性,比如消除一些未定义行为或者可利用漏洞。
C 和 C++ 各一份。他们同时还有其他语言的,比如 Java
、Android
、Perl
的代码规范。这里主要自己写 C/C++,所以只关注这两份。相关信息可以移步到研究所维护的公开 wiki 主页。他们也会定期发布出版物,C/C++ 就是下面这两本,最新的都是 2016 v1 版本,官方主页有有下载通道。
SEI CERT C Coding Standard: Rules for Developing Safe, Reliable, and Secure Systems
SEI CERT C++ Coding Standard: Rules for Developing Safe, Reliable, and Secure Systems
关于安全编码规范,目前全球比较受认可的还有汽车工业软件可靠性协会的 MISRA C 和 MISRA C++,前者最新为 2012 版,后者最新为 2008 版。相对来说 SEI CERT C
和 SEI CERT C++
主页维护还很活跃,一直在更新。
SEI CERT C++ Coding Standard 中总共有 11
条规则,每条规则分别由标题、描述、不合规代码示例、合规方案、风险评估及其他一些实际案例、参考文献等组成。这 11
条规则分别是:
- Rule 01. Declarations and Initialization (DCL) 声明和初始化 (DCL)
- Rule 02. Expressions (EXP) 表达式 (EXP)
- Rule 03. Integers (INT) 整型 (INT)
- Rule 04. Containers (CTR) 容器 (CTR)
- Rule 05. Characters and Strings (STR) 字符和字符串 (STR)
- Rule 06. Memory Management (MEM) 内存分配 (MEM)
- Rule 07. Input Output (FIO) 输入输出 (FIO)
- Rule 08. Exceptions and Error Handling (ERR) 异常及错误处理 (ERR)
- Rule 09. Object Oriented Programming (OOP) 面向对象编程 (OOP)
- Rule 10. Concurrency (CON) 并发 (CON)
- Rule 49. Miscellaneous (MSC) 杂项 (MSC)
关于这份规范的其他信息在主页也都已列出,其中How this Coding Standard Is Organized的需要看一下,能够知道编码标准如何组织的,有助于阅读。
- Usage
- Tool Selection and Validation
- System Qualities
- Scope
- Rules Versus Recommendations
- Relation to the CERT C Coding Standard
- Introduction
- How this Coding Standard Is Organized
- Government Regulations
- Development Process
- Conformance Testing
- Automatically Generated Code
- Automated Detection
- Audience
- Acknowledgments
本文标题:SEI CERT C++ Coding Standard 学习及翻译计划
文章作者:xwnb
发布时间:2020-06-24
最后更新:2023-04-17
原始链接:https://xwnb.github.io/posts/3114312552/
版权声明:本博客所有文章除特别声明外,均采用 BY-NC-SA 许可协议。转载请注明出处!并保留本声明。感谢您的阅读和支持!
分享