简体   繁体   English

C.使用的内存多于malloc中分配的内存-我可以返回sth,结束程序而不是使其崩溃吗?

[英]C. Using more memory than allocated in malloc - can I return sth, end program instead of letting it crash?

My program crashes when malloc(x*sizeof(char)) , x < limit of fgets , despite buffer == NULL check. malloc(x*sizeof(char))x < fgets限制,尽管buffer == NULL检查,我的程序崩溃。

In my example, when x is 1, and limit of what fgets can take is 100, and user types eg. 在我的示例中,当x为1时,fgets可以使用的限制为100,并且用户类型为。 5 characters from keyboard (fgets() call), program crashes, returning some random like: 19284791298 value. 键盘上的5个字符(调用fgets()),程序崩溃,返回一些随机值,例如:19284791298。

My problem: instead of crashing, I would prefer if it returned NULL. 我的问题:不是崩溃,我希望它返回NULL。

Reason: I upload my code to my univ's linux platform that tests program's reaction to heap limit change to 0 and to 130, when my program is written to return NULL if user's input exceeds 100 characters. 原因:我将代码上传到我的univ的linux平台,该平台测试程序对堆限制更改为0和130的反应,如果用户输入超过100个字符,则编写程序返回NULL时。 I don't quite understand how the environment changes memory limit to 0 and 130 and what exactly is changed, but even though, I noticed my program in CodeBlocks, windows 10, crashes in this situation described here (x < stdin input) despite checking buffer == NULL . 我不太了解环境如何将内存限制更改为0和130,以及到底发生了什么变化,但是尽管如此,我仍然注意到我的程序在CodeBlocks,Windows 10中仍在此处描述的这种情况下崩溃(x <stdin输入),尽管进行了检查buffer == NULL

I wish buffer == NULL check could somehow work and prevent the crash. 我希望buffer == NULL检查可以以某种方式工作并防止崩溃。

If x was 100, and size was 1 (instead of 1 and 100), my program would return NULL and set err_code to 1. 如果x为100, size为1(而不是1和100),则我的程序将返回NULL并将err_code设置为1。

I'm thinking: I can't do with x the same "if" statement I did for strlen(buffer), because... to check how long input written to buffer is, firstly I'd need to check length of what was written to this buffer?!. 我在想:我不能对x使用与strlen(buffer)相同的“ if”语句,因为...要检查写入缓冲区的输入时间,首先我需要检查长度被写入此缓冲区?!。

printf("Insert data: ");
char *buffer = (char* )malloc(1*sizeof(char));
if (buffer == NULL) 
    return NULL;

int size=100;
if (fgets(buffer, size, stdin)!=NULL) {
    if (strlen(buffer)>(unsigned)(size-2)) { //'\0' and enter are 2 chars
        free(buffer);
        *err_code=1;
        return NULL;
    }
//... here goes some sscanf to fill struct fields, etc.
}

In other words. 换一种说法。 A bit condensed what I think may lead to understanding of my problem: 我认为可能会导致对我的问题的理解有些凝结:

  1. Is there a way to end program returning something, instead of letting it crash in such situation? 有没有办法结束程序返回的东西,而不是让它在这种情况下崩溃? A way to make if(buffer == NULL) work? 一种使if(buffer == NULL)工作的方法吗? Why doesn't this check work? 为什么此检查无效?

  2. I'm unfamiliar with linux. 我不熟悉linux。 When I see a comment in report I get, that linux sets (heap?) limit to 0 or 130 (when testing my program), does it mean I can replicate the problems it encounters by setting my x to 0 , 130 ? 当我看到在报告中认为Linux套(堆?)限制为0或130(我的测试程序时)评论我得到,是否意味着我可以复制它遇到我的设置问题, x0130 (in the part malloc(x*sizeof(char)) . (在部分malloc(x*sizeof(char))

When you call fgets , you must tell it how big the destination buffer is . 调用fgets ,必须告诉它目标缓冲区的大小 You are not just telling it the maximum number of characters you want it to read, so that it can automatically allocate that much space, or anything like that. 您不只是告诉它要读取的最大字符数,以便它可以自动分配那么多的空间或类似的内容。 You are telling it what the size of the buffer already is, and you are telling fgets that it absolutely must not read any more characters than that, otherwise the buffer will overflow. 您正在告诉它缓冲区的大小已经是什么了,您在告诉fgets绝对不能读取更多的字符,否则缓冲区将溢出。 ( fgets never does any allocating of its own.) fgets从不进行任何分配。)

So when you say 所以当你说

char *buffer = (char* )malloc(1*sizeof(char));

followed by 其次是

int size=100;
fgets(buffer, size, stdin)

you have lied. 你撒谎了。 You have allocated a buffer of size 1, and you have told fgets that the buffer is of size 100. So fgets will read up to 99 characters, and store them into buf , and in most cases this will badly overflow the buffer. 您已经分配了一个大小为1的缓冲区,并且您已经告诉fgets该缓冲区的大小为100。因此fgets最多可以读取99个字符,并将它们存储到buf ,在大多数情况下,这将严重导致缓冲区溢出。

What you want to do is something more like this: 您想要做的更像是这样:

int size = 100;
char *buffer = (char* )malloc(size*sizeof(char));
if (buffer == NULL) 
    return NULL;

if (fgets(buffer, size, stdin)!=NULL) {
    ...

Also, although it doesn't have anything to do with your problem, there is no need to multiply by sizeof(char) when calling malloc , and in C, there is no need to cast the return from malloc into the destination pointer type, either. 同样,尽管它与您的问题没有任何关系,但是在调用malloc时不需要乘以sizeof(char) ,在C语言中,也无需将malloc的返回值malloc转换为目标指针类型,无论是。 I would just call 我会打电话给

char *buffer = malloc(size);

In your code, you have allocated buffer as a single byte array 在您的代码中,您已将缓冲区分配为单字节数组

char *buffer = (char* )malloc(1*sizeof(char));


int size=100;
if (fgets(buffer, size, stdin)!=NULL) {

In the fgets, you would want to read into buffer an input of 100 bytes. 在fget中,您希望将100字节的输入读入缓冲区。 When the input is read into the buffer it goes beyond the allocated area and overwrites other data. 当输入被读入缓冲区时,它会超出分配的区域并覆盖其他数据。 Because of this, your program crashes, 因此,您的程序崩溃了,

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM