Okay, this time, i have to say it's a weird error. This code runs fine in Code::Blocks 8.02 but fails to run in my college compiler.
I think my college compiler is the GCC Compiler (same as my home compiler) but in LINUX environment.
Something like

vi sort.c
cc sort.c -o sort
./sort

Here is the code ...

# include <stdio.h>
# include <stdlib.h>

void array_input    ( int *, int                );
void array_display  ( int *, int                );
void array_merge    ( int *, int , int , int    );
void sort_merge     ( int *, int , int          );
void pause          ( void                      );

int main()
{
    int option;
    int size_of_array = 0;
    int *array = NULL;

    do
    {
        printf("\n\t=========================================");
        printf("\n\t|          SORTING TECHNIQUES           |");
        printf("\n\t=========================================");
        printf("\n\n\tEstablish The Size Of Array           [1]");
        printf("\n\n\tEnter The Elements Into The Array     [2]");
        printf("\n\n\tUse Sorting Method : Merge Sort       [5]");
        printf("\n\n\tDisplay The Array                     [8]");
        printf("\n\n\tExit                                  [0]");

        printf("\n\n\t\tEnter Choice : ");
        scanf("%d", &option);

        switch (option)
        {
            case 1 :
                if(array != NULL)
                    free(array);
                printf("\n\n\t\tEnter The Size Of Array : ");
                scanf("%d", &size_of_array);
                array = (int *)calloc(size_of_array,sizeof(int));
                pause();
                break;

            case 2 :
                if (size_of_array < 1)
                {
                    printf("\n\n\t\tInvalid Size Of Array!");
                }
                else
                {
                    free(array);
                    printf("\n\n\t\tEnter The Elements Into The Array : ");
                    array_input(array,size_of_array);
                }
                pause();
                break;

            case 5 :
                if (array == NULL)
                {
                    printf("\n\n\t\tEmpty Array!");
                }
                else
                {
                    sort_merge(array,0,size_of_array);
                    printf("\n\n\t\tYour Array Has Been Sorted ... ");
                }
                pause();
                break;

            case 8 :
                if (array == NULL)
                {
                    printf("\n\n\t\tEmpty Array!");
                }
                else
                {
                    printf("\n\n\t\tYour Array : ");
                    array_display(array,size_of_array);
                }

                pause();
                break;

            case 0 :
                printf("\n\n\t\tThank You!");
                break;

            default:
                printf("\n\n\t\tWrong Option!\n\n\t\tTry Again");
                pause();
                break;
        }
    }
    while (option != 0);

    free(array);

    return EXIT_SUCCESS;
}

void array_input    (int * array, int size_of_array)
{
    int i;
    for (i = 0; i < size_of_array; i++)
    {
        printf("\n\t\t\t%d.\t", (i + 1));
        getchar();
        scanf("%d", (array + i));
    }
}

void array_display  (int * array, int size_of_array)
{
    int i;
    for (i = 0; i < size_of_array; i++)
    {
        printf("\n\t\t\t%d.\t%d", (i + 1), array[i]);
    }
}

void array_merge    (int * array, int low, int high, int mid)
{
    int i = low;
    int j = mid + 1;
    int k = low;

    int * array_temp = (int *)malloc(sizeof(array));

    while (i <= mid && j <= high)
    {
        if (array[i] < array[j])
        {
            array_temp[k++] = array[i++];
        }
        else
        {
            array_temp[k++] = array[j++];
        }
    }

    while (i <= mid)
    {
        array_temp[k++] = array[i++];
    }

    while (j <= high)
    {
        array_temp[k++] = array[j++];
    }

    for (i = low; i < k; i++)
    {
        array[i] = array_temp[i];
    }

    free(array_temp);
}

void sort_merge     (int * array, int low, int high)
{
    if (low < high)
    {
        int mid = (low + high) / 2;
        sort_merge  (array, low, mid);
        sort_merge  (array, mid + 1, high);
        array_merge (array, low, high, mid);
    }
}
void pause()
{
    getchar();
    printf("\n\n\t\tPress Enter To Continue ... ");
    getchar();
}

Here is the sample input

[sumitro_bhaumik@radix xvr]$ cc sort.c -o sort
[sumitro_bhaumik@radix xvr]$ ./sort

        =========================================
        |          SORTING TECHNIQUES           |
        =========================================

        Establish The Size Of Array           [1]

        Enter The Elements Into The Array     [2]

        Use Sorting Method : Merge Sort       [5]

        Display The Array                     [8]

        Exit                                  [0]

                Enter Choice : 1


                Enter The Size Of Array : 5


                Press Enter To Continue ... 

        =========================================
        |          SORTING TECHNIQUES           |
        =========================================

        Establish The Size Of Array           [1]

        Enter The Elements Into The Array     [2]

        Use Sorting Method : Merge Sort       [5]

        Display The Array                     [8]

        Exit                                  [0]

                Enter Choice : 2


                Enter The Elements Into The Array : 
                        1.      5

                        2.      1

                        3.      4

                        4.      2

                        5.      3


                Press Enter To Continue ... 

        =========================================
        |          SORTING TECHNIQUES           |
        =========================================

        Establish The Size Of Array           [1]

        Enter The Elements Into The Array     [2]

        Use Sorting Method : Merge Sort       [5]

        Display The Array                     [8]

        Exit                                  [0]

                Enter Choice : 5
*** glibc detected *** free(): invalid next size (fast): 0x08156020 ***
Aborted
[sumitro_bhaumik@radix xvr]$

I have tried Google about the "glibc detected" error but i could not come to any specific conclusion
Is this error same as segmentation fault?

Thanks in advance

Recommended Answers

All 35 Replies

I can't explain why it is working at home, but that is the nature of undefined behaviour, however at line 48 of your code listing you free the array just before you start writing values into it.

commented: ... the nature of undefined behaviour +5

In the case statement, in addition to the error of #2, you have a potential error in case #1.

You are asking calloc to give memory of some number * the size of an int. But you don't want the size of an int, you want the size of an int * (pointer). Those are not always the same!

If you are allocating memory for an array of int's then use sizeof(int), but if you are allocating memory for an array of pointers to int, then use sizeof(int *).

Since you are casting the result to an int *, it should be an int * in the sizeof(), not int.

you have a potential error in case #1.

No there isn't.

You are asking calloc to give memory of some number * the size of an int. But you don't want the size of an int, you want the size of an int * (pointer).

True but not relevent.

If you are allocating memory for an array of int's then use sizeof(int), but if you are allocating memory for an array of pointers to int, then use sizeof(int *).

Also true and not relevent.

Since you are casting the result to an int *, it should be an int * in the sizeof(), not int.

You are wrong on this point (which is why your other points are not relevent). The variable array is of type int * which is why the output of calloc is cast to int *. array is pointing to an array of ints it is easy to determine ask yourself what the type of array[0] is (or *array). It is int that is the type of the elements of the array. It it was an array of int * then array would have to be declared int **.

Since it is an array of int the size in calloc should be sizeof(int). This also works out with what the return is cast to, because there should be a single dereference level difference between the return type cast and the size of the type calloc'd.

For any generalised type T callocing an array of size N should take this form.

T *array;
array = calloc(N, sizeof(T));

Another way to do it is this

T *array;
array = calloc(N, sizeof *array);

this has the minor advantage that if you change your declaration of array you do not have to change you calloc line for it to still be correct.

Adding to what's already been said, line 125 is wrong, sizeof(array) is equivalent to sizeof(int *) there, so you have to know the correct array size there.

"Establish The Size Of Array" could ensure that the given array size is reasonable and the allocation succeeds (e.g. now it accepts and attempts allocations of sizes < 1). Consider changing to [I]size_t[/I] size_of_array; .

In general, upon allocation, check the return values of malloc()/calloc() against NULL.

I can't explain why it is working at home, but that is the nature of undefined behaviour

I hate this s**t

Okay after reading everything above this post. Here's what i think i have done wrong

1) Took the size of array from user BUT DID NOT check for negative inputs
2) Freed the memory AND AFTER THAT tried to store numbers at that memory location

@Banfa & @Adak
Bit confused here. Which standard should i follow? int *array = (int *)calloc(sizeof(int)); OR int *array = (int *)calloc(sizeof(int *)); This may sound lame but all the books that i've seen have used the first type of allocation method

@mitrmkar
I'll get back to you later. Have to go to sleep

Here is the corrected code but i don't know whether it's error free. Have to try it out at college

# include <stdio.h>
# include <stdlib.h>

void array_input    ( int *, int                );
void array_display  ( int *, int                );
void array_merge    ( int *, int , int , int    );
void sort_merge     ( int *, int , int          );
void pause          ( void                      );

int main()
{
    int option;
    int size_of_array = 0;
    int *array = NULL;

    do
    {
        printf("\n\t=========================================");
        printf("\n\t|          SORTING TECHNIQUES           |");
        printf("\n\t=========================================");
        printf("\n\n\tEstablish The Size Of Array           [1]");
        printf("\n\n\tEnter The Elements Into The Array     [2]");
        printf("\n\n\tUse Sorting Method : Merge Sort       [5]");
        printf("\n\n\tDisplay The Array                     [8]");
        printf("\n\n\tExit                                  [0]");

        printf("\n\n\t\tEnter Choice : ");
        scanf("%d", &option);

        switch (option)
        {
            case 1 :
                printf("\n\n\t\tEnter The Size Of Array : ");
                scanf("%d", &size_of_array);
                if(size_of_array < 1)
                {
                    printf("\n\n\t\tInvalid Size Of Array!");
                }
                pause();
                break;

            case 2 :
                if (size_of_array < 1)
                {
                    printf("\n\n\t\tInvalid Size Of Array!");
                }
                else
                {
                    free(array);
                    array = (int *)calloc(size_of_array,sizeof(int));
                    printf("\n\n\t\tEnter The Elements Into The Array : ");
                    array_input(array,size_of_array);
                }
                pause();
                break;

            case 5 :
                if (array == NULL)
                {
                    printf("\n\n\t\tEmpty Array!");
                }
                else
                {
                    sort_merge(array,0,size_of_array);
                    printf("\n\n\t\tYour Array Has Been Sorted ... ");
                }
                pause();
                break;

            case 8 :
                if (array == NULL)
                {
                    printf("\n\n\t\tEmpty Array!");
                }
                else
                {
                    printf("\n\n\t\tYour Array : ");
                    array_display(array,size_of_array);
                }

                pause();
                break;

            case 0 :
                printf("\n\n\t\tThank You!");
                break;

            default:
                printf("\n\n\t\tWrong Option!\n\n\t\tTry Again");
                pause();
                break;
        }
    }
    while (option != 0);

    free(array);

    return EXIT_SUCCESS;
}

Line 49 of the new listing, only free array if array is not NULL or you willl get a run time error.

This is correct

int *array = (int *)calloc(<NumberOfItems>,sizeof(int));

although I personally would not cast the return value of calloc so I would write

int *array = calloc(<NumberOfItems>,sizeof(int));

Casting the return value causes problems if your code needs to be portable or work on 64bit systems and you have failed to include stdlib.h. If you have included stdlib.h it's all a bit moot but I think it looks neater without the cast.

Of course in C++ you can call malloc/calloc without casting the return value but then you should be using new anyway.

c-faq - whats wrong with casting malloc

Line 49 of the new listing, only free array if array is not NULL or you willl get a run time error.

I don't get this error. I mean if i try to free a NULL memory, it does not say anything.

and you have failed to include stdlib.h

Hey! Look at line# 2 :P

Casting the return value causes problems if your code needs to be portable or work on 64bit systems

This was another one of my doubts. If i don't type caste calloc/malloc, my compiler is giving me errors. Take a look

# include <stdio.h>
# include <stdlib.h>

int main()
{
    int * element = malloc(sizeof(int));
    int * array   = calloc(5,sizeof(int));

    free(element);
    free(array);

    return EXIT_SUCCESS;
}

These are the error messages

In function `int main()':|
LINE |6| error: invalid conversion from `void*' to `int*'|
LINE |7| error: invalid conversion from `void*' to `int*'|
||=== Build finished: 2 errors, 0 warnings ===|

This was another one of my doubts. If i don't type caste calloc/malloc, my compiler is giving me errors. Take a look

Then you are compiling your code as C++. C++ and C handle the void pointer diferently in C void* can be implicitly cast to any other pointer type but in C++ all pointer casts must be explicit.

I have a feeling that I might think that writing C code and compiling it as C++ is a bad idea. That is if you are going to compile as C++ then write C++ code taking advantage of its features and library, such as the std::vector.

I don't get this error. I mean if i try to free a NULL memory, it does not say anything.


Hey! Look at line# 2 :P


This was another one of my doubts. If i don't type caste calloc/malloc, my compiler is giving me errors. Take a look

# include <stdio.h>
# include <stdlib.h>

int main()
{
    int * element = malloc(sizeof(int));
    int * array   = calloc(5,sizeof(int));

    free(element);
    free(array);

    return EXIT_SUCCESS;
}

These are the error messages

In function `int main()':|
LINE |6| error: invalid conversion from `void*' to `int*'|
LINE |7| error: invalid conversion from `void*' to `int*'|
||=== Build finished: 2 errors, 0 warnings ===|

You need to typecast void pointer to int pointer in C++ but in C there is no need to do that. Which compiler did you use to compile this code ?

I don't get this error. I mean if i try to free a NULL memory, it does not say anything.

That might be a feature of your plaform, and the fact you are compiling as C++.

C++ does allow

delete 0;

explicitly in the standard.


If free is calling the same underlying system routine it may be able to cope with free(0).

However the other option is that you have invoked undefined behaviour and at some random time in the future your program will stop working for no apparent reason. Is that what you want to happen?

A C program must avoid freeing 0.

I am using Code::Blocks 8.02 editor
When I go to Settings -> Compiler & Debugger, i see that "Selected Compiler" is 'GNU GCC Compiler'
The name of my file is sort_merge.c
I gave it a [DOT]C extension. I still can't figure out what I'm doing wrong.

What compiler do you people use?

is the .C or .c? gcc defaults to C++ compilation for .C

If you want c compilation rename all your source files to .c or put

-x c

on the gcc command line which forces c compilation. I recommend the first.

I use the following compilers and IDEs and editors

At Home
gcc 4.4.1
Eclipse
Code::Blocks

At Work
gcc 4.2.4
MinGW 3.4.1
Visual Studio 2008 Express (compiler and IDE)
Eclipse
Geany
Notepad++

Okay. I'm really becomming mad now. Here is the code from my college compiler and it's respective output

# include <stdio.h>
# include <stdlib.h>

void array_input    ( int *, int                );
void array_display  ( int *, int                );
void array_merge    ( int *, int , int , int    );
void sort_merge     ( int *, int , int          );
void pause          ( void                      );

int main()
{
    int option;
    int size_of_array = 0;
    int *array = NULL;

    do
    {
        printf("\n\t=========================================");
        printf("\n\t|          SORTING TECHNIQUES           |");
        printf("\n\t=========================================");
        printf("\n\n\tEstablish The Size Of Array           [1]");
        printf("\n\n\tEnter The Elements Into The Array     [2]");
        printf("\n\n\tUse Sorting Method : Merge Sort       [5]");
        printf("\n\n\tDisplay The Array                     [8]");
        printf("\n\n\tExit                                  [0]");

        printf("\n\n\t\tEnter Choice : ");
        scanf("%d", &option);

        switch (option)
        {
            case 1 :
                if(array != NULL)
                    free(array);

                printf("\n\n\t\tEnter The Size Of Array : ");

                scanf("%d", &size_of_array);

		if(size_of_array < 1)
		{    
		    printf("\n\n\t\tInvalid Size!");
		    size_of_array = 0;
 		}

                pause();
                break;

            case 2 :
                if (size_of_array < 1)
                {
                    printf("\n\n\t\tInvalid Size Of Array!");
                }
                else
                {
                    if(array != NULL)
		    	free(array);

		    array = (int *)calloc(size_of_array,sizeof(int));

		    if(array == NULL)
		    {
			printf("\n\n\t\tUnable To Allocate Memory!");
			return EXIT_FAILURE;
		    }

                    printf("\n\n\t\tEnter The Elements Into The Array : ");
                    array_input(array,size_of_array);
                }
                pause();
                break;

            case 5 :
                if (array == NULL)
                {    
		    printf("\n\n\t\tEmpty Array!");
                }
                else
                {
                    sort_merge(array,0,size_of_array);
                    printf("\n\n\t\tYour Array Has Been Sorted ... ");
                }
                pause();
                break;

            case 8 :
                if (array == NULL)
                {
                    printf("\n\n\t\tEmpty Array!");
                }
                else
                {
                    printf("\n\n\t\tYour Array : ");
                    array_display(array,size_of_array);
                }

                pause();
                break;

            case 0 :
                printf("\n\n\t\tThank You!");
                break;

            default:
                printf("\n\n\t\tWrong Option!\n\n\t\tTry Again");
                pause();
                break;
        }
    }
    while (option != 0);

    if(array != NULL)
        free(array);

    return EXIT_SUCCESS;
}

void array_input    (int * array, int size_of_array)
{
    int i;
    for (i = 0; i < size_of_array; i++)
    {
        printf("\n\t\t\t%d.\t", (i + 1));
        getchar();
        scanf("%d", &array[i]);
    }
}

void array_display  (int * array, int size_of_array)
{
    int i;
    for (i = 0; i < size_of_array; i++)
    {
        printf("\n\t\t\t%d.\t%d", (i + 1), array[i]);
    }
}

void array_merge    (int * array, int low, int high, int mid)
{
    int i = low;
    int j = mid + 1;
    int k = low;

    int * array_temp = (int *)malloc(sizeof(array));

    while (i <= mid && j <= high)
    {
        if (array[i] < array[j])
        {
            array_temp[k++] = array[i++];
        }
        else
        {
            array_temp[k++] = array[j++];
        }
    }

    while (i <= mid)
    {
        array_temp[k++] = array[i++];
    }

    while (j <= high)
    {
        array_temp[k++] = array[j++];
    }

    for (i = low; i < k; i++)
    {
        array[i] = array_temp[i];
    }

    free(array_temp);
}

void sort_merge     (int * array, int low, int high)
{
    if (low < high)
    {
        int mid = (low + high) / 2;
        sort_merge  (array, low, mid);
        sort_merge  (array, mid + 1, high);
        array_merge (array, low, high, mid);
    }
}
void pause()
{
    getchar();
    printf("\n\n\t\tPress Enter To Continue ... ");
    getchar();
}

And here is the output

[sumitro_bhaumik@radix xvr]$ ./sort

        =========================================
        |          SORTING TECHNIQUES           |
        =========================================

        Establish The Size Of Array           [1]

        Enter The Elements Into The Array     [2]

        Use Sorting Method : Merge Sort       [5]

        Display The Array                     [8]

        Exit                                  [0]

                Enter Choice : 1


                Enter The Size Of Array : 5


                Press Enter To Continue ... 

        =========================================
        |          SORTING TECHNIQUES           |
        =========================================

        Establish The Size Of Array           [1]

        Enter The Elements Into The Array     [2]

        Use Sorting Method : Merge Sort       [5]

        Display The Array                     [8]

        Exit                                  [0]

                Enter Choice : 2


                Enter The Elements Into The Array : 
                        1.      5

                        2.      4

                        3.      1

                        4.      2

                        5.      3


                Press Enter To Continue ... 

        =========================================
        |          SORTING TECHNIQUES           |
        =========================================

        Establish The Size Of Array           [1]

        Enter The Elements Into The Array     [2]

        Use Sorting Method : Merge Sort       [5]

        Display The Array                     [8]

        Exit                                  [0]

                Enter Choice : 5
*** glibc detected *** free(): invalid next size (fast): 0x09f44020 ***
Aborted
[sumitro_bhaumik@radix xvr]$

When i type gcc -v in the environment, here are the results

[sumitro_bhaumik@radix xvr]$ gcc -v
Reading specs from /usr/lib/gcc/i386-redhat-linux/3.4.3/specs
Configured with: ../configure --prefix=/usr --mandir=/usr/share/man --infodir=/usr/share/info --enable-shared --enable-threads=posix --disable-checking --with-system-zlib --enable-__cxa_atexit --disable-libunwind-exceptions --enable-java-awt=gtk --host=i386-redhat-linux
Thread model: posix
gcc version 3.4.3 20041212 (Red Hat 3.4.3-9.EL4)
[sumitro_bhaumik@radix xvr]$

Put in a cout statement as the first line of your function

void array_merge (int * array, int low, int high, int mid)

output low, high and mid. I think you will find that sometimes high has a value of 5. That tarnslates to j have a value of 5 sometimes and that translates to an out of bounds access into array because array has a size of 5 which means valid indexes are in the range 0 - 4.

I think this stems from the original call to sort_merge on line 80 using size_of_array.

After you malloc space, you should check if you actually got space or not. That could be one of the reasons for your error. You did not get the requested space.
I ran your code in my system. Using gcc compiler. It compiled and ran fine, but here is another thing you might want to look into.
I gave the input as 10,9,8,7,6 and this is some of the intermediate output that I got. I am printing the values at line 170. As you can see the merge sort adds an extra 0. There is no space allotted for this zero. This also could be causing the error.

Debug Start
9 10
Debug End
Debug Start
8 9 10
Debug End
Debug Start
6 7
Debug End
Debug Start
0 6 7
Debug End
Debug Start
0 6 7 8 9 10
Debug End

I'm sorry for all the trouble Banfa, i found about the error. The problem was a different matter entirely.

See Line # 144 int * array_temp = (int *)malloc(sizeof(array)); I was using sizeof(array) . I was expecting it to give me the size of entire memory allocated to array but it is actually giving me size of int So i changed my code to int * array_temp = (int *)calloc(size_of_array,sizeof(int)); Where size_of_array is the size of the given array and now it's all working fine
_________________________________________________________

Here's another problem. When I compile this line in my COLLEGE COMPILER, it gives a warning but no error int * array = malloc(sizeof(int)); But my HOME COMPILER flags it as an error. But ideally, neither of them shouldn't say anything. Why this anomaly?

After you malloc space, you should check if you actually got space or not. That could be one of the reasons for your error

I keep forgetting to put that check after allocation but no, that was not the cause for error. See my above post ...

int * array = malloc(sizeof(int)); But my HOME COMPILER flags it as an error. But ideally, neither of them shouldn't say anything. Why this anomaly?

Most likely you are accidentally compiling it as C++ code at home, what compiler are you using and what is the exact name of the file?

Here is the file. Name of the file is "memory.c".
http://img28.imageshack.us/img28/4342/memoryc.jpg
There is an attached image for confirmation
I have given stdlib.h Line # 6 & 7 are flaged as errors in HOME COMPILER but as warnings in COLLEGE COMPILER

HOME COMPILER
1) CODE::BLOCKS 8.02 Using GNU GCC Compiler
http://img338.imageshack.us/img338/6487/compiler.jpg
2) XP SP2

COLLEGE COMPILER
1) LINUX - RED HAT
2) Using SSH Client. It's a CUI environment

# include <stdio.h>
# include <stdlib.h>    //<-------------STDLIB.H---------------

int main()
{
    int * element = malloc(sizeof(int));
    int * array   = calloc(5,sizeof(int));

    free(element);
    free(array);

    return EXIT_SUCCESS;
}

In your program when you use malloc, you are allotting space for just one integer, which I think is not what you want to do... If you want to allot space for an array of 5 integers via malloc the correct syntax is

int* ip= (int*)malloc(5* sizeof(int));

Also my suggestion is to type cast irrespective of the fact that you use c or c++ . In that way you will never be wrong

In that way you will never be wrong

You will if you have accidentally forgotten to include stdlib.h on a 64bit system. You will be so wrong you will almost certainly crash.

In your program when you use malloc, you are allotting space for just one integer, which I think is not what you want to do... If you want to allot space for an array of 5 integers via malloc the correct syntax is

I was just showing that my compiler was flagging both of the statements as errors.
I know malloc(N * sizeof(TYPE)) = calloc(N, sizeof(TYPE)) but when there is a dedicated function for multiple allocation, why not use it.
Go through this one. You'll know what Banfa means.

I wish someone could tell me how to force my compiler to compile in C mode instead of C++

for gcc thats easy add the compiler switch -x c

Uh... how would I do that in Code::Blocks?

Project -> Build options -> Select Project Name in List -> Compiler Settings Tab -> Other Tab -> Type it in


I wish I could work out why it seems to be defaulting to C++ though I'm not happy about forcing the compilers hand in this manner but rom the information you have provided I can't see what the problem is.

Did it. But just a little improvement. No errors but warnings instead.

||In function `main':|
|9|warning: assignment makes pointer from integer without a cast|
|11|warning: int format, pointer arg (arg 2)|
||=== Build finished: 0 errors, 2 warnings ===|

Woe is me!

Are you including stdlib.h?

If the compiler thinks that malloc returns int then it has not seen a prototype for malloc telling it it returns void*

This is exactly the problem with casting the return of malloc in C it hides this error which can lead to a non-funcaional program on a 64bit system.

Yes, for the N'th time, i am including stdlib.h

Xaviar, This is a merge sort in C, using malloc'd memory, for both the primary and the index array. It gives no compiler warnings or errors.

In very limited testing it appears to work OK.

I was thinking you could compare your problems with how my program does it, and make your troubleshooting, much easier. You're welcome to use any or all of the code, if you wish.

If MAX is about 200, the numbers appear nicely on one page.

#include <stdio.h>
#include <stdlib.h>
#define MAX 10000

void merge(int A[], int Index[], int l, int m, int r);
void mergesort(int *A, int *Index, int l, int r);
void printIt(int *A);

int main() {
  
  int i;
  int *A, *Index; 

  A = malloc(MAX * sizeof(int));
  Index = malloc(MAX * sizeof(int));

  if(!A || !Index) {
    printf("memory allocation failed - terminating program");
    return 1;
  } 
  for(i = 0; i < MAX; i++) {
    A[i] = rand() % 1000;
    Index[i] = 0;
  }

  printf("\n\n  Unsorted Data\n");  
  printIt(A);
  getchar();

  mergesort(A, Index, 0, MAX-1);
  printf("\n\n Sorted Data\n");
  printIt(A);

  free(A);
  free(Index);
  printf("\n\n\t\t\t     press enter when ready");
  i = getchar(); ++i;
  return 0;
}
void mergesort(int *A, int *Index, int l, int r) {
   int m;
   if (l < r) {
      m = (l + r) /2;
      mergesort(A, Index, l, m);
      mergesort(A, Index, m + 1, r);
      merge(A, Index, l, m, r);
   }
}

/* First, index m in the middle between lo and hi is determined. Then the 
first part of the sequence (from lo to m) and the second part (from m+1 
to hi) are sorted by recursive calls of mergesort. Then the two sorted halves
are merged by merge(). Recursion ends when lo = hi, i.e. when a subsequence consists of only one element.
*/

void merge(int A[], int Index[], int l, int m, int r)
{
    int i, j, k;

    /* copy A to temp array Index */
    for (i = l; i <= r; i++)
        Index[i] = A[i];

    i = l; j = m + 1; k = l;
    /* copy back to A */
    while (i <= m && j <= r)
        if (Index[i] <= Index[j])
           A[k++] = Index[i++];
        else
           A[k++] = Index[j++];

    /* copy back remaining elements of first half (if any)  */
    while (i <= m)
        A[k++] = Index[i++]; 
}
/*Merge() does most of the work in Mergesort. The two halves are first copied 
into an extra array, Index. Then both halves are checked by the indicies i and
j, and the next number is copied back to array A, each time through the 
while loop of merge();
*/
void printIt(int A[]) {
  int i;
  for(i = 0; i < MAX; i++)
    printf(" %3d ", A[i]);

}
Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.