"Warning C6386 Buffer overrun while writing to 'buffer': the writable size is 'Param(1)*Param(2)' bytes, but '4294967295' bytes might be written."
I'm writing a code to calculate a postfix expression using a stack implemented using linked lists, and I'm reading the postfix expression from a local file in binary ( fopen(filename, "rb" ) into a buffer. I get the above mentioned warning at this line of code:
fread(buffer, sizeof(char), fileLength, file);
But, I've used calloc to allocate exactly the amount of memory I'd need based on the length of the file like this:
fseek(file, 0, SEEK_END);
fileLength = ftell(file);
buffer = (char*)calloc(fileLength 1, sizeof(char));
if (!buffer) {
perror("Can't allocate memory!\n");
return NULL;
}
I don't understand where it got the "'4294967295' bytes might be written". Anyone care enough to explain what might be the cause, I'm a student and I'm not that much experienced with C.
Here's the entire function block:
int CalculatePostfix(double* destination, char* fileName)
{
FILE* file = NULL;
int fileLength = 0;
char* buffer = NULL;
char* currentBuffer = NULL;
int numBytes = 0;
char operation = 0;
double number = 0;
int status = EXIT_SUCCESS;;
StackElement head = { .number = 0, .next = NULL };
file = fopen(fileName, "rb");
if (!file) {
perror("Can't open file!\n");
return -1;
}
fseek(file, 0, SEEK_END);
fileLength = ftell(file);
buffer = (char*)calloc(fileLength 1, sizeof(char));
if (!buffer) {
perror("Can't allocate memory!\n");
return NULL;
}
rewind(file);
fread(buffer, sizeof(char), fileLength, file);
printf("|%s|\n", buffer);
fclose(file);
currentBuffer = buffer;
while (strlen(currentBuffer) > 0) {
status = sscanf(currentBuffer, " %lf %n", &number, &numBytes);
if (status == 1) {
Push(&head, number);
currentBuffer = numBytes;
}
else {
sscanf(currentBuffer, " %c %n", &operation, &numBytes);
status = PerformOperation(&head, operation);
if (status != EXIT_SUCCESS) {
free(buffer);
while (head.next != NULL) {
DeleteAfter(&head);
}
return -1;
}
currentBuffer = numBytes;
}
}
free(buffer);
return EXIT_SUCCESS;
}
CodePudding user response:
ftell returns a long integer, fread takes a size_t which, depending on implementation, often is an unsigned int. So if you happen to get -1L (which is the error return code from ftell) back from ftell you will end up vid a massive large unsigned int.
So to solve this, check return value of ftell and make sure it is not -1L, then when calling fread cast to size_t