Stack Machine Trace
MediumOnline Assessment
Run a program on a tiny stack machine used by a label-printer controller and report exactly how it stopped.
The machine has a data stack of integers (empty at the start), a return stack of addresses, an output list, and a program counter pc starting at 0. program[pc] is executed, one instruction at a time:
PUSH npushesn.POPdiscards the top.DUPpushes a copy of the top.SWAPexchanges the top two values.PRINTpops the top and appends it to the output.ADD,SUB,MUL,LTpopa(the top) and thenb, and pushb + a,b - a,b * a, and1 if b < a else 0respectively.JMP tsetspc = t.JMPZ tpops the top and setspc = tif it was 0, otherwise continues with the next instruction.CALL tpushespc + 1on the return stack and setspc = t.RETpops the return stack intopc; if the return stack is empty,RETends the program normally.HALTends the program normally.
Unless an instruction jumps, pc moves to the next instruction. The program also ends normally when pc reaches len(program).
Errors. The machine stops with an error status, changing nothing for that instruction, in these cases (checked in this order, before the instruction runs):
"timeout":max_stepsinstructions have already run and the program has not ended. (A program that ends normally withinmax_stepsinstructions, withHALT,RETor running off the end, is not a timeout.)"bad-target": aJMP,JMPZorCALLwhose target is not in0..len(program)inclusive, whether or not the jump would be taken."underflow": the data stack has fewer values than the instruction needs (POP,DUP,PRINT,JMPZneed 1;SWAP,ADD,SUB,MUL,LTneed 2)."call-overflow": aCALLwhen the return stack already holds 16 addresses.
Input: program (each instruction is a string such as "PUSH -4" or "JMPZ 8"), max_steps.
Output: [status, output, stack] where status is "halted" for a normal end or one of the error names above, output is everything printed so far, and stack is the data stack from bottom to top when the machine stopped.
Example 1
- Input:
- [["PUSH 3","DUP","PRINT","PUSH 1","SUB","DUP","JMPZ 8","JMP 1","HALT"],100]
- Output:
- ["halted",[3,2,1],[0]]
- Explanation
- The program counts down from 3: it prints the counter, subtracts 1, and DUPs the result for JMPZ to test, which pops the copy. It prints 3, 2, 1, and when the counter reaches 0 the JMPZ jumps to HALT. The stack keeps the 0 and the status is halted.
Example 2
- Input:
- [["PUSH 5","CALL 4","PRINT","HALT","DUP","MUL","RET"],100]
- Output:
- ["halted",[25],[]]
- Explanation
- PUSH 5 then CALL 4 runs the subroutine DUP, MUL (5 * 5 = 25), and RET returns to instruction 2, which prints 25. HALT ends the program with an empty stack.
Example 3
- Input:
- [["PUSH 7","PRINT","PUSH 2","PUSH 3","ADD","ADD","PRINT"],100]
- Output:
- ["underflow",[7],[5]]
- Explanation
- 7 is pushed and printed. Then 2 and 3 are added to make 5. The second ADD needs two values but only one is on the stack, so the machine stops with underflow; the 5 is still there because the failed instruction changed nothing, and the output keeps the 7.
Constraints
- 0 ≤ program.length ≤ 60; every instruction is one of the listed forms with integer operands, -106 ≤ n ≤ 106
- 0 ≤ max_steps ≤ 3000
- Values on the stack never exceed 1015 in absolute value