mirror of
https://github.com/cc65/cc65.git
synced 2025-01-11 11:30:13 +00:00
Working on the new backend
git-svn-id: svn://svn.cc65.org/cc65/trunk@707 b7a2c559-68d2-44c3-8de9-860c34a00d81
This commit is contained in:
parent
8eadb8aee0
commit
8a3bacd7f4
@ -33,6 +33,9 @@
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
/* common */
|
||||||
|
#include "check.h"
|
||||||
|
|
||||||
/* b6502 */
|
/* b6502 */
|
||||||
#include "codeseg.h"
|
#include "codeseg.h"
|
||||||
#include "dataseg.h"
|
#include "dataseg.h"
|
||||||
@ -94,22 +97,23 @@ void WriteOutput (FILE* F)
|
|||||||
SymTable* SymTab;
|
SymTable* SymTab;
|
||||||
SymEntry* Entry;
|
SymEntry* Entry;
|
||||||
|
|
||||||
/* Output the global code and data segments */
|
/* Output the data segment (the global code segment should be empty) */
|
||||||
MergeCodeLabels (CS);
|
|
||||||
OutputDataSeg (F, DS);
|
OutputDataSeg (F, DS);
|
||||||
OutputCodeSeg (F, CS);
|
CHECK (GetCodeSegEntries (CS) == 0);
|
||||||
|
|
||||||
/* Output all global or referenced functions */
|
/* Output all global or referenced functions */
|
||||||
SymTab = GetGlobalSymTab ();
|
SymTab = GetGlobalSymTab ();
|
||||||
Entry = SymTab->SymHead;
|
Entry = SymTab->SymHead;
|
||||||
while (Entry) {
|
while (Entry) {
|
||||||
if (IsTypeFunc (Entry->Type) &&
|
if (IsTypeFunc (Entry->Type) &&
|
||||||
(Entry->Flags & SC_DEF) != 0 &&
|
(Entry->Flags & SC_DEF) != 0 &&
|
||||||
(Entry->Flags & (SC_REF | SC_EXTERN)) != 0) {
|
(Entry->Flags & (SC_REF | SC_EXTERN)) != 0) {
|
||||||
/* Function which is defined and referenced or extern */
|
/* Function which is defined and referenced or extern */
|
||||||
PrintFunctionHeader (F, Entry);
|
PrintFunctionHeader (F, Entry);
|
||||||
MergeCodeLabels (Entry->V.F.CS);
|
MergeCodeLabels (Entry->V.F.CS);
|
||||||
|
fprintf (F, "; Data segment for function %s:\n", Entry->Name);
|
||||||
OutputDataSeg (F, Entry->V.F.DS);
|
OutputDataSeg (F, Entry->V.F.DS);
|
||||||
|
fprintf (F, "; Code segment for function %s:\n", Entry->Name);
|
||||||
OutputCodeSeg (F, Entry->V.F.CS);
|
OutputCodeSeg (F, Entry->V.F.CS);
|
||||||
}
|
}
|
||||||
Entry = Entry->NextSym;
|
Entry = Entry->NextSym;
|
||||||
|
@ -107,7 +107,7 @@ static char* GetLabelName (unsigned flags, unsigned long label, unsigned offs)
|
|||||||
|
|
||||||
case CF_STATIC:
|
case CF_STATIC:
|
||||||
/* Static memory cell */
|
/* Static memory cell */
|
||||||
sprintf (lbuf, "L%04X+%u", (unsigned)(label & 0xFFFF), offs);
|
sprintf (lbuf, "%s+%u", LocalLabelName (label), offs);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case CF_EXTERNAL:
|
case CF_EXTERNAL:
|
||||||
@ -218,14 +218,6 @@ void g_popseg (void)
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
void g_usecode (void)
|
|
||||||
/* Switch to the code segment */
|
|
||||||
{
|
|
||||||
UseSeg (SEG_CODE);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void g_userodata (void)
|
void g_userodata (void)
|
||||||
/* Switch to the read only data segment */
|
/* Switch to the read only data segment */
|
||||||
{
|
{
|
||||||
@ -379,20 +371,24 @@ static unsigned MakeByteOffs (unsigned Flags, unsigned Offs)
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
void g_defloclabel (unsigned label)
|
void g_defcodelabel (unsigned label)
|
||||||
/* Define a local label */
|
/* Define a local code label */
|
||||||
{
|
{
|
||||||
if (CurSeg == SEG_CODE) {
|
AddCodeLabel (CS, LocalLabelName (label));
|
||||||
AddLocCodeLabel (CS, LocalLabelName (label));
|
}
|
||||||
} else {
|
|
||||||
AddDataSegLine (DS, "%s:", LocalLabelName (label));
|
|
||||||
}
|
|
||||||
|
void g_defdatalabel (unsigned label)
|
||||||
|
/* Define a local data label */
|
||||||
|
{
|
||||||
|
AddDataSegLine (DS, "%s:", LocalLabelName (label));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*****************************************************************************/
|
/*****************************************************************************/
|
||||||
/* Functions handling global labels */
|
/* Functions handling global labels */
|
||||||
/*****************************************************************************/
|
/*****************************************************************************/
|
||||||
|
|
||||||
|
|
||||||
@ -400,14 +396,8 @@ void g_defloclabel (unsigned label)
|
|||||||
void g_defgloblabel (const char* Name)
|
void g_defgloblabel (const char* Name)
|
||||||
/* Define a global label with the given name */
|
/* Define a global label with the given name */
|
||||||
{
|
{
|
||||||
if (CurSeg == SEG_CODE) {
|
/* Global labels are always data labels */
|
||||||
/* ##### */
|
AddDataSegLine (DS, "_%s:", Name);
|
||||||
char Buf[64];
|
|
||||||
xsprintf (Buf, sizeof (Buf), "_%s", Name);
|
|
||||||
AddExtCodeLabel (CS, Buf);
|
|
||||||
} else {
|
|
||||||
AddDataSegLine (DS, "_%s:", Name);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -597,12 +587,12 @@ void g_save_regvars (int RegOffs, unsigned Bytes)
|
|||||||
g_space (Bytes);
|
g_space (Bytes);
|
||||||
ldyconst (Bytes - 1);
|
ldyconst (Bytes - 1);
|
||||||
ldxconst (Bytes);
|
ldxconst (Bytes);
|
||||||
g_defloclabel (Label);
|
g_defcodelabel (Label);
|
||||||
AddCodeSegLine (CS, "lda regbank%+d,x", RegOffs-1);
|
AddCodeSegLine (CS, "lda regbank%+d,x", RegOffs-1);
|
||||||
AddCodeSegLine (CS, "sta (sp),y");
|
AddCodeSegLine (CS, "sta (sp),y");
|
||||||
AddCodeSegLine (CS, "dey");
|
AddCodeSegLine (CS, "dey");
|
||||||
AddCodeSegLine (CS, "dex");
|
AddCodeSegLine (CS, "dex");
|
||||||
AddCodeSegLine (CS, "bne L%04X", Label);
|
AddCodeSegLine (CS, "bne %s", LocalLabelName (Label));
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -641,12 +631,12 @@ void g_restore_regvars (int StackOffs, int RegOffs, unsigned Bytes)
|
|||||||
unsigned Label = GetLocalLabel ();
|
unsigned Label = GetLocalLabel ();
|
||||||
ldyconst (StackOffs+Bytes-1);
|
ldyconst (StackOffs+Bytes-1);
|
||||||
ldxconst (Bytes);
|
ldxconst (Bytes);
|
||||||
g_defloclabel (Label);
|
g_defcodelabel (Label);
|
||||||
AddCodeSegLine (CS, "lda (sp),y");
|
AddCodeSegLine (CS, "lda (sp),y");
|
||||||
AddCodeSegLine (CS, "sta regbank%+d,x", RegOffs-1);
|
AddCodeSegLine (CS, "sta regbank%+d,x", RegOffs-1);
|
||||||
AddCodeSegLine (CS, "dey");
|
AddCodeSegLine (CS, "dey");
|
||||||
AddCodeSegLine (CS, "dex");
|
AddCodeSegLine (CS, "dex");
|
||||||
AddCodeSegLine (CS, "bne L%04X", Label);
|
AddCodeSegLine (CS, "bne %s", LocalLabelName (Label));
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1706,11 +1696,11 @@ void g_addeqstatic (unsigned flags, unsigned long label, unsigned offs,
|
|||||||
case CF_INT:
|
case CF_INT:
|
||||||
if (flags & CF_CONST) {
|
if (flags & CF_CONST) {
|
||||||
if (val == 1) {
|
if (val == 1) {
|
||||||
label = GetLocalLabel ();
|
unsigned L = GetLocalLabel ();
|
||||||
AddCodeSegLine (CS, "inc %s", lbuf);
|
AddCodeSegLine (CS, "inc %s", lbuf);
|
||||||
AddCodeSegLine (CS, "bne L%04X", (int)label);
|
AddCodeSegLine (CS, "bne %s", LocalLabelName (L));
|
||||||
AddCodeSegLine (CS, "inc %s+1", lbuf);
|
AddCodeSegLine (CS, "inc %s+1", lbuf);
|
||||||
g_defloclabel (label);
|
g_defcodelabel (L);
|
||||||
AddCodeSegLine (CS, "lda %s", lbuf); /* Hmmm... */
|
AddCodeSegLine (CS, "lda %s", lbuf); /* Hmmm... */
|
||||||
AddCodeSegLine (CS, "ldx %s+1", lbuf);
|
AddCodeSegLine (CS, "ldx %s+1", lbuf);
|
||||||
} else {
|
} else {
|
||||||
@ -1719,10 +1709,10 @@ void g_addeqstatic (unsigned flags, unsigned long label, unsigned offs,
|
|||||||
AddCodeSegLine (CS, "adc %s", lbuf);
|
AddCodeSegLine (CS, "adc %s", lbuf);
|
||||||
AddCodeSegLine (CS, "sta %s", lbuf);
|
AddCodeSegLine (CS, "sta %s", lbuf);
|
||||||
if (val < 0x100) {
|
if (val < 0x100) {
|
||||||
label = GetLocalLabel ();
|
unsigned L = GetLocalLabel ();
|
||||||
AddCodeSegLine (CS, "bcc L%04X", (int)label);
|
AddCodeSegLine (CS, "bcc %s", LocalLabelName (L));
|
||||||
AddCodeSegLine (CS, "inc %s+1", lbuf);
|
AddCodeSegLine (CS, "inc %s+1", lbuf);
|
||||||
g_defloclabel (label);
|
g_defcodelabel (L);
|
||||||
AddCodeSegLine (CS, "ldx %s+1", lbuf);
|
AddCodeSegLine (CS, "ldx %s+1", lbuf);
|
||||||
} else {
|
} else {
|
||||||
AddCodeSegLine (CS, "lda #$%02X", (unsigned char)(val >> 8));
|
AddCodeSegLine (CS, "lda #$%02X", (unsigned char)(val >> 8));
|
||||||
@ -1967,10 +1957,10 @@ void g_subeqstatic (unsigned flags, unsigned long label, unsigned offs,
|
|||||||
AddCodeSegLine (CS, "sbc #$%02X", (unsigned char)val);
|
AddCodeSegLine (CS, "sbc #$%02X", (unsigned char)val);
|
||||||
AddCodeSegLine (CS, "sta %s", lbuf);
|
AddCodeSegLine (CS, "sta %s", lbuf);
|
||||||
if (val < 0x100) {
|
if (val < 0x100) {
|
||||||
label = GetLocalLabel ();
|
unsigned L = GetLocalLabel ();
|
||||||
AddCodeSegLine (CS, "bcs L%04X", (unsigned)label);
|
AddCodeSegLine (CS, "bcs %s", LocalLabelName (L));
|
||||||
AddCodeSegLine (CS, "dec %s+1", lbuf);
|
AddCodeSegLine (CS, "dec %s+1", lbuf);
|
||||||
g_defloclabel (label);
|
g_defcodelabel (L);
|
||||||
AddCodeSegLine (CS, "ldx %s+1", lbuf);
|
AddCodeSegLine (CS, "ldx %s+1", lbuf);
|
||||||
} else {
|
} else {
|
||||||
AddCodeSegLine (CS, "lda %s+1", lbuf);
|
AddCodeSegLine (CS, "lda %s+1", lbuf);
|
||||||
@ -2243,7 +2233,7 @@ void g_save (unsigned flags)
|
|||||||
|
|
||||||
|
|
||||||
void g_restore (unsigned flags)
|
void g_restore (unsigned flags)
|
||||||
/* Copy hold register to P. */
|
/* Copy hold register to primary. */
|
||||||
{
|
{
|
||||||
/* Check the size and determine operation */
|
/* Check the size and determine operation */
|
||||||
switch (flags & CF_TYPE) {
|
switch (flags & CF_TYPE) {
|
||||||
@ -2360,7 +2350,7 @@ static void oper (unsigned flags, unsigned long val, char** subs)
|
|||||||
|
|
||||||
|
|
||||||
void g_test (unsigned flags)
|
void g_test (unsigned flags)
|
||||||
/* Force a test to set cond codes right */
|
/* Test the value in the primary and set the condition codes */
|
||||||
{
|
{
|
||||||
switch (flags & CF_TYPE) {
|
switch (flags & CF_TYPE) {
|
||||||
|
|
||||||
@ -2519,7 +2509,7 @@ void g_callind (unsigned Flags, unsigned ArgSize)
|
|||||||
void g_jump (unsigned Label)
|
void g_jump (unsigned Label)
|
||||||
/* Jump to specified internal label number */
|
/* Jump to specified internal label number */
|
||||||
{
|
{
|
||||||
AddCodeSegLine (CS, "jmp L%04X", Label);
|
AddCodeSegLine (CS, "jmp %s", LocalLabelName (Label));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -2553,14 +2543,14 @@ void g_case (unsigned flags, unsigned label, unsigned long val)
|
|||||||
|
|
||||||
case CF_CHAR:
|
case CF_CHAR:
|
||||||
case CF_INT:
|
case CF_INT:
|
||||||
AddCodeSegLine (CS, ".word $%04X, L%04X",
|
AddCodeSegLine (CS, ".word $%04X, %s",
|
||||||
(unsigned)(val & 0xFFFF),
|
(unsigned)(val & 0xFFFF),
|
||||||
(unsigned)(label & 0xFFFF));
|
LocalLabelName (label));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case CF_LONG:
|
case CF_LONG:
|
||||||
AddCodeSegLine (CS, ".dword $%08lX", val);
|
AddCodeSegLine (CS, ".dword $%08lX", val);
|
||||||
AddCodeSegLine (CS, ".word L%04X", label & 0xFFFF);
|
AddCodeSegLine (CS, ".word %s", LocalLabelName (label));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
@ -2574,11 +2564,7 @@ void g_case (unsigned flags, unsigned label, unsigned long val)
|
|||||||
void g_truejump (unsigned flags, unsigned label)
|
void g_truejump (unsigned flags, unsigned label)
|
||||||
/* Jump to label if zero flag clear */
|
/* Jump to label if zero flag clear */
|
||||||
{
|
{
|
||||||
if (flags & CF_SHORT) {
|
AddCodeSegLine (CS, "jne %s", LocalLabelName (label));
|
||||||
AddCodeSegLine (CS, "bne L%04X", label);
|
|
||||||
} else {
|
|
||||||
AddCodeSegLine (CS, "jne L%04X", label);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -2586,11 +2572,7 @@ void g_truejump (unsigned flags, unsigned label)
|
|||||||
void g_falsejump (unsigned flags, unsigned label)
|
void g_falsejump (unsigned flags, unsigned label)
|
||||||
/* Jump to label if zero flag set */
|
/* Jump to label if zero flag set */
|
||||||
{
|
{
|
||||||
if (flags & CF_SHORT) {
|
AddCodeSegLine (CS, "jeq %s", LocalLabelName (label));
|
||||||
AddCodeSegLine (CS, "beq L%04X", label);
|
|
||||||
} else {
|
|
||||||
AddCodeSegLine (CS, "jeq L%04X", label);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -3970,10 +3952,10 @@ void g_strlen (unsigned flags, unsigned long val, unsigned offs)
|
|||||||
|
|
||||||
/* Generate the strlen code */
|
/* Generate the strlen code */
|
||||||
AddCodeSegLine (CS, "ldy #$FF");
|
AddCodeSegLine (CS, "ldy #$FF");
|
||||||
g_defloclabel (label);
|
g_defcodelabel (label);
|
||||||
AddCodeSegLine (CS, "iny");
|
AddCodeSegLine (CS, "iny");
|
||||||
AddCodeSegLine (CS, "lda %s,y", lbuf);
|
AddCodeSegLine (CS, "lda %s,y", lbuf);
|
||||||
AddCodeSegLine (CS, "bne L%04X", label);
|
AddCodeSegLine (CS, "bne %s", LocalLabelName (label));
|
||||||
AddCodeSegLine (CS, "tax");
|
AddCodeSegLine (CS, "tax");
|
||||||
AddCodeSegLine (CS, "tya");
|
AddCodeSegLine (CS, "tya");
|
||||||
|
|
||||||
@ -3988,10 +3970,10 @@ void g_strlen (unsigned flags, unsigned long val, unsigned offs)
|
|||||||
AddCodeSegLine (CS, "sta ptr1");
|
AddCodeSegLine (CS, "sta ptr1");
|
||||||
AddCodeSegLine (CS, "stx ptr1+1");
|
AddCodeSegLine (CS, "stx ptr1+1");
|
||||||
AddCodeSegLine (CS, "ldy #$FF");
|
AddCodeSegLine (CS, "ldy #$FF");
|
||||||
g_defloclabel (label);
|
g_defcodelabel (label);
|
||||||
AddCodeSegLine (CS, "iny");
|
AddCodeSegLine (CS, "iny");
|
||||||
AddCodeSegLine (CS, "lda (ptr1),y");
|
AddCodeSegLine (CS, "lda (ptr1),y");
|
||||||
AddCodeSegLine (CS, "bne L%04X", label);
|
AddCodeSegLine (CS, "bne %s", LocalLabelName (label));
|
||||||
AddCodeSegLine (CS, "tax");
|
AddCodeSegLine (CS, "tax");
|
||||||
AddCodeSegLine (CS, "tya");
|
AddCodeSegLine (CS, "tya");
|
||||||
}
|
}
|
||||||
|
@ -75,7 +75,6 @@ struct DataSeg;
|
|||||||
#define CF_TEST 0x0080 /* Test value */
|
#define CF_TEST 0x0080 /* Test value */
|
||||||
#define CF_FIXARGC 0x0100 /* Function has fixed arg count */
|
#define CF_FIXARGC 0x0100 /* Function has fixed arg count */
|
||||||
#define CF_FORCECHAR 0x0200 /* Handle chars as chars, not ints */
|
#define CF_FORCECHAR 0x0200 /* Handle chars as chars, not ints */
|
||||||
#define CF_SHORT 0x0400 /* Use short addressing */
|
|
||||||
#define CF_REG 0x0800 /* Value is in primary register */
|
#define CF_REG 0x0800 /* Value is in primary register */
|
||||||
|
|
||||||
/* Type of static address */
|
/* Type of static address */
|
||||||
@ -116,9 +115,6 @@ void g_pushseg (struct CodeSeg** CS, struct DataSeg** DS, const char* FuncName);
|
|||||||
void g_popseg (void);
|
void g_popseg (void);
|
||||||
/* Restore the old segments */
|
/* Restore the old segments */
|
||||||
|
|
||||||
void g_usecode (void);
|
|
||||||
/* Switch to the code segment */
|
|
||||||
|
|
||||||
void g_userodata (void);
|
void g_userodata (void);
|
||||||
/* Switch to the read only data segment */
|
/* Switch to the read only data segment */
|
||||||
|
|
||||||
@ -148,8 +144,11 @@ void g_bssname (const char* Name);
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
void g_defloclabel (unsigned label);
|
void g_defcodelabel (unsigned label);
|
||||||
/* Define a local label */
|
/* Define a local code label */
|
||||||
|
|
||||||
|
void g_defdatalabel (unsigned label);
|
||||||
|
/* Define a local data label */
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@ -376,7 +375,10 @@ void g_addaddr_static (unsigned flags, unsigned long label, unsigned offs);
|
|||||||
|
|
||||||
|
|
||||||
void g_save (unsigned flags);
|
void g_save (unsigned flags);
|
||||||
|
/* Copy primary register to hold register. */
|
||||||
|
|
||||||
void g_restore (unsigned flags);
|
void g_restore (unsigned flags);
|
||||||
|
/* Copy hold register to primary. */
|
||||||
|
|
||||||
void g_cmp (unsigned flags, unsigned long val);
|
void g_cmp (unsigned flags, unsigned long val);
|
||||||
/* Immidiate compare. The primary register will not be changed, Z flag
|
/* Immidiate compare. The primary register will not be changed, Z flag
|
||||||
@ -384,8 +386,15 @@ void g_cmp (unsigned flags, unsigned long val);
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
void g_test (unsigned flags);
|
void g_test (unsigned flags);
|
||||||
|
/* Test the value in the primary and set the condition codes */
|
||||||
|
|
||||||
void g_push (unsigned flags, unsigned long val);
|
void g_push (unsigned flags, unsigned long val);
|
||||||
|
/* Push the primary register or a constant value onto the stack */
|
||||||
|
|
||||||
void g_swap (unsigned flags);
|
void g_swap (unsigned flags);
|
||||||
|
/* Swap the primary register and the top of the stack. flags give the type
|
||||||
|
* of *both* values (must have same size).
|
||||||
|
*/
|
||||||
|
|
||||||
void g_call (unsigned Flags, const char* Label, unsigned ArgSize);
|
void g_call (unsigned Flags, const char* Label, unsigned ArgSize);
|
||||||
/* Call the specified subroutine name */
|
/* Call the specified subroutine name */
|
||||||
|
@ -53,7 +53,6 @@
|
|||||||
|
|
||||||
/* Label flags, bitmapped */
|
/* Label flags, bitmapped */
|
||||||
#define LF_DEF 0x0001U /* Label was defined */
|
#define LF_DEF 0x0001U /* Label was defined */
|
||||||
#define LF_EXT 0x0002U /* Label is external */
|
|
||||||
|
|
||||||
/* Label structure */
|
/* Label structure */
|
||||||
typedef struct CodeLabel CodeLabel;
|
typedef struct CodeLabel CodeLabel;
|
||||||
|
@ -270,18 +270,25 @@ static CodeEntry* ParseInsn (CodeSeg* S, const char* L)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* If the instruction is a branch, check for the label and generate it
|
/* If the instruction is a branch, check for the label and generate it
|
||||||
* if it does not exist.
|
* if it does not exist. In case of a PC relative branch (*+x) we will
|
||||||
|
* not generate a label, because the target label will not be defined.
|
||||||
*/
|
*/
|
||||||
Label = 0;
|
Label = 0;
|
||||||
if ((OPC->Info & CI_MASK_BRA) == CI_BRA) {
|
if ((OPC->Info & CI_MASK_BRA) == CI_BRA && Expr[0] != '*') {
|
||||||
|
|
||||||
unsigned Hash;
|
unsigned Hash;
|
||||||
|
|
||||||
/* ### Check for local labels here */
|
/* Addressing mode must be alsobute or something is really wrong */
|
||||||
CHECK (AM == AM_ABS);
|
CHECK (AM == AM_ABS);
|
||||||
|
|
||||||
|
/* Addressing mode is a branch/jump */
|
||||||
AM = AM_BRA;
|
AM = AM_BRA;
|
||||||
|
|
||||||
|
/* Generate the hash over the label, then search for the label */
|
||||||
Hash = HashStr (Expr) % CS_LABEL_HASH_SIZE;
|
Hash = HashStr (Expr) % CS_LABEL_HASH_SIZE;
|
||||||
Label = FindCodeLabel (S, Expr, Hash);
|
Label = FindCodeLabel (S, Expr, Hash);
|
||||||
|
|
||||||
|
/* If we don't have the label, it's a forward ref - create it */
|
||||||
if (Label == 0) {
|
if (Label == 0) {
|
||||||
/* Generate a new label */
|
/* Generate a new label */
|
||||||
Label = NewCodeSegLabel (S, Expr, Hash);
|
Label = NewCodeSegLabel (S, Expr, Hash);
|
||||||
@ -461,7 +468,7 @@ void AddCodeSegLine (CodeSeg* S, const char* Format, ...)
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
CodeLabel* AddCodeLabel (CodeSeg* S, const char* Name)
|
void AddCodeLabel (CodeSeg* S, const char* Name)
|
||||||
/* Add a code label for the next instruction to follow */
|
/* Add a code label for the next instruction to follow */
|
||||||
{
|
{
|
||||||
/* Calculate the hash from the name */
|
/* Calculate the hash from the name */
|
||||||
@ -481,30 +488,6 @@ CodeLabel* AddCodeLabel (CodeSeg* S, const char* Name)
|
|||||||
|
|
||||||
/* We do now have a valid label. Remember it for later */
|
/* We do now have a valid label. Remember it for later */
|
||||||
CollAppend (&S->Labels, L);
|
CollAppend (&S->Labels, L);
|
||||||
|
|
||||||
/* Return the label */
|
|
||||||
return L;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void AddExtCodeLabel (CodeSeg* S, const char* Name)
|
|
||||||
/* Add an external code label for the next instruction to follow */
|
|
||||||
{
|
|
||||||
/* Add the code label */
|
|
||||||
CodeLabel* L = AddCodeLabel (S, Name);
|
|
||||||
|
|
||||||
/* Mark it as external label */
|
|
||||||
L->Flags |= LF_EXT;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void AddLocCodeLabel (CodeSeg* S, const char* Name)
|
|
||||||
/* Add a local code label for the next instruction to follow */
|
|
||||||
{
|
|
||||||
/* Add the code label */
|
|
||||||
AddCodeLabel (S, Name);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -630,11 +613,7 @@ void MergeCodeLabels (CodeSeg* S)
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* We have at least one label. Use the first one as reference label.
|
/* We have at least one label. Use the first one as reference label. */
|
||||||
* We don't have a notification for global labels for now, and using
|
|
||||||
* the first one will also keep the global function labels, since these
|
|
||||||
* are inserted at position 0.
|
|
||||||
*/
|
|
||||||
RefLab = CollAt (&E->Labels, 0);
|
RefLab = CollAt (&E->Labels, 0);
|
||||||
|
|
||||||
/* Walk through the remaining labels and change references to these
|
/* Walk through the remaining labels and change references to these
|
||||||
@ -663,29 +642,21 @@ void MergeCodeLabels (CodeSeg* S)
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* If the label is not an external label, we may remove the
|
/* Remove the label completely. */
|
||||||
* label completely.
|
FreeCodeLabel (L);
|
||||||
*/
|
CollDelete (&E->Labels, J);
|
||||||
#if 0
|
|
||||||
if ((L->Flags & LF_EXT) == 0) {
|
|
||||||
FreeCodeLabel (L);
|
|
||||||
CollDelete (&E->Labels, J);
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* The reference label is the only remaining label. If it is not an
|
/* The reference label is the only remaining label. Check if there
|
||||||
* external label, check if there are any references to this label,
|
* are any references to this label, and delete it if this is not
|
||||||
* and delete it if this is not the case.
|
* the case.
|
||||||
*/
|
*/
|
||||||
#if 0
|
if (CollCount (&RefLab->JumpFrom) == 0) {
|
||||||
if ((RefLab->Flags & LF_EXT) == 0 && CollCount (&RefLab->JumpFrom) == 0) {
|
|
||||||
/* Delete the label */
|
/* Delete the label */
|
||||||
FreeCodeLabel (RefLab);
|
FreeCodeLabel (RefLab);
|
||||||
/* Remove it from the list */
|
/* Remove it from the list */
|
||||||
CollDelete (&E->Labels, 0);
|
CollDelete (&E->Labels, 0);
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -95,11 +95,8 @@ CodeSeg* PopCodeSeg (void);
|
|||||||
void AddCodeSegLine (CodeSeg* S, const char* Format, ...) attribute ((format(printf,2,3)));
|
void AddCodeSegLine (CodeSeg* S, const char* Format, ...) attribute ((format(printf,2,3)));
|
||||||
/* Add a line to the given code segment */
|
/* Add a line to the given code segment */
|
||||||
|
|
||||||
void AddExtCodeLabel (CodeSeg* S, const char* Name);
|
void AddCodeLabel (CodeSeg* S, const char* Name);
|
||||||
/* Add an external code label for the next instruction to follow */
|
/* Add a code label for the next instruction to follow */
|
||||||
|
|
||||||
void AddLocCodeLabel (CodeSeg* S, const char* Name);
|
|
||||||
/* Add a local code label for the next instruction to follow */
|
|
||||||
|
|
||||||
void AddCodeSegHint (CodeSeg* S, unsigned Hint);
|
void AddCodeSegHint (CodeSeg* S, unsigned Hint);
|
||||||
/* Add a hint for the preceeding instruction */
|
/* Add a hint for the preceeding instruction */
|
||||||
|
@ -2450,7 +2450,7 @@ static int hieAnd (struct expent* lval, unsigned TrueLab, int* BoolOp)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Define the false jump label here */
|
/* Define the false jump label here */
|
||||||
g_defloclabel (lab);
|
g_defcodelabel (lab);
|
||||||
|
|
||||||
/* Define the label */
|
/* Define the label */
|
||||||
lval->e_flags = E_MEXPR;
|
lval->e_flags = E_MEXPR;
|
||||||
@ -2536,9 +2536,9 @@ static int hieOr (struct expent *lval)
|
|||||||
DoneLab = GetLocalLabel ();
|
DoneLab = GetLocalLabel ();
|
||||||
g_getimmed (CF_INT | CF_CONST, 0, 0); /* Load FALSE */
|
g_getimmed (CF_INT | CF_CONST, 0, 0); /* Load FALSE */
|
||||||
g_falsejump (CF_NONE, DoneLab);
|
g_falsejump (CF_NONE, DoneLab);
|
||||||
g_defloclabel (TrueLab);
|
g_defcodelabel (TrueLab);
|
||||||
g_getimmed (CF_INT | CF_CONST, 1, 0); /* Load TRUE */
|
g_getimmed (CF_INT | CF_CONST, 1, 0); /* Load TRUE */
|
||||||
g_defloclabel (DoneLab);
|
g_defcodelabel (DoneLab);
|
||||||
}
|
}
|
||||||
return k;
|
return k;
|
||||||
}
|
}
|
||||||
@ -2577,7 +2577,7 @@ static int hieQuest (struct expent *lval)
|
|||||||
labt = GetLocalLabel ();
|
labt = GetLocalLabel ();
|
||||||
ConsumeColon ();
|
ConsumeColon ();
|
||||||
g_jump (labt);
|
g_jump (labt);
|
||||||
g_defloclabel (labf);
|
g_defcodelabel (labf);
|
||||||
expression1 (&lval3);
|
expression1 (&lval3);
|
||||||
|
|
||||||
/* Check if any conversions are needed, if so, do them.
|
/* Check if any conversions are needed, if so, do them.
|
||||||
@ -2609,7 +2609,7 @@ static int hieQuest (struct expent *lval)
|
|||||||
g_jump (labf); /* Jump around code */
|
g_jump (labf); /* Jump around code */
|
||||||
|
|
||||||
/* The jump for expr2 goes here */
|
/* The jump for expr2 goes here */
|
||||||
g_defloclabel (labt);
|
g_defcodelabel (labt);
|
||||||
|
|
||||||
/* Create the typecast code for expr2 */
|
/* Create the typecast code for expr2 */
|
||||||
Mark2 = GetCodePos (); /* Remember position */
|
Mark2 = GetCodePos (); /* Remember position */
|
||||||
@ -2622,7 +2622,7 @@ static int hieQuest (struct expent *lval)
|
|||||||
RemoveCode (Mark1); /* Remove code */
|
RemoveCode (Mark1); /* Remove code */
|
||||||
} else {
|
} else {
|
||||||
/* We have typecast code, output label */
|
/* We have typecast code, output label */
|
||||||
g_defloclabel (labf);
|
g_defcodelabel (labf);
|
||||||
labt = 0; /* Mark other label as invalid */
|
labt = 0; /* Mark other label as invalid */
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -2646,7 +2646,7 @@ static int hieQuest (struct expent *lval)
|
|||||||
|
|
||||||
/* If we don't have the label defined until now, do it */
|
/* If we don't have the label defined until now, do it */
|
||||||
if (labt) {
|
if (labt) {
|
||||||
g_defloclabel (labt);
|
g_defcodelabel (labt);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Setup the target expression */
|
/* Setup the target expression */
|
||||||
|
@ -190,9 +190,6 @@ void AllocLocalSpace (Function* F)
|
|||||||
{
|
{
|
||||||
if (F->Reserved > 0) {
|
if (F->Reserved > 0) {
|
||||||
|
|
||||||
/* Switch to the code segment */
|
|
||||||
g_usecode ();
|
|
||||||
|
|
||||||
/* Create space on the stack */
|
/* Create space on the stack */
|
||||||
g_space (F->Reserved);
|
g_space (F->Reserved);
|
||||||
|
|
||||||
@ -317,7 +314,7 @@ void NewFunc (SymEntry* Func)
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* Output the function exit code label */
|
/* Output the function exit code label */
|
||||||
g_defloclabel (GetRetLab (CurrentFunc));
|
g_defcodelabel (GetRetLab (CurrentFunc));
|
||||||
|
|
||||||
/* Restore the register variables */
|
/* Restore the register variables */
|
||||||
RestoreRegVars (!IsVoidFunc);
|
RestoreRegVars (!IsVoidFunc);
|
||||||
|
@ -80,7 +80,7 @@ void DoLabel (void)
|
|||||||
SymEntry* Entry = AddLabelSym (CurTok.Ident, SC_DEF);
|
SymEntry* Entry = AddLabelSym (CurTok.Ident, SC_DEF);
|
||||||
|
|
||||||
/* Emit the jump label */
|
/* Emit the jump label */
|
||||||
g_defloclabel (Entry->V.Label);
|
g_defcodelabel (Entry->V.Label);
|
||||||
|
|
||||||
/* Eat the ident and colon */
|
/* Eat the ident and colon */
|
||||||
NextToken ();
|
NextToken ();
|
||||||
|
@ -103,16 +103,13 @@ void DumpLiteralPool (void)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Define the label */
|
/* Define the label */
|
||||||
g_defloclabel (LiteralPoolLabel);
|
g_defdatalabel (LiteralPoolLabel);
|
||||||
|
|
||||||
/* Translate the buffer contents into the target charset */
|
/* Translate the buffer contents into the target charset */
|
||||||
TranslateLiteralPool (0);
|
TranslateLiteralPool (0);
|
||||||
|
|
||||||
/* Output the buffer data */
|
/* Output the buffer data */
|
||||||
g_defbytes (LiteralPoolBuf, LiteralPoolOffs);
|
g_defbytes (LiteralPoolBuf, LiteralPoolOffs);
|
||||||
|
|
||||||
/* Switch back to the code segment */
|
|
||||||
g_usecode ();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -185,9 +185,6 @@ static void ParseOneDecl (const DeclSpec* Spec)
|
|||||||
/* Allocate previously reserved local space */
|
/* Allocate previously reserved local space */
|
||||||
AllocLocalSpace (CurrentFunc);
|
AllocLocalSpace (CurrentFunc);
|
||||||
|
|
||||||
/* Switch to the code segment. */
|
|
||||||
g_usecode ();
|
|
||||||
|
|
||||||
/* Skip the '=' */
|
/* Skip the '=' */
|
||||||
NextToken ();
|
NextToken ();
|
||||||
|
|
||||||
@ -230,7 +227,7 @@ static void ParseOneDecl (const DeclSpec* Spec)
|
|||||||
|
|
||||||
/* Define the variable label */
|
/* Define the variable label */
|
||||||
SymData = GetLocalLabel ();
|
SymData = GetLocalLabel ();
|
||||||
g_defloclabel (SymData);
|
g_defdatalabel (SymData);
|
||||||
|
|
||||||
/* Reserve space for the data */
|
/* Reserve space for the data */
|
||||||
g_res (Size);
|
g_res (Size);
|
||||||
@ -240,9 +237,6 @@ static void ParseOneDecl (const DeclSpec* Spec)
|
|||||||
|
|
||||||
struct expent lval;
|
struct expent lval;
|
||||||
|
|
||||||
/* Switch to the code segment. */
|
|
||||||
g_usecode ();
|
|
||||||
|
|
||||||
/* Skip the '=' */
|
/* Skip the '=' */
|
||||||
NextToken ();
|
NextToken ();
|
||||||
|
|
||||||
@ -280,7 +274,7 @@ static void ParseOneDecl (const DeclSpec* Spec)
|
|||||||
|
|
||||||
/* Define the variable label */
|
/* Define the variable label */
|
||||||
SymData = GetLocalLabel ();
|
SymData = GetLocalLabel ();
|
||||||
g_defloclabel (SymData);
|
g_defdatalabel (SymData);
|
||||||
|
|
||||||
/* Skip the '=' */
|
/* Skip the '=' */
|
||||||
NextToken ();
|
NextToken ();
|
||||||
@ -298,7 +292,7 @@ static void ParseOneDecl (const DeclSpec* Spec)
|
|||||||
|
|
||||||
/* Define the variable label */
|
/* Define the variable label */
|
||||||
SymData = GetLocalLabel ();
|
SymData = GetLocalLabel ();
|
||||||
g_defloclabel (SymData);
|
g_defdatalabel (SymData);
|
||||||
|
|
||||||
/* Reserve space for the data */
|
/* Reserve space for the data */
|
||||||
g_res (Size);
|
g_res (Size);
|
||||||
@ -371,9 +365,6 @@ void DeclareLocals (void)
|
|||||||
/* Be sure to allocate any reserved space for locals */
|
/* Be sure to allocate any reserved space for locals */
|
||||||
AllocLocalSpace (CurrentFunc);
|
AllocLocalSpace (CurrentFunc);
|
||||||
|
|
||||||
/* In case we switched away from code segment, switch back now */
|
|
||||||
g_usecode ();
|
|
||||||
|
|
||||||
/* In case we've allocated local variables in this block, emit a call to
|
/* In case we've allocated local variables in this block, emit a call to
|
||||||
* the stack checking routine if stack checks are enabled.
|
* the stack checking routine if stack checks are enabled.
|
||||||
*/
|
*/
|
||||||
|
@ -91,7 +91,7 @@ static const OPCDesc OPCTable[OPC_COUNT] = {
|
|||||||
{ "jmp", OPC_JMP, 3, CI_BRA },
|
{ "jmp", OPC_JMP, 3, CI_BRA },
|
||||||
{ "jne", OPC_JNE, 5, CI_BRA },
|
{ "jne", OPC_JNE, 5, CI_BRA },
|
||||||
{ "jpl", OPC_JPL, 5, CI_BRA },
|
{ "jpl", OPC_JPL, 5, CI_BRA },
|
||||||
{ "jsr", OPC_JSR, 3, CI_BRA },
|
{ "jsr", OPC_JSR, 3, CI_NONE },
|
||||||
{ "jvc", OPC_JVC, 5, CI_BRA },
|
{ "jvc", OPC_JVC, 5, CI_BRA },
|
||||||
{ "jvs", OPC_JVS, 5, CI_BRA },
|
{ "jvs", OPC_JVS, 5, CI_BRA },
|
||||||
{ "lda", OPC_LDA, 0, CI_CHG_A },
|
{ "lda", OPC_LDA, 0, CI_CHG_A },
|
||||||
|
@ -71,7 +71,7 @@ static int doif (void)
|
|||||||
/* Else clause present? */
|
/* Else clause present? */
|
||||||
if (curtok != TOK_ELSE) {
|
if (curtok != TOK_ELSE) {
|
||||||
|
|
||||||
g_defloclabel (flab1);
|
g_defcodelabel (flab1);
|
||||||
/* Since there's no else clause, we're not sure, if the a break
|
/* Since there's no else clause, we're not sure, if the a break
|
||||||
* statement is really executed.
|
* statement is really executed.
|
||||||
*/
|
*/
|
||||||
@ -93,12 +93,12 @@ static int doif (void)
|
|||||||
/* Mark the label as unused */
|
/* Mark the label as unused */
|
||||||
flab2 = 0;
|
flab2 = 0;
|
||||||
}
|
}
|
||||||
g_defloclabel (flab1);
|
g_defcodelabel (flab1);
|
||||||
gotbreak &= Statement ();
|
gotbreak &= Statement ();
|
||||||
|
|
||||||
/* Generate the label for the else clause */
|
/* Generate the label for the else clause */
|
||||||
if (flab2) {
|
if (flab2) {
|
||||||
g_defloclabel (flab2);
|
g_defcodelabel (flab2);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Done */
|
/* Done */
|
||||||
@ -118,7 +118,7 @@ static void dowhile (char wtype)
|
|||||||
loop = GetLocalLabel ();
|
loop = GetLocalLabel ();
|
||||||
lab = GetLocalLabel ();
|
lab = GetLocalLabel ();
|
||||||
AddLoop (oursp, loop, lab, 0, 0);
|
AddLoop (oursp, loop, lab, 0, 0);
|
||||||
g_defloclabel (loop);
|
g_defcodelabel (loop);
|
||||||
if (wtype == 'w') {
|
if (wtype == 'w') {
|
||||||
|
|
||||||
/* While loop */
|
/* While loop */
|
||||||
@ -139,7 +139,7 @@ static void dowhile (char wtype)
|
|||||||
/* There is code inside the while loop */
|
/* There is code inside the while loop */
|
||||||
Statement ();
|
Statement ();
|
||||||
g_jump (loop);
|
g_jump (loop);
|
||||||
g_defloclabel (lab);
|
g_defcodelabel (lab);
|
||||||
}
|
}
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
@ -149,7 +149,7 @@ static void dowhile (char wtype)
|
|||||||
Consume (TOK_WHILE, "`while' expected");
|
Consume (TOK_WHILE, "`while' expected");
|
||||||
test (loop, 1);
|
test (loop, 1);
|
||||||
ConsumeSemi ();
|
ConsumeSemi ();
|
||||||
g_defloclabel (lab);
|
g_defcodelabel (lab);
|
||||||
|
|
||||||
}
|
}
|
||||||
DelLoop ();
|
DelLoop ();
|
||||||
@ -297,7 +297,7 @@ static void cascadeswitch (struct expent* eval)
|
|||||||
|
|
||||||
/* If we have a cascade label, emit it */
|
/* If we have a cascade label, emit it */
|
||||||
if (NextLab) {
|
if (NextLab) {
|
||||||
g_defloclabel (NextLab);
|
g_defcodelabel (NextLab);
|
||||||
NextLab = 0;
|
NextLab = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -400,7 +400,7 @@ static void cascadeswitch (struct expent* eval)
|
|||||||
|
|
||||||
/* Emit a code label if we have one */
|
/* Emit a code label if we have one */
|
||||||
if (CodeLab) {
|
if (CodeLab) {
|
||||||
g_defloclabel (CodeLab);
|
g_defcodelabel (CodeLab);
|
||||||
CodeLab = 0;
|
CodeLab = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -422,9 +422,9 @@ static void cascadeswitch (struct expent* eval)
|
|||||||
* one, too.
|
* one, too.
|
||||||
*/
|
*/
|
||||||
if (NextLab) {
|
if (NextLab) {
|
||||||
g_defloclabel (NextLab);
|
g_defcodelabel (NextLab);
|
||||||
}
|
}
|
||||||
g_defloclabel (ExitLab);
|
g_defcodelabel (ExitLab);
|
||||||
|
|
||||||
/* End the loop */
|
/* End the loop */
|
||||||
DelLoop ();
|
DelLoop ();
|
||||||
@ -491,7 +491,7 @@ static void tableswitch (struct expent* eval)
|
|||||||
}
|
}
|
||||||
ConsumeColon ();
|
ConsumeColon ();
|
||||||
} while (curtok == TOK_CASE || curtok == TOK_DEFAULT);
|
} while (curtok == TOK_CASE || curtok == TOK_DEFAULT);
|
||||||
g_defloclabel (label);
|
g_defcodelabel (label);
|
||||||
HaveBreak = 0;
|
HaveBreak = 0;
|
||||||
}
|
}
|
||||||
if (curtok != TOK_RCURLY) {
|
if (curtok != TOK_RCURLY) {
|
||||||
@ -513,7 +513,7 @@ static void tableswitch (struct expent* eval)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Actual selector code goes here */
|
/* Actual selector code goes here */
|
||||||
g_defloclabel (lcase);
|
g_defcodelabel (lcase);
|
||||||
|
|
||||||
/* Create the call to the switch subroutine */
|
/* Create the call to the switch subroutine */
|
||||||
Flags = TypeOf (eval->e_tptr);
|
Flags = TypeOf (eval->e_tptr);
|
||||||
@ -534,7 +534,7 @@ static void tableswitch (struct expent* eval)
|
|||||||
if (dlabel) {
|
if (dlabel) {
|
||||||
g_jump (dlabel);
|
g_jump (dlabel);
|
||||||
}
|
}
|
||||||
g_defloclabel (lab);
|
g_defcodelabel (lab);
|
||||||
DelLoop ();
|
DelLoop ();
|
||||||
|
|
||||||
/* Free the allocated space for the labels */
|
/* Free the allocated space for the labels */
|
||||||
@ -591,7 +591,7 @@ static void dofor (void)
|
|||||||
expression (&lval1);
|
expression (&lval1);
|
||||||
}
|
}
|
||||||
ConsumeSemi ();
|
ConsumeSemi ();
|
||||||
g_defloclabel (loop);
|
g_defcodelabel (loop);
|
||||||
if (curtok != TOK_SEMI) { /* exp2 */
|
if (curtok != TOK_SEMI) { /* exp2 */
|
||||||
boolexpr (&lval2);
|
boolexpr (&lval2);
|
||||||
g_truejump (CF_NONE, lstat);
|
g_truejump (CF_NONE, lstat);
|
||||||
@ -600,16 +600,16 @@ static void dofor (void)
|
|||||||
g_jump (lstat);
|
g_jump (lstat);
|
||||||
}
|
}
|
||||||
ConsumeSemi ();
|
ConsumeSemi ();
|
||||||
g_defloclabel (linc);
|
g_defcodelabel (linc);
|
||||||
if (curtok != TOK_RPAREN) { /* exp3 */
|
if (curtok != TOK_RPAREN) { /* exp3 */
|
||||||
expression (&lval3);
|
expression (&lval3);
|
||||||
}
|
}
|
||||||
ConsumeRParen ();
|
ConsumeRParen ();
|
||||||
g_jump (loop);
|
g_jump (loop);
|
||||||
g_defloclabel (lstat);
|
g_defcodelabel (lstat);
|
||||||
Statement ();
|
Statement ();
|
||||||
g_jump (linc);
|
g_jump (linc);
|
||||||
g_defloclabel (lab);
|
g_defcodelabel (lab);
|
||||||
DelLoop ();
|
DelLoop ();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user