pic patches by Slade
[fw/sdcc] / src / pic / pcode.h
1 /*-------------------------------------------------------------------------
2
3    pcode.h - post code generation
4    Written By -  Scott Dattalo scott@dattalo.com
5
6    This program is free software; you can redistribute it and/or modify it
7    under the terms of the GNU General Public License as published by the
8    Free Software Foundation; either version 2, or (at your option) any
9    later version.
10    
11    This program is distributed in the hope that it will be useful,
12    but WITHOUT ANY WARRANTY; without even the implied warranty of
13    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14    GNU General Public License for more details.
15    
16    You should have received a copy of the GNU General Public License
17    along with this program; if not, write to the Free Software
18    Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
19    
20 -------------------------------------------------------------------------*/
21
22 //#include "ralloc.h"
23 struct regs;
24
25 /*
26    Post code generation
27
28    The post code generation is an assembler optimizer. The assembly code
29    produced by all of the previous steps is fully functional. This step
30    will attempt to analyze the flow of the assembly code and agressively 
31    optimize it. The peep hole optimizer attempts to do the same thing.
32    As you may recall, the peep hole optimizer replaces blocks of assembly
33    with more optimal blocks (e.g. removing redundant register loads).
34    However, the peep hole optimizer has to be somewhat conservative since
35    an assembly program has implicit state information that's unavailable 
36    when only a few instructions are examined.
37      Consider this example:
38
39    example1:
40      movwf  t1
41      movf   t1,w
42
43    The movf seems redundant since we know that the W register already
44    contains the same value of t1. So a peep hole optimizer is tempted to
45    remove the "movf". However, this is dangerous since the movf affects
46    the flags in the status register (specifically the Z flag) and subsequent
47    code may depend upon this. Look at these two examples:
48
49    example2:
50      movwf  t1
51      movf   t1,w     ; Can't remove this movf
52      skpz
53       return
54
55    example3:
56      movwf  t1
57      movf   t1,w     ; This  movf can be removed
58      xorwf  t2,w     ; since xorwf will over write Z 
59      skpz
60       return
61
62 */
63
64
65 #ifndef __PCODE_H__
66 #define __PCODE_H__
67
68 /***********************************************************************
69  * debug stuff
70  * 
71  * The DFPRINTF macro will call fprintf if PCODE_DEBUG is defined.
72  * The macro is used like:
73  *
74  * DPRINTF(("%s #%d\n","test", 1));
75  *
76  * The double parenthesis (()) are necessary
77  * 
78  ***********************************************************************/
79 //#define PCODE_DEBUG
80
81 #ifdef PCODE_DEBUG
82 #define DFPRINTF(args) (fprintf args)
83 #else
84 #define DFPRINTF(args) ;
85 #endif
86
87
88 /***********************************************************************
89  *  PIC status bits - this will move into device dependent headers
90  ***********************************************************************/
91 #define PIC_C_BIT    0
92 #define PIC_DC_BIT   1
93 #define PIC_Z_BIT    2
94 #define PIC_RP0_BIT  5   /* Register Bank select bits RP1:0 : */
95 #define PIC_RP1_BIT  6   /* 00 - bank 0, 01 - bank 1, 10 - bank 2, 11 - bank 3 */
96 #define PIC_IRP_BIT  7   /* Indirect register page select */
97
98 /***********************************************************************
99  *  PIC INTCON bits - this will move into device dependent headers
100  ***********************************************************************/
101 #define PIC_RBIF_BIT 0   /* Port B level has changed flag */
102 #define PIC_INTF_BIT 1   /* Port B bit 0 interrupt on edge flag */
103 #define PIC_T0IF_BIT 2   /* TMR0 has overflowed flag */
104 #define PIC_RBIE_BIT 3   /* Port B level has changed - Interrupt Enable */
105 #define PIC_INTE_BIT 4   /* Port B bit 0 interrupt on edge - Int Enable */
106 #define PIC_T0IE_BIT 5   /* TMR0 overflow Interrupt Enable */
107 #define PIC_PIE_BIT  6   /* Peripheral Interrupt Enable */
108 #define PIC_GIE_BIT  7   /* Global Interrupt Enable */
109
110 /***********************************************************************
111  *  Operand types 
112  ***********************************************************************/
113 #define POT_RESULT  0
114 #define POT_LEFT    1
115 #define POT_RIGHT   2
116
117
118 /***********************************************************************
119  *
120  *  PIC_OPTYPE - Operand types that are specific to the PIC architecture
121  *
122  *  If a PIC assembly instruction has an operand then here is where we
123  *  associate a type to it. For example,
124  *
125  *     movf    reg,W
126  *
127  *  The movf has two operands: 'reg' and the W register. 'reg' is some
128  *  arbitrary general purpose register, hence it has the type PO_GPR_REGISTER.
129  *  The W register, which is the PIC's accumulator, has the type PO_W.
130  *
131  ***********************************************************************/
132
133
134
135 typedef enum 
136 {
137   PO_NONE=0,         // No operand e.g. NOP
138   PO_W,              // The 'W' register
139   PO_STATUS,         // The 'STATUS' register
140   PO_FSR,            // The "file select register" (in 18c it's one of three)
141   PO_INDF,           // The Indirect register
142   PO_INTCON,         // Interrupt Control register
143   PO_GPR_REGISTER,   // A general purpose register
144   PO_GPR_BIT,        // A bit of a general purpose register
145   PO_GPR_TEMP,       // A general purpose temporary register
146   PO_GPR_POINTER,    // A general purpose pointer
147   PO_SFR_REGISTER,   // A special function register (e.g. PORTA)
148   PO_PCL,            // Program counter Low register
149   PO_PCLATH,         // Program counter Latch high register
150   PO_LITERAL,        // A constant
151   PO_IMMEDIATE,      //  (8051 legacy)
152   PO_DIR,            // Direct memory (8051 legacy)
153   PO_CRY,            // bit memory (8051 legacy)
154   PO_BIT,            // bit operand.
155   PO_STR,            //  (8051 legacy)
156   PO_LABEL,
157   PO_WILD            // Wild card operand in peep optimizer
158 } PIC_OPTYPE;
159
160
161 /***********************************************************************
162  *
163  *  PIC_OPCODE
164  *
165  *  This is not a list of the PIC's opcodes per se, but instead
166  *  an enumeration of all of the different types of pic opcodes. 
167  *
168  ***********************************************************************/
169
170 typedef enum
171 {
172   POC_WILD=-1,   /* Wild card - used in the pCode peep hole optimizer
173                   * to represent ANY pic opcode */
174   POC_ADDLW=0,
175   POC_ADDWF,
176   POC_ADDFW,
177   POC_ANDLW,
178   POC_ANDWF,
179   POC_ANDFW,
180   POC_BCF,
181   POC_BSF,
182   POC_BTFSC,
183   POC_BTFSS,
184   POC_CALL,
185   POC_COMF,
186   POC_COMFW,
187   POC_CLRF,
188   POC_CLRW,
189   POC_CLRWDT,
190   POC_DECF,
191   POC_DECFW,
192   POC_DECFSZ,
193   POC_DECFSZW,
194   POC_GOTO,
195   POC_INCF,
196   POC_INCFW,
197   POC_INCFSZ,
198   POC_INCFSZW,
199   POC_IORLW,
200   POC_IORWF,
201   POC_IORFW,
202   POC_MOVF,
203   POC_MOVFW,
204   POC_MOVLW,
205   POC_MOVWF,
206   POC_NOP,
207   POC_RETLW,
208   POC_RETURN,
209   POC_RETFIE,
210   POC_RLF,
211   POC_RLFW,
212   POC_RRF,
213   POC_RRFW,
214   POC_SUBLW,
215   POC_SUBWF,
216   POC_SUBFW,
217   POC_SWAPF,
218   POC_SWAPFW,
219   POC_TRIS,
220   POC_XORLW,
221   POC_XORWF,
222   POC_XORFW
223 } PIC_OPCODE;
224
225
226 /***********************************************************************
227  *  PC_TYPE  - pCode Types
228  ***********************************************************************/
229
230 typedef enum
231 {
232   PC_COMMENT=0,   /* pCode is a comment     */
233   PC_INLINE,      /* user's inline code     */
234   PC_OPCODE,      /* PORT dependent opcode  */
235   PC_LABEL,       /* assembly label         */
236   PC_FLOW,        /* flow analysis          */
237   PC_FUNCTION,    /* Function start or end  */
238   PC_WILD,        /* wildcard - an opcode place holder used 
239                    * in the pCode peep hole optimizer */
240   PC_CSOURCE,     /* C-Source Line  */
241   PC_BAD          /* Mark the pCode object as being bad */
242 } PC_TYPE;
243
244 /************************************************/
245 /***************  Structures ********************/
246 /************************************************/
247 /* These are here as forward references - the 
248  * full definition of these are below           */
249 struct pCode;
250 struct pCodeWildBlock;
251 struct pCodeRegLives;
252
253 /*************************************************
254   pBranch
255
256   The first step in optimizing pCode is determining
257  the program flow. This information is stored in
258  single-linked lists in the for of 'from' and 'to'
259  objects with in a pcode. For example, most instructions
260  don't involve any branching. So their from branch
261  points to the pCode immediately preceding them and
262  their 'to' branch points to the pcode immediately
263  following them. A skip instruction is an example of
264  a pcode that has multiple (in this case two) elements
265  in the 'to' branch. A 'label' pcode is an where there
266  may be multiple 'from' branches.
267  *************************************************/
268
269 typedef struct pBranch
270 {
271   struct pCode   *pc;    // Next pCode in a branch
272   struct pBranch *next;  /* If more than one branch
273                           * the next one is here */
274
275 } pBranch;
276
277 /*************************************************
278   pCodeOp
279
280   pCode Operand structure.
281   For those assembly instructions that have arguments, 
282   the pCode will have a pCodeOp in which the argument
283   can be stored. For example
284
285     movf   some_register,w
286
287   'some_register' will be stored/referenced in a pCodeOp
288
289  *************************************************/
290
291 typedef struct pCodeOp
292 {
293   PIC_OPTYPE type;
294   char *name;
295   
296 } pCodeOp;
297 #if 0
298 typedef struct pCodeOpBit
299 {
300   pCodeOp pcop;
301   int bit;
302   unsigned int inBitSpace: 1; /* True if in bit space, else
303                                  just a bit of a register */
304 } pCodeOpBit;
305 #endif
306 typedef struct pCodeOpLit
307 {
308   pCodeOp pcop;
309   int lit;
310 } pCodeOpLit;
311
312 typedef struct pCodeOpImmd
313 {
314   pCodeOp pcop;
315   int offset;           /* low,med, or high byte of immediate value */
316   int index;            /* add this to the immediate value */
317   unsigned _const:1;    /* is in code space    */
318   unsigned _function:1; /* is a (pointer to a) function */
319
320   int rIdx;             /* If this immd points to a register */
321   struct regs *r;       /* then this is the reg. */
322
323 } pCodeOpImmd;
324
325 typedef struct pCodeOpLabel
326 {
327   pCodeOp pcop;
328   int key;
329   int offset;           /* low or high byte of label */
330 } pCodeOpLabel;
331
332 typedef struct pCodeOpReg
333 {
334   pCodeOp pcop;    // Can be either GPR or SFR
335   int rIdx;        // Index into the register table
336   struct regs *r;
337   int instance;    // byte # of Multi-byte registers
338   struct pBlock *pb;
339 } pCodeOpReg;
340
341 typedef struct pCodeOpRegBit
342 {
343   pCodeOpReg  pcor;       // The Register containing this bit
344   int bit;                // 0-7 bit number.
345   PIC_OPTYPE subtype;     // The type of this register.
346   unsigned int inBitSpace: 1; /* True if in bit space, else
347                                  just a bit of a register */
348 } pCodeOpRegBit;
349
350
351 typedef struct pCodeOpRegPtr
352 {
353   pCodeOpReg  pcor;       // The Register containing this bit
354
355   //  PIC_OPTYPE subtype;     // The type of this register.
356   //  unsigned int inBitSpace: 1; /* True if in bit space, else
357
358 } pCodeOpRegPtr;
359
360 typedef struct pCodeOpWild
361 {
362   pCodeOp pcop;
363
364   struct pCodeWildBlock *pcwb;
365
366   int id;                 /* index into an array of char *'s that will match
367                            * the wild card. The array is in *pcp. */
368   pCodeOp *subtype;       /* Pointer to the Operand type into which this wild
369                            * card will be expanded */
370   pCodeOp *matched;       /* When a wild matches, we'll store a pointer to the
371                            * opcode we matched */
372
373 } pCodeOpWild;
374
375
376 /*************************************************
377     pCode
378
379     Here is the basic build block of a PIC instruction.
380     Each pic instruction will get allocated a pCode.
381     A linked list of pCodes makes a program.
382
383 **************************************************/
384
385 typedef struct pCode
386 {
387   PC_TYPE    type;
388
389   struct pCode *prev;  // The pCode objects are linked together
390   struct pCode *next;  // in doubly linked lists.
391
392   int seq;             // sequence number
393
394   struct pBlock *pb;   // The pBlock that contains this pCode.
395
396   /* "virtual functions"
397    *  The pCode structure is like a base class
398    * in C++. The subsequent structures that "inherit"
399    * the pCode structure will initialize these function
400    * pointers to something useful */
401   //  void (*analyze) (struct pCode *_this);
402   void (*destruct)(struct pCode *_this);
403   void (*print)  (FILE *of,struct pCode *_this);
404
405 } pCode;
406
407
408 /*************************************************
409     pCodeComment
410 **************************************************/
411
412 typedef struct pCodeComment
413 {
414
415   pCode  pc;
416
417   char *comment;
418
419 } pCodeComment;
420
421 /*************************************************
422     pCodeComment
423 **************************************************/
424
425 typedef struct pCodeCSource
426 {
427
428   pCode  pc;
429
430   int  line_number;
431   char *line;
432   char *file_name;
433
434 } pCodeCSource;
435
436
437 /*************************************************
438     pCodeFlow
439
440   The Flow object is used as marker to separate 
441  the assembly code into contiguous chunks. In other
442  words, everytime an instruction cause or potentially
443  causes a branch, a Flow object will be inserted into
444  the pCode chain to mark the beginning of the next
445  contiguous chunk.
446
447 **************************************************/
448
449 typedef struct pCodeFlow
450 {
451
452   pCode  pc;
453
454   pCode *end;   /* Last pCode in this flow. Note that
455                    the first pCode is pc.next */
456
457   /*  set **uses;   * map the pCode instruction inCond and outCond conditions 
458                  * in this array of set's. The reason we allocate an 
459                  * array of pointers instead of declaring each type of 
460                  * usage is because there are port dependent usage definitions */
461   //int nuses;    /* number of uses sets */
462
463   set *from;    /* flow blocks that can send control to this flow block */
464   set *to;      /* flow blocks to which this one can send control */
465   struct pCodeFlow *ancestor; /* The most immediate "single" pCodeFlow object that
466                                * executes prior to this one. In many cases, this 
467                                * will be just the previous */
468
469   int inCond;   /* Input conditions - stuff assumed defined at entry */
470   int outCond;  /* Output conditions - stuff modified by flow block */
471
472   int firstBank; /* The first and last bank flags are the first and last */
473   int lastBank;  /* register banks used within one flow object */
474
475   int FromConflicts;
476   int ToConflicts;
477
478   set *registers;/* Registers used in this flow */
479
480 } pCodeFlow;
481
482 /*************************************************
483   pCodeFlowLink
484
485   The Flow Link object is used to record information
486  about how consecutive excutive Flow objects are related.
487  The pCodeFlow objects demarcate the pCodeInstructions
488  into contiguous chunks. The FlowLink records conflicts
489  in the discontinuities. For example, if one Flow object
490  references a register in bank 0 and the next Flow object
491  references a register in bank 1, then there is a discontinuity
492  in the banking registers.
493
494 */
495 typedef struct pCodeFlowLink
496 {
497   pCodeFlow  *pcflow;   /* pointer to linked pCodeFlow object */
498
499   int bank_conflict;    /* records bank conflicts */
500
501 } pCodeFlowLink;
502
503 /*************************************************
504     pCodeInstruction
505
506     Here we describe all the facets of a PIC instruction
507     (expansion for the 18cxxx is also provided).
508
509 **************************************************/
510
511 typedef struct pCodeInstruction
512 {
513
514   pCode  pc;
515
516   PIC_OPCODE op;        // The opcode of the instruction.
517
518   char const * const mnemonic;       // Pointer to mnemonic string
519
520   pBranch *from;       // pCodes that execute before this one
521   pBranch *to;         // pCodes that execute after
522   pBranch *label;      // pCode instructions that have labels
523
524   pCodeOp *pcop;               /* Operand, if this instruction has one */
525   pCodeFlow *pcflow;           /* flow block to which this instruction belongs */
526   pCodeCSource *cline;         /* C Source from which this instruction was derived */
527
528   unsigned int num_ops;        /* Number of operands (0,1,2 for mid range pics) */
529   unsigned int isModReg:  1;   /* If destination is W or F, then 1==F */
530   unsigned int isBitInst: 1;   /* e.g. BCF */
531   unsigned int isBranch:  1;   /* True if this is a branching instruction */
532   unsigned int isSkip:    1;   /* True if this is a skip instruction */
533   unsigned int isLit:     1;   /* True if this instruction has an literal operand */
534
535   PIC_OPCODE inverted_op;      /* Opcode of instruction that's the opposite of this one */
536   unsigned int inCond;   // Input conditions for this instruction
537   unsigned int outCond;  // Output conditions for this instruction
538
539 } pCodeInstruction;
540
541
542 /*************************************************
543     pCodeLabel
544 **************************************************/
545
546 typedef struct pCodeLabel
547 {
548
549   pCode  pc;
550
551   char *label;
552   int key;
553
554 } pCodeLabel;
555
556 /*************************************************
557     pCodeFunction
558 **************************************************/
559
560 typedef struct pCodeFunction
561 {
562
563   pCode  pc;
564
565   char *modname;
566   char *fname;     /* If NULL, then this is the end of
567                       a function. Otherwise, it's the
568                       start and the name is contained
569                       here */
570
571   pBranch *from;       // pCodes that execute before this one
572   pBranch *to;         // pCodes that execute after
573   pBranch *label;      // pCode instructions that have labels
574
575   int  ncalled;    /* Number of times function is called */
576
577 } pCodeFunction;
578
579
580 /*************************************************
581     pCodeWild
582 **************************************************/
583
584 typedef struct pCodeWild
585 {
586
587   pCodeInstruction  pci;
588
589   int    id;     /* Index into the wild card array of a peepBlock 
590                   * - this wild card will get expanded into that pCode
591                   *   that is stored at this index */
592
593   /* Conditions on wild pcode instruction */
594   int    mustBeBitSkipInst:1;
595   int    mustNotBeBitSkipInst:1;
596   int    invertBitSkipInst:1;
597
598   pCodeOp *operand;  // Optional operand
599   pCodeOp *label;    // Optional label
600
601 } pCodeWild;
602
603 /*************************************************
604     pBlock
605
606     Here are PIC program snippets. There's a strong
607     correlation between the eBBlocks and pBlocks.
608     SDCC subdivides a C program into managable chunks.
609     Each chunk becomes a eBBlock and ultimately in the
610     PIC port a pBlock.
611
612 **************************************************/
613
614 typedef struct pBlock
615 {
616   memmap *cmemmap;   /* The snippet is from this memmap */
617   char   dbName;     /* if cmemmap is NULL, then dbName will identify the block */
618   pCode *pcHead;     /* A pointer to the first pCode in a link list of pCodes */
619   pCode *pcTail;     /* A pointer to the last pCode in a link list of pCodes */
620
621   struct pBlock *next;      /* The pBlocks will form a doubly linked list */
622   struct pBlock *prev;
623
624   set *function_entries;    /* dll of functions in this pblock */
625   set *function_exits;
626   set *function_calls;
627   set *tregisters;
628
629   set *FlowTree;
630   unsigned visited:1;       /* set true if traversed in call tree */
631
632   unsigned seq;             /* sequence number of this pBlock */
633
634 } pBlock;
635
636 /*************************************************
637     pFile
638
639     The collection of pBlock program snippets are
640     placed into a linked list that is implemented
641     in the pFile structure.
642
643     The pcode optimizer will parse the pFile.
644
645 **************************************************/
646
647 typedef struct pFile
648 {
649   pBlock *pbHead;     /* A pointer to the first pBlock */
650   pBlock *pbTail;     /* A pointer to the last pBlock */
651
652   pBranch *functions; /* A SLL of functions in this pFile */
653
654 } pFile;
655
656
657
658 /*************************************************
659   pCodeWildBlock
660
661   The pCodeWildBlock object keeps track of the wild
662   variables, operands, and opcodes that exist in
663   a pBlock.
664 **************************************************/
665 typedef struct pCodeWildBlock {
666   pBlock    *pb;
667   struct pCodePeep *pcp;    // pointer back to ... I don't like this...
668
669   int       nvars;          // Number of wildcard registers in target.
670   char    **vars;           // array of pointers to them
671
672   int       nops;           // Number of wildcard operands in target.
673   pCodeOp **wildpCodeOps;   // array of pointers to the pCodeOp's.
674
675   int       nwildpCodes;    // Number of wildcard pCodes in target/replace
676   pCode   **wildpCodes;     // array of pointers to the pCode's.
677
678 } pCodeWildBlock;
679
680 /*************************************************
681   pCodePeep
682
683   The pCodePeep object mimics the peep hole optimizer
684   in the main SDCC src (e.g. SDCCpeeph.c). Essentially
685   there is a target pCode chain and a replacement
686   pCode chain. The target chain is compared to the
687   pCode that is generated by gen.c. If a match is
688   found then the pCode is replaced by the replacement
689   pCode chain.
690 **************************************************/
691 typedef struct pCodePeep {
692   pCodeWildBlock target;     // code we'd like to optimize
693   pCodeWildBlock replace;    // and this is what we'll optimize it with.
694
695   //pBlock *target;
696   //pBlock replace;            // and this is what we'll optimize it with.
697
698
699
700   /* (Note: a wildcard register is a place holder. Any register
701    * can be replaced by the wildcard when the pcode is being 
702    * compared to the target. */
703
704   /* Post Conditions. A post condition is a condition that
705    * must be either true or false before the peep rule is
706    * accepted. For example, a certain rule may be accepted
707    * if and only if the Z-bit is not used as an input to 
708    * the subsequent instructions in a pCode chain.
709    */
710   unsigned int postFalseCond;  
711   unsigned int postTrueCond;
712
713 } pCodePeep;
714
715 /*************************************************
716
717   pCode peep command definitions 
718
719  Here are some special commands that control the
720 way the peep hole optimizer behaves
721
722 **************************************************/
723
724 enum peepCommandTypes{
725   NOTBITSKIP = 0,
726   BITSKIP,
727   INVERTBITSKIP,
728   _LAST_PEEP_COMMAND_
729 };
730
731 /*************************************************
732     peepCommand structure stores the peep commands.
733
734 **************************************************/
735
736 typedef struct peepCommand {
737   int id;
738   char *cmd;
739 } peepCommand;
740
741 /*************************************************
742     pCode Macros
743
744 **************************************************/
745 #define PCODE(x)  ((pCode *)(x))
746 #define PCI(x)    ((pCodeInstruction *)(x))
747 #define PCL(x)    ((pCodeLabel *)(x))
748 #define PCF(x)    ((pCodeFunction *)(x))
749 #define PCFL(x)   ((pCodeFlow *)(x))
750 #define PCFLINK(x)((pCodeFlowLink *)(x))
751 #define PCW(x)    ((pCodeWild *)(x))
752 #define PCCS(x)   ((pCodeCSource *)(x))
753
754 #define PCOP(x)   ((pCodeOp *)(x))
755 //#define PCOB(x)   ((pCodeOpBit *)(x))
756 #define PCOL(x)   ((pCodeOpLit *)(x))
757 #define PCOI(x)   ((pCodeOpImmd *)(x))
758 #define PCOLAB(x) ((pCodeOpLabel *)(x))
759 #define PCOR(x)   ((pCodeOpReg *)(x))
760 #define PCORB(x)  ((pCodeOpRegBit *)(x))
761 #define PCOW(x)   ((pCodeOpWild *)(x))
762
763 #define PBR(x)    ((pBranch *)(x))
764
765 #define PCWB(x)   ((pCodeWildBlock *)(x))
766
767
768 /*
769   macros for checking pCode types
770 */
771 #define isPCI(x)        ((PCODE(x)->type == PC_OPCODE))
772 #define isPCI_BRANCH(x) ((PCODE(x)->type == PC_OPCODE) &&  PCI(x)->isBranch)
773 #define isPCI_SKIP(x)   ((PCODE(x)->type == PC_OPCODE) &&  PCI(x)->isSkip)
774 #define isPCI_LIT(x)    ((PCODE(x)->type == PC_OPCODE) &&  PCI(x)->isLit)
775 #define isPCI_BITSKIP(x)((PCODE(x)->type == PC_OPCODE) &&  PCI(x)->isSkip && PCI(x)->isBitInst)
776 #define isPCFL(x)       ((PCODE(x)->type == PC_FLOW))
777 #define isPCF(x)        ((PCODE(x)->type == PC_FUNCTION))
778 #define isPCL(x)        ((PCODE(x)->type == PC_LABEL))
779 #define isPCW(x)        ((PCODE(x)->type == PC_WILD))
780 #define isPCCS(x)       ((PCODE(x)->type == PC_CSOURCE))
781
782 #define isCALL(x)       ((isPCI(x)) && (PCI(x)->op == POC_CALL))
783 #define isSTATUS_REG(r) ((r)->pc_type == PO_STATUS)
784
785 #define isPCOLAB(x)     ((PCOP(x)->type) == PO_LABEL)
786
787 /*-----------------------------------------------------------------*
788  * pCode functions.
789  *-----------------------------------------------------------------*/
790
791 pCode *newpCode (PIC_OPCODE op, pCodeOp *pcop); // Create a new pCode given an operand
792 pCode *newpCodeCharP(char *cP);              // Create a new pCode given a char *
793 pCode *newpCodeInlineP(char *cP);            // Create a new pCode given a char *
794 pCode *newpCodeFunction(char *g, char *f);   // Create a new function
795 pCode *newpCodeLabel(char *name,int key);    // Create a new label given a key
796 pCode *newpCodeCSource(int ln, char *f, char *l); // Create a new symbol line 
797 pBlock *newpCodeChain(memmap *cm,char c, pCode *pc); // Create a new pBlock
798 void printpBlock(FILE *of, pBlock *pb);      // Write a pBlock to a file
799 void printpCode(FILE *of, pCode *pc);        // Write a pCode to a file
800 void addpCode2pBlock(pBlock *pb, pCode *pc); // Add a pCode to a pBlock
801 void addpBlock(pBlock *pb);                  // Add a pBlock to a pFile
802 void copypCode(FILE *of, char dbName);       // Write all pBlocks with dbName to *of
803 void movepBlock2Head(char dbName);           // move pBlocks around
804 void AnalyzepCode(char dbName);
805 int OptimizepCode(char dbName);
806 void printCallTree(FILE *of);
807 void pCodePeepInit(void);
808 void pBlockConvert2ISR(pBlock *pb);
809
810 pCodeOp *newpCodeOpLabel(char *name, int key);
811 pCodeOp *newpCodeOpImmd(char *name, int offset, int index, int code_space,int is_func);
812 pCodeOp *newpCodeOpLit(int lit);
813 pCodeOp *newpCodeOpBit(char *name, int bit,int inBitSpace);
814 pCodeOp *newpCodeOpRegFromStr(char *name);
815 pCodeOp *newpCodeOp(char *name, PIC_OPTYPE p);
816 pCodeOp *pCodeOpCopy(pCodeOp *pcop);
817
818 pCode * findNextInstruction(pCode *pci);
819 pCode * findNextpCode(pCode *pc, PC_TYPE pct);
820 int isPCinFlow(pCode *pc, pCode *pcflow);
821 struct regs * getRegFromInstruction(pCode *pc);
822
823 extern void pcode_test(void);
824
825 /*-----------------------------------------------------------------*
826  * pCode objects.
827  *-----------------------------------------------------------------*/
828
829 extern pCodeOpReg pc_status;
830 extern pCodeOpReg pc_intcon;
831 extern pCodeOpReg pc_indf;
832 extern pCodeOpReg pc_fsr;
833 extern pCodeOpReg pc_pcl;
834 extern pCodeOpReg pc_pclath;
835 extern pCodeOpReg pc_kzero;
836 extern pCodeOpReg pc_wsave;     /* wsave, ssave and psave are used to save W, the Status and PCLATH*/
837 extern pCodeOpReg pc_ssave;     /* registers during an interrupt */
838 extern pCodeOpReg pc_psave;     /* registers during an interrupt */
839
840
841 #endif // __PCODE_H__