#include <stdarg.h>
/* common */
+#include "xmalloc.h"
#include "xsprintf.h"
/* da65 */
+static unsigned short SubroutineParamSize[0x10000];
+
/*****************************************************************************/
/* Helper functions */
/*****************************************************************************/
+void OH_ImmediateWord (const OpcDesc* D)
+{
+ OneLine (D, "#$%04X", GetCodeWord (PC+1));
+}
+
+
+
void OH_Direct (const OpcDesc* D)
{
/* Get the operand */
+void OH_RelativeLong4510 (const OpcDesc* D attribute ((unused)))
+{
+ /* Get the operand */
+ signed short Offs = GetCodeWord (PC+1);
+
+ /* Calculate the target address */
+ unsigned Addr = (((int) PC+2) + Offs) & 0xFFFF;
+
+ /* Generate a label in pass 1 */
+ GenerateLabel (D->Flags, Addr);
+
+ /* Output the line */
+ OneLine (D, "%s", GetAddrArg (D->Flags, Addr));
+}
+
+
+
void OH_DirectIndirect (const OpcDesc* D)
{
/* Get the operand */
+void OH_DirectIndirectZ (const OpcDesc* D)
+{
+ /* Get the operand */
+ unsigned Addr = GetCodeByte (PC+1);
+
+ /* Generate a label in pass 1 */
+ GenerateLabel (D->Flags, Addr);
+
+ /* Output the line */
+ OneLine (D, "(%s),z", GetAddrArg (D->Flags, Addr));
+}
+
+
+
void OH_DirectXIndirect (const OpcDesc* D)
{
/* Get the operand */
void OH_BitBranch (const OpcDesc* D)
{
+ char* BranchLabel;
+
/* Get the operands */
unsigned char TestAddr = GetCodeByte (PC+1);
signed char BranchOffs = GetCodeByte (PC+2);
GenerateLabel (D->Flags, TestAddr);
GenerateLabel (flLabel, BranchAddr);
+ /* Make a copy of an operand, so that
+ ** the other operand can't overwrite it.
+ ** [GetAddrArg() uses a statically-stored buffer.]
+ */
+ BranchLabel = xstrdup (GetAddrArg (flLabel, BranchAddr));
+
/* Output the line */
- OneLine (D, "%s,%s", GetAddrArg (D->Flags, TestAddr), GetAddrArg (flLabel, BranchAddr));
+ OneLine (D, "%s,%s", GetAddrArg (D->Flags, TestAddr), BranchLabel);
+
+ xfree (BranchLabel);
}
void OH_StackRelativeIndirectY (const OpcDesc* D attribute ((unused)))
{
- Error ("Not implemented");
+ /* Output the line */
+ OneLine (D, "($%02X,s),y", GetCodeByte (PC+1));
+}
+
+
+
+void OH_StackRelativeIndirectY4510 (const OpcDesc* D attribute ((unused)))
+{
+ /* Output the line */
+ OneLine (D, "($%02X,sp),y", GetCodeByte (PC+1));
}
-void OH_BlockMove (const OpcDesc* D attribute ((unused)))
+void OH_BlockMove (const OpcDesc* D)
{
+ char* DstLabel;
+
/* Get source operand */
unsigned Src = GetCodeWord (PC+1);
/* Get destination operand */
GenerateLabel (D->Flags, Src);
GenerateLabel (D->Flags, Dst);
+ /* Make a copy of an operand, so that
+ ** the other operand can't overwrite it.
+ ** [GetAddrArg() uses a statically-stored buffer.]
+ */
+ DstLabel = xstrdup (GetAddrArg (D->Flags, Dst));
+
/* Output the line */
- OneLine (D, "%s%s,%s%s,#$%02X",
+ OneLine (D, "%s%s,%s%s,$%04X",
GetAbsOverride (D->Flags, Src), GetAddrArg (D->Flags, Src),
- GetAbsOverride (D->Flags, Dst), GetAddrArg (D->Flags, Dst),
+ GetAbsOverride (D->Flags, Dst), DstLabel,
GetCodeWord (PC+5));
+
+ xfree (DstLabel);
}
}
SeparatorLine ();
}
+
+
+
+void OH_JmpAbsoluteXIndirect (const OpcDesc* D)
+{
+ OH_AbsoluteXIndirect (D);
+ if (NewlineAfterJMP) {
+ LineFeed ();
+ }
+ SeparatorLine ();
+}
+
+
+
+void OH_JsrAbsolute (const OpcDesc* D)
+{
+ unsigned ParamSize = SubroutineParamSize[GetCodeWord (PC+1)];
+ OH_Absolute (D);
+ if (ParamSize > 0) {
+ unsigned RemainingBytes;
+ unsigned BytesLeft;
+ PC += D->Size;
+ RemainingBytes = GetRemainingBytes ();
+ if (RemainingBytes < ParamSize) {
+ ParamSize = RemainingBytes;
+ }
+ BytesLeft = ParamSize;
+ while (BytesLeft > 0) {
+ unsigned Chunk = (BytesLeft > BytesPerLine) ? BytesPerLine : BytesLeft;
+ DataByteLine (Chunk);
+ BytesLeft -= Chunk;
+ PC += Chunk;
+ }
+ PC -= D->Size;
+ }
+}
+
+
+
+void SetSubroutineParamSize (unsigned Addr, unsigned Size)
+{
+ SubroutineParamSize[Addr] = Size;
+}