OpenCores
URL https://opencores.org/ocsvn/or1k/or1k/trunk

Subversion Repositories or1k

[/] [or1k/] [tags/] [nog_patch_39/] [or1ksim/] [cuc/] [memory.c] - Diff between revs 907 and 937

Go to most recent revision | Only display areas with differences | Details | Blame | View Log

Rev 907 Rev 937
/* memory.c -- OpenRISC Custom Unit Compiler, memory optimization and scheduling
/* memory.c -- OpenRISC Custom Unit Compiler, memory optimization and scheduling
 *    Copyright (C) 2002 Marko Mlinar, markom@opencores.org
 *    Copyright (C) 2002 Marko Mlinar, markom@opencores.org
 *
 *
 *    This file is part of OpenRISC 1000 Architectural Simulator.
 *    This file is part of OpenRISC 1000 Architectural Simulator.
 *
 *
 *    This program is free software; you can redistribute it and/or modify
 *    This program is free software; you can redistribute it and/or modify
 *    it under the terms of the GNU General Public License as published by
 *    it under the terms of the GNU General Public License as published by
 *    the Free Software Foundation; either version 2 of the License, or
 *    the Free Software Foundation; either version 2 of the License, or
 *    (at your option) any later version.
 *    (at your option) any later version.
 *
 *
 *    This program is distributed in the hope that it will be useful,
 *    This program is distributed in the hope that it will be useful,
 *    but WITHOUT ANY WARRANTY; without even the implied warranty of
 *    but WITHOUT ANY WARRANTY; without even the implied warranty of
 *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *    GNU General Public License for more details.
 *    GNU General Public License for more details.
 *
 *
 *    You should have received a copy of the GNU General Public License
 *    You should have received a copy of the GNU General Public License
 *    along with this program; if not, write to the Free Software
 *    along with this program; if not, write to the Free Software
 *    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
 *    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
 
 
#include <stdio.h>
#include <stdio.h>
#include <stdlib.h>
#include <stdlib.h>
#include <stdarg.h>
#include <stdarg.h>
#include <assert.h>
#include <assert.h>
#include "sim-config.h"
#include "sim-config.h"
#include "cuc.h"
#include "cuc.h"
#include "insn.h"
#include "insn.h"
 
 
/* Checks for memory conflicts between two instructions; returns 1 if detected
/* Checks for memory conflicts between two instructions; returns 1 if detected
  0 - exact; 1 - strong; 2 - weak; 3 - none */
  0 - exact; 1 - strong; 2 - weak; 3 - none */
static int check_memory_conflict (cuc_func *f, cuc_insn *a, cuc_insn *b, int otype)
static int check_memory_conflict (cuc_func *f, cuc_insn *a, cuc_insn *b, int otype)
{
{
  switch (otype) {
  switch (otype) {
    case MO_EXACT: /* exact */
    case MO_EXACT: /* exact */
    case MO_STRONG: /* strong */
    case MO_STRONG: /* strong */
      return 1;
      return 1;
    case MO_WEAK: /* weak */
    case MO_WEAK: /* weak */
      assert (a->type & IT_MEMORY);
      assert (a->type & IT_MEMORY);
      assert (b->type & IT_MEMORY);
      assert (b->type & IT_MEMORY);
      if ((a->opt[1] & OPT_REF) && f->INSN(a->op[1]).index == II_ADD
      if ((a->opt[1] & OPT_REF) && f->INSN(a->op[1]).index == II_ADD
        &&(b->opt[1] & OPT_REF) && f->INSN(b->op[1]).index == II_ADD) {
        &&(b->opt[1] & OPT_REF) && f->INSN(b->op[1]).index == II_ADD) {
        int aw, bw;
        int aw, bw;
        assert ((aw = II_MEM_WIDTH (a->index)) >= 0);
        assert ((aw = II_MEM_WIDTH (a->index)) >= 0);
        assert ((bw = II_MEM_WIDTH (b->index)) >= 0);
        assert ((bw = II_MEM_WIDTH (b->index)) >= 0);
 
 
        a = &f->INSN(a->op[1]);
        a = &f->INSN(a->op[1]);
        b = &f->INSN(b->op[1]);
        b = &f->INSN(b->op[1]);
        if (a->opt[1] != b->opt[1] || a->op[1] != b->op[1]
        if (a->opt[1] != b->opt[1] || a->op[1] != b->op[1]
         || a->opt[2] != OPT_CONST || b->opt[2] != OPT_CONST) return 1;
         || a->opt[2] != OPT_CONST || b->opt[2] != OPT_CONST) return 1;
 
 
        /* Check if they overlap */
        /* Check if they overlap */
        if (a->op[2] >= b->op[2] && a->op[2] < b->op[2] + bw) return 1;
        if (a->op[2] >= b->op[2] && a->op[2] < b->op[2] + bw) return 1;
        if (b->op[2] >= a->op[2] && b->op[2] < a->op[2] + aw) return 1;
        if (b->op[2] >= a->op[2] && b->op[2] < a->op[2] + aw) return 1;
        return 0;
        return 0;
      } else return 1;
      } else return 1;
    case MO_NONE: /* none */
    case MO_NONE: /* none */
      return 0;
      return 0;
    default:
    default:
      assert (0);
      assert (0);
  }
  }
  return 1;
  return 1;
}
}
 
 
/* Adds memory dependencies based on ordering type:
/* Adds memory dependencies based on ordering type:
  0 - exact; 1 - strong; 2 - weak;  3 - none */
  0 - exact; 1 - strong; 2 - weak;  3 - none */
void add_memory_dep (cuc_func *f, int otype)
void add_memory_dep (cuc_func *f, int otype)
{
{
  int b, i;
  int b, i;
  dep_list *all_mem = NULL;
  dep_list *all_mem = NULL;
 
 
  for (b = 0; b < f->num_bb; b++) {
  for (b = 0; b < f->num_bb; b++) {
    cuc_insn *insn = f->bb[b].insn;
    cuc_insn *insn = f->bb[b].insn;
    for (i = 0; i < f->bb[b].ninsn; i++)
    for (i = 0; i < f->bb[b].ninsn; i++)
      if (insn[i].type & IT_MEMORY) {
      if (insn[i].type & IT_MEMORY) {
        dep_list *tmp = all_mem;
        dep_list *tmp = all_mem;
        while (tmp) {
        while (tmp) {
          //printf ("%x %x\n", REF (b,i), tmp->ref);
          //printf ("%x %x\n", REF (b,i), tmp->ref);
          if (check_memory_conflict (f, &insn[i], &f->INSN(tmp->ref), otype))
          if (check_memory_conflict (f, &insn[i], &f->INSN(tmp->ref), otype))
            add_dep (&insn[i].dep, tmp->ref);
            add_dep (&insn[i].dep, tmp->ref);
          tmp = tmp->next;
          tmp = tmp->next;
        }
        }
        add_dep (&all_mem, REF (b, i));
        add_dep (&all_mem, REF (b, i));
      }
      }
  }
  }
  dispose_list (&all_mem);
  dispose_list (&all_mem);
}
}
 
 
/* returns nonzero if a < b */
/* returns nonzero if a < b */
int mem_ordering_cmp (cuc_func *f, cuc_insn *a, cuc_insn *b)
int mem_ordering_cmp (cuc_func *f, cuc_insn *a, cuc_insn *b)
{
{
  assert (a->type & IT_MEMORY);
  assert (a->type & IT_MEMORY);
  assert (b->type & IT_MEMORY);
  assert (b->type & IT_MEMORY);
  if ((a->opt[1] & OPT_REF) && f->INSN(a->op[1]).index == II_ADD
  if ((a->opt[1] & OPT_REF) && f->INSN(a->op[1]).index == II_ADD
    &&(b->opt[1] & OPT_REF) && f->INSN(b->op[1]).index == II_ADD) {
    &&(b->opt[1] & OPT_REF) && f->INSN(b->op[1]).index == II_ADD) {
    a = &f->INSN(a->op[1]);
    a = &f->INSN(a->op[1]);
    b = &f->INSN(b->op[1]);
    b = &f->INSN(b->op[1]);
    if (a->opt[1] != b->opt[1] || a->op[1] != b->op[1]
    if (a->opt[1] != b->opt[1] || a->op[1] != b->op[1]
     || a->opt[2] != OPT_CONST || b->opt[2] != OPT_CONST) return 0;
     || a->opt[2] != OPT_CONST || b->opt[2] != OPT_CONST) return 0;
 
 
    /* Order linearly, we can then join them to bursts */
    /* Order linearly, we can then join them to bursts */
    return a->op[2] < b->op[2];
    return a->op[2] < b->op[2];
  } else return 0;
  } else return 0;
}
}
 
 
/* Schedule memory accesses
/* Schedule memory accesses
  0 - exact; 1 - strong; 2 - weak;  3 - none */
  0 - exact; 1 - strong; 2 - weak;  3 - none */
void schedule_memory (cuc_func *f, int otype)
void schedule_memory (cuc_func *f, int otype)
{
{
  int b, i, j;
  int b, i, j;
  f->nmsched = 0;
  f->nmsched = 0;
 
 
  for (b = 0; b < f->num_bb; b++) {
  for (b = 0; b < f->num_bb; b++) {
    cuc_insn *insn = f->bb[b].insn;
    cuc_insn *insn = f->bb[b].insn;
    for (i = 0; i < f->bb[b].ninsn; i++)
    for (i = 0; i < f->bb[b].ninsn; i++)
      if (insn[i].type & IT_MEMORY) {
      if (insn[i].type & IT_MEMORY) {
        f->msched[f->nmsched++] = REF (b, i);
        f->msched[f->nmsched++] = REF (b, i);
        if (otype == MO_NONE || otype == MO_WEAK) insn[i].type |= IT_FLAG1; /* mark unscheduled */
        if (otype == MO_NONE || otype == MO_WEAK) insn[i].type |= IT_FLAG1; /* mark unscheduled */
      }
      }
  }
  }
#if 0
 
  for (i = 0; i < f->nmsched; i++)
  for (i = 0; i < f->nmsched; i++)
    printf ("[%i]%i%c ", f->msched[i], f->mtype[i] & MT_WIDTH, (f->mtype[i] & MT_BURST) ? (f->mtype[i] & MT_BURSTE) ? 'E' : 'B' : ' ');
    cucdebug (2, "[%x]%x%c ", f->msched[i], f->mtype[i] & MT_WIDTH, (f->mtype[i] & MT_BURST) ? (f->mtype[i] & MT_BURSTE) ? 'E' : 'B' : ' ');
  printf ("\n");
  cucdebug (2, "\n");
#endif
 
 
 
  /* We can reorder just more loose types
  /* We can reorder just more loose types
     We assume, that memory accesses are currently in valid (but not neccesserly)
     We assume, that memory accesses are currently in valid (but not neccesserly)
     optimal order */
     optimal order */
  if (otype == MO_WEAK || otype == MO_NONE) {
  if (otype == MO_WEAK || otype == MO_NONE) {
    for (i = 0; i < f->nmsched; i++) {
    for (i = 0; i < f->nmsched; i++) {
      int best = i;
      int best = i;
      int tmp;
      int tmp;
      for (j = i + 1; j < f->nmsched; j++) if (REF_BB(f->msched[j]) == REF_BB(f->msched[best])) {
      for (j = i + 1; j < f->nmsched; j++) if (REF_BB(f->msched[j]) == REF_BB(f->msched[best])) {
        if (mem_ordering_cmp (f, &f->INSN (f->msched[j]), &f->INSN(f->msched[best]))) {
        if (mem_ordering_cmp (f, &f->INSN (f->msched[j]), &f->INSN(f->msched[best]))) {
          /* Check dependencies */
          /* Check dependencies */
          dep_list *t = f->INSN(f->msched[j]).dep;
          dep_list *t = f->INSN(f->msched[j]).dep;
          while (t) {
          while (t) {
            if (f->INSN(t->ref).type & IT_FLAG1) break;
            if (f->INSN(t->ref).type & IT_FLAG1) break;
            t = t->next;
            t = t->next;
          }
          }
          if (!t) best = j; /* no conflicts -> ok */
          if (!t) best = j; /* no conflicts -> ok */
        }
        }
      }
      }
 
 
      /* we have to shift instructions up, to maintain valid dependencies
      /* we have to shift instructions up, to maintain valid dependencies
         and make space for best candidate */
         and make space for best candidate */
 
 
      /* make local copy */
      /* make local copy */
      tmp = f->msched[best];
      tmp = f->msched[best];
      for (j = best; j > i; j--) f->msched[j] = f->msched[j - 1];
      for (j = best; j > i; j--) f->msched[j] = f->msched[j - 1];
      f->msched[i] = tmp;
      f->msched[i] = tmp;
      f->INSN(f->msched[i]).type &= ~IT_FLAG1; /* mark scheduled */
      f->INSN(f->msched[i]).type &= ~IT_FLAG1; /* mark scheduled */
    }
    }
  }
  }
 
 
#if 0
 
  for (i = 0; i < f->nmsched; i++)
  for (i = 0; i < f->nmsched; i++)
    printf ("[%i]%i%c ", f->msched[i], f->mtype[i] & MT_WIDTH, (f->mtype[i] & MT_BURST) ? (f->mtype[i] & MT_BURSTE) ? 'E' : 'B' : ' ');
    cucdebug (2, "[%x]%x%c ", f->msched[i], f->mtype[i] & MT_WIDTH, (f->mtype[i] & MT_BURST) ? (f->mtype[i] & MT_BURSTE) ? 'E' : 'B' : ' ');
  printf ("\n");
  cucdebug (2, "\n");
#endif
 
 
 
  /* Assign memory types */
  /* Assign memory types */
  for (i = 0; i < f->nmsched; i++) {
  for (i = 0; i < f->nmsched; i++) {
    cuc_insn *a = &f->INSN(f->msched[i]);
    cuc_insn *a = &f->INSN(f->msched[i]);
    f->mtype[i] = !II_IS_LOAD(a->index) ? MT_STORE : MT_LOAD;
    f->mtype[i] = !II_IS_LOAD(a->index) ? MT_STORE : MT_LOAD;
    f->mtype[i] |= II_MEM_WIDTH (a->index);
    f->mtype[i] |= II_MEM_WIDTH (a->index);
    if (a->type & IT_SIGNED) f->mtype[i] |= MT_SIGNED;
    if (a->type & IT_SIGNED) f->mtype[i] |= MT_SIGNED;
  }
  }
 
 
  /* Check if they address the same location, so we can join them */
  /* Check if they address the same location, so we can join them */
  if (otype == MO_WEAK || otype == MO_NONE) {
  if (otype == MO_WEAK || otype == MO_NONE) {
    for (i = 1, j = 1; i < f->nmsched; i++)
    for (i = 1, j = 1; i < f->nmsched; i++)
      /* Exclude memory stores and different memory types */
      /* Exclude memory stores and different memory types */
      if (f->mtype[i - 1] == f->mtype[i] && f->mtype[i] & MT_LOAD) {
      if (f->mtype[i - 1] == f->mtype[i] && f->mtype[i] & MT_LOAD) {
        cuc_insn *a = &f->INSN(f->msched[i - 1]);
        cuc_insn *a = &f->INSN(f->msched[i - 1]);
        cuc_insn *b = &f->INSN(f->msched[i]);
        cuc_insn *b = &f->INSN(f->msched[i]);
        if ((a->opt[1] & OPT_REF) && f->INSN(a->op[1]).index == II_ADD
        if ((a->opt[1] & OPT_REF) && f->INSN(a->op[1]).index == II_ADD
          &&(b->opt[1] & OPT_REF) && f->INSN(b->op[1]).index == II_ADD) {
          &&(b->opt[1] & OPT_REF) && f->INSN(b->op[1]).index == II_ADD) {
          a = &f->INSN(a->op[1]);
          a = &f->INSN(a->op[1]);
          b = &f->INSN(b->op[1]);
          b = &f->INSN(b->op[1]);
          /* Not in usual form? */
          /* Not in usual form? */
          if (a->opt[1] != b->opt[1] || a->op[1] != b->op[1]
          if (a->opt[1] != b->opt[1] || a->op[1] != b->op[1]
           || a->opt[2] != OPT_CONST || b->opt[2] != OPT_CONST) goto keep;
           || a->opt[2] != OPT_CONST || b->opt[2] != OPT_CONST) goto keep;
 
 
          //printf ("%i %i, ", a->op[2], b->op[2]);
          //printf ("%i %i, ", a->op[2], b->op[2]);
 
 
          /* Check if they are the same => do not copy */
          /* Check if they are the same => do not copy */
          if (a->op[2] == b->op[2]
          if (a->op[2] == b->op[2]
            && REF_BB(f->msched[i - 1]) == REF_BB(f->msched[i])) {
            && REF_BB(f->msched[i - 1]) == REF_BB(f->msched[i])) {
            /* yes => remove actual instruction */
            /* yes => remove actual instruction */
            int t1 = MIN (f->msched[i - 1], f->msched[i]);
            int t1 = MIN (f->msched[i - 1], f->msched[i]);
            int t2 = MAX (f->msched[i - 1], f->msched[i]);
            int t2 = MAX (f->msched[i - 1], f->msched[i]);
            int b, i, j;
            int b, i, j;
            cucdebug (2, "Removing %x_%x and using %x_%x instead.\n",
            cucdebug (2, "Removing %x_%x and using %x_%x instead.\n",
              REF_BB(t2), REF_I(t2), REF_BB(t1), REF_I(t1));
              REF_BB(t2), REF_I(t2), REF_BB(t1), REF_I(t1));
            change_insn_type (&f->INSN(t2), II_NOP);
            change_insn_type (&f->INSN(t2), II_NOP);
            /* Update references */
            /* Update references */
            for (b = 0; b < f->num_bb; b++)
            for (b = 0; b < f->num_bb; b++)
              for (i = 0; i < f->bb[b].ninsn; i++)
              for (i = 0; i < f->bb[b].ninsn; i++)
                for (j = 0; j < MAX_OPERANDS; j++)
                for (j = 0; j < MAX_OPERANDS; j++)
                  if (f->bb[b].insn[i].opt[j] & OPT_REF && f->bb[b].insn[i].op[j] == t2)
                  if (f->bb[b].insn[i].opt[j] & OPT_REF && f->bb[b].insn[i].op[j] == t2)
                    f->bb[b].insn[i].op[j] = t1;
                    f->bb[b].insn[i].op[j] = t1;
 
 
          } else goto keep;
          } else goto keep;
        }
        } else goto keep;
      } else {
      } else {
keep:
keep:
        f->msched[j] = f->msched[i];
        f->msched[j] = f->msched[i];
        f->mtype[j++] = f->mtype[i];
        f->mtype[j++] = f->mtype[i];
      }
      }
    f->nmsched = j;
    f->nmsched = j;
  }
  }
 
 
 
  for (i = 0; i < f->nmsched; i++)
 
    cucdebug (2, "[%x]%x%c ", f->msched[i], f->mtype[i] & MT_WIDTH, (f->mtype[i] & MT_BURST) ? (f->mtype[i] & MT_BURSTE) ? 'E' : 'B' : ' ');
 
  cucdebug (2, "\n");
 
  if (cuc_debug > 5) print_cuc_bb (f, "AFTER_MEM_REMOVAL");
 
 
  if (config.cuc.enable_bursts) {
  if (config.cuc.enable_bursts) {
    //printf ("\n");
    //printf ("\n");
    for (i = 1; i < f->nmsched; i++) {
    for (i = 1; i < f->nmsched; i++) {
      cuc_insn *a = &f->INSN(f->msched[i - 1]);
      cuc_insn *a = &f->INSN(f->msched[i - 1]);
      cuc_insn *b = &f->INSN(f->msched[i]);
      cuc_insn *b = &f->INSN(f->msched[i]);
      int aw = f->mtype[i - 1] & MT_WIDTH;
      int aw = f->mtype[i - 1] & MT_WIDTH;
 
 
      if ((a->opt[1] & OPT_REF) && f->INSN(a->op[1]).index == II_ADD
      if ((a->opt[1] & OPT_REF) && f->INSN(a->op[1]).index == II_ADD
        &&(b->opt[1] & OPT_REF) && f->INSN(b->op[1]).index == II_ADD) {
        &&(b->opt[1] & OPT_REF) && f->INSN(b->op[1]).index == II_ADD) {
        a = &f->INSN(a->op[1]);
        a = &f->INSN(a->op[1]);
        b = &f->INSN(b->op[1]);
        b = &f->INSN(b->op[1]);
        /* Not in usual form? */
        /* Not in usual form? */
        if (a->opt[1] != b->opt[1] || a->op[1] != b->op[1]
        if (a->opt[1] != b->opt[1] || a->op[1] != b->op[1]
         || a->opt[2] != OPT_CONST || b->opt[2] != OPT_CONST) continue;
         || a->opt[2] != OPT_CONST || b->opt[2] != OPT_CONST) continue;
 
 
        //printf ("%i %i, ", a->op[2], b->op[2]);
        //printf ("%i %i, ", a->op[2], b->op[2]);
 
 
        /* Check if they touch together */
        /* Check if they touch together */
        if (a->op[2] + aw == b->op[2]) {
        if (a->op[2] + aw == b->op[2]) {
          /* yes => do burst */
          /* yes => do burst */
          f->mtype[i - 1] &= ~MT_BURSTE;
          f->mtype[i - 1] &= ~MT_BURSTE;
          f->mtype[i - 1] |= MT_BURST;
          f->mtype[i - 1] |= MT_BURST;
          f->mtype[i] |= MT_BURST | MT_BURSTE;
          f->mtype[i] |= MT_BURST | MT_BURSTE;
        }
        }
      }
      }
    }
    }
  }
  }
 
 
#if 0
 
  printf ("\n");
 
  for (i = 0; i < f->nmsched; i++)
  for (i = 0; i < f->nmsched; i++)
    printf ("[%i]%i%c ", f->msched[i], f->mtype[i] & MT_WIDTH, (f->mtype[i] & MT_BURST) ? (f->mtype[i] & MT_BURSTE) ? 'E' : 'B' : ' ');
    cucdebug (2, "[%x]%x%c ", f->msched[i], f->mtype[i] & MT_WIDTH, (f->mtype[i] & MT_BURST) ? (f->mtype[i] & MT_BURSTE) ? 'E' : 'B' : ' ');
  printf ("\n");
  cucdebug (2, "\n");
#endif
 
 
 
  /* We don't need dependencies in non-memory instructions */
  /* We don't need dependencies in non-memory instructions */
  for (b = 0; b < f->num_bb; b++) {
  for (b = 0; b < f->num_bb; b++) {
    cuc_insn *insn = f->bb[b].insn;
    cuc_insn *insn = f->bb[b].insn;
    for (i = 0; i < f->bb[b].ninsn; i++) if (!(insn[i].type & IT_MEMORY))
    for (i = 0; i < f->bb[b].ninsn; i++) if (!(insn[i].type & IT_MEMORY))
      dispose_list (&insn[i].dep);
      dispose_list (&insn[i].dep);
  }
  }
 
 
  /* Reduce number of dependecies, keeping just direct dependencies, based on memory schedule */
  /* Reduce number of dependecies, keeping just direct dependencies, based on memory schedule */
  {
  {
    int lastl[3] = {-1, -1, -1};
    int lastl[3] = {-1, -1, -1};
    int lasts[3] = {-1, -1, -1};
    int lasts[3] = {-1, -1, -1};
    int lastc[3] = {-1, -1, -1};
    int lastc[3] = {-1, -1, -1};
    int last_load = -1, last_store = -1, last_call = -1;
    int last_load = -1, last_store = -1, last_call = -1;
    for (i = 0; i < f->nmsched; i++) {
    for (i = 0; i < f->nmsched; i++) {
      int t = f->mtype[i] & MT_LOAD ? 0 : f->mtype[i] & MT_STORE ? 1 : 2;
      int t = f->mtype[i] & MT_LOAD ? 0 : f->mtype[i] & MT_STORE ? 1 : 2;
      int maxl = lastl[t];
      int maxl = lastl[t];
      int maxs = lasts[t];
      int maxs = lasts[t];
      int maxc = lastc[t];
      int maxc = lastc[t];
      dep_list *tmp = f->INSN(f->msched[i]).dep;
      dep_list *tmp = f->INSN(f->msched[i]).dep;
      while (tmp) {
      while (tmp) {
        if (f->INSN(tmp->ref).type & IT_MEMORY && REF_BB(tmp->ref) == REF_BB(f->msched[i])) {
        if (f->INSN(tmp->ref).type & IT_MEMORY && REF_BB(tmp->ref) == REF_BB(f->msched[i])) {
 
          printf ("%i %x %x\n", i, f->msched[i], tmp->ref);
          /* Search for the reference */
          /* Search for the reference */
          for (j = 0; j < f->nmsched; j++) if (f->msched[j] == tmp->ref) break;
          for (j = 0; j < f->nmsched; j++) if (f->msched[j] == tmp->ref) break;
          assert (j < f->nmsched);
          assert (j < f->nmsched);
          if (f->mtype[j] & MT_STORE) {
          if (f->mtype[j] & MT_STORE) {
            if (maxs < j) maxs = j;
            if (maxs < j) maxs = j;
          } else if (f->mtype[j] & MT_LOAD) {
          } else if (f->mtype[j] & MT_LOAD) {
            if (maxl < j) maxl = j;
            if (maxl < j) maxl = j;
          } else if (f->mtype[j] & MT_CALL) {
          } else if (f->mtype[j] & MT_CALL) {
            if (maxc < j) maxc = j;
            if (maxc < j) maxc = j;
          }
          }
        }
        }
        tmp = tmp->next;
        tmp = tmp->next;
      }
      }
      dispose_list (&f->INSN(f->msched[i]).dep);
      dispose_list (&f->INSN(f->msched[i]).dep);
      if (f->mtype[i] & MT_STORE) {
      if (f->mtype[i] & MT_STORE) {
        maxs = last_store;
        maxs = last_store;
        last_store = i;
        last_store = i;
      } else if (f->mtype[i] & MT_LOAD) {
      } else if (f->mtype[i] & MT_LOAD) {
        maxl = last_load;
        maxl = last_load;
        last_load = i;
        last_load = i;
      } else if (f->mtype[i] & MT_CALL) {
      } else if (f->mtype[i] & MT_CALL) {
        maxc = last_call;
        maxc = last_call;
        last_call = i;
        last_call = i;
      }
      }
 
 
      if (maxl > lastl[t]) {
      if (maxl > lastl[t]) {
        add_dep (&f->INSN(f->msched[i]).dep, f->msched[maxl]);
        add_dep (&f->INSN(f->msched[i]).dep, f->msched[maxl]);
        lastl[t] = maxl;
        lastl[t] = maxl;
      }
      }
      if (maxs > lasts[t]) {
      if (maxs > lasts[t]) {
        add_dep (&f->INSN(f->msched[i]).dep, f->msched[maxs]);
        add_dep (&f->INSN(f->msched[i]).dep, f->msched[maxs]);
        lasts[t] = maxs;
        lasts[t] = maxs;
      }
      }
      if (maxc > lastc[t]) {
      if (maxc > lastc[t]) {
        add_dep (&f->INSN(f->msched[i]).dep, f->msched[maxc]);
        add_dep (&f->INSN(f->msched[i]).dep, f->msched[maxc]);
        lastc[t] = maxc;
        lastc[t] = maxc;
      }
      }
      //printf ("%i(%i)> ml %i(%i) ms %i(%i) lastl %i %i lasts %i %i last_load %i last_store %i\n", i, f->msched[i], maxl, f->msched[maxl], maxs, f->msched[maxs], lastl[0], lastl[1], lasts[0], lasts[1], last_load, last_store);
      //printf ("%i(%i)> ml %i(%i) ms %i(%i) lastl %i %i lasts %i %i last_load %i last_store %i\n", i, f->msched[i], maxl, f->msched[maxl], maxs, f->msched[maxs], lastl[0], lastl[1], lasts[0], lasts[1], last_load, last_store);
 
 
      /* What we have to wait to finish this BB? */
      /* What we have to wait to finish this BB? */
      if (i + 1 >= f->nmsched || REF_BB(f->msched[i + 1]) != REF_BB(f->msched[i])) {
      if (i + 1 >= f->nmsched || REF_BB(f->msched[i + 1]) != REF_BB(f->msched[i])) {
        if (last_load > lastl[t]) {
        if (last_load > lastl[t]) {
          add_dep (&f->bb[REF_BB(f->msched[i])].mdep, f->msched[last_load]);
          add_dep (&f->bb[REF_BB(f->msched[i])].mdep, f->msched[last_load]);
          lastl[t] = last_load;
          lastl[t] = last_load;
        }
        }
        if (last_store > lasts[t]) {
        if (last_store > lasts[t]) {
          add_dep (&f->bb[REF_BB(f->msched[i])].mdep, f->msched[last_store]);
          add_dep (&f->bb[REF_BB(f->msched[i])].mdep, f->msched[last_store]);
          lasts[t] = last_store;
          lasts[t] = last_store;
        }
        }
        if (last_call > lastc[t]) {
        if (last_call > lastc[t]) {
          add_dep (&f->bb[REF_BB(f->msched[i])].mdep, f->msched[last_call]);
          add_dep (&f->bb[REF_BB(f->msched[i])].mdep, f->msched[last_call]);
          lastc[t] = last_call;
          lastc[t] = last_call;
        }
        }
      }
      }
    }
    }
  }
  }
}
}
 
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.