psp crash when I try to resize image with SDL

Discuss the development of new homebrew software, tools and libraries.

Moderators: cheriff, TyRaNiD

Post Reply
danny_dot_net
Posts: 4
Joined: Fri Jul 11, 2008 5:38 pm

psp crash when I try to resize image with SDL

Post by danny_dot_net »

the program is simply for loading a jpg file each time and displaying it.

there are altogether 3 jpg files, the sizes of the first two are all 512*340.

When I load, resize and display the first image, it goes fine. but when it comes to the second image, the psp get crashed, but it goes well on pc. I use "zoomSurface" from SDL_rotozoom to resize image. If image is not resized, just simply loading and displaying, the program runs fine in both pc and psp.

the main function is void DrawPic(int id), possible error are hiding there.

Code: Select all

#pragma warning(disable : 4786)
#ifdef WIN32
#else
#include <pspkernel.h>
#endif
#include <stdio.h>
#include <malloc.h>
#include <sdl.h>
#include <sdl_image.h>
#include <sdl_ttf.h>
#include "sdl_rotozoom.h"

#define SCREEN_WIDTH 480
#define SCREEN_HEIGHT 272

#ifdef WIN32
#else
PSP_HEAP_SIZE_KB&#40;20480&#41;;
#endif

SDL_Surface *Screen;
SDL_Surface *Image;
SDL_Surface *Message;
TTF_Font *Font;

int freemem&#40;&#41; 
&#123; 
 void *ptrs&#91;480&#93;; 
 int mem, x, i; 
 for &#40;x = 0; x < 480; x++&#41; 
 &#123; 
    void *ptr = malloc&#40;51200&#41;; 
    if &#40;!ptr&#41; break; 
  
    ptrs&#91;x&#93; = ptr; 
 &#125; 
 mem = x * 51200; 
 for &#40;i = 0; i < x; i++&#41; 
  free&#40;ptrs&#91;i&#93;&#41;; 

 return mem; 
&#125;


void Write&#40;char *content,int x, int y&#41;
&#123;
	SDL_Color fontcolor=&#123;0,255,0&#125;;
	SDL_Rect coord=&#123;x,y,0,0&#125;;
	
	Message=TTF_RenderText_Solid&#40;Font,content,fontcolor&#41;;
	SDL_BlitSurface&#40;Message,NULL,Screen,&coord&#41;;
	SDL_FreeSurface&#40;Message&#41;;
	SDL_Flip&#40; Screen &#41;;
&#125;


void DrawPic&#40;int id&#41;
&#123;
	char filename&#91;30&#93;;
	char string&#91;30&#93;;
	double ratio,ratio1,ratio2;
	SDL_RWops *rwop;
	SDL_Surface *resizedImage;

	if&#40;Image!=NULL&#41;
	&#123;
		SDL_FreeSurface&#40;Image&#41;;
	&#125;
	//load a image
	sprintf&#40;filename,"gamebg%d.jpg",id&#41;;
	rwop=SDL_RWFromFile&#40;filename,"rb"&#41;;
	Image=IMG_LoadJPG_RW&#40;rwop&#41;;
	if&#40;Image==NULL&#41;
	&#123;
		sprintf&#40;string,"Err&#58; Image load error!\n"&#41;;
		Write&#40;string,10,30&#41;;
		return;
	&#125;
	rwop->close&#40;rwop&#41;;
	SDL_FreeRW&#40;rwop&#41;; 

	//-----------------------------------------------
	//-----------Error part starts here--------------
	//-----------------------------------------------
	//zoom the image
	ratio1=&#40;double&#41;SCREEN_WIDTH/Image->w;
	ratio2=&#40;double&#41;SCREEN_HEIGHT/Image->h;
	if&#40;ratio1<ratio2&#41;
		ratio=ratio1;
	else
		ratio=ratio2;
	resizedImage=zoomSurface&#40;Image,ratio,ratio,0&#41;;
	if&#40;resizedImage==NULL&#41;
	&#123;
		sprintf&#40;string,"Image resize error!\n"&#41;;
		Write&#40;string,10,30&#41;;
		return;
	&#125;
	if&#40;Image!=NULL&#41;SDL_FreeSurface&#40;Image&#41;;
	Image=resizedImage;
	//---------------------------------------------
	//-----------Error part ends here--------------
	//---------------------------------------------

	//draw black background
	SDL_FillRect&#40;Screen,NULL,SDL_MapRGB&#40;Screen->format,0,0,0&#41;&#41;;
	//draw the image
	SDL_BlitSurface&#40;Image, NULL, Screen, NULL&#41;;
	//update screen
	SDL_Flip&#40; Screen &#41;;
	//Show pic id
	sprintf&#40;string,"PicID&#58; %d",id&#41;;
	Write&#40;string,10,10&#41;;
	sprintf&#40;string,"Available Mem&#58; %.2fM",freemem&#40;&#41;*1.0/&#40;1024*1024&#41;&#41;;
	Write&#40;string,200,10&#41;;
&#125;


extern "C"
int main&#40;int argc, char* argv&#91;&#93;&#41;
&#123;
	//Initialize SDL and other sub-systems
	SDL_Init&#40;SDL_INIT_VIDEO&#41;;
	Screen = SDL_SetVideoMode&#40;SCREEN_WIDTH, SCREEN_HEIGHT, 32, SDL_SWSURFACE|SDL_ANYFORMAT&#41;;
	SDL_ShowCursor&#40;SDL_DISABLE&#41;;
	TTF_Init&#40;&#41;;
	Font=TTF_OpenFont&#40;"times.ttf",12&#41;;

	//first image show
	DrawPic&#40;1&#41;;
	SDL_Delay&#40;2000&#41;;
	DrawPic&#40;2&#41;;
	SDL_Delay&#40;2000&#41;;
	DrawPic&#40;3&#41;;
	SDL_Delay&#40;2000&#41;;

	//end program
	SDL_Quit&#40;&#41;;
	
	return 0;
&#125;
User avatar
Jim
Posts: 476
Joined: Sat Jul 02, 2005 10:06 pm
Location: Sydney
Contact:

Post by Jim »

free resizedImage
danny_dot_net
Posts: 4
Joined: Fri Jul 11, 2008 5:38 pm

Post by danny_dot_net »

Now I find what makes the program get crashed in PSP, the bug is that

Code: Select all

resizedImage=zoomSurface&#40;Image,ratio,ratio,0&#41;; 
can not exist at the same time with the following code

Code: Select all

   sprintf&#40;string,"PicID&#58; %d",id&#41;; 
   Write&#40;string,10,10&#41;; 
   sprintf&#40;string,"Available Mem&#58; %.2fM",freemem&#40;&#41;*1.0/&#40;1024*1024&#41;&#41;; 
   Write&#40;string,200,10&#41;; 
If one of them is deleted from the code, the whole program runs wll in PSP, but it does not happen when both of them are there.
User avatar
Jim
Posts: 476
Joined: Sat Jul 02, 2005 10:06 pm
Location: Sydney
Contact:

Post by Jim »

What if you just take out the freemem() call from the sprintf? Does it still work then? If so, the heap has got corrupted. But from the size of your images you're going to run out of memory too, hence my first suggestion.

Jim
danny_dot_net
Posts: 4
Joined: Fri Jul 11, 2008 5:38 pm

Post by danny_dot_net »

Jim wrote:What if you just take out the freemem() call from the sprintf? Does it still work then? If so, the heap has got corrupted. But from the size of your images you're going to run out of memory too, hence my first suggestion.

Jim
as you can see freemem() just checks the residual memory size but does not possese any memory after calling it. anyway, I will give a shot.
User avatar
Jim
Posts: 476
Joined: Sat Jul 02, 2005 10:06 pm
Location: Sydney
Contact:

Post by Jim »

I know, but if the heap were corrupted (eg. by some function allocating too little space then overwriting the end of the allocation), then using the heap next time (like freemem does) will likely trigger a crash caused by corrupting heap earlier on.

If taking out the freemem call moves the error back into the next zoomSurface then either you are running out of ram entirely, or zoomSurface is corrupting the heap.

Jim
Smong
Posts: 82
Joined: Tue Sep 04, 2007 4:44 am

Post by Smong »

This probably isn't related to the error you are expeiencing, but you don't need to be calling SDL_Flip() so often. Try taking it out of Write() and DrawPic(), then call it after DrawPic like this:

Code: Select all

   //first image show
   DrawPic&#40;1&#41;;
   SDL_Flip&#40;Screen&#41;;
   SDL_Delay&#40;2000&#41;;
   
   DrawPic&#40;2&#41;;
   SDL_Flip&#40;Screen&#41;;
   SDL_Delay&#40;2000&#41;;
   
   DrawPic&#40;3&#41;;
   SDL_Flip&#40;Screen&#41;;
   SDL_Delay&#40;2000&#41;; 
(+[__]%)
User avatar
Jim
Posts: 476
Joined: Sat Jul 02, 2005 10:06 pm
Location: Sydney
Contact:

Post by Jim »

Post Reply