[Bf-blender-cvs] SVN commit: /data/svn/bf-blender [11149] branches/soc-2007-joeedh/source/ blender: This commit adds a generic tile cache implementation to

Joseph Eagar joeedh at gmail.com
Tue Jul 3 09:07:49 CEST 2007


Revision: 11149
          http://projects.blender.org/plugins/scmsvn/viewcvs.php?view=rev&root=bf-blender&revision=11149
Author:   joeedh
Date:     2007-07-03 09:07:49 +0200 (Tue, 03 Jul 2007)

Log Message:
-----------
This commit adds a generic tile cache implementation to
blender, with DSM support.

Note that the tile size is fixed, and also that I still
need to work on making DSM maps less memory hungry
in general.

The tiling system works by first writing tiles to
compressed (with zlib level 2 currently I think)
memory files, then writing the compressed tiles
to disk as needed.

More info forthcoming when I'm not so tired.

Modified Paths:
--------------
    branches/soc-2007-joeedh/source/blender/blenkernel/BKE_tile.h
    branches/soc-2007-joeedh/source/blender/blenkernel/intern/tcs_cache.c
    branches/soc-2007-joeedh/source/blender/blenkernel/intern/tcs_dsm.c
    branches/soc-2007-joeedh/source/blender/blenkernel/intern/tcs_file.c
    branches/soc-2007-joeedh/source/blender/blenlib/BLI_memarena.h
    branches/soc-2007-joeedh/source/blender/blenlib/intern/BLI_memarena.c
    branches/soc-2007-joeedh/source/blender/render/intern/source/convertblender.c
    branches/soc-2007-joeedh/source/blender/render/intern/source/shadbuf.c
    branches/soc-2007-joeedh/source/blender/render/intern/source/zbuf.c

Added Paths:
-----------
    branches/soc-2007-joeedh/source/blender/blenkernel/BKE_dsm.h

Added: branches/soc-2007-joeedh/source/blender/blenkernel/BKE_dsm.h
===================================================================
--- branches/soc-2007-joeedh/source/blender/blenkernel/BKE_dsm.h	                        (rev 0)
+++ branches/soc-2007-joeedh/source/blender/blenkernel/BKE_dsm.h	2007-07-03 07:07:49 UTC (rev 11149)
@@ -0,0 +1,71 @@
+#ifndef BKE_DSM_H
+#define BKE_DSM_H
+
+#include "BKE_tile.h"
+
+struct MemArena;
+
+typedef struct DSMSample {
+	float clr[4];
+	int depth;
+} DSMSample;
+
+/*Each tile has its own memarena to work better with caching.*/
+typedef struct DSMTile {
+	TCS_Tile tile;
+
+	/*the first element of the arrays pointed to by
+	  depth_rect is the length of the pixel depth
+	  array, and is 1/4th the size of the pixel color array (since it
+	  stores rgba colors of course)
+
+	  at the moment alpha is stored as 0 == shadow, 1 == no shadow, due
+	  to how I've managed to paint myself into a corner where that is
+	  concerned (I originally wanted 0=shadow, 1=no shadow like alpha
+	  in materials work).
+	  */
+	//float **color_rect; /* includes alpha */
+	//unsigned int **depth_rect;
+	
+	DSMSample **sample_rect; /*first entry's depth is the length of the pixel arra*/
+	
+	/*tile coordinates inside poly_rect.
+	  Note: this is *not* in image space units!
+	  Multiple by the parent buffer's tsizex/y
+	  to get the tile position in image space.*/
+	int x, y;
+	int sizex, sizey;
+	struct MemArena *arena;
+} DSMTile;
+
+typedef struct DSMBuffer {
+	TCS_TileBuffer buffer;
+
+	DSMTile *poly_rect;
+	int sizex, sizey;
+	int tilex, tiley; /*total number of tiles in x and y dimensions.*/
+
+	/*tile dimensions, isn't necassarily true for 100% of the tiles.
+	 this is because the image might not be divisible into equally sized tiles of
+	 a user-definable size.*/
+	int tsizex, tsizey;
+	int max_depth; /*the maximum number of samples in a single pixel*/
+} DSMBuffer;
+
+/*private*/
+/*ok, this was meant for using TCS_MakeBuffer, but that's kindof a bad idea really so
+  instead the dsm creation function uses TCS_InitBuffer*/
+typedef struct DSMParams {
+	void *re, *buf;
+} DSMParams;
+
+void _DSM_maketile(TCS_TileBuffer *self, TCS_TilePool *pool, TCS_Tile *vtile);
+void DSM_MakeTilePool(int maxbytes);
+void DSM_FreeTilePool(void);
+void DSM_FreeBuffer(DSMBuffer *dbuf);
+
+struct Render;
+struct ShadBuf;
+void DSM_CreateBuffer(struct Render *re, struct ShadBuf *buf, int tilesize);
+
+#endif /* BKE_DSM_H */

Modified: branches/soc-2007-joeedh/source/blender/blenkernel/BKE_tile.h
===================================================================
--- branches/soc-2007-joeedh/source/blender/blenkernel/BKE_tile.h	2007-07-03 06:48:48 UTC (rev 11148)
+++ branches/soc-2007-joeedh/source/blender/blenkernel/BKE_tile.h	2007-07-03 07:07:49 UTC (rev 11149)
@@ -96,10 +96,14 @@
 	unsigned int (*getTileMem)(struct TCS_Tile *self);
 	void *(*getTilePixel)(struct TCS_Tile *self, int x, int y, int z);
 	
-	int is_cached; /*is 1 if either (or both) is_compressed or is_written is 1.*/
+	/*length of uncompressed tile in memory.
+	  mem_used is length of part of tile that gets saved/compressed,
+	  struct_overhead is length of the part of the tile that isn't
+	  saved/compressed.*/
+	int mem_used, struct_overhead; 
 	
 	/*-privae variables, do not touch!-*/
-	int is_compressed, is_written, mem_used;
+	int is_compressed, is_written;
 	TCS_File *file, *compressed_memfile;
 	
 	/*filepos is the cached tile position.  this must *never* be messed up!*/
@@ -145,7 +149,7 @@
 	int (*getTileSizeY)(struct TCS_TileBuffer *self);
 	int (*getSizeX)(struct TCS_TileBuffer *self);
 	int (*getSizeY)(struct TCS_TileBuffer *self);
-	unsigned int flags;
+	unsigned int flag;
 	
 	/*should be set by TCS_MakePool, not the newBuffer function*/
 	TCS_TilePool *pool;
@@ -180,6 +184,10 @@
 /*as may dimensions can be used as needed, others can just be passed in as 0.*/
 void *TCS_GetTile(void *buf, int x, int y, int z);
 
+/*This function frees generic data associated with a tile, removes it from its pool, etc,
+  but it doesn't actually free the client tile data itself.*/
+void TCS_FreeTile(void *vtile);
+
 /*hrm, not sure if this next one will be needed, its possible it can
   all be done from within TCS_GetTile(), perhaps even progressively*/
 void TCS_RunCacher(TCS_TilePool *pool);

Modified: branches/soc-2007-joeedh/source/blender/blenkernel/intern/tcs_cache.c
===================================================================
--- branches/soc-2007-joeedh/source/blender/blenkernel/intern/tcs_cache.c	2007-07-03 06:48:48 UTC (rev 11148)
+++ branches/soc-2007-joeedh/source/blender/blenkernel/intern/tcs_cache.c	2007-07-03 07:07:49 UTC (rev 11149)
@@ -52,7 +52,7 @@
 	pool->maxmem = max_mem_bytes;
 	
 	/*this is to group cache runs so they process no less then 5 megs at a time.*/
-	pool->grace_period = 1024*1024*5; 
+	pool->grace_period = 1024*1024*8; 
 	
 	return pool;
 }
@@ -69,6 +69,19 @@
 	MEM_freeN(pool);
 }
 
+void TCS_FreeTile(void *vtile)
+{
+	TCS_Tile *tile = vtile;
+	
+	if (tile->is_compressed) {
+		if (!tile->is_written) {
+			if (tile->pool) BLI_remlink(&tile->pool->compressed_tiles, tile);
+		}
+	} else if (tile->pool) BLI_remlink(&tile->pool->compressed_tiles, tile);
+
+	if (tile->compressed_memfile) TCS_fclose(tile->compressed_memfile);
+}
+
 void TCS_InitBuffer(TCS_TileBuffer *type, void *buffer)
 {
 	memcpy(buffer, type, sizeof(TCS_TileBuffer));
@@ -118,7 +131,7 @@
 //static int TCS_deflate(TCS_File *source, TCS_File *dest, int level);
 //static int TCS_inflate(TCS_File *source, TCS_File *dest, int len);
 
-//#define USECOMPRESSION
+#define USECOMPRESSION
 
 static void TCS_CompressMemFile(TCS_File *file)
 {
@@ -207,7 +220,6 @@
 				TCS_fseek(tile->file, tile->filepos+1, SEEK_SET);
 				TCS_fread(s, 4, 1, tile->file);
 
-				memcpy(s, &len, 4);
 				printf("id: %s \n", s);
 			}
 			
@@ -235,14 +247,21 @@
 			tile->loadFromCache(tile, file);
 			#endif
 			
+			pool->memused += tile->mem_used;
 			//tile->loadFromCache(tile, file);
 			BASSERT(tile->compressed_memfile == NULL);
 		} else {
 			printf("loading a compressed memory tile\n");
+			pool->memused -= tile->compressed_memfile->length;			
+			pool->memused += tile->mem_used;
 			
 			TCS_fseek(file, 0, SEEK_SET);
 			TCS_DecompressMemFile(file, tile->len);
 			tile->loadFromCache(tile, file);
+
+			BLI_remlink(&pool->compressed_tiles, tile);
+			TCS_fclose(tile->compressed_memfile);
+			tile->compressed_memfile = NULL;
 		}
 		
 		if (file->error_occured) {
@@ -252,21 +271,9 @@
 			return NULL;
 		}
 		
-		/*if the tile was only compressed, free the memory file it was using*/
-		if (tile->is_compressed && !tile->is_written) {
-			pool->memused -= tile->compressed_memfile->length;
-			
-			BLI_remlink(&pool->compressed_tiles, tile);
-			TCS_fclose(tile->compressed_memfile);
-			tile->compressed_memfile = NULL;
-		}
-
 		tile->is_written = 0;
 		tile->is_compressed = 0;
 		
-		if (tile->len==0) tile->len = tile->getTileMem(tile);
-		
-		pool->memused += tile->len;
 		BLI_addhead(&pool->tiles, tile);
 	}
 		
@@ -321,18 +328,28 @@
 void TCS_RunCacher(TCS_TilePool *pool)
 {
 	TCS_Tile *tile, *prev;
-	unsigned long mem, i=0;
+	unsigned long mem, memconfirm, i=0;
 	
 	BASSERT(pool);
 	if (!pool) return;
 	
-	mem = pool->memused;
 	printf("running memcacher!\n");
 	
 	if (pool->memused <= pool->maxmem) return;
 	
+	mem = pool->memused;
 	for (tile=pool->tiles.first; tile; tile=tile->next) i++;
 	
+	memconfirm = 0;
+	for (tile=pool->tiles.first; tile; tile=tile->next) {
+		memconfirm += tile->mem_used + tile->struct_overhead;
+	}
+	for (tile=pool->compressed_tiles.first; tile; tile=tile->next) {
+		memconfirm += tile->compressed_memfile->length + tile->struct_overhead;
+	}
+	
+	printf("memused: %lud, memconfirm (should be a bit smaller): %lud", pool->memused, memconfirm);
+	
 	/*first mark tiles to be cached.*/
 	for (tile=pool->tiles.last; tile; i--, tile=tile->prev) {
 		if (tile->prev == pool->tiles.first) {
@@ -342,7 +359,7 @@
 		}
 
 		if (tile->len == 0) tile->len = tile->getTileMem(tile);
-		mem -= tile->len;
+		mem -= tile->mem_used;
 
 		printf("marking a tile!\n");
 		tile->is_compressed = 1;
@@ -361,17 +378,26 @@
 			
 			printf("compressing a tile\n");
 			tile->saveToCache(tile, tile->compressed_memfile, 0);
-			
+			{
+				char s[5];
+				s[4] = 0;
+				//memcpy(s, tile->compressed_memfile->ptr, 4);
+				s[0] = ((char*)tile->compressed_memfile->ptr)[0];
+				s[1] = ((char*)tile->compressed_memfile->ptr)[1];
+				s[2] = ((char*)tile->compressed_memfile->ptr)[2];
+				s[3] = ((char*)tile->compressed_memfile->ptr)[3];
+				printf("----immediate id: %s----\n", s);
+			}
 			/*paranoia check*/
 			BASSERT(tile->len == tile->compressed_memfile->length);
 			if (tile->len != tile->compressed_memfile->length) printf("bleh %d %d\n", (int)tile->len, (int)tile->compressed_memfile->length);
 			//tile->len = tile->compressed_memfile->length;
 			
 			TCS_CompressMemFile(tile->compressed_memfile);
-			BASSERT(tile->compressed_memfile->length != tile->len);
+			//BASSERT(tile->compressed_memfile->length != tile->len);
 			printf("compressed tile length: %lud, uncompressed length: %d\n", tile->compressed_memfile->length, tile->len);
 	
-			pool->memused -= tile->len;
+			pool->memused -= tile->mem_used;
 			pool->memused += tile->compressed_memfile->length;
 			
 			BLI_remlink(&pool->tiles, tile);
@@ -383,13 +409,17 @@
 	for (tile=pool->compressed_tiles.last; tile; tile=prev) {
 		prev = tile->prev;
 
-		seek_to_tile_pos(tile, pool);
-		BASSERT(tile->file);
-		if (!tile->file) break;
+		printf("caching a tile to disk\n");
 		
-		printf("writing a tile to disk\n");
-		TCS_fwrite(&tile->compressed_memfile->length, sizeof(unsigned long), 1, tile->file);
-		TCS_fwrite(tile->compressed_memfile->ptr, tile->compressed_memfile->length, 1, tile->file);
+		if (tile->file == NULL || (tile->buffer->flag & TCS_READONLY)==0) {
+			seek_to_tile_pos(tile, pool);
+			BASSERT(tile->file);
+			if (!tile->file) break;
+
+			TCS_fwrite(&tile->compressed_memfile->length, sizeof(unsigned long), 1, tile->file);
+			TCS_fwrite(tile->compressed_memfile->ptr, tile->compressed_memfile->length, 1, tile->file);
+			TCS_fflush(tile->file);
+		}
 		
 		/*error occured, load the tile back from the memfile.
 		  NOTE: Remember to account for compression for this
@@ -415,8 +445,8 @@
 			break;
 		}
 		
-		TCS_fflush(tile->file);
-		if (mem > tile->compressed_memfile->length) mem -= tile->compressed_memfile->length;

@@ Diff output truncated at 10240 characters. @@




More information about the Bf-blender-cvs mailing list