glutSwapBuffers "Access violation reading location 0x0000000004C0F000"

396 views Asked by At

What I have to do is to display an image using a .ptm file.

So, I open the file, read the W and H and set the RGBA to each pixel. But when I try to display I get an Access Violation error at glutSwapBuffers().

Here is the code. It's kind of a mess because I'm trying many different things to fix it but I'm starting to think that each time I create a new problem :D

Image.h

    class Image {
public:
    Image() {};
    Image(int w, int h);
    ~Image();
    void setPixel(int rgb, int x, int y) {
        pixels[x + y] = rgb;
    }
    int setRgb(int r, int g, int b);
    int setRgb(int r, int g, int b, int a);
    int getPixel(int x, int y) {
        return pixels[x + y*width];
    }
    int * getPixel() { return pixels; }
    int getWidth() { return width; }
    int getHeight() { return height; }
private:
    int *pixels; 
    int width, height;
};

Image.cpp

#include "Image.h"
#include <stdlib.h>


Image::Image(int w, int h)
{
    width = w; height = h;
    pixels = (int*)malloc(h*w);
}


Image::~Image()
{
}

int Image::setRgb(int r, int g, int b)
{
    int rgb;
    rgb = (r << 16) | (g << 8) | b;
    return rgb;
}

int Image::setRgb(int r, int g, int b, int a)
{
    int rgba;
    rgba = (a<< 24) | (r << 16) | (g << 8) | b;
    return rgba;
}

source.cpp

#include <GL\freeglut.h>
#include <GL\GL.h>
#include <iostream>
#include <fstream>
#include <string>
#include <Windows.h>
#include "Image.h"

using namespace std;

void display()
{
    glClear(GL_COLOR_BUFFER_BIT);

    Image *img = new Image(800, 500);
    int w, h, max; //width height MaxValue
    char *w_ = new char; //in case of the file doesn't have a comment
    string fileModel, comment;
    ifstream myfile("dba.ptm"); //open the file

    if (myfile.is_open())
    {
        myfile >> fileModel;
        if (fileModel == "P7")
        {
            myfile >> w_;
            if (*w_ == '#')
                getline(myfile, comment);
            else
                w = atoi(w_);
            myfile >> h;

            int a, r, g, b, rgba;
            myfile >> max;
            for (int i = 0; i < w; i++)
            {
                for (int k = 0; k < h; k++)
                {
                    myfile >> a;
                    myfile >> r;
                    myfile >> g;
                    myfile >> b;
                    rgba = img->setRgb(r, g, b, a);
                    img->setPixel(rgba, i, k);
                }
            }
        }
    }
    myfile.close();


    glDrawPixels(img->getWidth(), img->getHeight(), GL_BGRA_EXT, GL_UNSIGNED_BYTE, img->getPixel());
    glutSwapBuffers();
}

void init(void)
{

    glClearColor(0.0, 0.0, 0.0, 0.0);
    glShadeModel(GL_FLAT);
    glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
    glEnable(GL_BLEND);
    glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);


    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();
    glOrtho(0.0, 800.0, 0.0, 500.0, -1.0, 1.0);
}

int main(int argc, char** argv)
{
    glutInit(&argc, argv);
    glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGBA);
    glutInitWindowSize(800, 500);
    glutInitWindowPosition(100, 100);
    glutCreateWindow("PTM");
    init();
    glutDisplayFunc(display);
    glutMainLoop();
    return 0;   
}
2

There are 2 answers

0
Cameron On

malloc(h*w) should be malloc(h*w*sizeof(int)), otherwise you're only allocating enough memory for a quarter of your image.

You also seem to be leaking the entire image every single frame, which will quickly exhaust your available RAM. You need to free and delete everything you malloc and new, respectively.

You probably also want to clear the memory you allocate for your image right away to avoid problems where only some of the pixels are set (the rest will be random values, which is likely less preferable than e.g. full transparency). You can do this with a memset or std::fill after the malloc.

0
Roddy On

Sorry, but you have LOTS wrong... :)

  • You're using malloc instead of new[]
  • You never free or delete anything
  • In most cases (apart from pixels) you don't need to create things on the heap anyway
  • This pixels[x + y] = rgb; is obviously wrong
  • This : char *w_ = new char; //in case of the file doesn't have a comment myfile >> w_; if (*w_ == '#') .. absolutely does NOT do what you think it does, or what you want it to do.

There's probably more. :(