diff options
author | Max Horn | 2003-06-26 00:47:39 +0000 |
---|---|---|
committer | Max Horn | 2003-06-26 00:47:39 +0000 |
commit | 3c296b36b7a2cbf9bd049e65810f1d5c43fe6573 (patch) | |
tree | 7ff5ab22bd2e6476d14156040505738dbc80f309 /scumm/resource.cpp | |
parent | 7f3118f8d864f6d0beec385cb5776979581d6e2a (diff) | |
download | scummvm-rg350-3c296b36b7a2cbf9bd049e65810f1d5c43fe6573.tar.gz scummvm-rg350-3c296b36b7a2cbf9bd049e65810f1d5c43fe6573.tar.bz2 scummvm-rg350-3c296b36b7a2cbf9bd049e65810f1d5c43fe6573.zip |
added ResourceIterator, replacing two of the old findResource/findResourceSmall function - contraty to those, this approach is thread safe
svn-id: r8650
Diffstat (limited to 'scumm/resource.cpp')
-rw-r--r-- | scumm/resource.cpp | 114 |
1 files changed, 50 insertions, 64 deletions
diff --git a/scumm/resource.cpp b/scumm/resource.cpp index 8cd61c5166..3e3ed7b522 100644 --- a/scumm/resource.cpp +++ b/scumm/resource.cpp @@ -1349,9 +1349,9 @@ const byte *Scumm::findResourceData(uint32 tag, const byte *ptr) { if (_features & GF_OLD_BUNDLE) error("findResourceData must not be used in GF_OLD_BUNDLE games"); else if (_features & GF_SMALL_HEADER) - ptr = findResourceSmall(tag, ptr, 0); + ptr = findResourceSmall(tag, ptr); else - ptr = findResource(tag, ptr, 0); + ptr = findResource(tag, ptr); if (ptr == NULL) return NULL; @@ -1370,72 +1370,58 @@ int Scumm::getResourceDataSize(const byte *ptr) const { return READ_BE_UINT32(ptr - 4) - 8; } -struct FindResourceState { - uint32 size, pos; - const byte *ptr; -}; - -/* just O(N) complexity when iterating with this function */ -const byte *findResource(uint32 tag, const byte *searchin) { - uint32 size; - static FindResourceState frs; - FindResourceState *f = &frs; /* easier to make it thread safe like this */ - - if (searchin) { - f->size = READ_BE_UINT32(searchin + 4); - f->pos = 8; - f->ptr = searchin + 8; - goto StartScan; +ResourceIterator::ResourceIterator(const byte *searchin, bool smallHeader) + : _ptr(searchin), _smallHeader(smallHeader) { + assert(searchin); + if (_smallHeader) { + _size = READ_LE_UINT32(searchin); + _pos = 6; + _ptr = searchin + 6; + } else { + _size = READ_BE_UINT32(searchin + 4); + _pos = 8; + _ptr = searchin + 8; } - - do { - size = READ_BE_UINT32(f->ptr + 4); - if ((int32)size <= 0) - return NULL; - - f->pos += size; - f->ptr += size; - - StartScan: - if (f->pos >= f->size) - return NULL; - } while (READ_UINT32(f->ptr) != tag); - - return f->ptr; + } -const byte *findResourceSmall(uint32 tag, const byte *searchin) { - uint32 size; - static FindResourceState frs; - FindResourceState *f = &frs; /* easier to make it thread safe like this */ - uint16 smallTag; - - smallTag = newTag2Old(tag); - - if (searchin) { - f->size = READ_LE_UINT32(searchin); - f->pos = 6; - f->ptr = searchin + 6; - goto StartScan; +const byte *ResourceIterator::findNext(uint32 tag) { + uint32 size = 0; + const byte *result = 0; + + if (_smallHeader) { + uint16 smallTag = newTag2Old(tag); + do { + if (_pos >= _size) + return 0; + + result = _ptr; + size = READ_LE_UINT32(result); + if ((int32)size <= 0) + return 0; // Avoid endless loop + + _pos += size; + _ptr += size; + } while (READ_LE_UINT16(result + 4) != smallTag); + } else { + do { + if (_pos >= _size) + return 0; + + result = _ptr; + size = READ_BE_UINT32(result + 4); + if ((int32)size <= 0) + return 0; // Avoid endless loop + + _pos += size; + _ptr += size; + } while (READ_UINT32(result) != tag); } - do { - size = READ_LE_UINT32(f->ptr); - if ((int32)size <= 0) - return NULL; - - f->pos += size; - f->ptr += size; - - StartScan: - if (f->pos >= f->size) - return NULL; - } while (READ_LE_UINT16(f->ptr + 4) != smallTag); - - return f->ptr; + return result; } -const byte *findResource(uint32 tag, const byte *searchin, int idx) { +const byte *findResource(uint32 tag, const byte *searchin) { uint32 curpos, totalsize, size; assert(searchin); @@ -1446,7 +1432,7 @@ const byte *findResource(uint32 tag, const byte *searchin, int idx) { searchin += 4; while (curpos < totalsize) { - if (READ_UINT32(searchin) == tag && !idx--) + if (READ_UINT32(searchin) == tag) return searchin; size = READ_BE_UINT32(searchin + 4); @@ -1463,7 +1449,7 @@ const byte *findResource(uint32 tag, const byte *searchin, int idx) { return NULL; } -const byte *findResourceSmall(uint32 tag, const byte *searchin, int idx) { +const byte *findResourceSmall(uint32 tag, const byte *searchin) { uint32 curpos, totalsize, size; uint16 smallTag; @@ -1478,7 +1464,7 @@ const byte *findResourceSmall(uint32 tag, const byte *searchin, int idx) { while (curpos < totalsize) { size = READ_LE_UINT32(searchin); - if (READ_LE_UINT16(searchin + 4) == smallTag && !idx--) + if (READ_LE_UINT16(searchin + 4) == smallTag) return searchin; if ((int32)size <= 0) { |