* src/pic16/gen.c (pic16_freeAsmop): release any temp registers
[fw/sdcc] / src / pic16 / pcode.h
1 /*-------------------------------------------------------------------------
2
3    pcode.h - post code generation
4    Written By -  Scott Dattalo scott@dattalo.com
5    Ported to PIC16 By -  Martin Dubuc m.dubuc@rogers.com
6
7    This program is free software; you can redistribute it and/or modify it
8    under the terms of the GNU General Public License as published by the
9    Free Software Foundation; either version 2, or (at your option) any
10    later version.
11    
12    This program is distributed in the hope that it will be useful,
13    but WITHOUT ANY WARRANTY; without even the implied warranty of
14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15    GNU General Public License for more details.
16    
17    You should have received a copy of the GNU General Public License
18    along with this program; if not, write to the Free Software
19    Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
20    
21 -------------------------------------------------------------------------*/
22
23 //#include "ralloc.h"
24 struct regs;
25
26 /*
27    Post code generation
28
29    The post code generation is an assembler optimizer. The assembly code
30    produced by all of the previous steps is fully functional. This step
31    will attempt to analyze the flow of the assembly code and agressively 
32    optimize it. The peep hole optimizer attempts to do the same thing.
33    As you may recall, the peep hole optimizer replaces blocks of assembly
34    with more optimal blocks (e.g. removing redundant register loads).
35    However, the peep hole optimizer has to be somewhat conservative since
36    an assembly program has implicit state information that's unavailable 
37    when only a few instructions are examined.
38      Consider this example:
39
40    example1:
41      movwf  t1
42      movf   t1,w
43
44    The movf seems redundant since we know that the W register already
45    contains the same value of t1. So a peep hole optimizer is tempted to
46    remove the "movf". However, this is dangerous since the movf affects
47    the flags in the status register (specifically the Z flag) and subsequent
48    code may depend upon this. Look at these two examples:
49
50    example2:
51      movwf  t1
52      movf   t1,w     ; Can't remove this movf
53      skpz
54       return
55
56    example3:
57      movwf  t1
58      movf   t1,w     ; This  movf can be removed
59      xorwf  t2,w     ; since xorwf will over write Z 
60      skpz
61       return
62
63 */
64
65
66 #ifndef __PCODE_H__
67 #define __PCODE_H__
68
69 /***********************************************************************
70  * debug stuff
71  * 
72  * The DFPRINTF macro will call fprintf if PCODE_DEBUG is defined.
73  * The macro is used like:
74  *
75  * DPRINTF(("%s #%d\n","test", 1));
76  *
77  * The double parenthesis (()) are necessary
78  * 
79  ***********************************************************************/
80 //#define PCODE_DEBUG
81
82 #ifdef PCODE_DEBUG
83 #define DFPRINTF(args) (fprintf args)
84 #else
85 #define DFPRINTF(args) ;
86 #endif
87
88
89 #ifdef WORDS_BIGENDIAN
90   #define _ENDIAN(x)  (3-x)
91 #else
92   #define _ENDIAN(x)  (x)
93 #endif
94
95
96 #define BYTE_IN_LONG(x,b) ((x>>(8*_ENDIAN(b)))&0xff)
97
98
99 /***********************************************************************
100  * Extended Instruction Set/Indexed Literal Offset Mode                *
101  * Set this macro to enable code generation with the extended          *
102  * instruction set and the new Indexed Literal Offset Mode             *
103  ***********************************************************************/
104 #define XINST   1
105
106 /***********************************************************************
107  *  PIC status bits - this will move into device dependent headers
108  ***********************************************************************/
109 #define PIC_C_BIT    0
110 #define PIC_DC_BIT   1
111 #define PIC_Z_BIT    2
112 #define PIC_OV_BIT   3
113 #define PIC_N_BIT    4
114 #define PIC_IRP_BIT  7   /* Indirect register page select */
115
116 /***********************************************************************
117  *  PIC INTCON bits - this will move into device dependent headers
118  ***********************************************************************/
119 #define PIC_RBIF_BIT 0   /* Port B level has changed flag */
120 #define PIC_INTF_BIT 1   /* Port B bit 0 interrupt on edge flag */
121 #define PIC_T0IF_BIT 2   /* TMR0 has overflowed flag */
122 #define PIC_RBIE_BIT 3   /* Port B level has changed - Interrupt Enable */
123 #define PIC_INTE_BIT 4   /* Port B bit 0 interrupt on edge - Int Enable */
124 #define PIC_T0IE_BIT 5   /* TMR0 overflow Interrupt Enable */
125 #define PIC_PIE_BIT  6   /* Peripheral Interrupt Enable */
126 #define PIC_GIE_BIT  7   /* Global Interrupt Enable */
127
128 /***********************************************************************
129  *  PIC bank definitions
130  ***********************************************************************/
131 #define PIC_BANK_FIRST 0
132 #define PIC_BANK_LAST  0xf
133
134
135 /***********************************************************************
136  *  Operand types 
137  ***********************************************************************/
138 #define POT_RESULT  0
139 #define POT_LEFT    1
140 #define POT_RIGHT   2
141
142
143 /***********************************************************************
144  *
145  *  PIC_OPTYPE - Operand types that are specific to the PIC architecture
146  *
147  *  If a PIC assembly instruction has an operand then here is where we
148  *  associate a type to it. For example,
149  *
150  *     movf    reg,W
151  *
152  *  The movf has two operands: 'reg' and the W register. 'reg' is some
153  *  arbitrary general purpose register, hence it has the type PO_GPR_REGISTER.
154  *  The W register, which is the PIC's accumulator, has the type PO_W.
155  *
156  ***********************************************************************/
157
158
159
160 typedef enum 
161 {
162   PO_NONE=0,         // No operand e.g. NOP
163   PO_W,              // The working register (as a destination)
164   PO_WREG,           // The working register (as a file register)
165   PO_STATUS,         // The 'STATUS' register
166   PO_BSR,            // The 'BSR' register
167   PO_FSR0,           // The "file select register" (in PIC18 family it's one 
168                      // of three)
169   PO_INDF0,          // The Indirect register
170   PO_INTCON,         // Interrupt Control register
171   PO_GPR_REGISTER,   // A general purpose register
172   PO_GPR_BIT,        // A bit of a general purpose register
173   PO_GPR_TEMP,       // A general purpose temporary register
174   PO_SFR_REGISTER,   // A special function register (e.g. PORTA)
175   PO_PCL,            // Program counter Low register
176   PO_PCLATH,         // Program counter Latch high register
177   PO_PCLATU,         // Program counter Latch upper register
178   PO_PRODL,          // Product Register Low
179   PO_PRODH,          // Product Register High
180   PO_LITERAL,        // A constant
181   PO_REL_ADDR,       // A relative address
182   PO_IMMEDIATE,      //  (8051 legacy)
183   PO_DIR,            // Direct memory (8051 legacy)
184   PO_CRY,            // bit memory (8051 legacy)
185   PO_BIT,            // bit operand.
186   PO_STR,            //  (8051 legacy)
187   PO_LABEL,
188   PO_WILD            // Wild card operand in peep optimizer
189 } PIC_OPTYPE;
190
191
192 /***********************************************************************
193  *
194  *  PIC_OPCODE
195  *
196  *  This is not a list of the PIC's opcodes per se, but instead
197  *  an enumeration of all of the different types of pic opcodes. 
198  *
199  ***********************************************************************/
200
201 typedef enum
202 {
203   POC_WILD=-1,   /* Wild card - used in the pCode peep hole optimizer
204                   * to represent ANY pic opcode */
205   POC_ADDLW=0,
206   POC_ADDWF,
207   POC_ADDFW,
208   POC_ADDFWC,
209   POC_ADDWFC,
210   POC_ANDLW,
211   POC_ANDWF,
212   POC_ANDFW,
213   POC_BC,
214   POC_BCF,
215   POC_BN,
216   POC_BNC,
217   POC_BNN,
218   POC_BNOV,
219   POC_BNZ,
220   POC_BOV,
221   POC_BRA,
222   POC_BSF,
223   POC_BTFSC,
224   POC_BTFSS,
225   POC_BTG,
226   POC_BZ,
227   POC_CALL,
228   POC_CLRF,
229   POC_CLRWDT,
230   POC_COMF,
231   POC_COMFW,
232   POC_CPFSEQ,
233   POC_CPFSGT,
234   POC_CPFSLT,
235   POC_DAW,
236   POC_DCFSNZ,
237   POC_DCFSNZW,
238   POC_DECF,
239   POC_DECFW,
240   POC_DECFSZ,
241   POC_DECFSZW,
242   POC_GOTO,
243   POC_INCF,
244   POC_INCFW,
245   POC_INCFSZ,
246   POC_INCFSZW,
247   POC_INFSNZ,
248   POC_INFSNZW,
249   POC_IORWF,
250   POC_IORFW,
251   POC_IORLW,
252   POC_LFSR,
253   POC_MOVF,
254   POC_MOVFW,
255   POC_MOVFF,
256   POC_MOVLB,
257   POC_MOVLW,
258   POC_MOVWF,
259   POC_MULLW,
260   POC_MULWF,
261   POC_NEGF,
262   POC_NOP,
263   POC_POP,
264   POC_PUSH,
265   POC_RCALL,
266   POC_RETFIE,
267   POC_RETLW,
268   POC_RETURN,
269   POC_RLCF,
270   POC_RLCFW,
271   POC_RLNCF,
272   POC_RLNCFW,
273   POC_RRCF,
274   POC_RRCFW,
275   POC_RRNCF,
276   POC_RRNCFW,
277   POC_SETF,
278   POC_SUBLW,
279   POC_SUBFWB,
280   POC_SUBWF,
281   POC_SUBFW,
282   POC_SUBWFB_D0,
283   POC_SUBWFB_D1,
284   POC_SUBFWB_D0,
285   POC_SUBFWB_D1,
286   POC_SWAPF,
287   POC_SWAPFW,
288   POC_TBLRD,
289   POC_TBLRD_POSTINC,
290   POC_TBLRD_POSTDEC,
291   POC_TBLRD_PREINC,
292   POC_TBLWT,
293   POC_TBLWT_POSTINC,
294   POC_TBLWT_POSTDEC,
295   POC_TBLWT_PREINC,
296   POC_TSTFSZ,
297   POC_XORLW,
298   POC_XORWF,
299   POC_XORFW,
300
301   POC_BANKSEL
302
303   /* pseudo-instructions */
304 } PIC_OPCODE;
305
306
307 /***********************************************************************
308  *  PC_TYPE  - pCode Types
309  ***********************************************************************/
310
311 typedef enum
312 {
313   PC_COMMENT=0,   /* pCode is a comment     */
314   PC_INLINE,      /* user's inline code     */
315   PC_OPCODE,      /* PORT dependent opcode  */
316   PC_LABEL,       /* assembly label         */
317   PC_FLOW,        /* flow analysis          */
318   PC_FUNCTION,    /* Function start or end  */
319   PC_WILD,        /* wildcard - an opcode place holder used 
320                    * in the pCode peep hole optimizer */
321   PC_CSOURCE,     /* C-Source Line  */
322   PC_ASMDIR,      /* Assembler directive */
323   PC_BAD,         /* Mark the pCode object as being bad */
324   PC_INFO         /* pCode information node, used primarily in optimizing */
325 } PC_TYPE;
326
327
328 /***********************************************************************
329  *  INFO_TYPE  - information node types
330  ***********************************************************************/
331
332 typedef enum
333 {
334   INF_OPTIMIZATION,      /* structure contains optimization information */
335   INF_LOCALREGS          /* structure contains local register information */
336 } INFO_TYPE;
337
338
339
340 /***********************************************************************
341  *  OPT_TYPE  - optimization node types
342  ***********************************************************************/
343
344 typedef enum
345 {
346   OPT_BEGIN,             /* mark beginning of optimization block */
347   OPT_END,               /* mark ending of optimization block */
348   OPT_JUMPTABLE_BEGIN,   /* mark beginning of a jumptable */
349   OPT_JUMPTABLE_END      /* mark end of jumptable */
350 } OPT_TYPE;
351
352 /***********************************************************************
353  *  LR_TYPE  - optimization node types
354  ***********************************************************************/
355
356 typedef enum
357 {
358   LR_ENTRY_BEGIN,             /* mark beginning of optimization block */
359   LR_ENTRY_END,               /* mark ending of optimization block */
360   LR_EXIT_BEGIN,
361   LR_EXIT_END
362 } LR_TYPE;
363
364
365 /************************************************/
366 /***************  Structures ********************/
367 /************************************************/
368 /* These are here as forward references - the 
369  * full definition of these are below           */
370 struct pCode;
371 struct pCodeWildBlock;
372 struct pCodeRegLives;
373
374 /*************************************************
375   pBranch
376
377   The first step in optimizing pCode is determining
378  the program flow. This information is stored in
379  single-linked lists in the for of 'from' and 'to'
380  objects with in a pcode. For example, most instructions
381  don't involve any branching. So their from branch
382  points to the pCode immediately preceding them and
383  their 'to' branch points to the pcode immediately
384  following them. A skip instruction is an example of
385  a pcode that has multiple (in this case two) elements
386  in the 'to' branch. A 'label' pcode is an where there
387  may be multiple 'from' branches.
388  *************************************************/
389
390 typedef struct pBranch
391 {
392   struct pCode   *pc;    // Next pCode in a branch
393   struct pBranch *next;  /* If more than one branch
394                           * the next one is here */
395
396 } pBranch;
397
398 /*************************************************
399   pCodeOp
400
401   pCode Operand structure.
402   For those assembly instructions that have arguments, 
403   the pCode will have a pCodeOp in which the argument
404   can be stored. For example
405
406     movf   some_register,w
407
408   'some_register' will be stored/referenced in a pCodeOp
409
410  *************************************************/
411
412 typedef struct pCodeOp
413 {
414   PIC_OPTYPE type;
415   char *name;
416   
417 } pCodeOp;
418
419 #if 0
420 typedef struct pCodeOpBit
421 {
422   pCodeOp pcop;
423   int bit;
424   unsigned int inBitSpace: 1; /* True if in bit space, else
425                                  just a bit of a register */
426 } pCodeOpBit;
427 #endif
428
429 typedef struct pCodeOpLit
430 {
431   pCodeOp pcop;
432   int lit;
433   pCodeOp *arg2;        /* needed as pCodeOpLit and pCodeOpLit2 are not separable via their type (PO_LITERAL) */
434 } pCodeOpLit;
435
436 typedef struct pCodeOpLit2
437 {
438   pCodeOp pcop;
439   int lit;
440   pCodeOp *arg2;
441 } pCodeOpLit2;
442
443
444 typedef struct pCodeOpImmd
445 {
446   pCodeOp pcop;
447   int offset;           /* low,high or upper byte of immediate value */
448   int index;            /* add this to the immediate value */
449   unsigned _const:1;    /* is in code space    */
450
451   int rIdx;             /* If this immd points to a register */
452   struct regs *r;       /* then this is the reg. */
453
454 } pCodeOpImmd;
455
456 typedef struct pCodeOpLabel
457 {
458   pCodeOp pcop;
459   int key;
460 } pCodeOpLabel;
461
462 typedef struct pCodeOpReg
463 {
464   pCodeOp pcop;    // Can be either GPR or SFR
465   int rIdx;        // Index into the register table
466   struct regs *r;
467   int instance;    // byte # of Multi-byte registers
468   struct pBlock *pb;
469
470   pCodeOp *pcop2;       // second memory operand (NEEDED IN gen.c:pic16_popGet2p (pCodeOpReg casted into pCodeOpReg2) 
471 } pCodeOpReg;
472
473 typedef struct pCodeOpReg2
474 {
475   pCodeOp pcop;         // used by default to all references
476   int rIdx;
477   struct regs *r;
478   int instance;         // assume same instance for both operands
479   struct pBlock *pb;
480
481   pCodeOp *pcop2;       // second memory operand
482 } pCodeOpReg2;
483
484 typedef struct pCodeOpRegBit
485 {
486   pCodeOpReg  pcor;       // The Register containing this bit
487   int bit;                // 0-7 bit number.
488   PIC_OPTYPE subtype;     // The type of this register.
489   unsigned int inBitSpace: 1; /* True if in bit space, else
490                                  just a bit of a register */
491 } pCodeOpRegBit;
492
493
494 typedef struct pCodeOpWild
495 {
496   pCodeOp pcop;
497
498   struct pCodeWildBlock *pcwb;
499
500   int id;                 /* index into an array of char *'s that will match
501                            * the wild card. The array is in *pcp. */
502   pCodeOp *subtype;       /* Pointer to the Operand type into which this wild
503                            * card will be expanded */
504   pCodeOp *matched;       /* When a wild matches, we'll store a pointer to the
505                            * opcode we matched */
506
507   pCodeOp *pcop2;         /* second operand if exists */
508
509 } pCodeOpWild;
510
511
512 typedef struct pCodeOpOpt
513 {
514   pCodeOp pcop;
515   
516   OPT_TYPE type;          /* optimization node type */
517   
518   char *key;              /* key by which a block is identified */
519 } pCodeOpOpt;
520
521 typedef struct pCodeOpLocalReg
522 {
523   pCodeOp pcop;
524
525   LR_TYPE type;
526 } pCodeOpLocalReg;  
527
528 /*************************************************
529     pCode
530
531     Here is the basic build block of a PIC instruction.
532     Each pic instruction will get allocated a pCode.
533     A linked list of pCodes makes a program.
534
535 **************************************************/
536
537 typedef struct pCode
538 {
539   PC_TYPE    type;
540
541   struct pCode *prev;  // The pCode objects are linked together
542   struct pCode *next;  // in doubly linked lists.
543
544   int seq;             // sequence number
545
546   struct pBlock *pb;   // The pBlock that contains this pCode.
547
548   /* "virtual functions"
549    *  The pCode structure is like a base class
550    * in C++. The subsequent structures that "inherit"
551    * the pCode structure will initialize these function
552    * pointers to something useful */
553   //  void (*analyze) (struct pCode *_this);
554   void (*destruct)(struct pCode *_this);
555   void (*print)  (FILE *of,struct pCode *_this);
556
557 } pCode;
558
559
560 /*************************************************
561     pCodeComment
562 **************************************************/
563
564 typedef struct pCodeComment
565 {
566
567   pCode  pc;
568
569   char *comment;
570
571 } pCodeComment;
572
573
574 /*************************************************
575     pCodeCSource
576 **************************************************/
577
578 typedef struct pCodeCSource
579 {
580
581   pCode  pc;
582
583   int  line_number;
584   char *line;
585   char *file_name;
586
587 } pCodeCSource;
588
589
590 /*************************************************
591     pCodeAsmDir
592 **************************************************/
593
594 /*************************************************
595     pCodeFlow
596
597   The Flow object is used as marker to separate 
598  the assembly code into contiguous chunks. In other
599  words, everytime an instruction cause or potentially
600  causes a branch, a Flow object will be inserted into
601  the pCode chain to mark the beginning of the next
602  contiguous chunk.
603
604 **************************************************/
605 struct defmap_s; // defined in pcode.c
606
607 typedef struct pCodeFlow
608 {
609
610   pCode  pc;
611
612   pCode *end;   /* Last pCode in this flow. Note that
613                    the first pCode is pc.next */
614
615   /*  set **uses;   * map the pCode instruction inCond and outCond conditions 
616                  * in this array of set's. The reason we allocate an 
617                  * array of pointers instead of declaring each type of 
618                  * usage is because there are port dependent usage definitions */
619   //int nuses;    /* number of uses sets */
620
621   set *from;    /* flow blocks that can send control to this flow block */
622   set *to;      /* flow blocks to which this one can send control */
623   struct pCodeFlow *ancestor; /* The most immediate "single" pCodeFlow object that
624                                * executes prior to this one. In many cases, this 
625                                * will be just the previous */
626
627   int inCond;   /* Input conditions - stuff assumed defined at entry */
628   int outCond;  /* Output conditions - stuff modified by flow block */
629
630   int firstBank; /* The first and last bank flags are the first and last */
631   int lastBank;  /* register banks used within one flow object */
632
633   int FromConflicts;
634   int ToConflicts;
635
636   set *registers;/* Registers used in this flow */
637
638   struct defmap_s *defmap;      /* chronologically ordered list of definitions performed
639                            in this flow (most recent at the front) */
640   struct defmap_s *in_vals;     /* definitions of all symbols reaching this flow
641                                  * symbols with multiple different definitions are stored
642                                  * with an assigned value of 0. */
643   struct defmap_s *out_vals;    /* definitions valid AFTER thie flow */
644
645 } pCodeFlow;
646
647 /*************************************************
648   pCodeFlowLink
649
650   The Flow Link object is used to record information
651  about how consecutive excutive Flow objects are related.
652  The pCodeFlow objects demarcate the pCodeInstructions
653  into contiguous chunks. The FlowLink records conflicts
654  in the discontinuities. For example, if one Flow object
655  references a register in bank 0 and the next Flow object
656  references a register in bank 1, then there is a discontinuity
657  in the banking registers.
658
659 */
660 typedef struct pCodeFlowLink
661 {
662   pCodeFlow  *pcflow;   /* pointer to linked pCodeFlow object */
663
664   int bank_conflict;    /* records bank conflicts */
665
666 } pCodeFlowLink;
667
668 /*************************************************
669     pCodeInstruction
670
671     Here we describe all the facets of a PIC instruction
672     (expansion for the 18cxxx is also provided).
673
674 **************************************************/
675
676 typedef struct pCodeInstruction
677 {
678
679   pCode  pc;
680
681   PIC_OPCODE op;        // The opcode of the instruction.
682
683   char const * const mnemonic;       // Pointer to mnemonic string
684
685   char isize;          // pCode instruction size
686
687   pBranch *from;       // pCodes that execute before this one
688   pBranch *to;         // pCodes that execute after
689   pBranch *label;      // pCode instructions that have labels
690
691   pCodeOp *pcop;               /* Operand, if this instruction has one */
692   pCodeFlow *pcflow;           /* flow block to which this instruction belongs */
693   pCodeCSource *cline;         /* C Source from which this instruction was derived */
694
695   unsigned int num_ops;        /* Number of operands (0,1,2 for mid range pics) */
696   unsigned int isModReg:  1;   /* If destination is W or F, then 1==F */
697   unsigned int isBitInst: 1;   /* e.g. BCF */
698   unsigned int isBranch:  1;   /* True if this is a branching instruction */
699   unsigned int isSkip:    1;   /* True if this is a skip instruction */
700   unsigned int isLit:     1;   /* True if this instruction has an literal operand */
701   unsigned int isAccess:   1;   /* True if this instruction has an access RAM operand */
702   unsigned int isFastCall: 1;   /* True if this instruction has a fast call/return mode select operand */
703   unsigned int is2MemOp: 1;     /* True is second operand is a memory operand VR - support for MOVFF */
704   unsigned int is2LitOp: 1;     /* True if instruction takes 2 literal operands VR - support for LFSR */
705
706   PIC_OPCODE inverted_op;      /* Opcode of instruction that's the opposite of this one */
707   unsigned int inCond;   // Input conditions for this instruction
708   unsigned int outCond;  // Output conditions for this instruction
709
710 #define PCI_MAGIC       0x6e12
711   unsigned int pci_magic;       // sanity check for pci initialization
712 } pCodeInstruction;
713
714
715
716 /*************************************************
717     pCodeAsmDir
718 **************************************************/
719
720 typedef struct pCodeAsmDir
721 {
722   pCodeInstruction pci;
723   
724   char *directive;
725   char *arg;
726 } pCodeAsmDir;
727
728
729 /*************************************************
730     pCodeLabel
731 **************************************************/
732
733 typedef struct pCodeLabel
734 {
735
736   pCode  pc;
737
738   char *label;
739   int key;
740   int force;            /* label cannot be optimized out */
741
742 } pCodeLabel;
743
744 /*************************************************
745     pCodeFunction
746 **************************************************/
747
748 typedef struct pCodeFunction
749 {
750
751   pCode  pc;
752
753   char *modname;
754   char *fname;     /* If NULL, then this is the end of
755                       a function. Otherwise, it's the
756                       start and the name is contained
757                       here */
758
759   pBranch *from;       // pCodes that execute before this one
760   pBranch *to;         // pCodes that execute after
761   pBranch *label;      // pCode instructions that have labels
762
763   int  ncalled;    /* Number of times function is called */
764
765   int absblock;    /* hack to emulate a block pCodes in absolute position
766                       but not inside a function */
767   int stackusage;  /* stack positions used in function */
768   
769 } pCodeFunction;
770
771
772 /*************************************************
773     pCodeWild
774 **************************************************/
775
776 typedef struct pCodeWild
777 {
778
779   pCodeInstruction  pci;
780
781   int    id;     /* Index into the wild card array of a peepBlock 
782                   * - this wild card will get expanded into that pCode
783                   *   that is stored at this index */
784
785   /* Conditions on wild pcode instruction */
786   int    mustBeBitSkipInst:1;
787   int    mustNotBeBitSkipInst:1;
788   int    invertBitSkipInst:1;
789
790   pCodeOp *operand;  // Optional operand
791   pCodeOp *label;    // Optional label
792
793 } pCodeWild;
794
795
796 /*************************************************
797     pInfo
798     
799     Here are stored generic informaton
800 *************************************************/
801 typedef struct pCodeInfo
802 {
803   pCodeInstruction pci;
804   
805   INFO_TYPE type;       /* info node type */
806   
807   pCodeOp *oper1;       /* info node arguments */
808 } pCodeInfo;
809   
810
811 /*************************************************
812     pBlock
813
814     Here are PIC program snippets. There's a strong
815     correlation between the eBBlocks and pBlocks.
816     SDCC subdivides a C program into managable chunks.
817     Each chunk becomes a eBBlock and ultimately in the
818     PIC port a pBlock.
819
820 **************************************************/
821
822 typedef struct pBlock
823 {
824   memmap *cmemmap;   /* The snippet is from this memmap */
825   char   dbName;     /* if cmemmap is NULL, then dbName will identify the block */
826   pCode *pcHead;     /* A pointer to the first pCode in a link list of pCodes */
827   pCode *pcTail;     /* A pointer to the last pCode in a link list of pCodes */
828
829   struct pBlock *next;      /* The pBlocks will form a doubly linked list */
830   struct pBlock *prev;
831
832   set *function_entries;    /* dll of functions in this pblock */
833   set *function_exits;
834   set *function_calls;
835   set *tregisters;
836
837   set *FlowTree;
838   unsigned visited:1;       /* set true if traversed in call tree */
839
840   unsigned seq;             /* sequence number of this pBlock */
841
842 } pBlock;
843
844 /*************************************************
845     pFile
846
847     The collection of pBlock program snippets are
848     placed into a linked list that is implemented
849     in the pFile structure.
850
851     The pcode optimizer will parse the pFile.
852
853 **************************************************/
854
855 typedef struct pFile
856 {
857   pBlock *pbHead;     /* A pointer to the first pBlock */
858   pBlock *pbTail;     /* A pointer to the last pBlock */
859
860   pBranch *functions; /* A SLL of functions in this pFile */
861
862 } pFile;
863
864
865
866 /*************************************************
867   pCodeWildBlock
868
869   The pCodeWildBlock object keeps track of the wild
870   variables, operands, and opcodes that exist in
871   a pBlock.
872 **************************************************/
873 typedef struct pCodeWildBlock {
874   pBlock    *pb;
875   struct pCodePeep *pcp;    // pointer back to ... I don't like this...
876
877   int       nvars;          // Number of wildcard registers in target.
878   char    **vars;           // array of pointers to them
879
880   int       nops;           // Number of wildcard operands in target.
881   pCodeOp **wildpCodeOps;   // array of pointers to the pCodeOp's.
882
883   int       nwildpCodes;    // Number of wildcard pCodes in target/replace
884   pCode   **wildpCodes;     // array of pointers to the pCode's.
885
886 } pCodeWildBlock;
887
888 /*************************************************
889   pCodePeep
890
891   The pCodePeep object mimics the peep hole optimizer
892   in the main SDCC src (e.g. SDCCpeeph.c). Essentially
893   there is a target pCode chain and a replacement
894   pCode chain. The target chain is compared to the
895   pCode that is generated by gen.c. If a match is
896   found then the pCode is replaced by the replacement
897   pCode chain.
898 **************************************************/
899 typedef struct pCodePeep {
900   pCodeWildBlock target;     // code we'd like to optimize
901   pCodeWildBlock replace;    // and this is what we'll optimize it with.
902
903   //pBlock *target;
904   //pBlock replace;            // and this is what we'll optimize it with.
905
906
907
908   /* (Note: a wildcard register is a place holder. Any register
909    * can be replaced by the wildcard when the pcode is being 
910    * compared to the target. */
911
912   /* Post Conditions. A post condition is a condition that
913    * must be either true or false before the peep rule is
914    * accepted. For example, a certain rule may be accepted
915    * if and only if the Z-bit is not used as an input to 
916    * the subsequent instructions in a pCode chain.
917    */
918   unsigned int postFalseCond;  
919   unsigned int postTrueCond;
920
921 } pCodePeep;
922
923 /*************************************************
924
925   pCode peep command definitions 
926
927  Here are some special commands that control the
928 way the peep hole optimizer behaves
929
930 **************************************************/
931
932 enum peepCommandTypes{
933   NOTBITSKIP = 0,
934   BITSKIP,
935   INVERTBITSKIP,
936   _LAST_PEEP_COMMAND_
937 };
938
939 /*************************************************
940     peepCommand structure stores the peep commands.
941
942 **************************************************/
943
944 typedef struct peepCommand {
945   int id;
946   char *cmd;
947 } peepCommand;
948
949 /*************************************************
950     pCode Macros
951
952 **************************************************/
953 #define PCODE(x)  ((pCode *)(x))
954 #define PCI(x)    ((pCodeInstruction *)(x))
955 #define PCL(x)    ((pCodeLabel *)(x))
956 #define PCF(x)    ((pCodeFunction *)(x))
957 #define PCFL(x)   ((pCodeFlow *)(x))
958 #define PCFLINK(x)((pCodeFlowLink *)(x))
959 #define PCW(x)    ((pCodeWild *)(x))
960 #define PCCS(x)   ((pCodeCSource *)(x))
961 #define PCAD(x)   ((pCodeAsmDir *)(x))
962 #define PCINF(x)  ((pCodeInfo *)(x))
963
964 #define PCOP(x)   ((pCodeOp *)(x))
965 //#define PCOB(x)   ((pCodeOpBit *)(x))
966 #define PCOL(x)   ((pCodeOpLit *)(x))
967 #define PCOI(x)   ((pCodeOpImmd *)(x))
968 #define PCOLAB(x) ((pCodeOpLabel *)(x))
969 #define PCOR(x)   ((pCodeOpReg *)(x))
970 #define PCOR2(x)  ((pCodeOpReg2 *)(x))
971 #define PCORB(x)  ((pCodeOpRegBit *)(x))
972 #define PCOO(x)   ((pCodeOpOpt *)(x))
973 #define PCOLR(x)  ((pCodeOpLocalReg *)(x))
974 #define PCOW(x)   ((pCodeOpWild *)(x))
975 #define PCOW2(x)  (PCOW(PCOW(x)->pcop2))
976 #define PBR(x)    ((pBranch *)(x))
977
978 #define PCWB(x)   ((pCodeWildBlock *)(x))
979
980
981 /*
982   macros for checking pCode types
983 */
984 #define isPCI(x)        ((PCODE(x)->type == PC_OPCODE))
985 #define isPCI_BRANCH(x) ((PCODE(x)->type == PC_OPCODE) &&  PCI(x)->isBranch)
986 #define isPCI_SKIP(x)   ((PCODE(x)->type == PC_OPCODE) &&  PCI(x)->isSkip)
987 #define isPCI_LIT(x)    ((PCODE(x)->type == PC_OPCODE) &&  PCI(x)->isLit)
988 #define isPCI_BITSKIP(x)((PCODE(x)->type == PC_OPCODE) &&  PCI(x)->isSkip && PCI(x)->isBitInst)
989 #define isPCFL(x)       ((PCODE(x)->type == PC_FLOW))
990 #define isPCF(x)        ((PCODE(x)->type == PC_FUNCTION))
991 #define isPCL(x)        ((PCODE(x)->type == PC_LABEL))
992 #define isPCW(x)        ((PCODE(x)->type == PC_WILD))
993 #define isPCCS(x)       ((PCODE(x)->type == PC_CSOURCE))
994 #define isPCAD(x)       ((PCODE(x)->type == PC_ASMDIR))
995 #define isPCINFO(x)     ((PCODE(x)->type == PC_INFO))
996
997 #define isCALL(x)       ((isPCI(x)) && (PCI(x)->op == POC_CALL))
998 #define isSTATUS_REG(r) ((r)->pc_type == PO_STATUS)
999 #define isBSR_REG(r)    ((r)->pc_type == PO_BSR)
1000 #define isACCESS_BANK(r)        (r->accessBank)
1001
1002
1003
1004 #define isPCOLAB(x)     ((PCOP(x)->type) == PO_LABEL)
1005
1006 /*-----------------------------------------------------------------*
1007  * pCode functions.
1008  *-----------------------------------------------------------------*/
1009
1010 pCode *pic16_newpCode (PIC_OPCODE op, pCodeOp *pcop); // Create a new pCode given an operand
1011 pCode *pic16_newpCodeCharP(char *cP);              // Create a new pCode given a char *
1012 pCode *pic16_newpCodeInlineP(char *cP);            // Create a new pCode given a char *
1013 pCode *pic16_newpCodeFunction(char *g, char *f);   // Create a new function
1014 pCode *pic16_newpCodeLabel(char *name,int key);    // Create a new label given a key
1015 pCode *pic16_newpCodeLabelFORCE(char *name, int key); // Same as newpCodeLabel but label cannot be optimized out
1016 pCode *pic16_newpCodeCSource(int ln, char *f, char *l); // Create a new symbol line 
1017 pBlock *pic16_newpCodeChain(memmap *cm,char c, pCode *pc); // Create a new pBlock
1018 void pic16_printpBlock(FILE *of, pBlock *pb);      // Write a pBlock to a file
1019 void pic16_addpCode2pBlock(pBlock *pb, pCode *pc); // Add a pCode to a pBlock
1020 void pic16_addpBlock(pBlock *pb);                  // Add a pBlock to a pFile
1021 void pic16_copypCode(FILE *of, char dbName);       // Write all pBlocks with dbName to *of
1022 void pic16_movepBlock2Head(char dbName);           // move pBlocks around
1023 void pic16_AnalyzepCode(char dbName);
1024 void pic16_OptimizeLocalRegs(void);
1025 void pic16_AssignRegBanks(void);
1026 void pic16_printCallTree(FILE *of);
1027 void pCodePeepInit(void);
1028 void pic16_pBlockConvert2ISR(pBlock *pb);
1029 void pic16_pBlockConvert2Absolute(pBlock *pb);
1030 void pic16_initDB(void);
1031 void pic16_emitDB(int c, char ptype, void *p);            // Add DB directives to a pBlock
1032 void pic16_emitDS(char *s, char ptype, void *p);
1033 void pic16_flushDB(char ptype, void *p);                          // Add pending DB data to a pBlock
1034
1035 pCode *pic16_newpCodeAsmDir(char *asdir, char *argfmt, ...); 
1036
1037 pCodeOp *pic16_newpCodeOpLabel(char *name, int key);
1038 pCodeOp *pic16_newpCodeOpImmd(char *name, int offset, int index, int code_space);
1039 pCodeOp *pic16_newpCodeOpLit(int lit);
1040 pCodeOp *pic16_newpCodeOpLit12(int lit);
1041 pCodeOp *pic16_newpCodeOpLit2(int lit, pCodeOp *arg2);
1042 pCodeOp *pic16_newpCodeOpBit(char *name, int bit,int inBitSpace, PIC_OPTYPE subt);
1043 pCodeOp *pic16_newpCodeOpBit_simple (struct asmop *op, int offs, int bit);
1044 pCodeOp *pic16_newpCodeOpRegFromStr(char *name);
1045 pCodeOp *pic16_newpCodeOpReg(int rIdx);
1046 pCodeOp *pic16_newpCodeOp(char *name, PIC_OPTYPE p);
1047 pCodeOp *pic16_newpCodeOpRegNotVect(bitVect *bv);
1048 pCodeOp *pic16_pCodeOpCopy(pCodeOp *pcop);
1049
1050 pCode *pic16_newpCodeInfo(INFO_TYPE type, pCodeOp *pcop);
1051 pCodeOp *pic16_newpCodeOpOpt(OPT_TYPE type, char *key);
1052 pCodeOp *pic16_newpCodeOpLocalRegs(LR_TYPE type);
1053 pCodeOp *pic16_newpCodeOpReg(int rIdx);
1054
1055 pCode * pic16_findNextInstruction(pCode *pci);
1056 pCode * pic16_findNextpCode(pCode *pc, PC_TYPE pct);
1057 int pic16_isPCinFlow(pCode *pc, pCode *pcflow);
1058 struct regs * pic16_getRegFromInstruction(pCode *pc);
1059 struct regs * pic16_getRegFromInstruction2(pCode *pc);
1060 char *pic16_get_op(pCodeOp *pcop,char *buffer, size_t size);
1061 char *pic16_get_op2(pCodeOp *pcop,char *buffer, size_t size);
1062 char *dumpPicOptype(PIC_OPTYPE type);
1063
1064 extern void pic16_pcode_test(void);
1065 extern int pic16_debug_verbose;
1066 extern int pic16_pcode_verbose;
1067
1068 extern char *LR_TYPE_STR[];
1069
1070
1071 #ifndef debugf
1072 //#define debugf(frm, rest...)       _debugf(__FILE__, __LINE__, frm, rest)
1073 #define debugf(frm, rest)       _debugf(__FILE__, __LINE__, frm, rest)
1074 #define debugf2(frm, arg1, arg2)        _debugf(__FILE__, __LINE__, frm, arg1, arg2)
1075 #define debugf3(frm, arg1, arg2, arg3)  _debugf(__FILE__, __LINE__, frm, arg1, arg2, arg3)
1076
1077 #endif
1078
1079 extern void _debugf(char *f, int l, char *frm, ...);
1080
1081
1082 /*-----------------------------------------------------------------*
1083  * pCode objects.
1084  *-----------------------------------------------------------------*/
1085
1086 extern pCodeOpReg pic16_pc_status;
1087 extern pCodeOpReg pic16_pc_intcon;
1088 extern pCodeOpReg pic16_pc_pcl;
1089 extern pCodeOpReg pic16_pc_pclath;
1090 extern pCodeOpReg pic16_pc_pclatu;
1091 extern pCodeOpReg pic16_pc_wreg;
1092 extern pCodeOpReg pic16_pc_tosl;
1093 extern pCodeOpReg pic16_pc_tosh;
1094 extern pCodeOpReg pic16_pc_tosu;
1095 extern pCodeOpReg pic16_pc_tblptrl;
1096 extern pCodeOpReg pic16_pc_tblptrh;
1097 extern pCodeOpReg pic16_pc_tblptru;
1098 extern pCodeOpReg pic16_pc_tablat;
1099 extern pCodeOpReg pic16_pc_bsr;
1100 extern pCodeOpReg pic16_pc_fsr0;
1101 extern pCodeOpReg pic16_pc_fsr0l;
1102 extern pCodeOpReg pic16_pc_fsr0h;
1103 extern pCodeOpReg pic16_pc_fsr1l;
1104 extern pCodeOpReg pic16_pc_fsr1h;
1105 extern pCodeOpReg pic16_pc_fsr2l;
1106 extern pCodeOpReg pic16_pc_fsr2h;
1107 extern pCodeOpReg pic16_pc_indf0;
1108 extern pCodeOpReg pic16_pc_postinc0;
1109 extern pCodeOpReg pic16_pc_postdec0;
1110 extern pCodeOpReg pic16_pc_preinc0;
1111 extern pCodeOpReg pic16_pc_plusw0;
1112 extern pCodeOpReg pic16_pc_indf1;
1113 extern pCodeOpReg pic16_pc_postinc1;
1114 extern pCodeOpReg pic16_pc_postdec1;
1115 extern pCodeOpReg pic16_pc_preinc1;
1116 extern pCodeOpReg pic16_pc_plusw1;
1117 extern pCodeOpReg pic16_pc_indf2;
1118 extern pCodeOpReg pic16_pc_postinc2;
1119 extern pCodeOpReg pic16_pc_postdec2;
1120 extern pCodeOpReg pic16_pc_preinc2;
1121 extern pCodeOpReg pic16_pc_plusw2;
1122 extern pCodeOpReg pic16_pc_prodl;
1123 extern pCodeOpReg pic16_pc_prodh;
1124
1125 extern pCodeOpReg pic16_pc_eecon1;
1126 extern pCodeOpReg pic16_pc_eecon2;
1127 extern pCodeOpReg pic16_pc_eedata;
1128 extern pCodeOpReg pic16_pc_eeadr;
1129
1130 extern pCodeOpReg pic16_pc_kzero;
1131 extern pCodeOpReg pic16_pc_wsave;     /* wsave and ssave are used to save W and the Status */
1132 extern pCodeOpReg pic16_pc_ssave;     /* registers during an interrupt */
1133
1134 extern pCodeOpReg *pic16_stackpnt_lo;
1135 extern pCodeOpReg *pic16_stackpnt_hi;
1136 extern pCodeOpReg *pic16_stack_postinc;
1137 extern pCodeOpReg *pic16_stack_postdec;
1138 extern pCodeOpReg *pic16_stack_preinc;
1139 extern pCodeOpReg *pic16_stack_plusw;
1140
1141 extern pCodeOpReg *pic16_framepnt_lo;
1142 extern pCodeOpReg *pic16_framepnt_hi;
1143 extern pCodeOpReg *pic16_frame_postinc;
1144 extern pCodeOpReg *pic16_frame_postdec;
1145 extern pCodeOpReg *pic16_frame_preinc;
1146 extern pCodeOpReg *pic16_frame_plusw;
1147
1148 extern pCodeOpReg pic16_pc_gpsimio;
1149 extern pCodeOpReg pic16_pc_gpsimio2;
1150
1151 #endif // __PCODE_H__