save static method

List<int?> save(
  1. int pcAddr
)

Generates a stream of save bytes in the Quetzal format.

Implementation

static List<int?> save(int pcAddr){
  // bool padByte;

  List<int> saveData = <int>[];

  IFF.writeChunk(saveData, Chunk.form);
  IFF.writeChunk(saveData, Chunk.ifzs);

  //associated story file
  IFF.writeChunk(saveData, Chunk.ifhd);
  IFF.write4Byte(saveData, 13);
  IFF.write2Byte(saveData, Z.engine.mem.loadw(Header.release));
  IFF.write2Byte(saveData, Z.engine.mem.loadw(Header.serialNumber));
  IFF.write2Byte(saveData, Z.engine.mem.loadw(Header.serialNumber + 2));
  IFF.write2Byte(saveData, Z.engine.mem.loadw(Header.serialNumber + 4));
  IFF.write2Byte(saveData, Z.engine.mem.loadw(Header.checkSumOfFile));
  //pc
  IFF.write3Byte(saveData, pcAddr); //varies depending on version.
  saveData.add(0); //pad byte

  //uncompressed memory
  IFF.writeChunk(saveData, Chunk.umem);

  //IFF.write length in bytes
  IFF.write4Byte(saveData, Z.engine.mem.memList.length);

  saveData.addAll(Z.engine.mem.memList);

  if (Z.engine.mem.memList.length % 2 != 0){
    saveData.add(0); //pad byte
  }

  //stacks, oldest first
  IFF.writeChunk(saveData, Chunk.stks);

  var stackData = Queue<StackFrame>();

  stackData.addFirst(StackFrame(0,0));

  while(stackData.first.nextCallStackIndex != null){
    stackData.addFirst(StackFrame(stackData.first.nextCallStackIndex!, stackData.first.nextEvalStackIndex));
  }

  var totalStackBytes = 0;
  for(final sd in stackData){
    totalStackBytes += sd.computedByteSize;
  }

  IFF.write4Byte(saveData, totalStackBytes);

  for(StackFrame sd in stackData){
    IFF.write3Byte(saveData, sd.returnAddr);


    //flags byte
    var flagByte = 0;

    //set the call_xN bit if this stack frame is supposed to discard returns
    if (sd.returnVar == Engine.stackMarker){
      flagByte = BinaryHelper.set(flagByte, 4);
    }

    //using the first 4 bits, we set the number of locals... (not standard, but permissible)
    flagByte |= sd.locals.length;

    saveData.add(flagByte);

    // return variable number
    // (ref 4.6)
    saveData.add(sd.returnVar != Engine.stackMarker ? sd.returnVar : 0);

    //total args passed (4.3.4)
    saveData.add(BinaryHelper.setBottomBits(sd.totalArgsPassed));

    IFF.write2Byte(saveData, sd.evals.length);

    for(int? l in sd.locals){
      IFF.write2Byte(saveData, l!);
    }

    for(int? e in sd.evals){
      IFF.write2Byte(saveData, e!);
    }
  }

  if (totalStackBytes % 2 != 0) {
    saveData.add(0);
  } //pad byte

  return saveData;
}