• Main Page
  • Related Pages
  • Modules
  • Data Structures
  • Files
  • File List
  • Globals

sst/core/techModels/libsim-panalyzer/bpred.h

00001 /*
00002  * bpred.h - branch predictor interfaces
00003  *
00004  * This file is a part of the SimpleScalar tool suite written by
00005  * Todd M. Austin as a part of the Multiscalar Research Project.
00006  *  
00007  * The tool suite is currently maintained by Doug Burger and Todd M. Austin.
00008  * 
00009  * Copyright (C) 1994, 1995, 1996, 1997, 1998 by Todd M. Austin
00010  *
00011  * This source file is distributed "as is" in the hope that it will be
00012  * useful.  The tool set comes with no warranty, and no author or
00013  * distributor accepts any responsibility for the consequences of its
00014  * use. 
00015  * 
00016  * Everyone is granted permission to copy, modify and redistribute
00017  * this tool set under the following conditions:
00018  * 
00019  *    This source code is distributed for non-commercial use only. 
00020  *    Please contact the maintainer for restrictions applying to 
00021  *    commercial use.
00022  *
00023  *    Permission is granted to anyone to make or distribute copies
00024  *    of this source code, either as received or modified, in any
00025  *    medium, provided that all copyright notices, permission and
00026  *    nonwarranty notices are preserved, and that the distributor
00027  *    grants the recipient permission for further redistribution as
00028  *    permitted by this document.
00029  *
00030  *    Permission is granted to distribute this file in compiled
00031  *    or executable form under the same conditions that apply for
00032  *    source code, provided that either:
00033  *
00034  *    A. it is accompanied by the corresponding machine-readable
00035  *       source code,
00036  *    B. it is accompanied by a written offer, with no time limit,
00037  *       to give anyone a machine-readable copy of the corresponding
00038  *       source code in return for reimbursement of the cost of
00039  *       distribution.  This written offer must permit verbatim
00040  *       duplication by anyone, or
00041  *    C. it is distributed by someone who received only the
00042  *       executable form, and is accompanied by a copy of the
00043  *       written offer of source code that they received concurrently.
00044  *
00045  * In other words, you are welcome to use, share and improve this
00046  * source file.  You are forbidden to forbid anyone else to use, share
00047  * and improve what you give them.
00048  *
00049  * INTERNET: dburger@cs.wisc.edu
00050  * US Mail:  1210 W. Dayton Street, Madison, WI 53706
00051  *
00052  * $Id: bpred.h,v 1.1.1.1 2003/09/18 00:57:54 panalyzer Exp $
00053  *
00054  * $Log: bpred.h,v $
00055  * Revision 1.1.1.1  2003/09/18 00:57:54  panalyzer
00056  *
00057  *
00058  * Revision 1.1.1.1  2003/09/18 00:18:43  panalyzer
00059  *
00060  *
00061  * Revision 1.1.1.1  2003/09/16 18:48:14  gdm
00062  *
00063  *
00064  * Revision 1.1.1.1  2000/11/29 14:53:54  cu-cs
00065  * Grand unification of arm sources.
00066  *
00067  *
00068  * Revision 1.1.1.1  2000/05/26 15:18:57  taustin
00069  * SimpleScalar Tool Set
00070  *
00071  *
00072  * Revision 1.5  1998/08/31 17:12:11  taustin
00073  * eliminated unportable "uint" reference
00074  *
00075  * Revision 1.4  1998/08/27 08:00:15  taustin
00076  * implemented host interface description in host.h
00077  * explicit BTB sizing option added to branch predictors, use
00078  *       "-btb" option to configure BTB
00079  * return address stack (RAS) performance stats improved
00080  *
00081  * Revision 1.1.1.1  1997/05/22 18:04:05  aklauser
00082  *
00083  * Revision 1.8  1997/05/01 20:23:06  skadron
00084  * BTB bug fixes; jumps no longer update direction state; non-taken
00085  *    branches non longer update BTB
00086  *
00087  * Revision 1.7  1997/05/01 00:05:51  skadron
00088  * Separated BTB from direction-predictor
00089  *
00090  * Revision 1.6  1997/04/29  23:50:44  skadron
00091  * Added r31 info to distinguish between return-JRs and other JRs for bpred
00092  *
00093  * Revision 1.5  1997/04/29  22:53:10  skadron
00094  * Hopefully bpred is now right: bpred now allocates entries only for
00095  *    branches; on a BTB miss it still returns a direction; and it uses a
00096  *    return-address stack.  Returns are not yet distinguished among JR's
00097  *
00098  * Revision 1.4  1997/04/28  17:37:09  skadron
00099  * Bpred now allocates entries for any instruction instead of only
00100  *    branches; also added return-address stack
00101  *
00102  * Revision 1.3  1997/04/24  16:57:27  skadron
00103  * Bpred used to return no prediction if the indexing branch didn't match
00104  *    in the BTB.  Now it can predict a direction even on a BTB address
00105  *    conflict
00106  *
00107  * Revision 1.2  1997/03/25 16:17:21  skadron
00108  * Added function called after priming
00109  *
00110  * Revision 1.1  1997/02/16  22:23:54  skadron
00111  * Initial revision
00112  *
00113  *
00114  */
00115 
00116 #ifndef BPRED_H
00117 #define BPRED_H
00118 
00119 #define dassert(a) assert(a)
00120 
00121 #include <stdio.h>
00122 
00123 #include "host.h"
00124 #include "misc.h"
00125 #include "machine.h"
00126 #include "stats.h"
00127 
00128 /*
00129  * This module implements a number of branch predictor mechanisms.  The
00130  * following predictors are supported:
00131  *
00132  *      BPred2Level:  two level adaptive branch predictor
00133  *
00134  *              It can simulate many prediction mechanisms that have up to
00135  *              two levels of tables. Parameters are:
00136  *                   N   # entries in first level (# of shift register(s))
00137  *                   W   width of shift register(s)
00138  *                   M   # entries in 2nd level (# of counters, or other FSM)
00139  *              One BTB entry per level-2 counter.
00140  *
00141  *              Configurations:   N, W, M
00142  *
00143  *                  counter based: 1, 0, M
00144  *
00145  *                  GAg          : 1, W, 2^W
00146  *                  GAp          : 1, W, M (M > 2^W)
00147  *                  PAg          : N, W, 2^W
00148  *                  PAp          : N, W, M (M == 2^(N+W))
00149  *
00150  *      BPred2bit:  a simple direct mapped bimodal predictor
00151  *
00152  *              This predictor has a table of two bit saturating counters.
00153  *              Where counter states 0 & 1 are predict not taken and
00154  *              counter states 2 & 3 are predict taken, the per-branch counters
00155  *              are incremented on taken branches and decremented on
00156  *              no taken branches.  One BTB entry per counter.
00157  *
00158  *      BPredTaken:  static predict branch taken
00159  *
00160  *      BPredNotTaken:  static predict branch not taken
00161  *
00162  */
00163 
00164 /* branch predictor types */
00165 enum bpred_class {
00166   BPredComb,                    /* combined predictor (McFarling) */
00167   BPred2Level,                  /* 2-level correlating pred w/2-bit counters */
00168   BPred2bit,                    /* 2-bit saturating cntr pred (dir mapped) */
00169   BPredTaken,                   /* static predict taken */
00170   BPredNotTaken,                /* static predict not taken */
00171   BPred_NUM
00172 };
00173 
00174 /* an entry in a BTB */
00175 struct bpred_btb_ent_t {
00176   md_addr_t addr;               /* address of branch being tracked */
00177   enum md_opcode op;            /* opcode of branch corresp. to addr */
00178   md_addr_t target;             /* last destination of branch when taken */
00179   struct bpred_btb_ent_t *prev, *next; /* lru chaining pointers */
00180 };
00181 
00182 /* direction predictor def */
00183 struct bpred_dir_t {
00184   enum bpred_class class;       /* type of predictor */
00185   union {
00186     struct {
00187       unsigned int size;        /* number of entries in direct-mapped table */
00188       unsigned char *table;     /* prediction state table */
00189     } bimod;
00190     struct {
00191       int l1size;               /* level-1 size, number of history regs */
00192       int l2size;               /* level-2 size, number of pred states */
00193       int shift_width;          /* amount of history in level-1 shift regs */
00194       int xor;                  /* history xor address flag */
00195       int *shiftregs;           /* level-1 history table */
00196       unsigned char *l2table;   /* level-2 prediction state table */
00197     } two;
00198   } config;
00199 };
00200 
00201 /* branch predictor def */
00202 struct bpred_t {
00203   enum bpred_class class;       /* type of predictor */
00204   struct {
00205     struct bpred_dir_t *bimod;    /* first direction predictor */
00206     struct bpred_dir_t *twolev;   /* second direction predictor */
00207     struct bpred_dir_t *meta;     /* meta predictor */
00208   } dirpred;
00209 
00210   struct {
00211     int sets;                   /* num BTB sets */
00212     int assoc;                  /* BTB associativity */
00213     struct bpred_btb_ent_t *btb_data; /* BTB addr-prediction table */
00214   } btb;
00215 
00216   struct {
00217     int size;                   /* return-address stack size */
00218     int tos;                    /* top-of-stack */
00219     struct bpred_btb_ent_t *stack; /* return-address stack */
00220   } retstack;
00221 
00222   /* stats */
00223   counter_t addr_hits;          /* num correct addr-predictions */
00224   counter_t dir_hits;           /* num correct dir-predictions (incl addr) */
00225   counter_t used_ras;           /* num RAS predictions used */
00226   counter_t used_bimod;         /* num bimodal predictions used (BPredComb) */
00227   counter_t used_2lev;          /* num 2-level predictions used (BPredComb) */
00228   counter_t jr_hits;            /* num correct addr-predictions for JR's */
00229   counter_t jr_seen;            /* num JR's seen */
00230   counter_t jr_non_ras_hits;    /* num correct addr-preds for non-RAS JR's */
00231   counter_t jr_non_ras_seen;    /* num non-RAS JR's seen */
00232   counter_t misses;             /* num incorrect predictions */
00233 
00234   counter_t lookups;            /* num lookups */
00235   counter_t retstack_pops;      /* number of times a value was popped */
00236   counter_t retstack_pushes;    /* number of times a value was pushed */
00237   counter_t ras_hits;           /* num correct return-address predictions */
00238 };
00239 
00240 /* branch predictor update information */
00241 struct bpred_update_t {
00242   char *pdir1;          /* direction-1 predictor counter */
00243   char *pdir2;          /* direction-2 predictor counter */
00244   char *pmeta;          /* meta predictor counter */
00245   struct {              /* predicted directions */
00246     unsigned int ras    : 1;    /* RAS used */
00247     unsigned int bimod  : 1;    /* bimodal predictor */
00248     unsigned int twolev : 1;    /* 2-level predictor */
00249     unsigned int meta   : 1;    /* meta predictor (0..bimod / 1..2lev) */
00250   } dir;
00251 };
00252 
00253 /* create a branch predictor */
00254 struct bpred_t *                        /* branch predictory instance */
00255 bpred_create(enum bpred_class class,    /* type of predictor to create */
00256              unsigned int bimod_size,   /* bimod table size */
00257              unsigned int l1size,       /* level-1 table size */
00258              unsigned int l2size,       /* level-2 table size */
00259              unsigned int meta_size,    /* meta predictor table size */
00260              unsigned int shift_width,  /* history register width */
00261              unsigned int xor,          /* history xor address flag */
00262              unsigned int btb_sets,     /* number of sets in BTB */ 
00263              unsigned int btb_assoc,    /* BTB associativity */
00264              unsigned int retstack_size);/* num entries in ret-addr stack */
00265 
00266 /* create a branch direction predictor */
00267 struct bpred_dir_t *            /* branch direction predictor instance */
00268 bpred_dir_create (
00269   enum bpred_class class,       /* type of predictor to create */
00270   unsigned int l1size,          /* level-1 table size */
00271   unsigned int l2size,          /* level-2 table size (if relevant) */
00272   unsigned int shift_width,     /* history register width */
00273   unsigned int xor);            /* history xor address flag */
00274 
00275 /* print branch predictor configuration */
00276 void
00277 bpred_config(struct bpred_t *pred,      /* branch predictor instance */
00278              FILE *stream);             /* output stream */
00279 
00280 /* print predictor stats */
00281 void
00282 bpred_stats(struct bpred_t *pred,       /* branch predictor instance */
00283             FILE *stream);              /* output stream */
00284 
00285 /* register branch predictor stats */
00286 void
00287 bpred_reg_stats(struct bpred_t *pred,   /* branch predictor instance */
00288                 struct stat_sdb_t *sdb);/* stats database */
00289 
00290 /* reset stats after priming, if appropriate */
00291 void bpred_after_priming(struct bpred_t *bpred);
00292 
00293 /* probe a predictor for a next fetch address, the predictor is probed
00294    with branch address BADDR, the branch target is BTARGET (used for
00295    static predictors), and OP is the instruction opcode (used to simulate
00296    predecode bits; a pointer to the predictor state entry (or null for jumps)
00297    is returned in *DIR_UPDATE_PTR (used for updating predictor state),
00298    and the non-speculative top-of-stack is returned in stack_recover_idx 
00299    (used for recovering ret-addr stack after mis-predict).  */
00300 md_addr_t                               /* predicted branch target addr */
00301 bpred_lookup(struct bpred_t *pred,      /* branch predictor instance */
00302              md_addr_t baddr,           /* branch address */
00303              md_addr_t btarget,         /* branch target if taken */
00304              enum md_opcode op,         /* opcode of instruction */
00305              int is_call,               /* non-zero if inst is fn call */
00306              int is_return,             /* non-zero if inst is fn return */
00307              struct bpred_update_t *dir_update_ptr, /* pred state pointer */
00308              int *stack_recover_idx);   /* Non-speculative top-of-stack;
00309                                          * used on mispredict recovery */
00310 
00311 /* Speculative execution can corrupt the ret-addr stack.  So for each
00312  * lookup we return the top-of-stack (TOS) at that point; a mispredicted
00313  * branch, as part of its recovery, restores the TOS using this value --
00314  * hopefully this uncorrupts the stack. */
00315 void
00316 bpred_recover(struct bpred_t *pred,     /* branch predictor instance */
00317               md_addr_t baddr,          /* branch address */
00318               int stack_recover_idx);   /* Non-speculative top-of-stack;
00319                                          * used on mispredict recovery */
00320 
00321 /* update the branch predictor, only useful for stateful predictors; updates
00322    entry for instruction type OP at address BADDR.  BTB only gets updated
00323    for branches which are taken.  Inst was determined to jump to
00324    address BTARGET and was taken if TAKEN is non-zero.  Predictor 
00325    statistics are updated with result of prediction, indicated by CORRECT and 
00326    PRED_TAKEN, predictor state to be updated is indicated by *DIR_UPDATE_PTR 
00327    (may be NULL for jumps, which shouldn't modify state bits).  Note if
00328    bpred_update is done speculatively, branch-prediction may get polluted. */
00329 void
00330 bpred_update(struct bpred_t *pred,      /* branch predictor instance */
00331              md_addr_t baddr,           /* branch address */
00332              md_addr_t btarget,         /* resolved branch target */
00333              int taken,                 /* non-zero if branch was taken */
00334              int pred_taken,            /* non-zero if branch was pred taken */
00335              int correct,               /* was earlier prediction correct? */
00336              enum md_opcode op,         /* opcode of instruction */
00337              struct bpred_update_t *dir_update_ptr); /* pred state pointer */
00338 
00339 
00340 #ifdef foo0
00341 /* OBSOLETE */
00342 /* dump branch predictor state (for debug) */
00343 void
00344 bpred_dump(struct bpred_t *pred,        /* branch predictor instance */
00345            FILE *stream);               /* output stream */
00346 #endif
00347 
00348 #endif /* BPRED_H */

Generated on Fri Oct 22 2010 11:02:18 for SST by  doxygen 1.7.1