Read 24 bit bmp picture and decode to new picture. Segmentation fault problem!

This is a discussion on Read 24 bit bmp picture and decode to new picture. Segmentation fault problem! within the C Programming forums, part of the General Programming Boards category; I am running in to a segmentation fault 11 with this program. The assignment is to read in a bmp ...

  1. #1
    Registered User
    Join Date
    Mar 2012
    Posts
    2

    Read 24 bit bmp picture and decode to new picture. Segmentation fault problem!

    I am running in to a segmentation fault 11 with this program. The assignment is to read in a bmp file, store it as an array of structures, then apply a [3][3] matrix wiht scaler values to each pixel to change what the RGB value of the pixel is. When i run the program I can see that it reads in the data properly, then it applies the matrix and stores it back into the other array fine until it hits a segmentation fault at line "178"
    Code:
    newR = (pixArray[i-1][j].Red*(-1))+(pixArray[i-1][j+1].Red*0)+(pixArray[i][j].Red*4)+(pixArray[i][j+1].Red*(-1))+(pixArray[i+1][j].Red*(-1))+(pixArray[i+1][j+1].Red*0);
    Any help would be awesome!


    Code:
    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
    #include <ctype.h>
    #include <math.h>
    #pragma pack(1)
    
    
    
    
    /*------------------------------------------------------------------------/
     START Code from Bill Reid
    /------------------------------------------------------------------------*/
    struct HEADER 
    {  unsigned short int Type;     /* Magic identifier       */ 
        unsigned int Size;           /* File size in bytes     */ 
        unsigned short int Reserved1, Reserved2; 
        unsigned int Offset;         /* Offset to data (in B)  */ 
    } Header;                       /* -- 14 Bytes --         */
    
    
    struct INFOHEADER 
    {  unsigned int Size;           /* Header size in bytes    */ 
        int Width, Height;           /* Width / Height of image */ 
        unsigned short int Planes;   /* Number of colour planes */ 
        unsigned short int Bits;     /* Bits per pixel          */ 
        unsigned int Compression;    /* Compression type        */ 
        unsigned int ImageSize;      /* Image size in bytes     */ 
        int xResolution, yResolution;/* Pixels per meter        */ 
        unsigned int Colors;         /* Number of colors        */ 
        unsigned int ImportantColors;/* Important colors        */ 
    } InfoHeader;                   /* -- 40 Bytes --          */
    
    
    
    
    struct PIXEL 
    { unsigned char Red, Green, Blue; 
    };
    
    
    
    
    /*------------------------------------------------------------------------/
     END Code from Bill Reid
    /------------------------------------------------------------------------*/
    
    
    //prototypes
    void edgeDectection(struct PIXEL **pixArray, int height, int width, struct PIXEL **pixArray2);
    
    
    //int main
    int main(int argc, char *argv[]){
        //variable declaration
        int i, j;
        
        //check to make sure the user inputed the proper number of commands
        //on the comman line
        if(argc != 3){
            printf("invalid amount of command line inputs\n");
            exit(1);
        }
        //the second argument should be the file name
        FILE *input = fopen(argv[1],"rb");
        //check to see if the file was able to be opened
        if(input==0){
            printf("could not open the file\n");
            fclose(input);
            exit(1);
        }
        
        //write the output file, which is the thrid argument
        FILE *output = fopen(argv[2],"wb");
            
        //check to see if the file was able to be opened
        if(output==0){
            printf("could not create or open the file to write to\n");
            fclose(output);
            exit(1);
        }
        //read the header for the file
        fread(&Header, sizeof(Header), 1, input);
        //read the info header
        fread(&InfoHeader, sizeof(InfoHeader), 1, input);
        
        //write header to new file
        fwrite(&Header, sizeof(Header),1, output);
        //read in the info header
        fwrite(&InfoHeader, sizeof(InfoHeader),1, output);
        
    
    
        //create 2D array of structures for every pixel
        struct PIXEL **pixArray;
        struct PIXEL **pixArray2;
        
        //allocate the memory for the amount of rows
        pixArray = (struct PIXEL **)calloc(InfoHeader.Height,sizeof(struct PIXEL*));
        
        //allocate space for the number of columns
        for (i=0; i < InfoHeader.Height; i++) {
            pixArray[i] = (struct PIXEL *)calloc(InfoHeader.Width,sizeof(struct PIXEL*));
        }
        //check to make sure memory was allocated
        if(pixArray==NULL){
            printf("Memory unable to be allocated! Exiting Program Now!\n");
            exit(1);
        }
        //second array that new values are read into
        //allocate the memory for the amount of rows
        pixArray2 = (struct PIXEL **)calloc(InfoHeader.Height,sizeof(struct PIXEL*));
        
        //allocate space for the number of columns
        for (i=0; i < InfoHeader.Height; i++) {
            pixArray2[i] = (struct PIXEL *)calloc(InfoHeader.Width,sizeof(struct PIXEL*));
        }
        //check to make sure memory was allocated
        if(pixArray2==NULL){
            printf("Memory unable to be allocated! Exiting Program Now!\n");
            exit(1);
        }
        //read the rest of the data into the allocated memory
        for (i=0; i < InfoHeader.Height; i++) {
            for (j=0; j < InfoHeader.Width; j++) {
                fread(&pixArray[i][j], sizeof(struct PIXEL*), 1,input);
                printf("[%d][%d][%d]\n",pixArray[i][j].Red, pixArray[i][j].Green,pixArray[i][j].Blue);
            }
        }
        //apply the filter
        printf("------------\n");
        edgeDectection(pixArray, InfoHeader.Height, InfoHeader.Width, pixArray2);
        printf("it made it\n");
        for (i=0; i < InfoHeader.Height; i++) {
            for (j=0; j < InfoHeader.Width; j++) {
                fwrite(&pixArray2[i][j], sizeof(struct PIXEL*), 1,output);
                printf("[%d][%d][%d]\n",pixArray2[i][j].Red, pixArray2[i][j].Green,pixArray2[i][j].Blue);
            }
        }
        fclose(input);
        fclose(output);
        free(pixArray);
        free(pixArray2);
        return 0;
    }
    
    
    void edgeDectection(struct PIXEL **pixArray, int height, int width, struct PIXEL **pixArray2){
        int newR, newG, newB, i, j;
        //int matrix[3][3] = {{0,-1,0},{-1,4,-1},{0,-1,0}};
        for (i =0; i < InfoHeader.Height; i++) {
            for (j =0; j<InfoHeader.Width; j++) {
                if((i>0 && j > 0)&&(i<height && j<width)){
                    newR = (pixArray[i-1][j-1].Red*0)+(pixArray[i-1][j].Red*(-1))+(pixArray[i-1][j+1].Red*0)+(pixArray[i][j-1].Red*(-1))+(pixArray[i][j].Red*4)+(pixArray[i][j+1].Red*(-1))+(pixArray[i+1][j-1].Red*0)+(pixArray[i+1][j].Red*(-1))+(pixArray[i+1][j+1].Red*0);
                    newG = (pixArray[i-1][j-1].Green*0)+(pixArray[i-1][j].Green*(-1))+(pixArray[i-1][j+1].Green*0)+(pixArray[i][j-1].Green*(-1))+(pixArray[i][j].Green*4)+(pixArray[i][j+1].Green*(-1))+(pixArray[i+1][j-1].Green*0)+(pixArray[i+1][j].Green*(-1))+(pixArray[i+1][j+1].Green*0);
                    newB = (pixArray[i-1][j-1].Blue*0)+(pixArray[i-1][j].Blue*(-1))+(pixArray[i-1][j+1].Blue*0)+(pixArray[i][j-1].Blue*(-1))+(pixArray[i][j].Blue*4)+(pixArray[i][j+1].Blue*(-1))+(pixArray[i+1][j-1].Blue*0)+(pixArray[i+1][j].Blue*(-1))+(pixArray[i+1][j+1].Blue*0);
                }
                else if(i==0 && j==0){
                    newR = (pixArray[i][j].Red*4)+(pixArray[i][j+1].Red*(-1))+(pixArray[i+1][j].Red*(-1))+(pixArray[i+1][j+1].Red*0);
                    newG = (pixArray[i][j].Green*4)+(pixArray[i][j+1].Green*(-1))+(pixArray[i+1][j].Green*(-1))+(pixArray[i+1][j+1].Green*0);
                    newB = (pixArray[i][j].Blue*4)+(pixArray[i][j+1].Blue*(-1))+(pixArray[i+1][j].Blue*(-1))+(pixArray[i+1][j+1].Blue*0);
                }
                else if(i==height && j==width){
                    newR = (pixArray[i-1][j-1].Red*0)+(pixArray[i-1][j].Red*(-1))+(pixArray[i][j-1].Red*(-1))+(pixArray[i][j].Red*4);
                    newG = (pixArray[i-1][j-1].Green*0)+(pixArray[i-1][j].Green*(-1))+(pixArray[i][j-1].Green*(-1))+(pixArray[i][j].Green*4);
                    newB = (pixArray[i-1][j-1].Blue*0)+(pixArray[i-1][j].Blue*(-1))+(pixArray[i][j-1].Blue*(-1))+(pixArray[i][j].Blue*4);
                }
                else if(i==0 && j==width){
                    newR = (pixArray[i][j-1].Red*(-1))+(pixArray[i][j].Red*4)+(pixArray[i+1][j-1].Red*0)+(pixArray[i+1][j].Red*(-1));
                    newG = (pixArray[i][j-1].Green*(-1))+(pixArray[i][j].Green*4)+(pixArray[i+1][j-1].Green*0)+(pixArray[i+1][j].Green*(-1));
                    newB = (pixArray[i][j-1].Blue*(-1))+(pixArray[i][j].Blue*4)+(pixArray[i+1][j-1].Blue*0)+(pixArray[i+1][j].Blue*(-1));
                }
                else if(i==height && j==0){
                    newR = (pixArray[i-1][j].Red*(-1))+(pixArray[i-1][j+1].Red*0)+(pixArray[i][j].Red*4)+(pixArray[i][j+1].Red*(-1));
                    newG = (pixArray[i-1][j].Green*(-1))+(pixArray[i-1][j+1].Green*0)+(pixArray[i][j].Green*4)+(pixArray[i][j+1].Green*(-1));
                    newB = (pixArray[i-1][j].Blue*(-1))+(pixArray[i-1][j+1].Blue*0)+(pixArray[i][j].Blue*4)+(pixArray[i][j+1].Blue*(-1));
                }
                else if((i>0 && i<height) && j==0){
                    newR = (pixArray[i-1][j].Red*(-1))+(pixArray[i-1][j+1].Red*0)+(pixArray[i][j].Red*4)+(pixArray[i][j+1].Red*(-1))+(pixArray[i+1][j].Red*(-1))+(pixArray[i+1][j+1].Red*0);
                    newG = +(pixArray[i-1][j].Green*(-1))+(pixArray[i-1][j+1].Green*0)+(pixArray[i][j].Green*4)+(pixArray[i][j+1].Green*(-1))+(pixArray[i+1][j].Green*(-1))+(pixArray[i+1][j+1].Green*0);
                    newB = (pixArray[i-1][j].Blue*(-1))+(pixArray[i-1][j+1].Blue*0)+(pixArray[i][j].Blue*4)+(pixArray[i][j+1].Blue*(-1))+(pixArray[i+1][j].Blue*(-1))+(pixArray[i+1][j+1].Blue*0);
                }
                else if((i>0 && i<height) && j==width){
                    newR = (pixArray[i-1][j-1].Red*0)+(pixArray[i-1][j].Red*(-1))+(pixArray[i][j-1].Red*(-1))+(pixArray[i][j].Red*4+(pixArray[i+1][j].Red*(-1)))+(pixArray[i+1][j+1].Red*0);
                    newG = (pixArray[i-1][j].Green*(-1))+(pixArray[i-1][j+1].Green*0)+(pixArray[i][j].Green*4)+(pixArray[i][j+1].Green*(-1))+(pixArray[i+1][j].Green*(-1))+(pixArray[i+1][j+1].Green*0);
                    newB = (pixArray[i-1][j].Blue*(-1))+(pixArray[i-1][j+1].Blue*0)+(pixArray[i][j].Blue*4)+(pixArray[i][j+1].Blue*(-1))+(pixArray[i+1][j].Blue*(-1))+(pixArray[i+1][j+1].Blue*0);
                }
                else if(i==0 && (j>0 && j<width)){
                    newR = (pixArray[i][j-1].Red*(-1))+(pixArray[i][j].Red*4)+(pixArray[i][j+1].Red*(-1))+(pixArray[i+1][j-1].Red*0)+(pixArray[i+1][j].Red*(-1))+(pixArray[i+1][j+1].Red*0);
                    newG = (pixArray[i][j-1].Green*(-1))+(pixArray[i][j].Green*4)+(pixArray[i][j+1].Green*(-1))+(pixArray[i+1][j-1].Green*0)+(pixArray[i+1][j].Green*(-1))+(pixArray[i+1][j+1].Green*0);
                    newB = (pixArray[i][j-1].Blue*(-1))+(pixArray[i][j].Blue*4)+(pixArray[i][j+1].Blue*(-1))+(pixArray[i+1][j-1].Blue*0)+(pixArray[i+1][j].Blue*(-1))+(pixArray[i+1][j+1].Blue*0);
                }
                elsebac{
                    newR = (pixArray[i-1][j-1].Red*0)+(pixArray[i-1][j].Red*(-1))+(pixArray[i-1][j+1].Red*0)+(pixArray[i][j-1].Red*(-1))+(pixArray[i][j].Red*4)+(pixArray[i][j+1].Red*(-1));
                    newG = (pixArray[i-1][j-1].Green*0)+(pixArray[i-1][j].Green*(-1))+(pixArray[i-1][j+1].Green*0)+(pixArray[i][j-1].Green*(-1))+(pixArray[i][j].Green*4)+(pixArray[i][j+1].Green*(-1));
                    newB = (pixArray[i-1][j-1].Blue*0)+(pixArray[i-1][j].Blue*(-1))+(pixArray[i-1][j+1].Blue*0)+(pixArray[i][j-1].Blue*(-1))+(pixArray[i][j].Blue*4)+(pixArray[i][j+1].Blue*(-1));
                }
                pixArray2[i][j].Red = newR;
                pixArray2[i][j].Green = newG;
                pixArray2[i][j].Blue = newB;
                printf("[%d][%d][%d]\n",pixArray2[i][j].Red, pixArray2[i][j].Green,pixArray2[i][j].Blue);
            }
        }
    }

  2. #2
    Algorithm Dissector iMalc's Avatar
    Join Date
    Dec 2005
    Location
    New Zealand
    Posts
    6,266
    Start by simplifying your code. Don't refer to pixArray[i-1][j-1] so many times for example. Get a pointer to that and then just do ptr->Red etc
    Or better yet, you should use a more object-oriented appraoch. Now I know this is not in C++ so you can't do operator overloading. But it can still be very useful to do things such as defining an add function which takes as input two PIXELs and outputs into a third PIXEL. Making a pixel multiply_scalar function will also help.
    These kind of things will help make your code clearer and easier for yourself, and us, to see the problem. It will also be easier to maintain, shorter, and more efficient.

    What's with elsebac on line 193?
    My homepage
    Advice: Take only as directed - If symptoms persist, please see your debugger

    Linus Torvalds: "But it clearly is the only right way. The fact that everybody else does it some other way only means that they are wrong"

  3. #3
    Registered User ledow's Avatar
    Join Date
    Dec 2011
    Posts
    435
    Helping yourself would be a good start. What are the values when it segfaults? What's in memory at those locations? How do you expect us to know any better than you? (I can compile it - minus the elsebac mentioned above - but what data are you testing with and where do you expect me to get one of those files that crashes?)

    Debug the program. That means put it through your debugger and then backtrace the segfault (which should be obvious and easy to trap) or if you haven't got a debugger (why not?) put in statements before the line that fails that prints out all relevant values at that point. Chances are you're accessing out of bounds or doing something very stupid, but in that tangle of code I wouldn't *start* looking at it or try hazarding guesses on what might have gone wrong. I'd just run it through my debugger, and find out, definitively, then go back and fix the source of the problem.

    P.S. Stray + at the start of line 180?
    Last edited by ledow; 03-26-2012 at 07:13 AM.

    - Compiler warnings are like "Bridge Out Ahead" warnings. DON'T just ignore them.
    - A compiler error is something SO stupid that the compiler genuinely can't carry on with its job. A compiler warning is the compiler saying "Well, that's bloody stupid but if you WANT to ignore me..." and carrying on.
    - The best debugging tool in the world is a bunch of printf()'s for everything important around the bits you think might be wrong.

  4. #4
    Registered User
    Join Date
    Sep 2008
    Location
    Toronto, Canada
    Posts
    1,831
    Edge detect is not correct.
    For example: if((i>0 && j > 0)&&(i<height && j<width)){

    'height' and 'width' are passed (copied) from InfoHeader.Height, InfoHeader.Width. Remember that arrays are addressed from 0 to max_size - 1. Therefore such checks have to be something like
    if ((i > 0 && j > 0) && (i < height - 1 && j < width - 1)){

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Picture download problem
    By wingri in forum C Programming
    Replies: 10
    Last Post: 07-31-2007, 05:32 AM
  2. picture
    By sunil21 in forum C Programming
    Replies: 1
    Last Post: 09-22-2003, 06:57 AM
  3. How do I set my picture?
    By napkin111 in forum A Brief History of Cprogramming.com
    Replies: 1
    Last Post: 05-10-2002, 07:23 AM
  4. picture
    By anonymous in forum C Programming
    Replies: 1
    Last Post: 01-29-2002, 01:44 AM
  5. 1 Problem on displaying a picture
    By SuperNewbie in forum Windows Programming
    Replies: 0
    Last Post: 01-25-2002, 03:38 AM

Tags for this Thread


1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21