Guide to Advanced Programming in C
Table of Contents
http://pfacka.binaryparadise.com/articles/guide-to-advanced-programming-in-C.html
1. Integer Overflows and Promotions
2. Memory Allocation and Management
Many operating systems provide interface to control access over memory regions to protect memory against unintended read/write operations such as Posix mprotect . These mechanisms usually apply to whole memory pages. (mprotect以page为单位)
http://www.cs.nyu.edu/exact/core/doc/stackOverflow.txt 给出了每个平台默认stack大小以及修改方法
Stack Overflow Problems ======================= This file gives some hints on addressing this problem on different platforms. Under Unix-like systems, programs may throw a "Segmentation Fault" error. This can be due to stack overflow, especially from recursive function calls or huge data sets. In our demo program "Pi" (see "$(CORE_PATH)/progs/pi"), we compute Pi to any number of desired bits or digits. Here are some test results on when stack overflows will occur on different platforms, using their default stack sizes. platform default size # bits # digits =============================================================== SunOS/Solaris 8172K bytes <=39875 <=12003 (Shared Version) Linux 8172K bytes <=62407 <=18786 Windows 1024K bytes <=10581 <=3185 (Release Version) cygwin 2048K bytes <=3630 <=1092 If we now change their stack size to their maximum, our Pi program can compute more bits. platform stack size # bits # digits =============================================================== SunOS/Solaris unlimited >=100,000 30102 Linux 8172K bytes <=33,219,282 <=10,000,000(?) Windows 32768K bytes <=343077 <=12041 How to change the default stack size on different platforms: In general, under Unix-like platforms, the stack size is controlled by environment variable, not the program itself. So you cannot pass any flags to the compilers, like gcc, to setup stack size. Under Windows platforms, the stack size information is contained in the executable files. It can be set during compilation in Visual C++, but this is not available in gcc. Alternatively, Microsoft provides a program "editbin.exe" which can change the executable files directly. Here are more details: SunOS/Solaris: ============== > limit # shows the current stack size > unlimit # changes the stack size to unlimited > setenv STACKSIZE 32768 # limits the stack size to 32M bytes Linux: ====== > ulimit -a # shows the current stack size > ulimit -s 32768 # sets the stack size to 32M bytes Windows (during compilation): ============================= 1. Select "Project->Setting". 2. Select "Link" page. 3. Select "Category" to "Output". 4. Type your preferred stack size in "Reserve:" field under "Stack allocations". eg, 32768 in decimal or 0x20000 in hexadecimal. Windows (to modify the executable file): ======================================= There are two programs included in Microsoft Visual Studio, "dumpbin.exe" and "editbin.exe". Run "dumpbin /headers executable_file", and you can see the "size of stack reserve" information in "optional header values". Run "editbin /STACK:size" to change the default stack size.
3. Pointers and Arrays
4. Interpositioning
__attribute__ ((visibility (<value>))) 可以用来控制符号可见域,其中value可以指定为
- "default" # 对其他单元可见
- "hidden" # 仅对本单元可见
然后我们还能够通过编译选项-fvisibility来控制可见域默认值。
5. Explicit Inlining
inline __attribute__((always _inline)) 可以强制inline.
6. Vector Extensions
通常编译器都会提供对应的头文件(提供指令以及数据类型)
- x86: x86intrin.h
- MMX: mmintrin.h
- SSE: xmmintrin.h
- SSE2: emmintrin.h
- SSE3: mm3dnow.h
- 3dnow: tmmintrin.h
- AVX: immintrin.h
SIMD指令操作参数通常要求字节对齐(比如16字节),头文件里面应该都会定义这些数据类型
/* SSE2 */ typedef double __v2df __attribute__ ((__vector_size__ (16))); typedef long long __v2di __attribute__ ((__vector_size__ (16))); typedef int __v4si __attribute__ ((__vector_size__ (16))); typedef short __v8hi __attribute__ ((__vector_size__ (16))); typedef char __v16qi __attribute__ ((__vector_size__ (16)));