Tag: gcc

snprintf错误。 sizeof的参数与destination相同

gcc 4.8在构建时给我一个错误 #include #include static inline void toto(char str[3]) { snprintf(str, sizeof(str), “XX”); } int main(){ char str[3]; toto(str); return 0; } 这是gcc错误 错误:’snprintf’调用中’sizeof’的参数与目标的表达式相同; 你的意思是提供一个明确的长度? 注意:我使用-Wall -Werror标志将警告转换为错误。 这里有类似的东西在评论中,有人回答了这个问题 “对于固定长度的缓冲区,我通常使用strncpy(dest,src,sizeof(dest)); dest [sizeof(dest)-1] =’\ 0′;这保证了NULL终止,并且比snprintf更麻烦,更不用说了很多人都使用snprintf(dest,sizeof(dest),src);相反,当他们的程序任意崩溃时会非常惊讶。“ 但这是错误的:gcc 4.8说 “错误:’strncpy’调用中’sizeof’的参数与目标的表达式相同;你的意思是提供显式长度吗?[-Werror = sizeof-pointer-memaccess]” 在gcc 4.8文档中,他们正在讨论这个问题 :他们说: -Wall的行为已更改,现在包含新警告标志-Wsizeof-pointer-memaccess。 这可能会导致代码中的新警告与以前版本的GCC一起干净地编译。 例如, include string.h struct A { }; int main(void) { A obj; […]

为什么在堆栈中为局部变量分配的内存多于C ++中所需的内存?

我正在阅读缓冲区溢出。 我发现有关堆栈上局部变量的内存分配的一个奇怪的事情 int f1 () { char string1[12]; char string2[4]; } 这里分配发生在堆栈上。 现在,在GCC中, string2被分配了4个字节,但是如果我声明除了2的幂(最多16个)之外,那么它由编译器分配16个字节。 这意味着如果我在3,5,6,7,….,15个字节中分配string2,那么它由编译器分配16个字节,但如果我分配2的幂,如1,2,4,8 ……然后它被分配完全相同的大小。 如果我分配超过16个字节(不是2的幂),那么它分配32个字节(我估计高达32个字节)。 而在Visual Studio中,如果我分配1个字节,则分配9个字节,如果从2-4个字节分配,则分配12个字节,如果从5-8个字节开始,则编译器分配16个字节。 任何人都知道为什么这样的任务??? Atleast在Visual Studio中,如果有缓冲区溢出,我会收到调试错误,但在gcc中没有任何反应。 GCC仅在发生过大的溢出时才提供分段故障。

`({…})`如何返回一个值?

我最近发现了这个GCC宏: #define max(a,b) \ ({ typeof (a) _a = (a); \ typeof (b) _b = (b); \ _a > _b ? _a : _b; }) 在我看到这段代码之前我没有意识到,代码块{…}可以某种方式在C中返回值。 1)你能给我一个暗示它是如何工作的吗? 虽然,我通常可以通过滥用逗号运算符来实现相同的结果: #define max(a,b) \ (typeof (a) _a = (a), \ typeof (b) _b = (b), \ (_a > _b ? _a : _b)) 或者如果只是为了副作用,我会使用do { … } while(0) […]

“警告:假设循环不是无限”的解释是什么?

我刚刚决定将unsigned变量更改为int并在重新编译有问题的代码时受到此警告消息的欢迎: freespace_state.c:203: warning: assuming that the loop is not infinite 有问题的一行: for (x = startx; x <= endx; ++x, ++xptr) 这个循环是60行代码(包括空格/括号等),并且在其中有一个goto ,并且至少出现一次continue 。 在这种情况下,我认为我很欣赏GCC假设这个循环不是无限的,因为它永远不应该无限循环。 GCC试图在这里告诉我什么? 警告的语法几乎暗示警告应该在其他警告的范围内进行,但在该背景下没有警告。 [编辑]这完全是我自己的错。 我从这里的一个问题偷了一些优化和警告选项而没有真正了解它们,并且忘记了它们。 请参阅Mark Rushakoff的回答,此外,我还使用-Wunsafe-loop-optimizations来明确警告GCC是否对循环做出假设。 请参阅http://gcc.gnu.org/onlinedocs/gcc/Optimize-Options.html

为什么C99中不包含定点类型?

值得庆幸的是, complex类型修饰符被引入C99标准。 我不明白为什么决定省略对定点运算的支持(特别是支持分数类型,如1.15 {signed}或0.32 {unsigned}),这些类型对DSP编程如此重要? GCC是否通过扩展支持这些?

vsnprintf和gcc

我有以下声明: vsnprintf(target, size – 1, “%ls_%ls”, str16_1, str16_2); 为什么这会在gcc上失败? 我在Windows上使用过这样的: vsnprintf(target, size – 1, “%S_%S”, str16_1, str16_2); 它按预期工作。 在gcc文档中我发现%S是%ls的同义词,但我不能使用它。 我也试过%S,但是没有用。 我在具有可变参数列表的函数中使用它。 有可能无法工作,因为我更改了传递给va_start的格式变量吗? 我必须搜索%S并将其替换为格式变量中的%ls。 function如下: void f(const char* format, …){ char* new_format = format with %S replaced with %ls; va_list argptr; va_start(args, format); vsnprintf(str, size-1, new_format, argptr); } 我查了一下,new_format是正确的。 谢谢!

scanf()中的反转参数

我(很快)编写了一些代码并意外地反转了scanf()的参数: char i[] = “ABC1\t”; scanf(i, “%s”); 使用gcc -Werror -Wall -Wextra编译并没有抱怨这一点。 显然,这段代码不起作用,但为什么没有gcc告诉我,我颠倒了参数? 它不能检测到i不是格式字符串,或者第二个参数不是可存储类型吗? 编辑 感谢所有的洞察力,看起来我找到了答案, -Wformat标志上有一个扭曲使得这个“可捕获”(在下面发布以供参考)

在“重定位具有无效符号索引”错误期间会发生什么?

这是一个重现问题的测试: $ echo “void whatever() {}” > prog.c $ gcc prog.c 这会在GCC 4.8.4上产生以下错误: /usr/bin/ld: /usr/lib/debug/usr/lib/x86_64-linux-gnu/crt1.o(.debug_info): relocation 0 has invalid symbol index 11 /usr/bin/ld: /usr/lib/debug/usr/lib/x86_64-linux-gnu/crt1.o(.debug_info): relocation 1 has invalid symbol index 12 /usr/bin/ld: /usr/lib/debug/usr/lib/x86_64-linux-gnu/crt1.o(.debug_info): relocation 2 has invalid symbol index 2 /usr/bin/ld: /usr/lib/debug/usr/lib/x86_64-linux-gnu/crt1.o(.debug_info): relocation 3 has invalid symbol index 2 … etc … /usr/bin/ld: /usr/lib/debug/usr/lib/x86_64-linux-gnu/crt1.o(.debug_info): relocation […]

使用什么代替mudflap与gcc / llvm(用于检测内存访问错误)?

似乎 -fmudflap function 已从 GCC中删除 。 因此,我的问题是:使用什么来代替它来动态分析程序的超出读/写,未初始化的读取和此类问题? (也许作为一个附带问题:它为什么被删除了?) mudflap的方法(在编译器中使用工具化生成的代码)看起来非常优雅。 背景 其他工具在源代码级别(例如Insure)上对机器代码级别(例如Purify)进行工具化,或者在仿真CPU(例如Valgrind)期间进行工具化。 mudflap方法有可能找到valgrind或purify无法检测到的错误(例如,基于堆栈的arrays访问错误)。 它比其他方法更轻巧。 我正在寻找一个开源解决方案。

无符号整数位域移位产生有符号整数

让我们考虑以下程序test.c : #include struct test { unsigned int a:5; }; int main () { unsigned int i; struct test t = {1}; for (i = 0; i < ta << 1; i++) printf("%u\n", i); return 0; } 使用gcc -Wsign-compare test.c编译时,会生成以下警告(使用gcc 4.8.1进行测试): test.c:9:19: warning: comparison between signed and unsigned integer expressions [-Wsign-compare] for (i = 0; […]