0

I do not know what is wrong with my code.

It seems to be something related to memory access but I don't find what or why. I would appreciate some help.

Code:

#include <stdio.h> #include <time.h> #include "ist.h" #define LOGMESSAGE "Error. Try again: " typedef struct { usint size; double *value; } Vector; void showVector(Vector vector); /* generateVector(int, int) -> double*/ Vector generateVector( int max, int size ) { usint i; Vector vector; if(size == 0) { fprintf( stdout, "1 element added to array\n" ); vector.size = 1; } vector.value = malloc( ((size) * sizeof (double)) + 1); for(i = 0; i < size; i++) { vector.value[i] = ( (double)rand() * max / (double)RAND_MAX ); printf("\n%f\n", vector.value[i]); } vector.value[size] = '\0'; fprintf( stdout, "\nVector generated\n" ); showVector(vector); return vector; } /* save(double *) -> void*/ unsigned int save(Vector vector) { sint i; FILE *f_data = fopen("savedata.txt", "wt"); if(f_data == NULL) { fprintf( stdout, "can't open file" ); return 1; } for(i = 0; i < vector.size; i++) fprintf( f_data, "%.3f\n", vector.value[i] ); fclose( f_data ); return 0; } /* showvector(double) -> void*/ void showVector(Vector vector) { usint i; line( 2, 0 ); for(i = 0; i < vector.size; i++) fprintf( stdout, "[%2.d] %.3lf%c", i, vector.value[i], (i % 5) ? '\t' : '\n' ); line( 2, 0 ); } /* sort(double*) -> double*/ Vector sort(Vector vector) { sint i; int change = true; while(change == true) { change = false; for(i = 0; i < vector.size; i++) if(vector.value[i + 1] > vector.value[i]) { double temp = vector.value[i]; vector.value[i] = vector.value[i + 1]; vector.value[i + 1] = temp; change = true; } } showVector( vector ); return vector; } /* interface(void) -> int*/ int interface(char **argv) { Vector vector; clear(); fseek( stdin, 0, SEEK_END ); vector = (argv == NULL) ? generateVector( i_dialog( "Max val: ", LOGMESSAGE ), i_dialog( "Vector size: ", LOGMESSAGE ) ) : generateVector( atoi( argv[1] ), atoi( argv[2] ) ); showVector( vector ); save( sort(vector) ); free( vector.value ); fprintf( stdout, "Press <ENTER>..." ); CLEARBUFF(); line( 2, 1 ); menu( 2, "Repeat", "Exit" ); return i_dialog( "\nchoice: ", LOGMESSAGE ) ? true : false; } int main(int argc, char **argv) { srand( (unsigned)time(NULL) ); if(argc != 3) argv = NULL; while(interface( argv )); return 0; } 

Output (error):

Vector Size: 4 Max value: 5 0.659987 2.609337 2.122152 1.464432 s1e2: malloc.c:2451: sYSMALLOc: Assertion `(old_top == (((mbinptr) (((char *) &((av)->bins[((1) - 1) * 2])) - __builtin_offsetof (struct malloc_chunk, fd)))) && old_size == 0) || ((unsigned long) (old_size) >= (unsigned long)((((__builtin_offsetof (struct malloc_chunk, fd_nextsize))+((2 * (sizeof(size_t))) - 1)) & ~((2 * (sizeof(size_t))) - 1))) && ((old_top)->size & 0x1) && ((unsigned long)old_end & pagemask) == 0)' failed. Aborted (core dumped) 

Thank you very much

2
  • You appear to be indexing one past the end of the allocated memory. It looks like maybe you tried to allocate an extra element, but the +1 is in the wrong place in your malloc call for that. You might consider simplifying your example to demonstrate the problem more clearly. Commented Oct 26, 2014 at 21:57
  • Why do you add an extra element to the value array in the first place? You have a size field that says how many elements there are, you don't need an end marker. Commented Oct 26, 2014 at 22:00

2 Answers 2

2
vector.value = malloc( ((size) * sizeof (double)) + 1); 

That allocates enough space for size doubles plus one byte.

vector.value[size] = '\0'; 

This is a problem. Because value is of the type double*, dereferencing it results in getting or setting a double value. You use a character literal, which is of the type int. It is implicitly converted to a double, you write past the end of your allocated memory, and the result is undefined behavior.

Perhaps you meant to write the following because you also index past the end of your array in your sort function.

vector.value = malloc((size + 1) * sizeof(double)); 
Sign up to request clarification or add additional context in comments.

1 Comment

The sentinel value is redundant so I'd suggest removing it entirely (it looks like the code is halfway through being converted from sentinel values to length-counting)
0

should be:

vector.value = malloc(size * sizeof(double) + sizeof(int)); 

and:

*((int *)(&vector.value[size])) = 0; 

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.