0

I write some code in C

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

int width=3,height=6;
//if width>height, the programe will crash

void test(int ** input){
    printf("test value:\n\n");
    for(int i=0;i<width;i++){
        for(int j=0;j<height;j++)
            printf("%dx%d=%d\t",i,j,input[i][j]);
        printf("\n");
    }
}

int main()
{
    int **p = (int**)malloc(sizeof(int*)*width); //for rows
    for(int i = 0; i < height; i++)  
    {  
        *(p+i) = (int*)malloc(sizeof(int)*height);//for cols  
    }  
    for(int i =0;i<width;i++)
        for(int j=0;j<height;j++)
            p[i][j]=i*j;

    test(p);
    return 0;
}

run it: gcc test.c && a.out Nothing is wrong, everything is OK. But, if i change width=7 at line 4. The code will crash:

Segmentation fault: 11

Why?

I run it in:

zenith@zenithdeMacBook-Air:/ramdisk$ uname -a
Darwin bogon 13.3.0 Darwin Kernel Version 13.3.0: Tue Jun  3 21:27:35 PDT 2014; root:xnu-2422.110.17~1/RELEASE_X86_64 x86_64
zenith@zenithdeMacBook-Air:/ramdisk$ gcc -v
Configured with: --prefix=/Applications/Xcode.app/Contents/Developer/usr --with-gxx-include-dir=/usr/include/c++/4.2.1
Apple LLVM version 5.1 (clang-503.0.40) (based on LLVM 3.4svn)
Target: x86_64-apple-darwin13.3.0
Thread model: posix
Kuangfeng
  • 71
  • 6
  • [Please don't cast the return value of `malloc()` in C](http://stackoverflow.com/questions/605845/do-i-cast-the-result-of-malloc). – unwind Sep 02 '14 at 09:13

1 Answers1

4

In main, the line for(int i = 0; i < height; i++) should be for(int i = 0; i < width; i++).

Your array consists of width number of pointers, each of which points to the first element of an array of length height. (This is the opposite way around from the usual English meaning of those words, BTW).

The program works anyway if width <= height because you allocated enough space; but when width > height you do an out-of-bounds access with *(p+i) when i gets big enough.

NB. You can replace *(p+i) with the more readable p[i], and don't cast malloc.

Community
  • 1
  • 1
M.M
  • 138,810
  • 21
  • 208
  • 365