changeset 128:776eca0daa02

texture load use hash table
author gongo@charles.cr.ie.u-ryukyu.ac.jp
date Tue, 25 Nov 2008 15:52:28 +0900
parents 9ff71404cff2
children b9b3fb1f0d03
files TaskManager/Test/test_render/Makefile.def TaskManager/Test/test_render/spe/DrawSpan.cpp TaskManager/Test/test_render/spe/DrawSpan.h TaskManager/Test/test_render/spe/Load_Texture.cpp TaskManager/Test/test_render/task/create_sgp.cpp TaskManager/Test/test_render/task/update_sgp.cpp TaskManager/Test/test_render/viewer.cpp TaskManager/Test/test_render/viewer_types.h
diffstat 8 files changed, 142 insertions(+), 53 deletions(-) [+]
line wrap: on
line diff
--- a/TaskManager/Test/test_render/Makefile.def	Tue Nov 25 12:22:03 2008 +0900
+++ b/TaskManager/Test/test_render/Makefile.def	Tue Nov 25 15:52:28 2008 +0900
@@ -3,10 +3,10 @@
 # include/library path
 # ex: macosx
 #CERIUM = /Users/gongo/Source/Concurrency/Game_project/Cerium
-CERIUM = /Users/gongo/Source/hg/Cerium
+#CERIUM = /Users/gongo/Source/hg/Cerium
 
 # ex: linux/ps3
-#CERIUM = /home/gongo/Cerium
+CERIUM = /home/gongo/Cerium
 
 #CERIUM = ../../..
 
--- a/TaskManager/Test/test_render/spe/DrawSpan.cpp	Tue Nov 25 12:22:03 2008 +0900
+++ b/TaskManager/Test/test_render/spe/DrawSpan.cpp	Tue Nov 25 15:52:28 2008 +0900
@@ -11,7 +11,64 @@
 
 SchedDefineTask(DrawSpan);
 
-unsigned char *tex;
+static const int hashsize = 263;
+
+static TilePtr hash_table[hashsize] = {NULL};
+
+unsigned short PRIME[8] = {
+    0x002, 0x065, 0x0c7, 0x133, 0x191, 0x1f3, 0x259, 0x2bd,
+};
+
+static TileListPtr tileList;
+
+static int
+hash(uint32 data)
+{
+    int value = 0;
+    int n = 0;
+    int key;
+
+    for (int i = 0; i < 8; i ++) {
+	key = data & 0xf;
+	value += key * PRIME[n++];
+	data >>= 4;
+    }
+
+    return value % hashsize;
+}
+
+static int
+put(void *key, TilePtr data)
+{
+    int hashval = hash((uint32)key);
+
+    for (int i = 0; i < hashsize/2; i++) {
+	int index = (hashval + i*i)%hashsize;
+
+	if (hash_table[index] == 0) {
+	    hash_table[index] = data;
+	    return index;
+	}
+    }
+
+    return -1;
+}
+
+static TilePtr
+get(void *key)
+{
+    int hashval = hash((uint32)key);
+
+    for (int i = 0; i < hashsize/2; i++) {
+	int index = (hashval + i*i)%hashsize;
+	
+	if (hash_table[index]->texture_addr == key) {
+	    return hash_table[index];
+	}
+    }
+
+    return NULL;
+}
 
 void
 DrawSpan::linebuf_init(int *buf, int x, int rgb)
@@ -54,25 +111,44 @@
     Uint8 red, green, blue, alpha;
 
     if (tx<0) tx = 0;
-    if (128-1< tx) tx = 128-1 ;
+    if (tex_width-1< tx) tx = tex_width-1 ;
     if (ty<0) ty = 0;
-    if (128-1< ty) ty = 128-1 ;
+    if (tex_height-1< ty) ty = tex_height-1 ;
 
-#if 0
-    char *p = get_pixel(tx,ty,texture);
-#else
     void *texture_addr;
 
     int blockX = tx / 8;
     int blockY = ty / 8;
     void** addrList = (void**)global_get(TEXTURE2_ID);
-    
-    texture_addr = addrList[blockX + 16*blockY];
-    smanager->dma_load(tex, (uint32)texture_addr, sizeof(uint32)*64, TEX_LOAD);
-    smanager->dma_wait(TEX_LOAD);
+    TilePtr tile;
+
+    texture_addr = addrList[blockX + (tex_width/8)*blockY];
+
+    tile = get(texture_addr);
+    if (tile == NULL) {
+	if (tileList->size >= MAX_TILE) {
+	    tileList->init();
+	    bzero(hash_table, sizeof(TilePtr)*hashsize);
+	}
+
+	tile = &tileList->tile[tileList->size];
+	tile->texture_addr = texture_addr;
 
-    char *p = get_pixel(tx%8, ty%8, tex);
-#endif
+	smanager->dma_load(tile->pixel, (uint32)texture_addr,
+			   sizeof(uint32)*64, TEX_LOAD);
+
+	int index = put(tile->texture_addr, tile);
+	if (index < 0) {
+	    printf("[%p] Can't entry\n", tile);
+	    return 0xff0000;
+	}
+
+	tileList->size++;
+
+	smanager->dma_wait(TEX_LOAD);
+    }
+
+    char *p = get_pixel(tx%8, ty%8, tile);
     
     alpha = 255;
     red   = (Uint8) p[0];
@@ -93,6 +169,9 @@
     SpanPack *tmp_sp = NULL;
     Span *span;
 
+    tileList = (TileListPtr)smanager->allocate(sizeof(TileList));
+    tileList->init();
+
     int render_y = sp->info.y_top;
     void *texture_image = global_get(TEXTURE_ID);
 
@@ -105,14 +184,13 @@
 
     int **linebuf = (int**)smanager->allocate(sizeof(int*)*rangey);
 
-    tex = (unsigned char*)smanager->allocate(sizeof(unsigned char)*64*4);
-
     for (int i = 0; i < rangey; i++) {
 	linebuf[i] = (int*)smanager->get_output(i);
-	//linebuf_init(linebuf[i], rangex, 0x00ff00ff);
 	linebuf_init(linebuf[i], rangex, 0);
     }
 
+    bzero(hash_table, sizeof(TilePtr)*hashsize);
+
     do {
 	/**
 	 * SpanPack->next が存在する場合、
@@ -196,7 +274,7 @@
     free(free_sp);
     free(linebuf);
     free(zRow);
-    free(tex);
+    free(tileList);
 
     return 0;
 }
--- a/TaskManager/Test/test_render/spe/DrawSpan.h	Tue Nov 25 12:22:03 2008 +0900
+++ b/TaskManager/Test/test_render/spe/DrawSpan.h	Tue Nov 25 15:52:28 2008 +0900
@@ -13,6 +13,24 @@
 typedef uint32_t        Uint32;
 typedef unsigned short  GLushort;
 
+typedef struct {
+    uint32 pixel[64]; // 8*8
+    void *texture_addr;
+    int pad[3];
+} Tile, *TilePtr;
+
+#define MAX_TILE 100
+
+typedef struct {
+    int size;
+    int pad[3];
+    Tile tile[MAX_TILE];
+
+    void init(void) {
+	size = 0;
+    }
+} TileList, *TileListPtr;
+
 class DrawSpan : public SchedTask {
 public:
     SchedConstructor(DrawSpan);
--- a/TaskManager/Test/test_render/spe/Load_Texture.cpp	Tue Nov 25 12:22:03 2008 +0900
+++ b/TaskManager/Test/test_render/spe/Load_Texture.cpp	Tue Nov 25 15:52:28 2008 +0900
@@ -21,26 +21,12 @@
 int 
 LoadTexture::run(void *rbuf , void *wbuf) 
 {
-    int addr = smanager->get_param(0);
-    int addrNum = smanager->get_param(1);
+    int addrNum = smanager->get_param(0);
+    int addrSize = addrNum*sizeof(void*);
+    void **list = (void**)global_alloc(TEXTURE2_ID, addrSize);
 
     void **addrList = (void**)smanager->get_input(0);
-    void **list = (void**)global_alloc(TEXTURE2_ID, addrNum*sizeof(void*));
-
-    memcpy(list, addrList, addrNum*sizeof(void*));
-
-#if 0    
-    //帥鴻帥鴻
-    TaskPtr task = create_task(TASK_SET_TEXTURE);
-     
-    // 16kbyte ャらc
-    task->add_inData(addr, MAX_LOAD_SIZE);
-    task->add_inData(addr + MAX_LOAD_SIZE, MAX_LOAD_SIZE);
-    task->add_inData(addr + MAX_LOAD_SIZE*2, MAX_LOAD_SIZE);
-    task->add_inData(addr + MAX_LOAD_SIZE*3, MAX_LOAD_SIZE);
-    
-    wait_task(task);
-#endif
+    memcpy(list, addrList, addrSize);
 
     return 0;
 }
--- a/TaskManager/Test/test_render/task/create_sgp.cpp	Tue Nov 25 12:22:03 2008 +0900
+++ b/TaskManager/Test/test_render/task/create_sgp.cpp	Tue Nov 25 15:52:28 2008 +0900
@@ -102,16 +102,13 @@
 	if (t->children != NULL) {
 	    nnpn = curNumber;
 	    t = t->children;
-	    printf("children\n");
 	} else if (t->brother != NULL) {
 	    nnpn = node->pn;
 	    t = t->brother;
-	    printf("brother\n");
 	} else {
 	    while (t) {
 		if (t->brother != NULL) {
 		    t = t->brother;
-		    printf("brother2\n");
 		    break;
 		} else {
 		    if (t->parent == NULL) {
--- a/TaskManager/Test/test_render/task/update_sgp.cpp	Tue Nov 25 12:22:03 2008 +0900
+++ b/TaskManager/Test/test_render/task/update_sgp.cpp	Tue Nov 25 15:52:28 2008 +0900
@@ -46,6 +46,13 @@
 }
 
 static void
+no_move(SceneGraphNodePtr node, int w, int h)
+{
+    node->obj_pos[0] = w/2 - 200;
+    node->obj_pos[1] = h/2 - 100;
+}
+
+static void
 move1(SceneGraphNodePtr node, int w, int h)
 {
     node->angle[1] += 1.0f;
@@ -98,7 +105,8 @@
 static void
 init(void)
 {
-    moveList[0] = move0;
+    moveList[0] = no_move;
+    //moveList[0] = move0;
     moveList[1] = move3;
     moveList[2] = move2;
 
--- a/TaskManager/Test/test_render/viewer.cpp	Tue Nov 25 12:22:03 2008 +0900
+++ b/TaskManager/Test/test_render/viewer.cpp	Tue Nov 25 15:52:28 2008 +0900
@@ -121,24 +121,26 @@
     task_next->wait_for(task_sgp);
     task_sgp->spawn();
 
-    __texture = (void*)manager->malloc(128*128*4);
-    memcpy(__texture, polygon->texture_image->pixels, 128*128*4);
+    int tex_blocksize = tex_width*tex_height*4;
 
+    __texture = (void*)manager->malloc(tex_blocksize);
+    memcpy(__texture, polygon->texture_image->pixels, tex_blocksize);
 
     uint32 *tex_src = (uint32*)polygon->texture_image->pixels;
-    uint32 *tex_dest = (uint32*)manager->malloc(sizeof(uint32)*128*128);
+    uint32 *tex_dest = (uint32*)manager->malloc(tex_blocksize);
     int tile_size = TEXTURE_SPLIT_PIXEL*TEXTURE_SPLIT_PIXEL;
-    int tile_num = 128*128/tile_size;
+    int tile_num = tex_width*tex_height/tile_size;
+    tile_num = (tile_num + 15)&(~15);
     void **tex_addrList = (void**)manager->malloc(sizeof(void*)*tile_num);
 
     {
 	int t = 0;
 
-	for (int y = 0; y < 128; y += TEXTURE_SPLIT_PIXEL) {
-	    for (int x = 0; x < 128; x += TEXTURE_SPLIT_PIXEL) {
+	for (int y = 0; y < tex_height; y += TEXTURE_SPLIT_PIXEL) {
+	    for (int x = 0; x < tex_width; x += TEXTURE_SPLIT_PIXEL) {
 		for (int j = 0; j < TEXTURE_SPLIT_PIXEL; j++) {
 		    for (int i = 0; i < TEXTURE_SPLIT_PIXEL; i++) {
-			tex_dest[t++] = tex_src[(x+i) + 128*(y+j)];
+			tex_dest[t++] = tex_src[(x+i) + tex_width*(y+j)];
 		    }
 		}
 	    }
@@ -146,7 +148,7 @@
 
 	t = 0;
 
-	for (int i = 0, t = 0; i < 128*128; i += tile_size, t++) {
+	for (int i = 0, t = 0; i < tex_width*tex_height; i += tile_size, t++) {
 	    tex_addrList[t] = (void*)&tex_dest[i];
 	}
     }
@@ -154,7 +156,6 @@
     for (int i = 0; i < spe_num; i++) {
 	task_init_tex = manager->create_task(TASK_INIT_TEXTURE);
 	task_init_tex->add_inData(tex_addrList, sizeof(void*)*tile_num);
-	task_init_tex->add_param((int)__texture);
 	task_init_tex->add_param(tile_num);
 	task_init_tex->set_cpu(SPE_ANY);
 	task_next->wait_for(task_init_tex);
@@ -285,15 +286,13 @@
 		// Draw Background (憜紂ゃ吟)
 		//break;
 		task_draw = manager->create_task(TASK_DRAW_BACK);
-		task_draw->add_param(0x00ffcc55);
-		//task_draw->add_param(0);
+		task_draw->add_param(0);
 		//task_draw->add_param(st_rgb);
 	    }
 
 	    for (int k = 0; k < rangey; k++) {
-		int hoge = (k > rangey-3) ? 0 : 0;
 		task_draw->add_outData(
-		    &pixels[(startx-1)+this->width*(k+start_y-1)+hoge],
+		    &pixels[(startx-1)+this->width*(k+start_y-1)],
 		    (endx - startx + 1)*sizeof(int));
 	    }
 
--- a/TaskManager/Test/test_render/viewer_types.h	Tue Nov 25 12:22:03 2008 +0900
+++ b/TaskManager/Test/test_render/viewer_types.h	Tue Nov 25 15:52:28 2008 +0900
@@ -5,6 +5,9 @@
 #define MAX_WIDTH  1920
 #define MAX_HEIGHT 1080
 
+const int tex_width = 576;
+const int tex_height = 384;
+
 // texture は 8x8 に分割
 // この値は、SpanPack にも使う
 #define TEXTURE_SPLIT_PIXEL 8