diff options
author | Scott Percival | 2019-12-22 19:03:08 +0800 |
---|---|---|
committer | Scott Percival | 2019-12-23 08:58:14 +0800 |
commit | d1347b0ce120b3fef101de0736c243a82932c583 (patch) | |
tree | 8fb144b8978289e3496fc84a26c1d3790607369b | |
parent | 48499ac10a1f2b72959d763ac23462085276de79 (diff) | |
download | scummvm-rg350-d1347b0ce120b3fef101de0736c243a82932c583.tar.gz scummvm-rg350-d1347b0ce120b3fef101de0736c243a82932c583.tar.bz2 scummvm-rg350-d1347b0ce120b3fef101de0736c243a82932c583.zip |
DIRECTOR: LINGO: Add define() support for bytecode
-rw-r--r-- | engines/director/lingo/lingo-bytecode.cpp | 13 | ||||
-rw-r--r-- | engines/director/lingo/lingo-codegen.cpp | 44 | ||||
-rw-r--r-- | engines/director/lingo/lingo.h | 1 | ||||
-rw-r--r-- | engines/director/score.cpp | 25 |
4 files changed, 49 insertions, 34 deletions
diff --git a/engines/director/lingo/lingo-bytecode.cpp b/engines/director/lingo/lingo-bytecode.cpp index 0d8d598e01..735a877008 100644 --- a/engines/director/lingo/lingo-bytecode.cpp +++ b/engines/director/lingo/lingo-bytecode.cpp @@ -369,7 +369,6 @@ void Lingo::cb_v4theentityassign() { } } - void Lingo::addCodeV4(Common::SeekableSubReadStreamEndian &stream, ScriptType type, uint16 id) { debugC(1, kDebugLingoCompile, "Add V4 bytecode for type %s with id %d", scriptType2str(type), id); @@ -513,11 +512,11 @@ void Lingo::addCodeV4(Common::SeekableSubReadStreamEndian &stream, ScriptType ty _currentScriptContext->functions.push_back(new ScriptData); _currentScript = _currentScriptContext->functions[_currentScriptFunction]; - /*uint16 nameIndex = */stream.readUint16(); + uint16 nameIndex = stream.readUint16(); stream.readUint16(); uint32 length = stream.readUint32(); uint32 startOffset = stream.readUint32(); - /*uint16 argCount = */stream.readUint16(); + uint16 argCount = stream.readUint16(); /*uint32 argOffset = */stream.readUint32(); /*uint16 varCount = */stream.readUint16(); /*uint32 varNamesOffset = */stream.readUint32(); @@ -638,6 +637,14 @@ void Lingo::addCodeV4(Common::SeekableSubReadStreamEndian &stream, ScriptType ty warning("Jump of %d from position %d is outside the function!", jump, originalJumpAddressLoc); } } + + // Attach to handlers + if (nameIndex < _namelist.size()) { + g_lingo->define(_namelist[nameIndex], argCount, new ScriptData(&(*_currentScript)[0], _currentScript->size())); + + } else { + warning("Function has unknown name id %d, skipping define", nameIndex); + } } free(codeStore); } diff --git a/engines/director/lingo/lingo-codegen.cpp b/engines/director/lingo/lingo-codegen.cpp index d0fd95d85f..44ce2d070d 100644 --- a/engines/director/lingo/lingo-codegen.cpp +++ b/engines/director/lingo/lingo-codegen.cpp @@ -214,14 +214,7 @@ void Lingo::cleanLocalVars() { g_lingo->_localvars = 0; } -Symbol *Lingo::define(Common::String &name, int start, int nargs, Common::String *prefix, int end, bool removeCode) { - if (prefix) - name = *prefix + "-" + name; - - debugC(1, kDebugLingoCompile, "define(\"%s\"(len: %d), %d, %d, \"%s\", %d) entity: %d", - name.c_str(), _currentScript->size() - 1, start, nargs, (prefix ? prefix->c_str() : ""), - end, _currentEntityId); - +Symbol *Lingo::define(Common::String &name, int nargs, ScriptData *code) { Symbol *sym = getHandler(name); if (sym == NULL) { // Create variable if it was not defined sym = new Symbol; @@ -241,19 +234,10 @@ Symbol *Lingo::define(Common::String &name, int start, int nargs, Common::String delete sym->u.defn; } - if (end == -1) - end = _currentScript->size(); - - sym->u.defn = new ScriptData(&(*_currentScript)[start], end - start); + sym->u.defn = code; sym->nargs = nargs; sym->maxArgs = nargs; - // Now remove all defined code from the _currentScript - if (removeCode) - for (int i = end - 1; i >= start; i--) { - _currentScript->remove_at(i); - } - if (debugChannelSet(1, kDebugLingoCompile)) { uint pc = 0; while (pc < sym->u.defn->size()) { @@ -267,6 +251,30 @@ Symbol *Lingo::define(Common::String &name, int start, int nargs, Common::String return sym; } +Symbol *Lingo::define(Common::String &name, int start, int nargs, Common::String *prefix, int end, bool removeCode) { + if (prefix) + name = *prefix + "-" + name; + + debugC(1, kDebugLingoCompile, "define(\"%s\"(len: %d), %d, %d, \"%s\", %d) entity: %d", + name.c_str(), _currentScript->size() - 1, start, nargs, (prefix ? prefix->c_str() : ""), + end, _currentEntityId); + + if (end == -1) + end = _currentScript->size(); + + ScriptData *code = new ScriptData(&(*_currentScript)[start], end - start); + Symbol *sym = define(name, nargs, code); + + // Now remove all defined code from the _currentScript + if (removeCode) + for (int i = end - 1; i >= start; i--) { + _currentScript->remove_at(i); + } + + + return sym; +} + int Lingo::codeString(const char *str) { int numInsts = calcStringAlignment(str); diff --git a/engines/director/lingo/lingo.h b/engines/director/lingo/lingo.h index de059c4ff4..ff294c25a0 100644 --- a/engines/director/lingo/lingo.h +++ b/engines/director/lingo/lingo.h @@ -214,6 +214,7 @@ public: void popContext(); Symbol *lookupVar(const char *name, bool create = true, bool putInGlobalList = false); void cleanLocalVars(); + Symbol *define(Common::String &s, int nargs, ScriptData *code); Symbol *define(Common::String &s, int start, int nargs, Common::String *prefix = NULL, int end = -1, bool removeCode = true); void processIf(int elselabel, int endlabel, int finalElse); diff --git a/engines/director/score.cpp b/engines/director/score.cpp index 062cff06bd..0d89aef723 100644 --- a/engines/director/score.cpp +++ b/engines/director/score.cpp @@ -175,6 +175,18 @@ void Score::loadArchive() { } } + // Try to load script name lists + if (_vm->getVersion() >= 4) { + Common::Array<uint16> lnam = _movieArchive->getResourceIDList(MKTAG('L','n','a','m')); + if (lnam.size() > 0) { + debugC(2, kDebugLoading, "****** Loading %d Lnam resources", lnam.size()); + + for (Common::Array<uint16>::iterator iterator = lnam.begin(); iterator != lnam.end(); ++iterator) { + loadLingoNames(*_movieArchive->getResource(MKTAG('L','n','a','m'), *iterator)); + } + } + } + Common::Array<uint16> vwci = _movieArchive->getResourceIDList(MKTAG('V', 'W', 'C', 'I')); if (vwci.size() > 0) { debugC(2, kDebugLoading, "****** Loading %d CastInfos", vwci.size()); @@ -197,19 +209,6 @@ void Score::loadArchive() { setSpriteCasts(); loadSpriteImages(false); - // Try to load script name lists - if (_vm->getVersion() >= 4) { - Common::Array<uint16> lnam = _movieArchive->getResourceIDList(MKTAG('L','n','a','m')); - if (lnam.size() > 0) { - debugC(2, kDebugLoading, "****** Loading %d Lnam resources", lnam.size()); - - for (Common::Array<uint16>::iterator iterator = lnam.begin(); iterator != lnam.end(); ++iterator) { - loadLingoNames(*_movieArchive->getResource(MKTAG('L','n','a','m'), *iterator)); - } - } - } - - // Now process STXTs Common::Array<uint16> stxt = _movieArchive->getResourceIDList(MKTAG('S','T','X','T')); debugC(2, kDebugLoading, "****** Loading %d STXT resources", stxt.size()); |