Strange pspgu behaviour

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

Moderators: cheriff, TyRaNiD

Post Reply
lego
Posts: 43
Joined: Fri Oct 17, 2008 1:09 am

Strange pspgu behaviour

Post by lego »

Hi.

I'm experimenting with GU. Now I have a simple code, that get my some strange result. First triangle is drawn nice, but a second one, which is dynamically allocated, isn't drawn. If I change an array from dynamically allocatable to a statically allocatable one, then all triangles are drawn well.

Code: Select all

#include <malloc.h>
#include <stdlib.h>
#include <stdio.h>
#include <unistd.h>
#include <signal.h>
#include <SDL/SDL.h>
#include <SDL/SDL_ttf.h>
/*
#include <GL/gl.h>
#include <GL/glu.h>
*/
#include <math.h>
#include <pspkernel.h>
#include <pspdebug.h>
#include <pspthreadman.h>
#include <pspdisplay.h>
#include <pspnet_inet.h>
#include <pspnet.h>
#include <psputility.h>
#include <pspgu.h>
#include <pspgum.h>
#include <psputils.h>


PSP_MODULE_INFO&#40;"ogl", 0, 3, 5&#41;;
PSP_MAIN_THREAD_ATTR&#40;PSP_THREAD_ATTR_USER | PSP_THREAD_ATTR_VFPU&#41;;
PSP_HEAP_SIZE_KB&#40;-1024&#41;;
PSP_MAIN_THREAD_STACK_SIZE_KB&#40;1024&#41;;

#define printf pspDebugScreenPrintf

#define BUF_WIDTH &#40;512&#41;
#define SCR_WIDTH &#40;480&#41;
#define SCR_HEIGHT &#40;272&#41;

void *dList;// display List, used by sceGUStart
void *fbp0;// frame buffer


typedef struct &#123;
  float x, y, z;
&#125; Vertex_t;

Vertex_t __attribute__&#40;&#40;aligned&#40;16&#41;&#41;&#41; triangle&#91;3&#93; =
&#123;
  &#123; 100, 100, 0 &#125;, &#123; 200, 200, 0&#125;, &#123; 100, 200, 0&#125;
&#125;  ;

Vertex_t *vv;


/*************************************************************
 * EXIT CALLBACK STUFF
 *************************************************************/
/* Exit callback */
int exit_callback&#40;int arg1, int arg2, void *common&#41; &#123;
  sceKernelExitGame&#40;&#41;;
  return 0;
&#125;

/* Callback thread */
int CallbackThread&#40;SceSize args, void *argp&#41; &#123;
  int cbid;

  cbid = sceKernelCreateCallback&#40;"Exit Callback", exit_callback, NULL&#41;;
  sceKernelRegisterExitCallback&#40;cbid&#41;;

  sceKernelSleepThreadCB&#40;&#41;;

  return 0;

&#125;

/* Sets up the callback thread and returns its thread id */
int SetupCallbacks&#40;void&#41; &#123;
  int thid = 0;

  thid = sceKernelCreateThread&#40;"update_thread", CallbackThread, 0x11, 0xFA0, 0, 0&#41;;
  if&#40;thid >= 0&#41; &#123;
    sceKernelStartThread&#40;thid, 0, 0&#41;;
  &#125;

  return thid;
&#125;

void initGU&#40; void &#41;
&#123;
  // Init GU
  sceGuInit&#40;&#41;;
  sceGuStart&#40; GU_DIRECT, dList &#41;;

  // Set Buffers
  sceGuDrawBuffer&#40; GU_PSM_8888, fbp0, BUF_WIDTH &#41;;
  sceGuDispBuffer&#40; SCR_WIDTH, SCR_HEIGHT, &#40;void*&#41;0x88000, BUF_WIDTH&#41;;
  sceGuDepthBuffer&#40; &#40;void*&#41;0x110000, BUF_WIDTH&#41;;

  sceGuOffset&#40; 2048 - &#40;SCR_WIDTH/2&#41;, 2048 - &#40;SCR_HEIGHT/2&#41;&#41;;
  sceGuViewport&#40; 2048, 2048, SCR_WIDTH, SCR_HEIGHT&#41;;
  sceGuDepthRange&#40; 65535, 0&#41;;

  // Set Render States
  sceGuScissor&#40; 0, 0, SCR_WIDTH, SCR_HEIGHT&#41;;
  sceGuEnable&#40; GU_SCISSOR_TEST &#41;;
  sceGuDepthFunc&#40; GU_GEQUAL &#41;;
  sceGuEnable&#40; GU_DEPTH_TEST &#41;;
  sceGuFrontFace&#40; GU_CW &#41;;
  sceGuShadeModel&#40; GU_SMOOTH &#41;;
  sceGuEnable&#40; GU_CULL_FACE &#41;;
  sceGuEnable&#40; GU_CLIP_PLANES &#41;;
  sceGuFinish&#40;&#41;;
  sceGuSync&#40;0,0&#41;;

  sceDisplayWaitVblankStart&#40;&#41;;
  sceGuDisplay&#40;GU_TRUE&#41;;
  // finish
&#125;

void setupProjection&#40; void &#41;
&#123;
  // setup matrices for the triangle

  sceGumMatrixMode&#40;GU_PROJECTION&#41;;
  sceGumLoadIdentity&#40;&#41;;
  sceGumPerspective&#40; 75.0f, 16.0f/9.0f, 0.5f, 1000.0f&#41;;

  sceGumMatrixMode&#40;GU_VIEW&#41;;
  sceGumLoadIdentity&#40;&#41;;

  sceGuClearColor&#40; GU_COLOR&#40; 0.0f, 0.0f, 0.0f, 1.0f &#41; &#41;;
  sceGuClearDepth&#40;0&#41;;

  sceGumMatrixMode&#40;GU_MODEL&#41;;
  sceGumLoadIdentity&#40;&#41;;
&#125;

int main&#40;void&#41;
&#123;
  SetupCallbacks&#40;&#41;;
  pspDebugScreenInit&#40;&#41;;

  if &#40; TTF_Init&#40;&#41; &#41; &#123;
    fprintf&#40;stderr, "TTF Error&#58; %s\n", TTF_GetError&#40;&#41;&#41;;
    exit&#40;1&#41;;
  &#125;
  atexit&#40;TTF_Quit&#41;;



  dList = memalign&#40;16, 524288&#41;;
  initGU&#40;&#41;;
  setupProjection&#40;&#41;;

  vv = &#40;Vertex_t*&#41;memalign&#40;16, 3 * sizeof&#40;Vertex_t&#41;&#41;;
  vv&#91;0&#93;.x = 100;
  vv&#91;0&#93;.y = 100;
  vv&#91;0&#93;.z = 0;
  vv&#91;1&#93;.x = 200;
  vv&#91;1&#93;.y = 100;
  vv&#91;1&#93;.z = 0;
  vv&#91;2&#93;.x = 200;
  vv&#91;2&#93;.y = 200;
  vv&#91;2&#93;.z = 0;

  sceGuStart&#40;GU_DIRECT, dList&#41;;

    sceGuClear&#40;GU_COLOR_BUFFER_BIT | GU_DEPTH_BUFFER_BIT&#41;;
    sceGuColor&#40;GU_COLOR&#40;1, 1, 1, 0&#41;&#41;;

    sceGumDrawArray&#40;GU_TRIANGLES, GU_VERTEX_32BITF | GU_TRANSFORM_2D,
                    3, 0, triangle&#41;;
    sceGuColor&#40;GU_COLOR&#40;0, 0, 1, 0&#41;&#41;;
    sceGumDrawArray&#40;GU_TRIANGLES, GU_VERTEX_32BITF | GU_TRANSFORM_2D,
                    3, 0, tr&#41;;
  sceGuFinish&#40;&#41;;
  sceGuSync&#40;0, 0&#41;;

  sceDisplayWaitVblankStart&#40;&#41;;
  sceGuSwapBuffers&#40;&#41;;

  sceKernelSleepThreadCB&#40;&#41;;

  return 0;
&#125;
What do I wrong :-)?
psPea
Posts: 60
Joined: Sat Sep 01, 2007 12:51 pm

Post by psPea »

It's probably a cache issue,
try sceKernelDCacheWritebackInvaidateRange on the vertices.
a_noob
Posts: 97
Joined: Sun Sep 17, 2006 8:33 am
Location: _start: jr 0xDEADBEEF

Post by a_noob »

you can avoid the cache problem by using local GU memory (from the display list). sceGuGetMemory(int size); (works just like malloc) You dont need to free this memory or write it back. However it is invalid at the end of the frame. Also if you choose you use malloc. It is 16bit aligned so no need to use memalign.

Code: Select all

.øOº'ºOø.
'ºOo.oOº'
lego
Posts: 43
Joined: Fri Oct 17, 2008 1:09 am

Post by lego »

a_noob wrote:you can avoid the cache problem by using local GU memory (from the display list). sceGuGetMemory(int size); (works just like malloc) You dont need to free this memory or write it back. However it is invalid at the end of the frame. Also if you choose you use malloc. It is 16bit aligned so no need to use memalign.
sceGuGetMemory() don't work for me. With or without sceKernelDcacheWritebackInvalidateRage() it give me nothing...

My changed code part:

Code: Select all

  vv = &#40;Vertex_t*&#41;sceGuGetMemory&#40;3 * sizeof&#40;Vertex_t&#41;&#41;;
instead of old:

Code: Select all

  vv = &#40;Vertex_t*&#41;memalign&#40;16, 3 * sizeof&#40;Vertex_t&#41;&#41;;
lego
Posts: 43
Joined: Fri Oct 17, 2008 1:09 am

Post by lego »

psPea wrote:It's probably a cache issue,
try sceKernelDCacheWritebackInvaidateRange on the vertices.
Thanks!
It's work. sceKernelDCacheWritebackInvaidateRange(vv, 3 * sizeof(Vertex_t)) help me.

Could you help me to understand a cache work?
May i call this function after malloc() or i need to call it after i filled up an array with right data? How it works?

What a difference in work between this functions:
- sceKernelDcacheWritebackAll
- sceKernelDcacheWritebackInvalidateAll
- sceKernelDcacheWritebackRange
- sceKernelDcacheWritebackInvalidateRange
- sceKernelDcacheInvalidateRange

Where do I call it?
lego
Posts: 43
Joined: Fri Oct 17, 2008 1:09 am

Post by lego »

lego wrote: May i call this function after malloc() or i need to call it after i filled up an array with right data?
Before an array data is filled, sceKernelDcacheWritebackInvalidateRange() don't give a needed result :-). So, this question has droped off.
Insert_witty_name
Posts: 376
Joined: Wed May 10, 2006 11:31 pm

Post by Insert_witty_name »

For the cache problem, see the first paragraph here: http://wiki.ps2dev.org/psp:ge_faq

sceGuGetMemory() should work fine. I would address this issue instead of allocating vertex memory and clearing the cache.
a_noob
Posts: 97
Joined: Sun Sep 17, 2006 8:33 am
Location: _start: jr 0xDEADBEEF

Post by a_noob »

you need to call sceGuGetMemory within your GU render context between sceGuStart and sceGuFinish

Code: Select all

.øOº'ºOø.
'ºOo.oOº'
lego
Posts: 43
Joined: Fri Oct 17, 2008 1:09 am

Post by lego »

Insert_witty_name wrote:For the cache problem, see the first paragraph here: http://wiki.ps2dev.org/psp:ge_faq

sceGuGetMemory() should work fine. I would address this issue instead of allocating vertex memory and clearing the cache.
Many thanks.

Very useful link.
lego
Posts: 43
Joined: Fri Oct 17, 2008 1:09 am

Post by lego »

a_noob wrote:you need to call sceGuGetMemory within your GU render context between sceGuStart and sceGuFinish
Thank you for reply.
Now it works, but I have some strange result - http://forums.ps2dev.org/viewtopic.php?t=12480 .
Post Reply