forked from Ports/goldeneye-pc-port
D85: give the stage texture pool (ptr_texture_alloc_start) real storage
The decomp declares ptr_texture_alloc_start as `struct texpool *` but no code ever dereferences it as a pointer -- every use takes its address and treats the storage itself as a `struct texpool` (texInitPool writes all four members through &ptr_texture_alloc_start; texLoad / texFindInPool read them back). On N64 the four members are 4 bytes each (16 total) and overlap the following split-out symbols (ptr_texture_alloc_end etc.); the layout happens to work. On x86-64 `struct texpool` is 32 bytes (four widened pointers), so texInitPool smashes 24 bytes past the 8-byte pointer global and, worse, reads of ->leftpos / ->rightpos (offsets 16 and 24) come back as unrelated BSS -- the stage texture pool then looks permanently exhausted (texFreeBytesInBuffer() < 0) the very first time texLoad() runs on the -level_09 path. Every room texLoad bails at its out-of-memory guard without adding to the pool, texFindInPool() returns NULL for every room texnum, and gfx_pc aborts with 'Bad size for RGBA texture in tile 0: 00'. Fix: under PORT, define ptr_texture_alloc_start as a real `struct texpool` (not a pointer). All call sites already do `&ptr_texture_alloc_start`, so they now get a correctly-typed `struct texpool *` and the N64 build is untouched. Verified: -level_09 stage texture pool now fills normally (no premature OOM), ~630 room textures resolve, and the 'Bad size for RGBA texture' FATAL is gone. Rendering now advances to a separate issue -- gfx_sp_matrix dereferencing an unrelocated N64 segment address (0x90000000) from a room GDL gsSPMatrix, the next D85 layer. Also renamed the D85 texLoad pool-full probe (GE_D85TEX) from 'OOM' since with this fix it now only fires on a genuinely full pool.
This commit is contained in:
1 parent
419a50a677
commit
c18c8b8366
2 files changed
+27
No files matched your search
@@ -12,7 +12,22 @@
|
||||
|
||||
// bss
|
||||
//8008C720
|
||||
#ifdef PORT
|
||||
/* D85: the decomp declares this as `struct texpool *` (a 4-byte pointer on
|
||||
* N64), but every use takes its address and treats the storage AS a
|
||||
* `struct texpool` -- texInitPool(&ptr_texture_alloc_start, ...) writes all
|
||||
* four members through it, and texLoad/texFindInPool read them back. On N64
|
||||
* `struct texpool` is 16 bytes and this "pointer" global only reserves 4,
|
||||
* so it already relies on the linker leaving the next 12 bytes unused; on
|
||||
* x86-64 the struct is 32 bytes (four widened pointers) and the write
|
||||
* smashes 24 bytes of whatever BSS follows -- and reads of ->leftpos /
|
||||
* ->rightpos (offsets 16, 24) come back as garbage, which is why the stage
|
||||
* texture pool looks permanently exhausted (free < 0) on the -level_09
|
||||
* path. Give it real storage. */
|
||||
struct texpool ptr_texture_alloc_start;
|
||||
#else
|
||||
struct texpool *ptr_texture_alloc_start;
|
||||
#endif
|
||||
//8008C724
|
||||
s32 ptr_texture_alloc_end;
|
||||
//8008C728
|
||||
@@ -2448,6 +2463,13 @@ void texLoad(s32 *updateword, struct texpool *pool)
|
||||
// only other option is a crash. GBI commands contain texture IDs
|
||||
// instead of pointers, and they must be replaced with pointers.
|
||||
if ((!iszlib && (texFreeBytesInBuffer(pool) < 0x10CC)) || (iszlib && texFreeBytesInBuffer(pool) < 0xA28)) {
|
||||
#if defined(PORT)
|
||||
/* D85: env-gated -- a room rendering with placeholder textures
|
||||
* usually means the stage pool filled up here. */
|
||||
if (getenv("GE_D85TEX"))
|
||||
osSyncPrintf("D85TEX texLoad pool-full texnum=%d iszlib=%d free=%d\n",
|
||||
(int)g_TexNumToLoad, (int)iszlib, (int)texFreeBytesInBuffer(pool));
|
||||
#endif
|
||||
*updateword = osVirtualToPhysical(pool->start);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -95,7 +95,12 @@ struct texcacheitem {
|
||||
};
|
||||
|
||||
extern struct texcacheitem g_TexCacheItems[];
|
||||
#ifdef PORT
|
||||
/* D85: real storage, not a pointer -- see the definition in image.c. */
|
||||
extern struct texpool ptr_texture_alloc_start;
|
||||
#else
|
||||
extern struct texpool *ptr_texture_alloc_start;
|
||||
#endif
|
||||
extern struct image_entry g_Textures[];
|
||||
extern s32 g_TexCacheCount;
|
||||
extern u32 bytes;
|
||||
|
||||
Reference in new issue
Block a user