| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542 |
- /* ScummVM Tools
- *
- * ScummVM Tools is the legal property of its developers, whose
- * names are too numerous to list here. Please refer to the
- * COPYRIGHT file distributed with this source distribution.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- */
- #include <iostream>
- #include <sstream>
- #include <boost/format.hpp>
- #include "disassembler.h"
- Scumm::v6::Scummv6Disassembler::Scummv6Disassembler(InstVec &insts) : SimpleDisassembler(insts) {
- }
- void Scumm::v6::Scummv6Disassembler::doDisassemble(){
- std::string blockName;
- for (int i = 0; i < 4; i++) {
- blockName += mStream->ReadS8();
- }
- if (blockName == "SCRP") {
- //std::clog << "Input is global script\n";
- mStream->Seek(8);
- } else if (blockName == "LSCR") {
- //std::clog << "Input is local script\n";
- mStream->Seek(9);
- } else if (blockName == "ENCD") {
- //std::clog << "Input is room entry script\n";
- mStream->Seek(8);
- } else if (blockName == "EXCD") {
- //std::clog << "Input is room exit script\n";
- mStream->Seek(8);
- } else if (blockName == "VERB") {
- //std::clog << "Input is object script\n";
- mStream->Seek(8);
- //std::clog << "Offset table:\n";
- uint32 verb = mStream->ReadU8();
- while (verb != 0) {
- /*std::clog << boost::format("%02x - %04x\n") % verb %*/ mStream->ReadU16();
- verb = mStream->ReadU8();
- }
- } else {
- std::stringstream s;
- s << "Unknown block name " << blockName;
- throw std::runtime_error(s.str());
- }
- START_OPCODES;
- OPCODE(0x00, "pushByte", Scummv6LoadInstruction, 1, "B");
- OPCODE(0x01, "pushWord", Scummv6LoadInstruction, 1, "s");
- OPCODE(0x02, "pushByteVar", Scummv6LoadInstruction, 1, "B");
- OPCODE(0x03, "pushWordVar", Scummv6LoadInstruction, 1, "w");
- OPCODE(0x06, "byteArrayRead", Scummv6LoadInstruction, 0, "B");
- OPCODE(0x07, "wordArrayRead", Scummv6LoadInstruction, 0, "w");
- OPCODE(0x0A, "byteArrayIndexedRead", Scummv6LoadInstruction, -1, "B");
- OPCODE(0x0B, "wordArrayIndexedRead", Scummv6LoadInstruction, -1, "w");
- OPCODE(0x0C, "dup", DupStackInstruction, 1, "");
- OPCODE(0x0D, "not", BoolNegateStackInstruction, 0, "");
- OPCODE_MD(0x0E, "eq", BinaryOpStackInstruction, -1, "", "==");
- OPCODE_MD(0x0F, "neq", BinaryOpStackInstruction, -1, "", "!=");
- OPCODE_MD(0x10, "gt", BinaryOpStackInstruction, -1, "", ">");
- OPCODE_MD(0x11, "lt", BinaryOpStackInstruction, -1, "", "<");
- OPCODE_MD(0x12, "le", BinaryOpStackInstruction, -1, "", "<=");
- OPCODE_MD(0x13, "ge", BinaryOpStackInstruction, -1, "", ">=");
- OPCODE_MD(0x14, "add", BinaryOpStackInstruction, -1, "", "+");
- OPCODE_MD(0x15, "sub", BinaryOpStackInstruction, -1, "", "-");
- OPCODE_MD(0x16, "mul", BinaryOpStackInstruction, -1, "", "*");
- OPCODE_MD(0x17, "div", BinaryOpStackInstruction, -1, "", "/");
- OPCODE_MD(0x18, "land", BinaryOpStackInstruction, -1, "", "&&");
- OPCODE_MD(0x19, "lor", BinaryOpStackInstruction, -1, "", "||");
- OPCODE(0x1A, "pop", Scummv6StackInstruction, -1, "");
- OPCODE(0x42, "writeByteVar", Scummv6StoreInstruction, -1, "B");
- OPCODE(0x43, "writeWordVar", Scummv6StoreInstruction, -1, "w");
- OPCODE(0x46, "byteArrayWrite", Scummv6StoreInstruction, -2, "B");
- OPCODE(0x47, "wordArrayWrite", Scummv6StoreInstruction, -2, "w");
- OPCODE(0x4A, "byteArrayIndexedWrite", Scummv6StoreInstruction, -3, "B");
- OPCODE(0x4B, "wordArrayIndexedWrite", Scummv6StoreInstruction, -3, "w");
- OPCODE_MD(0x4E, "byteVarInc", Scummv6IncDecInstruction, 0, "B", "++");
- OPCODE_MD(0x4F, "wordVarInc", Scummv6IncDecInstruction, 0, "w", "++");
- OPCODE_MD(0x52, "byteArrayInc", Scummv6IncDecInstruction, -1, "B", "++");
- OPCODE_MD(0x53, "wordArrayInc", Scummv6IncDecInstruction, -1, "w", "++");
- OPCODE_MD(0x56, "byteVarDec", Scummv6IncDecInstruction, 0, "B", "--");
- OPCODE_MD(0x57, "wordVarDec", Scummv6IncDecInstruction, 0, "w", "--");
- OPCODE_MD(0x5A, "byteArrayDec", Scummv6IncDecInstruction, -1, "B", "--");
- OPCODE_MD(0x5B, "wordArrayDec", Scummv6IncDecInstruction, -1, "w", "--");
- OPCODE(0x5C, "jumpTrue", Scummv6CondJumpInstruction, -1, "a");
- OPCODE(0x5D, "jumpFalse", Scummv6CondJumpInstruction, -1, "a");
- OPCODE_MD(0x5E, "startScript", KernelCallStackInstruction, 0x1020, "", "lpp"); // Variable stack arguments
- OPCODE_MD(0x5F, "startScriptQuick", KernelCallStackInstruction, 0x1010, "", "lp"); // Variable stack arguments
- OPCODE_MD(0x60, "startObject", KernelCallStackInstruction, 0x1030, "", "lppp"); // Variable stack arguments
- OPCODE_MD(0x61, "drawObject", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0x62, "drawObjectAt", KernelCallStackInstruction, -3, "", "ppp");
- OPCODE_MD(0x63, "drawBlastObject", KernelCallStackInstruction, -5, "", "ppppp");
- OPCODE_MD(0x64, "setBlastObjectWindow", KernelCallStackInstruction, -4, "", "pppp");
- OPCODE(0x65, "stopObjectCodeA", KernelCallStackInstruction, 0, "");
- OPCODE(0x66, "stopObjectCodeB", KernelCallStackInstruction, 0, "");
- OPCODE(0x67, "endCutscene", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x68, "beginCutscene", KernelCallStackInstruction, 0x1000, "", "l"); // Variable stack arguments
- OPCODE(0x69, "stopMusic", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x6A, "freezeUnfreeze", KernelCallStackInstruction, -1, "", "p");
- START_SUBOPCODE_WITH_PREFIX(0x6B, "cursorCommand");
- OPCODE(0x90, "cursorOn", KernelCallStackInstruction, 0, "");
- OPCODE(0x91, "cursorOff", KernelCallStackInstruction, 0, "");
- OPCODE(0x92, "userputOn", KernelCallStackInstruction, 0, "");
- OPCODE(0x93, "userputOff", KernelCallStackInstruction, 0, "");
- OPCODE(0x94, "softCursorOn", KernelCallStackInstruction, 0, "");
- OPCODE(0x95, "softCursorOff", KernelCallStackInstruction, 0, "");
- OPCODE(0x96, "softUserputOn", KernelCallStackInstruction, 0, "");
- OPCODE(0x97, "softUserputOff", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x99, "setCursorImg", KernelCallStackInstruction, -2, "", "z");
- OPCODE_MD(0x9A, "setCursorHotspot", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0x9C, "initCharset", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x9D, "charsetColors", KernelCallStackInstruction, 0x1000, "", "l"); // Variable stack arguments
- OPCODE_MD(0xD6, "setCursorTransparency", KernelCallStackInstruction, -1, "", "p");
- END_SUBOPCODE;
- OPCODE(0x6C, "breakHere", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x6D, "ifClassOfIs", KernelCallStackInstruction, 0x1011, "", "rlp"); // Variable stack arguments
- OPCODE_MD(0x6E, "setClass", KernelCallStackInstruction, 0x1010, "", "lp"); // Variable stack arguments
- OPCODE_MD(0x6F, "getState", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0x70, "setState", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0x71, "setOwner", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0x72, "getOwner", KernelCallStackInstruction, 0, "", "rp");
- OPCODE(0x73, "jump", Scummv6JumpInstruction, 0, "a");
- OPCODE_MD(0x74, "startSound", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x75, "stopSound", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x76, "startMusic", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x77, "stopObjectScript", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x78, "panCameraTo", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x79, "actorFollowCamera", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x7A, "setCameraAt", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x7B, "loadRoom", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x7C, "stopScript", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x7D, "walkActorToObj", KernelCallStackInstruction, -3, "", "ppp");
- OPCODE_MD(0x7E, "walkActorTo", KernelCallStackInstruction, -3, "", "ppp");
- OPCODE_MD(0x7F, "putActorAtXY", KernelCallStackInstruction, -4, "", "pppp");
- OPCODE_MD(0x80, "putActorAtObject", KernelCallStackInstruction, -3, "", "zp");
- OPCODE_MD(0x81, "faceActor", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0x82, "animateActor", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0x83, "doSentence", KernelCallStackInstruction, -4, "", "pppp");
- OPCODE_MD(0x84, "pickupObject", KernelCallStackInstruction, -2, "", "z");
- OPCODE_MD(0x85, "loadRoomWithEgo", KernelCallStackInstruction, -4, "", "ppz");
- OPCODE_MD(0x87, "getRandomNumber", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0x88, "getRandomNumberRange", KernelCallStackInstruction, -1, "", "rpp");
- OPCODE_MD(0x8A, "getActorMoving", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0x8B, "isScriptRunning", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0x8C, "getActorRoom", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0x8D, "getObjectX", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0x8E, "getObjectY", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0x8F, "getObjectDir", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0x90, "getActorWalkBox", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0x91, "getActorCostume", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0x92, "findInventory", KernelCallStackInstruction, -1, "", "rpp");
- OPCODE_MD(0x93, "getInventoryCount", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0x94, "getVerbFromXY", KernelCallStackInstruction, -1, "", "rpp");
- OPCODE_BASE(0x95)
- OPCODE_BODY("beginOverride", KernelCallStackInstruction, 0, "", "");
- // FIXME/TODO: beginOverride skips the following jump - that jump is instead to a "finally" handler
- // To simulate this, we simply skip the jump instruction, so the sequential order appears the same.
- // Semantically, it would probably be more correct to model this as a conditional jump,
- // but since precious little time remains of GSoC and that might not play very nice with the rest of the code,
- // this is the simplest way to handle the issue right now. Eventually, it should probably be fixed more properly.
- mStream->Seek(3);
- _address += 3;
- OPCODE_END;
- OPCODE(0x96, "endOverride", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x97, "setObjectName", KernelCallStackInstruction, -1, "c", "ps");
- OPCODE_MD(0x98, "isSoundRunning", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0x99, "setBoxFlags", KernelCallStackInstruction, 0x1100, "", "pl"); // Variable stack arguments
- OPCODE(0x9A, "createBoxMatrix", KernelCallStackInstruction, 0, "");
- START_SUBOPCODE_WITH_PREFIX(0x9B, "resourceRoutines");
- OPCODE_MD(0x64, "loadScript", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x65, "loadSound", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x66, "loadCostume", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x67, "loadRoom", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x68, "nukeScript", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x69, "nukeSound", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x6A, "nukeCostume", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x6B, "nukeRoom", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x6C, "lockScript", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x6D, "lockSound", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x6E, "lockCostume", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x6F, "lockRoom", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x70, "unlockScript", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x71, "unlockSound", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x72, "unlockCostume", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x73, "unlockRoom", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x75, "loadCharset", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x76, "nukeCharset", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x77, "loadFlObject", KernelCallStackInstruction, -2, "", "pp");
- END_SUBOPCODE;
- START_SUBOPCODE_WITH_PREFIX(0x9C, "roomOps");
- OPCODE_MD(0xAC, "roomScroll", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0xAE, "setScreen", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0xAF, "setPalColor", KernelCallStackInstruction, -4, "", "pppp");
- OPCODE(0xB0, "shakeOn", KernelCallStackInstruction, 0, "");
- OPCODE(0xB1, "shakeOff", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0xB3, "darkenPalette", KernelCallStackInstruction, -3, "", "ppp");
- OPCODE_MD(0xB4, "saveLoadRoom", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0xB5, "screenEffect", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0xB6, "darkenPaletteRGB", KernelCallStackInstruction, -5, "", "ppppp");
- OPCODE_MD(0xB7, "setupShadowPalette", KernelCallStackInstruction, -5, "", "ppppp");
- OPCODE_MD(0xBA, "palManipulate", KernelCallStackInstruction, -4, "", "pppp");
- OPCODE_MD(0xBB, "colorCycleDelay", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0xD5, "setPalette", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0xDC, "copyPalColor", KernelCallStackInstruction, -2, "", "pp");
- END_SUBOPCODE;
- START_SUBOPCODE_WITH_PREFIX(0x9D, "actorOps");
- OPCODE_MD(0x4C, "setCostume", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x4D, "setWalkSpeed", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0x4E, "setSound", KernelCallStackInstruction, 0x1000, "", "l"); // Variable stack arguments
- OPCODE_MD(0x4F, "setWalkFrame", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x50, "setTalkFrame", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0x51, "setStandFrame", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x52, "82?", KernelCallStackInstruction, -3, "", "ppp");
- OPCODE(0x53, "init", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x54, "setElevation", KernelCallStackInstruction, -1, "", "p");
- OPCODE(0x55, "setDefAnim", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x56, "setPalette", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0x57, "setTalkColor", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x58, "setName", KernelCallStackInstruction, 0, "c", "s");
- OPCODE_MD(0x59, "setInitFrame", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x5B, "setWidth", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x5C, "setScale", KernelCallStackInstruction, -1, "", "p");
- OPCODE(0x5D, "setNeverZClip", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x5E, "setAlwaysZClip", KernelCallStackInstruction, -1, "", "p");
- OPCODE(0x5F, "setIgnoreBoxes", KernelCallStackInstruction, 0, "");
- OPCODE(0x60, "setFollowBoxes", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x61, "setAnimSpeed", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x62, "setShadowMode", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x63, "setTalkPos", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0xC5, "setCurActor", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0xC6, "setAnimVar", KernelCallStackInstruction, -2, "", "pp");
- OPCODE(0xD7, "setIgnoreTurnsOn", KernelCallStackInstruction, 0, "");
- OPCODE(0xD8, "setIgnoreTurnsOff", KernelCallStackInstruction, 0, "");
- OPCODE(0xD9, "initLittle", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0xE1, "setAlwaysZClip?", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0xE3, "setLayer", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0xE4, "setWalkScript", KernelCallStackInstruction, -1, "", "p");
- OPCODE(0xE5, "setStanding", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0xE6, "setDirection", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0xE7, "turnToDirection", KernelCallStackInstruction, -1, "", "p");
- OPCODE(0xE9, "freeze", KernelCallStackInstruction, 0, "");
- OPCODE(0xEA, "unfreeze", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0xEB, "setTalkScript", KernelCallStackInstruction, -1, "", "p");
- END_SUBOPCODE;
- START_SUBOPCODE_WITH_PREFIX(0x9E, "verbOps");
- OPCODE_MD(0x7C, "loadImg", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x7D, "loadString", KernelCallStackInstruction, 0, "c", "s");
- OPCODE_MD(0x7E, "setColor", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x7F, "setHiColor", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x80, "setXY", KernelCallStackInstruction, -2, "", "pp");
- OPCODE(0x81, "setOn", KernelCallStackInstruction, 0, "");
- OPCODE(0x82, "setOff", KernelCallStackInstruction, 0, "");
- OPCODE(0x83, "kill", KernelCallStackInstruction, 0, "");
- OPCODE(0x84, "init", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x85, "setDimColor", KernelCallStackInstruction, -1, "", "p");
- OPCODE(0x86, "setDimmed", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x87, "setKey", KernelCallStackInstruction, -1, "", "p");
- OPCODE(0x88, "setCenter", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x89, "setToString", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x8B, "setToObject", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0x8C, "setBkColor", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0xC4, "setCurVerb", KernelCallStackInstruction, -1, "", "p");
- OPCODE(0xFF, "redraw", KernelCallStackInstruction, 0, "");
- END_SUBOPCODE;
- OPCODE_MD(0x9F, "getActorFromXY", KernelCallStackInstruction, -1, "", "rpp");
- OPCODE_MD(0xA0, "findObject", KernelCallStackInstruction, -1, "", "rpp");
- OPCODE_MD(0xA1, "pseudoRoom", KernelCallStackInstruction, 0x1010, "", "lp"); // Variable stack arguments
- OPCODE_MD(0xA2, "getActorElevation", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0xA3, "getVerbEntrypoint", KernelCallStackInstruction, -1, "", "rpp");
- START_SUBOPCODE_WITH_PREFIX(0xA4, "arrayOps");
- OPCODE_MD(0xCD, "assignString", Scummv6ArrayOpInstruction, -1, "wc", "");
- OPCODE_MD(0xD0, "assignIntList", Scummv6ArrayOpInstruction, 0x1100, "w", ""); // Variable stack arguments
- OPCODE_MD(0xD4, "assign2DimList", Scummv6ArrayOpInstruction, 0x1100, "w", ""); // Variable stack arguments
- END_SUBOPCODE;
- START_SUBOPCODE_WITH_PREFIX(0xA5, "saveRestoreVerbs");
- OPCODE_MD(0x8D, "saveVerbs", KernelCallStackInstruction, -3, "", "ppp");
- OPCODE_MD(0x8E, "restoreVerbs", KernelCallStackInstruction, -3, "", "ppp");
- OPCODE_MD(0x8F, "deleteVerbs", KernelCallStackInstruction, -3, "", "ppp");
- END_SUBOPCODE;
- OPCODE_MD(0xA6, "drawBox", KernelCallStackInstruction, -5, "", "ppppp");
- OPCODE(0xA7, "pop", Scummv6StackInstruction, -1, "");
- OPCODE_MD(0xA8, "getActorWidth", KernelCallStackInstruction, 0, "", "rp");
- START_SUBOPCODE(0xA9); // wait
- OPCODE_MD(0xA8, "waitForActor", KernelCallStackInstruction, -1, "s", "pj");
- OPCODE(0xA9, "waitForMessage", KernelCallStackInstruction, 0, "");
- OPCODE(0xAA, "waitForCamera", KernelCallStackInstruction, 0, "");
- OPCODE(0xAB, "waitForSentence", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0xE2, "waitUntilActorDrawn", KernelCallStackInstruction, -1, "s", "pj");
- OPCODE_MD(0xE8, "waitUntilActorTurned", KernelCallStackInstruction, -1, "s", "pj");
- END_SUBOPCODE;
- OPCODE_MD(0xAA, "getActorScaleX", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0xAB, "getActorAnimCounter", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0xAC, "soundKludge", KernelCallStackInstruction, 0x1000, "", "l"); // Variable stack arguments
- OPCODE_MD(0xAD, "isAnyOf", KernelCallStackInstruction, 0x1011, "", "rlp"); // Variable stack arguments
- START_SUBOPCODE_WITH_PREFIX(0xAE, "systemOps");
- OPCODE(0x9E, "restartGame", KernelCallStackInstruction, 0, "");
- OPCODE(0x9F, "pauseGame", KernelCallStackInstruction, 0, "");
- OPCODE(0xA0, "shutDown", KernelCallStackInstruction, 0, "");
- END_SUBOPCODE;
- OPCODE_MD(0xAF, "isActorInBox", KernelCallStackInstruction, -1, "", "rpp");
- OPCODE_MD(0xB0, "delay", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0xB1, "delaySeconds", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0xB2, "delayMinutes", KernelCallStackInstruction, -1, "", "p");
- OPCODE(0xB3, "stopSentence", KernelCallStackInstruction, 0, "");
- START_SUBOPCODE_WITH_PREFIX(0xB4, "printLine");
- OPCODE_MD(0x41, "XY", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0x42, "color", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x43, "right", KernelCallStackInstruction, -1, "", "p");
- OPCODE(0x45, "center", KernelCallStackInstruction, 0, "");
- OPCODE(0x47, "left", KernelCallStackInstruction, 0, "");
- OPCODE(0x48, "overhead", KernelCallStackInstruction, 0, "");
- OPCODE(0x4A, "mumble", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x4B, "msg", KernelCallStackInstruction, 0, "c", "s");
- OPCODE(0xFE, "begin", KernelCallStackInstruction, 0, "");
- OPCODE(0xFF, "end", KernelCallStackInstruction, 0, "");
- END_SUBOPCODE;
- START_SUBOPCODE_WITH_PREFIX(0xB5, "printText");
- OPCODE_MD(0x41, "XY", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0x42, "color", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x43, "right", KernelCallStackInstruction, -1, "", "p");
- OPCODE(0x45, "center", KernelCallStackInstruction, 0, "");
- OPCODE(0x47, "left", KernelCallStackInstruction, 0, "");
- OPCODE(0x48, "overhead", KernelCallStackInstruction, 0, "");
- OPCODE(0x4A, "mumble", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x4B, "msg", KernelCallStackInstruction, 0, "c", "s");
- OPCODE(0xFE, "begin", KernelCallStackInstruction, 0, "");
- OPCODE(0xFF, "end", KernelCallStackInstruction, 0, "");
- END_SUBOPCODE;
- START_SUBOPCODE_WITH_PREFIX(0xB6, "printDebug");
- OPCODE_MD(0x41, "XY", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0x42, "color", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x43, "right", KernelCallStackInstruction, -1, "", "p");
- OPCODE(0x45, "center", KernelCallStackInstruction, 0, "");
- OPCODE(0x47, "left", KernelCallStackInstruction, 0, "");
- OPCODE(0x48, "overhead", KernelCallStackInstruction, 0, "");
- OPCODE(0x4A, "mumble", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x4B, "msg", KernelCallStackInstruction, 0, "c", "s");
- OPCODE(0xFE, "begin", KernelCallStackInstruction, 0, "");
- OPCODE(0xFF, "end", KernelCallStackInstruction, 0, "");
- END_SUBOPCODE;
- START_SUBOPCODE_WITH_PREFIX(0xB7, "printSystem");
- OPCODE_MD(0x41, "XY", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0x42, "color", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x43, "right", KernelCallStackInstruction, -1, "", "p");
- OPCODE(0x45, "center", KernelCallStackInstruction, 0, "");
- OPCODE(0x47, "left", KernelCallStackInstruction, 0, "");
- OPCODE(0x48, "overhead", KernelCallStackInstruction, 0, "");
- OPCODE(0x4A, "mumble", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x4B, "msg", KernelCallStackInstruction, 0, "c", "s");
- OPCODE(0xFE, "begin", KernelCallStackInstruction, 0, "");
- OPCODE(0xFF, "end", KernelCallStackInstruction, 0, "");
- END_SUBOPCODE;
- START_SUBOPCODE_WITH_PREFIX(0xB8, "printActor");
- OPCODE_MD(0x41, "XY", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0x42, "color", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x43, "right", KernelCallStackInstruction, -1, "", "p");
- OPCODE(0x45, "center", KernelCallStackInstruction, 0, "");
- OPCODE(0x47, "left", KernelCallStackInstruction, 0, "");
- OPCODE(0x48, "overhead", KernelCallStackInstruction, 0, "");
- OPCODE(0x4A, "mumble", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x4B, "msg", KernelCallStackInstruction, 0, "c", "s");
- OPCODE_MD(0xFE, "begin", KernelCallStackInstruction, -1, "", "p");
- OPCODE(0xFF, "end", KernelCallStackInstruction, 0, "");
- END_SUBOPCODE;
- START_SUBOPCODE_WITH_PREFIX(0xB9, "printEgo");
- OPCODE_MD(0x41, "XY", KernelCallStackInstruction, -2, "", "pp");
- OPCODE_MD(0x42, "color", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0x43, "right", KernelCallStackInstruction, -1, "", "p");
- OPCODE(0x45, "center", KernelCallStackInstruction, 0, "");
- OPCODE(0x47, "left", KernelCallStackInstruction, 0, "");
- OPCODE(0x48, "overhead", KernelCallStackInstruction, 0, "");
- OPCODE(0x4A, "mumble", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0x4B, "msg", KernelCallStackInstruction, 0, "c", "s");
- OPCODE(0xFE, "begin", KernelCallStackInstruction, 0, "");
- OPCODE(0xFF, "end", KernelCallStackInstruction, 0, "");
- END_SUBOPCODE;
- OPCODE_MD(0xBA, "talkActor", KernelCallStackInstruction, -1, "c", "ps");
- OPCODE_MD(0xBB, "talkEgo", KernelCallStackInstruction, 0, "c", "s");
- START_SUBOPCODE(0xBC); // dimArray
- OPCODE_MD(0xC7, "dimArrayInt", KernelCallStackInstruction, -1, "w", "pv");
- OPCODE_MD(0xC8, "dimArrayBit", KernelCallStackInstruction, -1, "w", "pv");
- OPCODE_MD(0xC9, "dimArrayNibble", KernelCallStackInstruction, -1, "w", "pv");
- OPCODE_MD(0xCA, "dimArrayByte", KernelCallStackInstruction, -1, "w", "pv");
- OPCODE_MD(0xCB, "dimArrayString", KernelCallStackInstruction, -1, "w", "pv");
- OPCODE_MD(0xCC, "dimArray_nukeArray", KernelCallStackInstruction, 0, "w", "v");
- END_SUBOPCODE;
- OPCODE_MD(0xBE, "startObjectQuick", KernelCallStackInstruction, 0x1020, "", "lpp"); // Variable stack arguments
- OPCODE_MD(0xBF, "startScriptQuick2", KernelCallStackInstruction, 0x1010, "", "lp"); // Variable stack arguments
- START_SUBOPCODE(0xC0); // dim2DimArray
- OPCODE_MD(0xC7, "dim2DimArrayInt", KernelCallStackInstruction, -2, "w", "ppv");
- OPCODE_MD(0xC8, "dim2DimArrayBit", KernelCallStackInstruction, -2, "w", "ppv");
- OPCODE_MD(0xC9, "dim2DimArrayNibble", KernelCallStackInstruction, -2, "w", "ppv");
- OPCODE_MD(0xCA, "dim2DimArrayByte", KernelCallStackInstruction, -2, "w", "ppv");
- OPCODE_MD(0xCB, "dim2DimArrayString", KernelCallStackInstruction, -2, "w", "ppv");
- END_SUBOPCODE;
- OPCODE_MD(0xC4, "abs", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0xC5, "getDistObjObj", KernelCallStackInstruction, -1, "", "rpp");
- OPCODE_MD(0xC6, "getDistObjPt", KernelCallStackInstruction, -2, "", "rppp");
- OPCODE_MD(0xC7, "getDistPtPt", KernelCallStackInstruction, -3, "", "rpppp");
- OPCODE_MD(0xC8, "kernelGetFunctions", KernelCallStackInstruction, 0x1000, "", "l"); // Variable stack arguments
- OPCODE_MD(0xC9, "kernelSetFunctions", KernelCallStackInstruction, 0x1000, "", "l"); // Variable stack arguments
- OPCODE_MD(0xCA, "delayFrames", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0xCB, "pickOneOf", KernelCallStackInstruction, 0x1011, "", "rlp"); // Variable stack arguments
- OPCODE_MD(0xCC, "pickOneOfDefault", KernelCallStackInstruction, 0x111, "", "rplp"); // Variable stack arguments
- OPCODE_MD(0xCD, "stampObject", KernelCallStackInstruction, -4, "", "pppp");
- OPCODE(0xD0, "getDateTime", KernelCallStackInstruction, 0, "");
- OPCODE(0xD1, "stopTalking", KernelCallStackInstruction, 0, "");
- OPCODE_MD(0xD2, "getAnimateVariable", KernelCallStackInstruction, -1, "", "rpp");
- OPCODE_MD(0xD4, "shuffle", KernelCallStackInstruction, -2, "w", "vpp");
- OPCODE_MD(0xD5, "jumpToScript", KernelCallStackInstruction, 0x1020, "", "lpp"); // Variable stack arguments
- OPCODE_MD(0xD6, "band", BinaryOpStackInstruction, -1, "", "&");
- OPCODE_MD(0xD7, "bor", BinaryOpStackInstruction, -1, "", "|");
- OPCODE_MD(0xD8, "isRoomScriptRunning", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0xDD, "findAllObjects", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0xE1, "getPixel", KernelCallStackInstruction, -1, "", "rpp");
- OPCODE_MD(0xE3, "pickVarRandom", KernelCallStackInstruction, 0x1001, "w", "rlw"); // Variable stack arguments
- OPCODE_MD(0xE4, "setBoxSet", KernelCallStackInstruction, -1, "", "p");
- OPCODE_MD(0xEC, "getActorLayer", KernelCallStackInstruction, 0, "", "rp");
- OPCODE_MD(0xED, "getObjectNewDir", KernelCallStackInstruction, 0, "", "rp");
- END_OPCODES;
- InstIterator it;
- for (it = _insts.begin(); it != _insts.end(); ++it)
- if ((*it)->_stackChange >= 0x1000)
- fixStackEffect(it, ((*it)->_stackChange >> 8) & 0xF, ((*it)->_stackChange >> 4) & 0xF, (*it)->_stackChange & 0xF);
- }
- void Scumm::v6::Scummv6Disassembler::fixStackEffect(InstIterator &it, int popBefore, int popAfter, int pushTotal) {
- (*it)->_stackChange = static_cast<int16>(-popBefore - popAfter + pushTotal);
- InstIterator it2 = it;
- for (--it2; popBefore != 0; --it2)
- if ((*it2)->isLoad())
- --popBefore;
- (*it)->_stackChange -= static_cast<int16>((*it2)->_params[0]->getSigned() + 1);
- }
- ValuePtr Scumm::v6::Scummv6Disassembler::readParameter(InstPtr inst, std::string type) {
- ValuePtr retval = NULL;
- assert(type.length() == 1);
- switch (type.at(0)) {
- case 'a':
- retval = new RelAddressValue(inst->_address + 3, mStream->ReadS16());
- _address += 2;
- break;
- case 'c': { // Character string
- byte cmd;
- bool inStr = false;
- std::stringstream s;
- while ((cmd = mStream->ReadU8()) != 0) {
- if (cmd == 0xFF || cmd == 0xFE) {
- if (inStr) {
- s << '"';
- inStr = false;
- }
- cmd = mStream->ReadU8();
- switch (cmd) {
- case 1:
- s << ":newline:";
- _address += 2;
- break;
- case 2:
- s << ":keeptext:";
- _address += 2;
- break;
- case 3:
- s << ":wait:";
- _address += 2;
- break;
- case 4: // addIntToStack
- case 5: // addVerbToStack
- case 6: // addNameToStack
- case 7: { // addStringToStack
- uint16 var = mStream->ReadU16();
- // TODO: Clean output similar to descumm
- s << ":addToStack=" << var << ":";
- _address += 4;
- }
- break;
- case 9:
- s << ":startanim=" << mStream->ReadU16() << ":";
- _address += 4;
- break;
- case 10:
- s << ":sound:";
- mStream->Seek(14);
- _address += 16;
- break;
- case 12:
- s << ":setcolor=" << mStream->ReadU16() << ":";
- _address += 4;
- break;
- case 13:
- s << ":unk2=" << mStream->ReadU16() << ":";
- _address += 4;
- break;
- case 14:
- s << ":setfont=" << mStream->ReadU16() << ":";
- _address += 4;
- break;
- default:
- s << ":unk" << cmd << "=" << mStream->ReadU16() << ":";
- _address += 4;
- break;
- }
- } else {
- if (!inStr) {
- s << '"';
- inStr = true;
- }
- s << cmd;
- _address++;
- }
- }
- _address++;
- if (inStr)
- s << '"';
- retval = new Scummv6StringValue(s.str());
- }
- break;
- default: // Defer handling to parent implementation
- retval = SimpleDisassembler::readParameter(inst, type);
- break;
- }
- return retval;
- }
|