aboutsummaryrefslogtreecommitdiff
path: root/engines
diff options
context:
space:
mode:
Diffstat (limited to 'engines')
-rw-r--r--engines/sci/console.cpp14
-rw-r--r--engines/sci/console.h2
-rw-r--r--engines/sci/engine/script.cpp4
-rw-r--r--engines/sci/engine/script.h2
-rw-r--r--engines/sci/engine/scriptdebug.cpp4
-rw-r--r--engines/sci/engine/vm.cpp15
-rw-r--r--engines/sci/engine/vm.h4
-rw-r--r--engines/sci/engine/vm_types.h43
8 files changed, 69 insertions, 19 deletions
diff --git a/engines/sci/console.cpp b/engines/sci/console.cpp
index b0ed7e6225..40a6fd1415 100644
--- a/engines/sci/console.cpp
+++ b/engines/sci/console.cpp
@@ -2913,7 +2913,8 @@ bool Console::cmdDisassemble(int argc, const char **argv) {
if (jumpTarget > farthestTarget)
farthestTarget = jumpTarget;
}
- addr = disassemble(_engine->_gamestate, addr, printBWTag, printBytecode);
+ // TODO: Use a true 32-bit reg_t for the position (addr)
+ addr = disassemble(_engine->_gamestate, make_reg32(addr.getSegment(), addr.getOffset()), printBWTag, printBytecode);
if (addr.isNull() && prevAddr < farthestTarget)
addr = prevAddr + 1; // skip past the ret
} while (addr.getOffset() > 0);
@@ -2961,7 +2962,8 @@ bool Console::cmdDisassembleAddress(int argc, const char **argv) {
}
do {
- vpc = disassemble(_engine->_gamestate, vpc, printBWTag, printBytes);
+ // TODO: Use a true 32-bit reg_t for the position (vpc)
+ vpc = disassemble(_engine->_gamestate, make_reg32(vpc.getSegment(), vpc.getOffset()), printBWTag, printBytes);
} while ((vpc.getOffset() > 0) && (vpc.getOffset() + 6 < size) && (--opCount));
return true;
@@ -3652,10 +3654,14 @@ static int parse_reg_t(EngineState *s, const char *str, reg_t *dest, bool mayBeV
relativeOffset = true;
if (!scumm_strnicmp(str + 1, "PC", 2)) {
- *dest = s->_executionStack.back().addr.pc;
+ // TODO: Handle 32-bit PC addresses
+ reg32_t pc = s->_executionStack.back().addr.pc;
+ *dest = make_reg(pc.getSegment(), (uint16)pc.getOffset());
offsetStr = str + 3;
} else if (!scumm_strnicmp(str + 1, "P", 1)) {
- *dest = s->_executionStack.back().addr.pc;
+ // TODO: Handle 32-bit PC addresses
+ reg32_t pc = s->_executionStack.back().addr.pc;
+ *dest = make_reg(pc.getSegment(), (uint16)pc.getOffset());
offsetStr = str + 2;
} else if (!scumm_strnicmp(str + 1, "PREV", 4)) {
*dest = s->r_prev;
diff --git a/engines/sci/console.h b/engines/sci/console.h
index be17fdb728..1c54748842 100644
--- a/engines/sci/console.h
+++ b/engines/sci/console.h
@@ -33,7 +33,7 @@ namespace Sci {
class SciEngine;
struct List;
-reg_t disassemble(EngineState *s, reg_t pos, bool printBWTag, bool printBytecode);
+reg_t disassemble(EngineState *s, reg32_t pos, bool printBWTag, bool printBytecode);
bool isJumpOpcode(EngineState *s, reg_t pos, reg_t& jumpOffset);
class Console : public GUI::Debugger {
diff --git a/engines/sci/engine/script.cpp b/engines/sci/engine/script.cpp
index 80aaedfece..57334b89aa 100644
--- a/engines/sci/engine/script.cpp
+++ b/engines/sci/engine/script.cpp
@@ -385,7 +385,7 @@ void Script::setLockers(int lockers) {
_lockers = lockers;
}
-uint16 Script::validateExportFunc(int pubfunct, bool relocateSci3) {
+uint32 Script::validateExportFunc(int pubfunct, bool relocateSci3) {
bool exportsAreWide = (g_sci->_features->detectLofsType() == SCI_VERSION_1_MIDDLE);
if (_numExports <= pubfunct) {
@@ -396,7 +396,7 @@ uint16 Script::validateExportFunc(int pubfunct, bool relocateSci3) {
if (exportsAreWide)
pubfunct *= 2;
- uint16 offset;
+ uint32 offset;
if (getSciVersion() != SCI_VERSION_3) {
offset = READ_SCI11ENDIAN_UINT16(_exportTable + pubfunct);
diff --git a/engines/sci/engine/script.h b/engines/sci/engine/script.h
index 9747f072c5..1fc8caf313 100644
--- a/engines/sci/engine/script.h
+++ b/engines/sci/engine/script.h
@@ -201,7 +201,7 @@ public:
* @return NULL if the public function is invalid, its
* offset into the script's segment otherwise
*/
- uint16 validateExportFunc(int pubfunct, bool relocateSci3);
+ uint32 validateExportFunc(int pubfunct, bool relocateSci3);
/**
* Marks the script as deleted.
diff --git a/engines/sci/engine/scriptdebug.cpp b/engines/sci/engine/scriptdebug.cpp
index 04cbf1d97c..d3abb9ff41 100644
--- a/engines/sci/engine/scriptdebug.cpp
+++ b/engines/sci/engine/scriptdebug.cpp
@@ -68,7 +68,7 @@ const char *opcodeNames[] = {
#endif // REDUCE_MEMORY_USAGE
// Disassembles one command from the heap, returns address of next command or 0 if a ret was encountered.
-reg_t disassemble(EngineState *s, reg_t pos, bool printBWTag, bool printBytecode) {
+reg_t disassemble(EngineState *s, reg32_t pos, bool printBWTag, bool printBytecode) {
SegmentObj *mobj = s->_segMan->getSegment(pos.getSegment(), SEG_TYPE_SCRIPT);
Script *script_entity = NULL;
const byte *scr;
@@ -347,7 +347,7 @@ void SciEngine::scriptDebug() {
}
if (_debugState.seeking != kDebugSeekNothing) {
- const reg_t pc = s->xs->addr.pc;
+ const reg32_t pc = s->xs->addr.pc;
SegmentObj *mobj = s->_segMan->getSegment(pc.getSegment(), SEG_TYPE_SCRIPT);
if (mobj) {
diff --git a/engines/sci/engine/vm.cpp b/engines/sci/engine/vm.cpp
index a42606a6a6..5a2a39def2 100644
--- a/engines/sci/engine/vm.cpp
+++ b/engines/sci/engine/vm.cpp
@@ -233,7 +233,7 @@ ExecStack *execute_method(EngineState *s, uint16 script, uint16 pubfunct, StackP
g_sci->checkExportBreakpoint(script, pubfunct);
ExecStack xstack(calling_obj, calling_obj, sp, argc, argp,
- seg, make_reg(seg, exportAddr), -1, pubfunct, -1,
+ seg, make_reg32(seg, exportAddr), -1, pubfunct, -1,
s->_executionStack.size() - 1, EXEC_STACK_TYPE_CALL);
s->_executionStack.push_back(xstack);
return &(s->_executionStack.back());
@@ -289,11 +289,12 @@ ExecStack *send_selector(EngineState *s, reg_t send_obj, reg_t work_obj, StackPt
ExecStackType stackType = EXEC_STACK_TYPE_VARSELECTOR;
StackPtr curSP = NULL;
- reg_t curFP = NULL_REG;
+ reg32_t curFP = make_reg32(0, 0);
if (selectorType == kSelectorMethod) {
stackType = EXEC_STACK_TYPE_CALL;
curSP = sp;
- curFP = funcp;
+ // TODO: Will this offset suffice for large SCI3 scripts?
+ curFP = make_reg32(funcp.getSegment(), funcp.getOffset());
sp = CALL_SP_CARRY; // Destroy sp, as it will be carried over
}
@@ -327,7 +328,7 @@ static void addKernelCallToExecStack(EngineState *s, int kernelCallNr, int argc,
// Add stack frame to indicate we're executing a callk.
// This is useful in debugger backtraces if this
// kernel function calls a script itself.
- ExecStack xstack(NULL_REG, NULL_REG, NULL, argc, argv - 1, 0xFFFF, NULL_REG,
+ ExecStack xstack(NULL_REG, NULL_REG, NULL, argc, argv - 1, 0xFFFF, make_reg32(0, 0),
kernelCallNr, -1, -1, s->_executionStack.size() - 1, EXEC_STACK_TYPE_KERNEL);
s->_executionStack.push_back(xstack);
}
@@ -818,11 +819,11 @@ void run_vm(EngineState *s) {
StackPtr call_base = s->xs->sp - argc;
s->xs->sp[1].incOffset(s->r_rest);
- uint16 localCallOffset = s->xs->addr.pc.getOffset() + opparams[0];
+ uint32 localCallOffset = s->xs->addr.pc.getOffset() + opparams[0];
ExecStack xstack(s->xs->objp, s->xs->objp, s->xs->sp,
(call_base->requireUint16()) + s->r_rest, call_base,
- s->xs->local_segment, make_reg(s->xs->addr.pc.getSegment(), localCallOffset),
+ s->xs->local_segment, make_reg32(s->xs->addr.pc.getSegment(), localCallOffset),
NULL_SELECTOR, -1, localCallOffset, s->_executionStack.size() - 1,
EXEC_STACK_TYPE_CALL);
@@ -1117,7 +1118,7 @@ void run_vm(EngineState *s) {
switch (g_sci->_features->detectLofsType()) {
case SCI_VERSION_0_EARLY:
- r_temp.setOffset(s->xs->addr.pc.getOffset() + opparams[0]);
+ r_temp.setOffset((uint16)s->xs->addr.pc.getOffset() + opparams[0]);
break;
case SCI_VERSION_1_MIDDLE:
r_temp.setOffset(opparams[0]);
diff --git a/engines/sci/engine/vm.h b/engines/sci/engine/vm.h
index f2d225b1d8..a0fd6689df 100644
--- a/engines/sci/engine/vm.h
+++ b/engines/sci/engine/vm.h
@@ -82,7 +82,7 @@ struct ExecStack {
union {
ObjVarRef varp; // Variable pointer for r/w access
- reg_t pc; // Pointer to the initial program counter. Not accurate for the TOS element
+ reg32_t pc; // Pointer to the initial program counter. Not accurate for the TOS element
} addr;
StackPtr fp; // Frame pointer
@@ -102,7 +102,7 @@ struct ExecStack {
reg_t* getVarPointer(SegManager *segMan) const;
ExecStack(reg_t objp_, reg_t sendp_, StackPtr sp_, int argc_, StackPtr argp_,
- SegmentId localsSegment_, reg_t pc_, Selector debugSelector_,
+ SegmentId localsSegment_, reg32_t pc_, Selector debugSelector_,
int debugExportId_, int debugLocalCallOffset_, int debugOrigin_,
ExecStackType type_) {
objp = objp_;
diff --git a/engines/sci/engine/vm_types.h b/engines/sci/engine/vm_types.h
index 2995ba3c12..9a7589e9a7 100644
--- a/engines/sci/engine/vm_types.h
+++ b/engines/sci/engine/vm_types.h
@@ -169,6 +169,49 @@ static inline reg_t make_reg(SegmentId segment, uint16 offset) {
#define PRINT_REG(r) (0xffff) & (unsigned) (r).getSegment(), (unsigned) (r).getOffset()
+// A true 32-bit reg_t
+struct reg32_t {
+ // Segment and offset. These should never be accessed directly
+ SegmentId _segment;
+ uint32 _offset;
+
+ inline SegmentId getSegment() const {
+ return _segment;
+ }
+
+ inline void setSegment(SegmentId segment) {
+ _segment = segment;
+ }
+
+ inline uint32 getOffset() const {
+ return _offset;
+ }
+
+ inline void setOffset(uint32 offset) {
+ _offset = offset;
+ }
+
+ inline void incOffset(int32 offset) {
+ setOffset(getOffset() + offset);
+ }
+
+ // Comparison operators
+ bool operator==(const reg32_t &x) const {
+ return (getOffset() == x.getOffset()) && (getSegment() == x.getSegment());
+ }
+
+ bool operator!=(const reg32_t &x) const {
+ return (getOffset() != x.getOffset()) || (getSegment() != x.getSegment());
+ }
+};
+
+static inline reg32_t make_reg32(SegmentId segment, uint32 offset) {
+ reg32_t r;
+ r.setSegment(segment);
+ r.setOffset(offset);
+ return r;
+}
+
// Stack pointer type
typedef reg_t *StackPtr;