From 30218a2c324bc67f724100051ab9884a351928fb Mon Sep 17 00:00:00 2001 From: Max Horn Date: Mon, 28 Jun 2010 11:22:20 +0000 Subject: SCI: Make Script member vars private; add const qualifiers Only three Script members remain public (for now) svn-id: r50428 --- engines/sci/console.cpp | 10 +++---- engines/sci/engine/features.cpp | 10 +++---- engines/sci/engine/kernel.cpp | 2 +- engines/sci/engine/savegame.cpp | 4 +-- engines/sci/engine/script.cpp | 33 ++++++++++++----------- engines/sci/engine/script.h | 54 ++++++++++++++++++++------------------ engines/sci/engine/scriptdebug.cpp | 6 ++--- engines/sci/engine/seg_manager.cpp | 24 +++++++---------- engines/sci/engine/vm.cpp | 6 ++--- engines/sci/engine/vm.h | 2 +- 10 files changed, 76 insertions(+), 75 deletions(-) diff --git a/engines/sci/console.cpp b/engines/sci/console.cpp index 611d1481ad..f682e0e524 100644 --- a/engines/sci/console.cpp +++ b/engines/sci/console.cpp @@ -1381,7 +1381,7 @@ bool Console::cmdPrintSegmentTable(int argc, const char **argv) { switch (mobj->getType()) { case SEG_TYPE_SCRIPT: - DebugPrintf("S script.%03d l:%d ", (*(Script *)mobj)._nr, (*(Script *)mobj).getLockers()); + DebugPrintf("S script.%03d l:%d ", (*(Script *)mobj).getScriptNumber(), (*(Script *)mobj).getLockers()); break; case SEG_TYPE_CLONES: @@ -1455,9 +1455,9 @@ bool Console::segmentInfo(int nr) { case SEG_TYPE_SCRIPT: { Script *scr = (Script *)mobj; - DebugPrintf("script.%03d locked by %d, bufsize=%d (%x)\n", scr->_nr, scr->getLockers(), (uint)scr->getBufSize(), (uint)scr->getBufSize()); + DebugPrintf("script.%03d locked by %d, bufsize=%d (%x)\n", scr->getScriptNumber(), scr->getLockers(), (uint)scr->getBufSize(), (uint)scr->getBufSize()); if (scr->getExportTable()) - DebugPrintf(" Exports: %4d at %d\n", scr->getExportsNr(), (int)(((const byte *)scr->getExportTable()) - ((const byte *)scr->_buf))); + DebugPrintf(" Exports: %4d at %d\n", scr->getExportsNr(), (int)(((const byte *)scr->getExportTable()) - ((const byte *)scr->getBuf()))); else DebugPrintf(" Exports: none\n"); @@ -2377,7 +2377,7 @@ bool Console::cmdBacktrace(int argc, const char **argv) { DebugPrintf(" argp:ST:%04x", (unsigned)(call.variables_argp - _engine->_gamestate->stack_base)); if (call.type == EXEC_STACK_TYPE_CALL) - DebugPrintf(" script: %d", (*(Script *)_engine->_gamestate->_segMan->_heap[call.addr.pc.segment])._nr); + DebugPrintf(" script: %d", (*(Script *)_engine->_gamestate->_segMan->_heap[call.addr.pc.segment]).getScriptNumber()); DebugPrintf("\n"); } @@ -3351,7 +3351,7 @@ int Console::printObject(reg_t pos) { DebugPrintf(" [%03x] %s = %04x:%04x\n", obj->getFuncSelector(i), _engine->getKernel()->getSelectorName(obj->getFuncSelector(i)).c_str(), PRINT_REG(fptr)); } if (s->_segMan->_heap[pos.segment]->getType() == SEG_TYPE_SCRIPT) - DebugPrintf("\nOwner script: %d\n", s->_segMan->getScript(pos.segment)->_nr); + DebugPrintf("\nOwner script: %d\n", s->_segMan->getScript(pos.segment)->getScriptNumber()); return 0; } diff --git a/engines/sci/engine/features.cpp b/engines/sci/engine/features.cpp index 75f271f3ad..2ad494b37f 100644 --- a/engines/sci/engine/features.cpp +++ b/engines/sci/engine/features.cpp @@ -84,7 +84,7 @@ bool GameFeatures::autoDetectSoundType() { int16 opparams[4]; byte extOpcode; byte opcode; - offset += readPMachineInstruction(script->_buf + offset, extOpcode, opparams); + offset += readPMachineInstruction(script->getBuf(offset), extOpcode, opparams); opcode = extOpcode >> 1; // Check for end of script @@ -220,7 +220,7 @@ bool GameFeatures::autoDetectLofsType(int methodNum) { int16 opparams[4]; byte extOpcode; byte opcode; - offset += readPMachineInstruction(script->_buf + offset, extOpcode, opparams); + offset += readPMachineInstruction(script->getBuf(offset), extOpcode, opparams); opcode = extOpcode >> 1; // Check for end of script @@ -306,7 +306,7 @@ bool GameFeatures::autoDetectGfxFunctionsType(int methodNum) { int16 opparams[4]; byte extOpcode; byte opcode; - offset += readPMachineInstruction(script->_buf + offset, extOpcode, opparams); + offset += readPMachineInstruction(script->getBuf(offset), extOpcode, opparams); opcode = extOpcode >> 1; // Check for end of script @@ -409,7 +409,7 @@ bool GameFeatures::autoDetectSci21KernelType() { int16 opparams[4]; byte extOpcode; byte opcode; - offset += readPMachineInstruction(script->_buf + offset, extOpcode, opparams); + offset += readPMachineInstruction(script->getBuf(offset), extOpcode, opparams); opcode = extOpcode >> 1; // Check for end of script @@ -462,7 +462,7 @@ bool GameFeatures::autoDetectMoveCountType() { int16 opparams[4]; byte extOpcode; byte opcode; - offset += readPMachineInstruction(script->_buf + offset, extOpcode, opparams); + offset += readPMachineInstruction(script->getBuf(offset), extOpcode, opparams); opcode = extOpcode >> 1; // Check for end of script diff --git a/engines/sci/engine/kernel.cpp b/engines/sci/engine/kernel.cpp index d6dcf650bc..9bf0371a7a 100644 --- a/engines/sci/engine/kernel.cpp +++ b/engines/sci/engine/kernel.cpp @@ -644,7 +644,7 @@ int Kernel::findRegType(reg_t reg) { case SEG_TYPE_SCRIPT: if (reg.offset <= (*(Script *)mobj).getBufSize() && reg.offset >= -SCRIPT_OBJECT_MAGIC_OFFSET && - RAW_IS_OBJECT((*(Script *)mobj)._buf + reg.offset)) { + RAW_IS_OBJECT((*(Script *)mobj).getBuf(reg.offset)) ) { return ((Script *)mobj)->getObject(reg.offset) ? KSIG_OBJECT : KSIG_REF; } else return KSIG_REF; diff --git a/engines/sci/engine/savegame.cpp b/engines/sci/engine/savegame.cpp index f6a6afd196..c0ed515981 100644 --- a/engines/sci/engine/savegame.cpp +++ b/engines/sci/engine/savegame.cpp @@ -278,7 +278,7 @@ void SegManager::saveLoadWithSerializer(Common::Serializer &s) { // If we are loading a script, hook it up in the script->segment map. if (s.isLoading() && type == SEG_TYPE_SCRIPT) { - _scriptSegMap[((Script *)mobj)->_nr] = i; + _scriptSegMap[((Script *)mobj)->getScriptNumber()] = i; } } @@ -765,7 +765,7 @@ void SegManager::reconstructScripts(EngineState *s) { scr->_localsBlock = (scr->_localsSegment == 0) ? NULL : (LocalVariables *)(_heap[scr->_localsSegment]); for (ObjMap::iterator it = scr->_objects.begin(); it != scr->_objects.end(); ++it) - it->_value._baseObj = scr->_buf + it->_value.getPos().offset; + it->_value._baseObj = scr->getBuf(it->_value.getPos().offset); } for (i = 0; i < _heap.size(); i++) { diff --git a/engines/sci/engine/script.cpp b/engines/sci/engine/script.cpp index f9584a2897..ac6fb6f26d 100644 --- a/engines/sci/engine/script.cpp +++ b/engines/sci/engine/script.cpp @@ -88,14 +88,13 @@ void Script::init(int script_nr, ResourceManager *resMan) { if (getSciVersion() == SCI_VERSION_0_EARLY) { _bufSize += READ_LE_UINT16(script->data) * 2; } else if (getSciVersion() >= SCI_VERSION_1_1) { - /** - * In SCI11, the heap was in a separate space from the script. - * We append it to the end of the script, and adjust addressing accordingly. - * However, since we address the heap with a 16-bit pointer, the combined - * size of the stack and the heap must be 64KB. So far this has worked - * for SCI11, SCI2 and SCI21 games. SCI3 games use a different script format, - * and theoretically they can exceed the 64KB boundary using relocation. - */ + // In SCI11, the heap was in a separate space from the script. We append + // it to the end of the script, and adjust addressing accordingly. + // However, since we address the heap with a 16-bit pointer, the + // combined size of the stack and the heap must be 64KB. So far this has + // worked for SCI11, SCI2 and SCI21 games. SCI3 games use a different + // script format, and theoretically they can exceed the 64KB boundary + // using relocation. Resource *heap = resMan->findResource(ResourceId(kResourceTypeHeap, script_nr), 0); _bufSize += heap->size; _heapSize = heap->size; @@ -109,8 +108,8 @@ void Script::init(int script_nr, ResourceManager *resMan) { // As mentioned above, the script and the heap together should not exceed 64KB if (script->size + heap->size > 65535) error("Script and heap sizes combined exceed 64K. This means a fundamental " - "design bug was made regarding SCI1.1 and newer games.\nPlease " - "report this error to the ScummVM team"); + "design bug was made regarding SCI1.1 and newer games.\n" + "Please report this error to the ScummVM team"); } } @@ -256,7 +255,7 @@ bool Script::relocateLocal(SegmentId segment, int location) { } void Script::relocate(reg_t block) { - byte *heap = _buf; + const byte *heap = _buf; uint16 heapSize = (uint16)_bufSize; uint16 heapOffset = 0; @@ -452,10 +451,9 @@ void Script::initialiseClasses(SegManager *segMan) { } } -void Script::initialiseObjectsSci0(SegManager *segMan) { +void Script::initialiseObjectsSci0(SegManager *segMan, SegmentId segmentId) { bool oldScriptHeader = (getSciVersion() == SCI_VERSION_0_EARLY); const byte *seeker = _buf + (oldScriptHeader ? 2 : 0); - SegmentId segmentId = segMan->getScriptSegment(_nr); do { uint16 objType = READ_SCI11ENDIAN_UINT16(seeker); @@ -487,11 +485,14 @@ void Script::initialiseObjectsSci0(SegManager *segMan) { seeker += READ_SCI11ENDIAN_UINT16(seeker + 2); } while ((uint32)(seeker - _buf) < getScriptSize() - 2); + + byte *relocationBlock = findBlock(SCI_OBJ_POINTERS); + if (relocationBlock) + relocate(make_reg(segmentId, relocationBlock - getBuf() + 4)); } -void Script::initialiseObjectsSci11(SegManager *segMan) { +void Script::initialiseObjectsSci11(SegManager *segMan, SegmentId segmentId) { const byte *seeker = _heapStart + 4 + READ_SCI11ENDIAN_UINT16(_heapStart + 2) * 2; - SegmentId segmentId = segMan->getScriptSegment(_nr); while (READ_SCI11ENDIAN_UINT16(seeker) == SCRIPT_OBJECT_MAGIC_NUMBER) { reg_t reg = make_reg(segmentId, seeker - _buf); @@ -521,6 +522,8 @@ void Script::initialiseObjectsSci11(SegManager *segMan) { seeker += READ_SCI11ENDIAN_UINT16(seeker + 2) * 2; } + + relocate(make_reg(segmentId, READ_SCI11ENDIAN_UINT16(_heapStart))); } } // End of namespace Sci diff --git a/engines/sci/engine/script.h b/engines/sci/engine/script.h index 296570c218..aab073f3a1 100644 --- a/engines/sci/engine/script.h +++ b/engines/sci/engine/script.h @@ -51,19 +51,12 @@ enum ScriptObjectTypes { typedef Common::HashMap ObjMap; class Script : public SegmentObj { -public: +private: int _nr; /**< Script number */ byte *_buf; /**< Static data buffer, or NULL if not used */ byte *_heapStart; /**< Start of heap if SCI1.1, NULL otherwise */ - uint32 getScriptSize() { return _scriptSize; } - uint32 getHeapSize() { return _heapSize; } - uint32 getBufSize() { return _bufSize; } - -protected: int _lockers; /**< Number of classes and objects that require this script */ - -private: size_t _scriptSize; size_t _heapSize; uint16 _bufSize; @@ -77,19 +70,27 @@ private: int _localsOffset; uint16 _localsCount; + bool _markedAsDeleted; + public: /** * Table for objects, contains property variables. * Indexed by the TODO offset. */ ObjMap _objects; + SegmentId _localsSegment; /**< The local variable segment */ + LocalVariables *_localsBlock; +public: int getLocalsOffset() const { return _localsOffset; } uint16 getLocalsCount() const { return _localsCount; } - SegmentId _localsSegment; /**< The local variable segment */ - LocalVariables *_localsBlock; - bool _markedAsDeleted; + uint32 getScriptSize() const { return _scriptSize; } + uint32 getHeapSize() const { return _heapSize; } + uint32 getBufSize() const { return _bufSize; } + const byte *getBuf(uint offset = 0) const { return _buf + offset; } + + int getScriptNumber() const { return _nr; } public: Script(); @@ -129,15 +130,6 @@ public: */ void scriptObjRemove(reg_t obj_pos); - /** - * Processes a relocation block witin a script - * This function is idempotent, but it must only be called after all - * objects have been instantiated, or a run-time error will occur. - * @param obj_pos Location (segment, offset) of the block - * @return Location of the relocation block - */ - void relocate(reg_t block); - /** * Initializes the script's local variables * @param segMan A reference to the segment manager @@ -153,19 +145,17 @@ public: /** * Initializes the script's objects (SCI0) * @param segMan A reference to the segment manager + * @param segmentId The script's segment id */ - void initialiseObjectsSci0(SegManager *segMan); + void initialiseObjectsSci0(SegManager *segMan, SegmentId segmentId); /** * Initializes the script's objects (SCI1.1+) * @param segMan A reference to the segment manager + * @param segmentId The script's segment id */ - void initialiseObjectsSci11(SegManager *segMan); - -private: - bool relocateLocal(SegmentId segment, int location); + void initialiseObjectsSci11(SegManager *segMan, SegmentId segmentId); -public: // script lock operations /** Increments the number of lockers of this script by one. */ @@ -246,6 +236,18 @@ public: * Finds the pointer where a block of a specific type starts from */ byte *findBlock(int type); + +private: + /** + * Processes a relocation block witin a script + * This function is idempotent, but it must only be called after all + * objects have been instantiated, or a run-time error will occur. + * @param obj_pos Location (segment, offset) of the block + * @return Location of the relocation block + */ + void relocate(reg_t block); + + bool relocateLocal(SegmentId segment, int location); }; } // End of namespace Sci diff --git a/engines/sci/engine/scriptdebug.cpp b/engines/sci/engine/scriptdebug.cpp index d730856332..4813e083fd 100644 --- a/engines/sci/engine/scriptdebug.cpp +++ b/engines/sci/engine/scriptdebug.cpp @@ -69,7 +69,7 @@ DebugState g_debugState; // FIXME: Avoid non-const global vars reg_t disassemble(EngineState *s, reg_t pos, int print_bw_tag, int print_bytecode) { SegmentObj *mobj = s->_segMan->getSegment(pos.segment, SEG_TYPE_SCRIPT); Script *script_entity = NULL; - byte *scr; + const byte *scr; int scr_size; reg_t retval = make_reg(pos.segment, pos.offset + 1); uint16 param_value; @@ -82,7 +82,7 @@ reg_t disassemble(EngineState *s, reg_t pos, int print_bw_tag, int print_bytecod } else script_entity = (Script *)mobj; - scr = script_entity->_buf; + scr = script_entity->getBuf(); scr_size = script_entity->getBufSize(); if (pos.offset >= scr_size) { @@ -291,7 +291,7 @@ void script_debug(EngineState *s) { if (mobj) { Script *scr = (Script *)mobj; - byte *code_buf = scr->_buf; + const byte *code_buf = scr->getBuf(); int code_buf_size = scr->getBufSize(); int opcode = s->xs->addr.pc.offset >= code_buf_size ? 0 : code_buf[s->xs->addr.pc.offset]; int op = opcode >> 1; diff --git a/engines/sci/engine/seg_manager.cpp b/engines/sci/engine/seg_manager.cpp index b56a539c63..56591c4726 100644 --- a/engines/sci/engine/seg_manager.cpp +++ b/engines/sci/engine/seg_manager.cpp @@ -157,7 +157,7 @@ int SegManager::deallocate(SegmentId seg, bool recursive) { if (mobj->getType() == SEG_TYPE_SCRIPT) { Script *scr = (Script *)mobj; - _scriptSegMap.erase(scr->_nr); + _scriptSegMap.erase(scr->getScriptNumber()); if (recursive && scr->_localsSegment) deallocate(scr->_localsSegment, recursive); } @@ -173,7 +173,7 @@ bool SegManager::isHeapObject(reg_t pos) { if (obj == NULL || (obj && obj->isFreed())) return false; Script *scr = getScriptIfLoaded(pos.segment); - return !(scr && scr->_markedAsDeleted); + return !(scr && scr->isMarkedAsDeleted()); } void SegManager::deallocateScript(int script_nr) { @@ -237,7 +237,7 @@ Object *SegManager::getObject(reg_t pos) { } else if (mobj->getType() == SEG_TYPE_SCRIPT) { Script *scr = (Script *)mobj; if (pos.offset <= scr->getBufSize() && pos.offset >= -SCRIPT_OBJECT_MAGIC_OFFSET - && RAW_IS_OBJECT(scr->_buf + pos.offset)) { + && RAW_IS_OBJECT(scr->getBuf(pos.offset))) { obj = scr->getObject(pos.offset); } } @@ -384,12 +384,12 @@ LocalVariables *SegManager::allocLocalsSegment(Script *scr) { locals = (LocalVariables *)_heap[scr->_localsSegment]; VERIFY(locals != NULL, "Re-used locals segment was NULL'd out"); VERIFY(locals->getType() == SEG_TYPE_LOCALS, "Re-used locals segment did not consist of local variables"); - VERIFY(locals->script_id == scr->_nr, "Re-used locals segment belonged to other script"); + VERIFY(locals->script_id == scr->getScriptNumber(), "Re-used locals segment belonged to other script"); } else locals = (LocalVariables *)allocSegment(new LocalVariables(), &scr->_localsSegment); scr->_localsBlock = locals; - locals->script_id = scr->_nr; + locals->script_id = scr->getScriptNumber(); locals->_locals.resize(scr->getLocalsCount()); return locals; @@ -1012,13 +1012,9 @@ int SegManager::instantiateScript(int scriptNum) { scr->initialiseClasses(this); if (getSciVersion() >= SCI_VERSION_1_1) { - scr->initialiseObjectsSci11(this); - scr->relocate(make_reg(segmentId, READ_SCI11ENDIAN_UINT16(scr->_heapStart))); + scr->initialiseObjectsSci11(this, segmentId); } else { - scr->initialiseObjectsSci0(this); - byte *relocationBlock = scr->findBlock(SCI_OBJ_POINTERS); - if (relocationBlock) - scr->relocate(make_reg(segmentId, relocationBlock - scr->_buf + 4)); + scr->initialiseObjectsSci0(this, segmentId); } return segmentId; @@ -1067,16 +1063,16 @@ void SegManager::uninstantiateScriptSci0(int script_nr) { do { reg.offset += objLength; // Step over the last checked object - objType = READ_SCI11ENDIAN_UINT16(scr->_buf + reg.offset); + objType = READ_SCI11ENDIAN_UINT16(scr->getBuf(reg.offset)); if (!objType) break; - objLength = READ_SCI11ENDIAN_UINT16(scr->_buf + reg.offset + 2); + objLength = READ_SCI11ENDIAN_UINT16(scr->getBuf(reg.offset + 2)); reg.offset += 4; // Step over header if ((objType == SCI_OBJ_OBJECT) || (objType == SCI_OBJ_CLASS)) { // object or class? reg.offset += 8; // magic offset (SCRIPT_OBJECT_MAGIC_OFFSET) - int16 superclass = READ_SCI11ENDIAN_UINT16(scr->_buf + reg.offset + 2); + int16 superclass = READ_SCI11ENDIAN_UINT16(scr->getBuf(reg.offset + 2)); if (superclass >= 0) { int superclass_script = getClass(superclass).script; diff --git a/engines/sci/engine/vm.cpp b/engines/sci/engine/vm.cpp index 555576f579..686603ae21 100644 --- a/engines/sci/engine/vm.cpp +++ b/engines/sci/engine/vm.cpp @@ -299,7 +299,7 @@ static reg_t validate_read_var(reg_t *r, reg_t *stack_base, int type, int max, i EngineState *state = g_sci->getEngineState(); ExecStack *lastCall = state->xs; Script *local_script = state->_segMan->getScriptIfLoaded(lastCall->local_segment); - int curScriptNr = local_script->_nr; + int curScriptNr = local_script->getScriptNumber(); if (lastCall->localCallOffset != -1) { // if lastcall was actually a local call search back for a real call @@ -943,7 +943,7 @@ void run_vm(EngineState *s, bool restoring) { s->_executionStackPosChanged = false; obj = s->_segMan->getObject(s->xs->objp); - code_buf = scr->_buf; + code_buf = scr->getBuf(); code_buf_size = scr->getBufSize(); local_script = s->_segMan->getScriptIfLoaded(s->xs->local_segment); if (!local_script) { @@ -1287,7 +1287,7 @@ void run_vm(EngineState *s, bool restoring) { // for (int i = 0; i < opparams[0]; i++) // s->xs->sp[i] = make_reg(0, 'ss'); - //if (local_script->_nr == 140 && isIslandOfDrBrain) { + //if (local_script->getScriptNumber() == 140 && isIslandOfDrBrain) { // // WORKAROUND for The Island of Dr. Brain, room 140. // // Script 140 runs in an endless loop if we set its // // variables to 0 here. diff --git a/engines/sci/engine/vm.h b/engines/sci/engine/vm.h index ed4cc4a456..49169a456c 100644 --- a/engines/sci/engine/vm.h +++ b/engines/sci/engine/vm.h @@ -64,7 +64,7 @@ struct Class { reg_t reg; ///< offset; script-relative offset, segment: 0 if not instantiated }; -#define RAW_IS_OBJECT(datablock) (READ_SCI11ENDIAN_UINT16(((byte *) datablock) + SCRIPT_OBJECT_MAGIC_OFFSET) == SCRIPT_OBJECT_MAGIC_NUMBER) +#define RAW_IS_OBJECT(datablock) (READ_SCI11ENDIAN_UINT16(((const byte *) datablock) + SCRIPT_OBJECT_MAGIC_OFFSET) == SCRIPT_OBJECT_MAGIC_NUMBER) // A reference to an object's variable. // The object is stored as a reg_t, the variable as an index into _variables -- cgit v1.2.3