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

Subversion Repositories or1k

[/] [or1k/] [trunk/] [or1ksim/] [support/] [sched.c] - Blame information for rev 1688

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 807 markom
/* sched.c -- Abstract entities, handling job scheduling
2
   Copyright (C) 2001 Marko Mlinar, markom@opencores.org
3
 
4
This file is part of OpenRISC 1000 Architectural Simulator.
5
 
6
This program is free software; you can redistribute it and/or modify
7
it under the terms of the GNU General Public License as published by
8
the Free Software Foundation; either version 2 of the License, or
9
(at your option) any 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, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
19
 
20
/* Abstract memory and routines that go with this. I need to
21
add all sorts of other abstract entities. Currently we have
22
only memory. */
23
 
24
#include <stdlib.h>
25
#include <stdio.h>
26
#include <ctype.h>
27
#include <string.h>
28
#include <limits.h>
29
 
30
#include "config.h"
31 1365 nogj
 
32
#ifdef HAVE_INTTYPES_H
33
#include <inttypes.h>
34
#endif
35
 
36
#include "port.h"
37
#include "arch.h"
38
#include "sim-config.h"
39
#include "config.h"
40 807 markom
#include "sched.h"
41 1688 nogj
#include "debug.h"
42 807 markom
 
43 1688 nogj
DEFAULT_DEBUG_CHANNEL(sched);
44
DECLARE_DEBUG_CHANNEL(sched_jobs);
45
 
46
#define SCHED_HEAP_SIZE 128
47
#define SCHED_TIME_MAX  INT32_MAX
48
 
49 1557 nogj
/* FIXME: Scheduler should continue from previous cycles not current ones */
50
 
51 807 markom
struct scheduler_struct scheduler;
52
 
53
/* Dummy function, representing a guard, which protects heap from
54
   emptying */
55 1365 nogj
void sched_guard (void *dat)
56 807 markom
{
57 1390 nogj
  if(scheduler.job_queue)
58
    SCHED_ADD(sched_guard, dat, SCHED_TIME_MAX);
59
  else {
60
    scheduler.job_queue = scheduler.free_job_queue;
61
    scheduler.free_job_queue = scheduler.free_job_queue->next;
62
    scheduler.job_queue->next = NULL;
63
    scheduler.job_queue->func = sched_guard;
64
    scheduler.job_queue->time = SCHED_TIME_MAX;
65
  }
66 807 markom
}
67 1390 nogj
 
68
void sched_reset(void)
69
{
70
  struct sched_entry *cur, *next;
71
 
72
  for(cur = scheduler.job_queue; cur; cur = next) {
73
    next = cur->next;
74
    cur->next = scheduler.free_job_queue;
75
    scheduler.free_job_queue = cur;
76
  }
77
  scheduler.job_queue = NULL;
78
  sched_guard(NULL);
79
}
80
 
81
void sched_init(void)
82
{
83
  int i;
84
  struct sched_entry *new;
85
 
86
  scheduler.free_job_queue = NULL;
87
 
88
  for(i = 0; i < SCHED_HEAP_SIZE; i++) {
89
    if(!(new = malloc(sizeof(struct sched_entry)))) {
90
      fprintf(stderr, "Out-of-memory while allocateing scheduler queue\n");
91
      exit(1);
92
    }
93
    new->next = scheduler.free_job_queue;
94
    scheduler.free_job_queue = new;
95
  }
96
  scheduler.job_queue = NULL;
97
  sched_guard(NULL);
98
}
99 1545 nogj
 
100 1688 nogj
static void sched_print_jobs(void)
101
{
102
  struct sched_entry *cur;
103
  int i;
104
 
105
  for (cur = scheduler.job_queue, i = 0; cur; cur = cur->next, i++)
106
    TRACE("\t%i: %p $%p @ %"PRIi32"\n", i, cur->func, cur->param, cur->time);
107
}
108
 
109
/* Adds new job to the queue */
110
void sched_add(void (*job_func)(void *), void *job_param, int32_t job_time,
111
               const char *func)
112
{
113
  struct sched_entry *cur, *prev, *new_job;
114
  int32_t alltime;
115
 
116
  TRACE("%s@%lli:SCHED_ADD(time %"PRIi32")\n", func, runtime.sim.cycles,
117
        job_time);
118
  if(TRACE_ON(sched_jobs)) {
119
    sched_print_jobs();
120
    TRACE("--------\n");
121
  }
122
 
123
  cur = scheduler.job_queue;
124
  prev = NULL;
125
  alltime = cur->time;
126
  while(cur && (alltime < job_time)) {
127
    prev = cur;
128
    cur = cur->next;
129
    if(cur)
130
      alltime += cur->time;
131
  }
132
 
133
  new_job = scheduler.free_job_queue;
134
  scheduler.free_job_queue = new_job->next;
135
  new_job->next = cur;
136
 
137
  new_job->func = job_func;
138
  new_job->param = job_param;
139
 
140
  if(prev) {
141
    new_job->time = job_time - (alltime - (cur ? cur->time : 0));
142
    prev->next = new_job;
143
    TRACE("Scheduled job not going to head of queue, relative time: %"
144
          PRIi32"\n", new_job->time);
145
  } else {
146
    scheduler.job_queue = new_job;
147
    new_job->time = job_time >= 0 ? job_time : cur->time;
148
    TRACE("Setting to-go cycles to %"PRIi32" at %lli\n", job_time,
149
          runtime.sim.cycles);
150
  }
151
 
152
  if(cur)
153
    cur->time -= new_job->time;
154
 
155
  if(TRACE_ON(sched_jobs))
156
    sched_print_jobs();
157
}
158
 
159
/* Returns a job with specified function and param, NULL if not found */
160
void sched_find_remove(void (*job_func)(void *), void *dat, const char *func)
161
{
162
  struct sched_entry *cur;
163
  struct sched_entry *prev = NULL;
164
 
165
  TRACE("%s@%lli:SCHED_REMOVE()\n", func, runtime.sim.cycles);
166
 
167
  for (cur = scheduler.job_queue; cur; prev = cur, cur = cur->next) {
168
    if ((cur->func == job_func) && (cur->param == dat)) {
169
      if(cur->next)
170
        cur->next->time += cur->time;
171
 
172
      if(prev)
173
        prev->next = cur->next;
174
      else
175
        scheduler.job_queue = cur->next;
176
      cur->next = scheduler.free_job_queue;
177
      scheduler.free_job_queue = cur;
178
      break;
179
    }
180
  }
181
}
182
 
183 1545 nogj
/* Schedules the next job so that it will run after the next instruction */
184
void sched_next_insn(void (*func)(void *), void *dat)
185
{
186
  int32_t cycles = 1;
187
  struct sched_entry *cur = scheduler.job_queue;
188
 
189
  /* The cycles count of the jobs may go into negatives.  If this happens, func
190
   * will get called before the next instruction has executed. */
191
  while(cur && (cur->time < 0)) {
192
    cycles -= cur->time;
193
    cur = cur->next;
194
  }
195
 
196
  SCHED_ADD(func, dat, cycles);
197
}
198
 
199
 

powered by: WebSVN 2.1.0

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