[Solved] Textures to VRAM
[Solved] Textures to VRAM
Hello!
I 've have started porting NeHe's Tutorials for the PSPGU and was wondering of how can I assign a texture to the VRAM? I made a search but no similar posts appeared (if there is one already, i am sorry, but didn't find it..)
If you are interested about the tutorials (and with it the code I use..) you can find the here:
http://www.psp-programming.com/code/ind ... rt-lesson1
http://www.psp-programming.com/code/ind ... rt-lesson2
http://www.psp-programming.com/code/ind ... rt-lesson3
http://www.psp-programming.com/code/ind ... rt-lesson4
http://www.psp-programming.com/code/ind ... rt-lesson5
.. - will try to port them all -
I just found out that ps2dev had a wiki too..
Thank you for your time!
I 've have started porting NeHe's Tutorials for the PSPGU and was wondering of how can I assign a texture to the VRAM? I made a search but no similar posts appeared (if there is one already, i am sorry, but didn't find it..)
If you are interested about the tutorials (and with it the code I use..) you can find the here:
http://www.psp-programming.com/code/ind ... rt-lesson1
http://www.psp-programming.com/code/ind ... rt-lesson2
http://www.psp-programming.com/code/ind ... rt-lesson3
http://www.psp-programming.com/code/ind ... rt-lesson4
http://www.psp-programming.com/code/ind ... rt-lesson5
.. - will try to port them all -
I just found out that ps2dev had a wiki too..
Thank you for your time!
Last edited by skistovel on Sun Jul 23, 2006 1:49 pm, edited 1 time in total.
Yes, I saw the "sceGuCopyImage" function, but looking at the provided example I was a bit confused. How do you call bind the texture afterward?
Would you still use the variable name? Or do you provide a different variable for the vram placed texture?
the example i say is that:
I dont understand the last parameter (void*)(((unsigned int)framebuffer)+0x4000000))
Would you still use the variable name? Or do you provide a different variable for the vram placed texture?
the example i say is that:
Code: Select all
sceGuCopyImage(GU_PSM_8888,0,0,480,272,512,pixels,0,0,512,(void*)(((unsigned int)framebuffer)+0x4000000))
I am still not sure what exacly this function does, I suppose that somehow it moves the data to the video memory, but I didn't see any difference in speed!
In my head I imagined that it would create a new allocation in video memory and would copy the data there and so you would be able to free the data from the main memory afterwards. It seems I am wrong..
Thanks for the help anyway! Appreciate the quick reply!
In my head I imagined that it would create a new allocation in video memory and would copy the data there and so you would be able to free the data from the main memory afterwards. It seems I am wrong..
Thanks for the help anyway! Appreciate the quick reply!
There's no memory management provided for the graphics memory. It's up to you how to handle that. I think somebody wrote a basic dynamic memory allocation thingo for vram, you might want to search for it. sceGuCopyImage just does the transfer faster than if you were to do it on cpu, and also means you can use the cpu time for more important stuff.
The sceGuCopyImage function is nothing more than it's name tells - a simple hardware blitter, copying from source (7th param) to dest (last param).
As said already, the gu does not handle vram allocations and it also does not provide a texture manager as openGL does. It's all up to you to load textures into vram and keep them there. It's quite a demanding to code a texture manager, since the VRAM is pretty limited (2MB, and only 1.2MB for textures in 16bit mode with doublebuffering+zbuffer, 600kb in 32bit mode). I have just some time ago started to working on one myself and it's nearly finished, though I'm still thinking about better ways to handle the cases.
Most likely, you're already best setup if you just transfer every texture you need to VRAM without much worries for keeping as much textures as possible as long as possible in VRAM, since the transfer speed accounts for the lack of memory.
I have written the vram mmu mentioned by ReKleSS. You can get the current version here: http://www.fx-world.org/download/valloc101.zip
It provides you with alloc, free and realloc functions on VRAM. You need to allocate your framebuffers and zbuffer with this to correctly work with offscreen textures, since else it doesn't know which parts are already used.
As said already, the gu does not handle vram allocations and it also does not provide a texture manager as openGL does. It's all up to you to load textures into vram and keep them there. It's quite a demanding to code a texture manager, since the VRAM is pretty limited (2MB, and only 1.2MB for textures in 16bit mode with doublebuffering+zbuffer, 600kb in 32bit mode). I have just some time ago started to working on one myself and it's nearly finished, though I'm still thinking about better ways to handle the cases.
Most likely, you're already best setup if you just transfer every texture you need to VRAM without much worries for keeping as much textures as possible as long as possible in VRAM, since the transfer speed accounts for the lack of memory.
I have written the vram mmu mentioned by ReKleSS. You can get the current version here: http://www.fx-world.org/download/valloc101.zip
It provides you with alloc, free and realloc functions on VRAM. You need to allocate your framebuffers and zbuffer with this to correctly work with offscreen textures, since else it doesn't know which parts are already used.
Thanks a lot Raphael, I will try once more, to see if it actually worths the hassle to move the textures to video memory (if the speed is not increased dramatically I see no point..). Although its always useful to keep your most used texture maps (of your main character example) somewhere fast!
Just to make sure, in my image loader function, instead of malloc, i replace it with valloc and that should be enough? Do I still need to use sceGuTexSync()?
Also, in case you have any experience; I mentioned on my first post that I recently started porting nehe's tutorials. Reaching lesson 9 ( a simple particle system ), when the particle number increased more than 20, artifacts started appearing on the textures. The bigger the number of stars the bigger the space the artifacts took on the quads..
Is that because the texture was on the main memory and had to read it so many times per frame?
The code is here, if u want to take a look: http://www.skistovel.2plans.com/psp/Lesson8.rar
Just to make sure, in my image loader function, instead of malloc, i replace it with valloc and that should be enough? Do I still need to use sceGuTexSync()?
Also, in case you have any experience; I mentioned on my first post that I recently started porting nehe's tutorials. Reaching lesson 9 ( a simple particle system ), when the particle number increased more than 20, artifacts started appearing on the textures. The bigger the number of stars the bigger the space the artifacts took on the quads..
Is that because the texture was on the main memory and had to read it so many times per frame?
The code is here, if u want to take a look: http://www.skistovel.2plans.com/psp/Lesson8.rar
As long as you have some few textures which are heavily used, it does make much sense to keep them in VRAM all the time (speed difference, depending on texture size, is starting from double speed upwards). For other cases it's ok to just transfer the texture to VRAM each time you need it. As I said, the transfer speed (~150mb/s) makes up for the lack of VRAM.skistovel wrote:Thanks a lot Raphael, I will try once more, to see if it actually worths the hassle to move the textures to video memory (if the speed is not increased dramatically I see no point..). Although its always useful to keep your most used texture maps (of your main character example) somewhere fast!
You could do that, yes, but I wouldn't recommend that way. As long as it's your only texture used and you don't swizzle it, this might be ok, but if you have more textures or want to swizzle them, better load your textures to system ram, and then either do a swizzled upload or in the latter case from above swizzle them in sysram and upload every frame.Just to make sure, in my image loader function, instead of malloc, i replace it with valloc and that should be enough? Do I still need to use sceGuTexSync()?
SceGuTexSync() is needed when you upload a texture to VRAM and part of that memory is still in texture cash (which you won't know until you get some wrong texture artifacts). So just call it after each sceGuCopyImage and you're fine.
No, the number of times you use a texture is meaningless, since the gu just directly reads from the specified memory address. If that address is in sysram, it will slow down those reads quite frankly, but other than that have no influence.Also, in case you have any experience; I mentioned on my first post that I recently started porting nehe's tutorials. Reaching lesson 9 ( a simple particle system ), when the particle number increased more than 20, artifacts started appearing on the textures. The bigger the number of stars the bigger the space the artifacts took on the quads..
Is that because the texture was on the main memory and had to read it so many times per frame?
The code is here, if u want to take a look: http://www.skistovel.2plans.com/psp/Lesson8.rar
Your problem was that your commandlist was too short to hold much more than 20 of your stars. Increase it to somewhat much more than 1024bytes, especially if you want to extend your drawing code with models and other stuff. Actually, some 100 or 200kb statically allocated memory won't hurt your program, but get you on the safe side ;)
And as a sidenote:
I noticed you did something like that:
Code: Select all
fpsDisplay = (char*) malloc( 20*sizeof(char));
fpsDisplay = "FPS: calculating";
I wonder however, why the free( fpsDisplay ); statement at the end then doesn't crash the application, since it should try to free memory which wasn't allocated by malloc, but maybe the compiler is smart enough to make up for your static assignment from above.
Well, I'd just outcomment that second line from above, since you generate your fps string every time anyway, so it makes no difference.
Code: Select all
fpsDisplay = (char*) malloc( 20*sizeof(char));
fpsDisplay = "FPS: calculating";
I was drawing a few triangles and was fine, then i decided to add a cube. And then I though lets have them rotate with different values, different axis. Suddenly psplink crashed, again and again - running it from the VSH displayed a "drugged up" double screen with washed out colors. I found after many recompiles that the sprintf line was the root of all evil. So I tried everything .. At a point it worked and forgot to check it again!
Well, THAT - I didn't expect! PSP had crashed on me saw many times the past 3 days, that since it was running it didn't occur to me at all that it might be the display list size.. Anyway,your commandlist was too short
Thanks again the valuable info & you patience -to read my code-, you have been a great help!
sprintf can be evil sometimes :) especially if you don't exactly look at your buffer sizes and what you can end up writing there (that's why I prefer snprintf now). The results sometimes are even fancier than plain crashes (had a lot of out of memory problems once with that)skistovel wrote: That line actually, it was from crashes I had on my earlier attempts. I used to have fpsDisplay as a normal char array of 20, which i added the # of frames using the sprintf call at the fps() function.
I was drawing a few triangles and was fine, then i decided to add a cube. And then I though lets have them rotate with different values, different axis. Suddenly psplink crashed, again and again - running it from the VSH displayed a "drugged up" double screen with washed out colors. I found after many recompiles that the sprintf line was the root of all evil. So I tried everything .. At a point it worked and forgot to check it again!
No problem, glad to help :)Thanks again the valuable info & you patience -to read my code-, you have been a great help!
You are already my personal hero!
The now updated tutorial 8 thanks to you!
ps: I didnt know what to say, so I just wrote Raphael from ps2dev.org..
The now updated tutorial 8 thanks to you!
ps: I didnt know what to say, so I just wrote Raphael from ps2dev.org..