Thread: SDL read error

  1. #1
    Slave MadCow257's Avatar
    Join Date
    Jan 2005
    Posts
    735

    SDL read error

    I'm making my own lossy image compression codec in c++ w/ SDL, and the decoder isn't reading the header correctly (or more likely the encoder isn't writing it right)
    Code:
    #include <SDL.h>
    #include <SDL_image.h>
    #include <iostream>
    #include <fstream>
    #include <windows.h>
    using namespace std;
    int ICEC();
    int DICEC();
    void Slock(SDL_Surface *dest);
    void Sulock(SDL_Surface *dest);
    int main(int argc, char *argv[])
    {
    	if(SDL_Init(SDL_INIT_VIDEO) == -1)
    		return -1;
    	atexit(SDL_Quit);
    	ICEC();
    	DICEC();
    }
    int ICEC()
    {
    	SDL_Surface * inimage = IMG_Load("Image\\test.bmp");
    
    	// vars
    	Slock(inimage);
    	int w = inimage->w;
    	int h = inimage->h;
    	Uint8 bpp = inimage->format->BytesPerPixel;
    	bool subsample = true;
    	ofstream out;
    
    	//write width, height, and bytes per pixel as a header
    	out.open("Image\\test.ice", ios::binary);
    	out.write(reinterpret_cast<char*>(&w), sizeof(int));
    	out.write(reinterpret_cast<char*>(&h), sizeof(int));
    	out.write(reinterpret_cast<char*>(&bpp), sizeof(Uint8));
    	Sulock(inimage);
    	out.close();
    	return 0;
    }
    void Slock(SDL_Surface *dest)
    {
      if ( SDL_MUSTLOCK(dest) )
      {
        if ( SDL_LockSurface(dest) < 0 )
        {
          return;
        }
      }
    }
    void Sulock(SDL_Surface *dest)
    {
    	if ( SDL_MUSTLOCK(dest) )
    	{
    		SDL_UnlockSurface(dest);
    	}
    }
    If I replace w = inimage->w with w = 512, the reader still doesn't give the correct number
    Also, the call to Slock is causing an access violation.
    I can't figure out the source of all these problems

    Thanks,
    MC

  2. #2
    Frequently Quite Prolix dwks's Avatar
    Join Date
    Apr 2005
    Location
    Canada
    Posts
    8,057
    Are you sure this code, right after the call to Slock(), isn't causing the violation?
    Code:
    int w = inimage->w;
    It's the first time inimage is accessed. The SDL functions can probably handle NULL, but inimage->w can't. Check (maybe in the debugger) to see if inimage is NULL.

    If I replace w = inimage->w with w = 512, the reader still doesn't give the correct number
    So in other words, if you don't try to dereference a NULL pointer, it doesn't crash?

    My guess would be that "Image\\test.bmp" doesn't exist. Or it can't be opened for some reason.

    One other thing -- you don't free your image. And yes, I know SDL_Quit() will free it, so this isn't a problem.
    dwk

    Seek and ye shall find. quaere et invenies.

    "Simplicity does not precede complexity, but follows it." -- Alan Perlis
    "Testing can only prove the presence of bugs, not their absence." -- Edsger Dijkstra
    "The only real mistake is the one from which we learn nothing." -- John Powell


    Other boards: DaniWeb, TPS
    Unofficial Wiki FAQ: cpwiki.sf.net

    My website: http://dwks.theprogrammingsite.com/
    Projects: codeform, xuni, atlantis, nort, etc.

  3. #3
    Frequently Quite Prolix dwks's Avatar
    Join Date
    Apr 2005
    Location
    Canada
    Posts
    8,057
    Code:
    #include <SDL.h>
    This header should be installed as <SDL/SDL.h>. Oops.
    dwk

    Seek and ye shall find. quaere et invenies.

    "Simplicity does not precede complexity, but follows it." -- Alan Perlis
    "Testing can only prove the presence of bugs, not their absence." -- Edsger Dijkstra
    "The only real mistake is the one from which we learn nothing." -- John Powell


    Other boards: DaniWeb, TPS
    Unofficial Wiki FAQ: cpwiki.sf.net

    My website: http://dwks.theprogrammingsite.com/
    Projects: codeform, xuni, atlantis, nort, etc.

  4. #4
    Slave MadCow257's Avatar
    Join Date
    Jan 2005
    Posts
    735
    Hmm..."Image\\test.bmp" is valid (it's the famous 512X512 Lena test image)
    so I still don't know
    If anyone would be so nice, here is my full code
    The call to printf in DICEC reveals that the width, height, and bpp are crazy
    With that in mind I have to be suspicious of the rest of the data

    For clarification, this code should convert an image from RGB into the YUV color space, and then subsample it with 4 lumas to a chroma

    Code:
    #include <SDL.h>
    #include "engine.h"
    #include "SDL_image.h"
    #include "SDL_mixer.h"
    #include <iostream>
    #include <fstream>
    #include <windows.h>
    
    using namespace std;
    
    int ICEC();
    int DICEC();
    
    SDL_Surface * screen, * inimage;
    
    int main(int argc, char *argv[])
    {
    	if(SDL_Init(SDL_INIT_VIDEO|SDL_INIT_AUDIO|SDL_INIT_TIMER) == -1)
    		return -1;
    	atexit(SDL_Quit);
    	screen = SDL_SetVideoMode(512, 512, 32, SDL_HWSURFACE|SDL_DOUBLEBUF);
    	ICEC();
    	DICEC();
    	return 0;
    }
    int ICEC()
    {
    	SDL_Surface * inimage = IMG_Load("Image\\test.bmp");
    
    	// vars
    	int w = inimage->w;
    	int h = inimage->h;
    	Uint8 bpp = inimage->format->BytesPerPixel;
    	bool subsample = true;
    	ofstream out;
    
    	//write width, height, and bytes per pixel as a header
    	out.open("Image\\test.ice", ios::binary);
    	out.write(reinterpret_cast<char*>(&w), sizeof(int));
    	out.write(reinterpret_cast<char*>(&h), sizeof(int));
    	out.write(reinterpret_cast<char*>(&bpp), sizeof(Uint8));
    	switch (bpp)
    	{
    	case 3:
    		Uint8 R, G, B, Y1,Y2,Y3,Y4;
    		Uint32 U, V;
    		Uint8 U2, V2;
    		if (subsample == true)
    		{
    			for (int x = 0; x < w; x+=2)
    			{
    				for (int y = 0; y < h; y+=2)
    				{
    					U = 0; V = 0;
    
    					Slock(inimage);
    					SDL_GetRGB((Uint32)inimage->pixels + y*inimage->pitch + x * 3, inimage->format, &R, &G, &B);
    					Y1 = (0.299*R + 0.587*G + 0.114*B);
    					U+=(- 0.147*R - 0.289*G + 0.436*B);
    					V+=(0.615*R - 0.515*G - 0.100*B);
    
    					SDL_GetRGB((Uint32)inimage->pixels + y*inimage->pitch + (x+1) * 3, inimage->format, &R, &G, &B);
    					Y2 = (0.299*R + 0.587*G + 0.114*B);
    					U+=(- 0.147*R - 0.289*G + 0.436*B);
    					V+=(0.615*R - 0.515*G - 0.100*B);
    
    					SDL_GetRGB((Uint32)inimage->pixels + (y+1)*inimage->pitch + (x+1) * 3, inimage->format, &R, &G, &B);
    					Y3 = (0.299*R + 0.587*G + 0.114*B);
    					U+=(- 0.147*R - 0.289*G + 0.436*B);
    					V+=(0.615*R - 0.515*G - 0.100*B);
    
    					SDL_GetRGB((Uint32)inimage->pixels + (y+1)*inimage->pitch + x * 3, inimage->format, &R, &G, &B);
    					Y4 = (0.299*R + 0.587*G + 0.114*B);
    					U+=(- 0.147*R - 0.289*G + 0.436*B);
    					V+=(0.615*R - 0.515*G - 0.100*B);
    					Sulock(inimage);
    
    					out.write(reinterpret_cast<char*>(&Y1), sizeof(Uint8));
    					out.write(reinterpret_cast<char*>(&Y2), sizeof(Uint8));
    					out.write(reinterpret_cast<char*>(&Y3), sizeof(Uint8));
    					out.write(reinterpret_cast<char*>(&Y4), sizeof(Uint8));
    					U2 = (Uint8)(U/4);
    					V2 = (Uint8)(V/4);
    					out.write(reinterpret_cast<char*>(&U2), sizeof(Uint8));
    					out.write(reinterpret_cast<char*>(&V2), sizeof(Uint8));
    				}
    			}
    		}
    		break;
    	}
    	out.close();
    	return 0;
    }
    int DICEC()
    {
    	//vars
    	ifstream read;
    	int w, h;
    	Uint8 R, G, B, Y1,Y2,Y3,Y4,U,V;
    	Uint8 bpp;
    	bool subsample = true;
    
    	//header
    	read.open("Images\\test.ice", ios::binary);
    	read.read(reinterpret_cast<char*>(&w), sizeof(int));
    	read.read(reinterpret_cast<char*>(&h), sizeof(int));
    	read.read(reinterpret_cast<char*>(&bpp), sizeof(Uint8));
    	printf("%d%d%d", w, h, bpp);
    
    	//main
    	switch (bpp)
    	{
    	case 3:
    		if (subsample == true)
    		{
    			for (int x = 0; x < w; x+=2)
    			{
    				for (int y = 0; y < h; y+=2)
    				{
    					 read.read(reinterpret_cast<char*>(&Y1), sizeof(Uint8));
    					 read.read(reinterpret_cast<char*>(&Y2), sizeof(Uint8));
    					 read.read(reinterpret_cast<char*>(&Y3), sizeof(Uint8));
    					 read.read(reinterpret_cast<char*>(&Y4), sizeof(Uint8));
    					 read.read(reinterpret_cast<char*>(&U), sizeof(Uint8));
    					 read.read(reinterpret_cast<char*>(&V), sizeof(Uint8));
    					 Slock(screen);
    					 R = Y1 + 1.140*V;G = Y1 - 0.395*U - 0.581*V;B = Y1 + 2.032*U;
    					 DrawPixel(screen, x, y, R, G, B);
    					 R = Y2 + 1.140*V;G = Y2 - 0.395*U - 0.581*V;B = Y2 + 2.032*U;
    					 DrawPixel(screen, x+1, y, R, G, B);
    					 R = Y3 + 1.140*V;G = Y3 - 0.395*U - 0.581*V;B = Y3 + 2.032*U;
    					 DrawPixel(screen, x+1, y+1, R, G, B);
    					 R = Y4 + 1.140*V;G = Y4 - 0.395*U - 0.581*V;B = Y4 + 2.032*U;
    					 DrawPixel(screen, x, y+1, R, G, B);
    					 Sulock(screen);
    				}
    			}
    		}
    		else
    		{
    		}
    		break;
    	}
    	read.close();
    	while (!GetAsyncKeyState(VK_ESCAPE))
    	{
    		SDL_Flip(screen);
    		SDL_Delay(1000);
    	}
    	return 0;
    }

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. failure to import external C libraries in C++ project
    By nocturna_gr in forum C++ Programming
    Replies: 3
    Last Post: 12-02-2007, 03:49 PM
  2. file reading
    By gunghomiller in forum C++ Programming
    Replies: 9
    Last Post: 08-07-2007, 10:55 PM
  3. Please Help - Problem with Compilers
    By toonlover in forum C++ Programming
    Replies: 5
    Last Post: 07-23-2005, 10:03 AM
  4. Couple C questions :)
    By Divx in forum C Programming
    Replies: 5
    Last Post: 01-28-2003, 01:10 AM
  5. Linking error
    By DockyD in forum C++ Programming
    Replies: 10
    Last Post: 01-20-2003, 05:27 AM