diff options
Diffstat (limited to 'includes/compiler/PCode.h')
-rw-r--r-- | includes/compiler/PCode.h | 194 |
1 files changed, 194 insertions, 0 deletions
diff --git a/includes/compiler/PCode.h b/includes/compiler/PCode.h new file mode 100644 index 0000000..55aac38 --- /dev/null +++ b/includes/compiler/PCode.h @@ -0,0 +1,194 @@ +#ifndef COMPILER_PCODE_H +#define COMPILER_PCODE_H + +#include "compiler/common.h" + +#ifdef __MWERKS__ +#pragma options align=mac68k +#endif + +#define PCODE_FLAG_SET_T(pcode) (((pcode)->flags & (fPCodeFlag1 | fPCodeFlag8)) ? (pcode)->flags : 0) +#define PCODE_FLAG_SET_F(pcode) (((pcode)->flags & (fPCodeFlag1 | fPCodeFlag8)) ? 0 : (pcode)->flags) + +enum { + EffectRead = 1, + EffectWrite = 2 +}; + +typedef enum { + PCOp_REGISTER, + PCOp_SYSREG, + PCOp_IMMEDIATE, + PCOp_MEMORY, + PCOp_LABEL, + PCOp_LABELDIFF, + PCOp_PLACEHOLDEROPERAND +} PCOpKind; + +typedef enum { + RefType_0, + RefType_1, + RefType_2, + RefType_3, + RefType_4, + RefType_5, + RefType_6, + RefType_7, + RefType_8, + RefType_9, + RefType_A, + RefType_B, + RefType_C, + RefType_D +} PCRefType; + +struct PCodeArg { + PCOpKind kind; + char arg; + union { + struct { + unsigned short effect; + short reg; + } reg; + struct { + SInt32 value; + Object *obj; + } imm; + struct { + SInt32 offset; + Object *obj; + } mem; + struct { + PCodeLabel *label; + } label; + struct { + SInt16 offset; + PCodeLabel *labelA; + PCodeLabel *labelB; + } labeldiff; + unsigned char placeholder[10]; // keep the size + } data; +}; + +struct PCode { + PCode *nextPCode; + PCode *prevPCode; + PCodeBlock *block; + unsigned int xx_C; + unsigned int _10; + int flags; + void *_18; + SInt32 sourceoffset; + short op; + short argCount; + PCodeArg args[0]; +}; + +struct PCodeLabel { + PCodeLabel *nextLabel; + PCodeBlock *block; + short resolved; + short index; +}; + +typedef struct _PCLink { + struct _PCLink *nextLink; + struct PCodeBlock *block; +} PCLink; + +struct PCodeBlock { + struct PCodeBlock *nextBlock; + struct PCodeBlock *prevBlock; + PCodeLabel *labels; + PCLink *predecessors; + PCLink *successors; + PCode *firstPCode; + PCode *lastPCode; + int blockIndex; + int codeOffset; // in bytes + int loopWeight; + short pcodeCount; + unsigned short flags; +}; + +/* PCode Flags */ +enum { + fPCodeFlag1 = 1, + fPCodeFlag2 = 2, + fPCodeFlag4 = 4, + fPCodeFlag8 = 8, + fPCodeFlag10 = 0x10, + fPCodeFlag20 = 0x20, + // Always valid + fIsConst = 0x40, + fIsVolatile = 0x80, + fSideEffects = 0x100, + fPCodeFlag200 = 0x200, // ? + fPCodeFlag400 = 0x400, // ? + fPCodeFlag800 = 0x800, // ? + fPCodeFlag1000 = 0x1000, // ? + fCommutative = 0x2000, + fIsCSE = 0x4000, + fPCodeFlag8000 = 0x8000, + fPCodeFlag20000 = 0x20000, // ? + fPCodeFlag40000 = 0x40000, // ? + // Set 1 only + fLink = 0x1000000, + fBranchNotTaken = 0x4000000, + fBranchTaken = 0x8000000, + fAbsolute = 0x10000000, + // Set 2 only + fIsPtrOp = 0x20, + fOverflow = 0x800000, + fSetsCarry = 0x10000000, + // ?? + fPCodeFlag8000000 = 0x8000000, + fPCodeFlag10000000 = 0x10000000, + fPCodeFlag20000000 = 0x20000000, + fPCodeFlag40000000 = 0x40000000, + fPCodeFlag80000000 = 0x80000000 +}; + +enum { + fPCBlockFlag1 = 1, // prologue + fPCBlockFlag2 = 2, // epilogue + fPCBlockFlag4 = 4, + fPCBlockFlag8 = 8, + fPCBlockFlag10 = 0x10, + fPCBlockFlag20 = 0x20, + fPCBlockFlag4000 = 0x4000 +}; + +extern PCodeBlock *pcbasicblocks; +extern PCodeBlock *pclastblock; +extern PCodeBlock *prologue; +extern PCodeBlock *epilogue; +extern PCodeBlock **depthfirstordering; +extern int pcblockcount; +extern int pcloopweight; + +extern void initpcode(); +extern PCode *makepcode(short op, ...); +extern void emitpcode(short op, ...); +extern PCode *copypcode(PCode *pcode); +extern PCodeLabel *makepclabel(); +extern PCodeBlock *makepcblock(); +extern void pclabel(PCodeBlock *block, PCodeLabel *label); +extern void pcbranch(PCodeBlock *block, PCodeLabel *label); +extern void pccomputepredecessors(); +extern void deleteblock(PCodeBlock *block); +extern void deleteunreachableblocks(); +extern void appendpcode(PCodeBlock *block, PCode *pcode); +extern void deletepcode(PCode *pcode); +extern void insertpcodebefore(PCode *anchor, PCode *newpcode); +extern void insertpcodeafter(PCode *anchor, PCode *newpcode); +extern void setpcodeflags(int flags); +extern void clearpcodeflags(int flags); +extern int pccomputeoffsets(); +extern void computedepthfirstordering(); + +#ifdef __MWERKS__ +#pragma options align=reset +#endif + +#endif |