Subversion Repositories shark

Rev

Rev 708 | Rev 741 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
671 giacomo 1
/*
2
 * Project: S.Ha.R.K.
3
 *
4
 * Coordinators:
5
 *   Giorgio Buttazzo    <giorgio@sssup.it>
6
 *   Paolo Gai           <pj@gandalf.sssup.it>
7
 *
737 anton 8
 * Authors:
671 giacomo 9
 *      Giacomo Guidi    <giacomo@gandalf.sssup.it>
10
 *      Mauro Marinoni
11
 *      Anton Cervin
12
 *
13
 * ReTiS Lab (Scuola Superiore S.Anna - Pisa - Italy)
14
 *
15
 * http://www.sssup.it
16
 * http://retis.sssup.it
17
 * http://shark.sssup.it
18
 */
19
 
20
/*
21
 * This program is free software; you can redistribute it and/or modify
22
 * it under the terms of the GNU General Public License as published by
23
 * the Free Software Foundation; either version 2 of the License, or
24
 * (at your option) any later version.
25
 *
26
 * This program is distributed in the hope that it will be useful,
27
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
28
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
29
 * GNU General Public License for more details.
30
 *
31
 * You should have received a copy of the GNU General Public License
32
 * along with this program; if not, write to the Free Software
33
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
34
 *
35
 */
36
 
37
#include <kernel/model.h>
38
#include <kernel/descr.h>
39
#include <kernel/var.h>
40
#include <kernel/func.h>
41
 
42
#include <stdlib.h>
43
 
44
#include <modules/elastic.h>
45
 
46
#include <tracer.h>
47
 
707 anton 48
 
49
/* Task flags */
50
 
673 giacomo 51
#define ELASTIC_PRESENT       1
707 anton 52
#define ELASTIC_JOB_PRESENT   2  
671 giacomo 53
 
707 anton 54
/* Task statuses */
55
 
683 giacomo 56
#define ELASTIC_IDLE          APER_STATUS_BASE
57
 
676 giacomo 58
 
707 anton 59
#define ELASTIC_DEBUG
60
 
61
#ifdef ELASTIC_DEBUG
62
char *pnow() {
63
  static char buf[40];
64
  struct timespec t;
65
  kern_gettime(&t);
66
  sprintf(buf, "%ld.%06ld", t.tv_sec, t.tv_nsec/1000);
67
  return buf;
68
}
69
char *ptime1(struct timespec *t) {
70
  static char buf[40];
71
  sprintf(buf, "%ld.%06ld", t->tv_sec, t->tv_nsec/1000);
72
  return buf;
73
}
74
char *ptime2(struct timespec *t) {
75
  static char buf[40];
76
  sprintf(buf, "%ld.%06ld", t->tv_sec, t->tv_nsec/1000);
77
  return buf;
78
}
79
#endif
80
 
81
 
671 giacomo 82
typedef struct {
83
 
697 anton 84
  /* Task parameters (set/changed by the user) */
85
 
86
  TIME Tmin;   /* The nominal (minimum) period */
87
  TIME Tmax;   /* The maximum tolerable period */
88
  TIME C;      /* The declared worst-case execution time */
89
  int  E;      /* The elasticity coefficient */
90
  int  beta;   /* PERIOD_SCALING or WCET_SCALING */
91
 
92
  /* Task variables (changed by the module) */
93
 
707 anton 94
  struct timespec release;    /* The current activation time */
95
  struct timespec dline;      /* The current absolute deadline */
96
  int dltimer;                /* Deadline timer handle */
671 giacomo 97
 
700 anton 98
  ext_bandwidth_t Umax;       /* The maximum utilization, Umax = C/Tmin  */
99
  ext_bandwidth_t Umin;       /* The minimum utilization, Umin = C/Tmax  */
671 giacomo 100
 
707 anton 101
  ext_bandwidth_t U;          /* New assigned utilization             */
102
  ext_bandwidth_t oldU;       /* Old utilization                      */
103
  TIME T;                     /* The current period, T = C/U          */
673 giacomo 104
 
671 giacomo 105
  int  flags;
106
 
107
} ELASTIC_task_descr;
108
 
109
typedef struct {
110
  level_des l;     /*+ the standard level descriptor          +*/
111
 
700 anton 112
  ext_bandwidth_t U;   /*+ the bandwidth reserved for elastic tasks  +*/
671 giacomo 113
 
697 anton 114
  ELASTIC_task_descr elist[MAX_PROC];
671 giacomo 115
 
116
  LEVEL scheduling_level;
117
 
118
  LEVEL current_level;
119
 
120
  int flags;
121
 
122
} ELASTIC_level_des;
123
 
673 giacomo 124
 
707 anton 125
static void ELASTIC_activation(ELASTIC_level_des *lev, PID p,
126
                               struct timespec *acttime)
127
{
128
  JOB_TASK_MODEL job;
129
  ELASTIC_task_descr *et = &lev->elist[p];
697 anton 130
 
707 anton 131
  /* Assign release time */
132
  et->release = *acttime;
133
 
134
  /* Assign absolute deadline */
135
  et->dline = *acttime;
136
  ADDUSEC2TIMESPEC(et->T, &et->dline);
137
 
138
#ifdef ELASTIC_DEBUG
139
  cprintf("At %s: activating %s; rel=%s; dl=%s\n", pnow(), proc_table[p].name,
140
          ptime1(&et->release), ptime2(&et->dline));
141
#endif  
142
 
143
  proc_table[p].avail_time = et->C;
144
  proc_table[p].wcet = et->C;
145
 
146
  /* Job insertion */
147
  job_task_default_model(job, et->dline);
148
  level_table[lev->scheduling_level]->
149
    private_insert(lev->scheduling_level, p, (TASK_MODEL *)&job);
737 anton 150
  et->flags |= ELASTIC_JOB_PRESENT;
707 anton 151
}
152
 
153
 
154
static void ELASTIC_timer_act(void *arg) {
155
 
156
  PID p = (PID)(arg);
157
  ELASTIC_level_des *lev;
158
 
159
  lev = (ELASTIC_level_des *)level_table[proc_table[p].task_level];
160
  ELASTIC_task_descr *et = &lev->elist[p];
161
 
162
  /* Use the current deadline as the new activation time */
163
  ELASTIC_activation(lev, p, &et->dline);
164
 
165
  event_need_reschedule();
166
 
167
  /* Next activation */
168
  et->dltimer = kern_event_post(&et->dline, ELASTIC_timer_act, (void *)(p));
169
}
170
 
171
 
172
/* Check feasability and compute new utilizations for the task set */
173
 
697 anton 174
static int ELASTIC_compress(ELASTIC_level_des *lev) {
175
 
676 giacomo 176
  PID i;
707 anton 177
  ELASTIC_task_descr *et;
697 anton 178
  int ok;
179
 
180
  ext_bandwidth_t Umin;  // minimum utilization
181
  ext_bandwidth_t Umax;  // nominal (maximum) utilization of compressable tasks
676 giacomo 182
 
697 anton 183
  ext_bandwidth_t Uf;    // amount of non-compressable utilization
184
  int Ev;                // sum of elasticity among compressable tasks
185
 
707 anton 186
  JOB_TASK_MODEL job;
187
 
697 anton 188
  Umin = 0;
189
  Umax = 0;
190
 
676 giacomo 191
  for (i=0; i<MAX_PROC; i++) {
707 anton 192
    et = &lev->elist[i];
193
    if (et->flags & ELASTIC_PRESENT) {
194
      if (et->E == 0) {
195
        Umin += et->U;
196
        Umax += et->U;
697 anton 197
      } else {
707 anton 198
        Umin += et->Umin;
199
        Umax += et->Umax;
200
        et->U = et->Umax;   // reset previous saturations (if any)
697 anton 201
      }
691 anton 202
    }
676 giacomo 203
  }
697 anton 204
 
700 anton 205
  if (Umin > lev->U) return -1;  // NOT FEASIBLE
676 giacomo 206
 
700 anton 207
  if (Umax <= lev->U) return 0;  // FEASIBLE WITH MAXIMUM UTILIZATIONS
208
 
697 anton 209
  do {
210
    Uf = 0;
211
    Ev = 0;
212
    Umax = 0;
673 giacomo 213
 
697 anton 214
    for (i=0; i<MAX_PROC; i++) {
707 anton 215
      et = &lev->elist[i];
216
      if (et->flags & ELASTIC_PRESENT) {
217
        if (et->E == 0 || et->U == et->Umin) {
218
          Uf += et->U;
697 anton 219
        } else {
707 anton 220
          Ev += et->E;
221
          Umax += et->Umax;
697 anton 222
        }
223
      }
224
    }
225
 
226
    ok = 1;
227
 
228
    for (i=0; i<MAX_PROC; i++) {
707 anton 229
      et = &lev->elist[i];
230
      if (et->flags & ELASTIC_PRESENT) {
231
        if (et->E > 0 && et->U > et->Umin) {
232
          et->U = et->Umax - (Umax - lev->U + Uf) * et->E / Ev;
233
          if (et->U < et->Umin) {
234
            et->U = et->Umin;
697 anton 235
            ok = 0;
236
          }
237
        }
238
      }
239
    }
673 giacomo 240
 
697 anton 241
  } while (ok == 0);
673 giacomo 242
 
707 anton 243
  // Increase periods of compressed tasks IMMEDIATELY.
244
  // The other ones will be changed at their next activation
245
 
246
  for (i=0; i<MAX_PROC; i++) {
247
    et = &lev->elist[i];
248
    if (et->flags & ELASTIC_PRESENT) {
249
      if (et->U != et->oldU) {
250
        /* Utilization has been changed. Compute new period */
251
        et->T = ((long long)et->C * (long long)MAX_BANDWIDTH) / et->U;
252
      }
253
      if (et->U < et->oldU) {
254
        /* Task has been compressed. Change its deadline NOW! */
255
        if (et->flags & ELASTIC_JOB_PRESENT) {
737 anton 256
          /* Remove job from level */
707 anton 257
          level_table[lev->scheduling_level]->
258
            private_extract(lev->scheduling_level, i);
259
        }
260
        /* Compute new deadline */
261
        et->dline = et->release;
262
        ADDUSEC2TIMESPEC(et->T, &et->dline);
263
        if (et->dltimer != -1) {
264
          /* Delete old deadline timer, post new one */
265
          kern_event_delete(et->dltimer);
266
          et->dltimer = kern_event_post(&et->dline, ELASTIC_timer_act,(void *)(i));
267
        }
268
        if (et->flags & ELASTIC_JOB_PRESENT) {
269
          /* Reinsert job */
270
          job_task_default_model(job, et->dline);
271
          level_table[lev->scheduling_level]->
272
            private_insert(lev->scheduling_level, i, (TASK_MODEL *)&job);
273
        }
274
      }
275
      et->oldU = et->U;  /* Update oldU */
276
    }
277
  }
278
 
279
#ifdef ELASTIC_DEBUG
697 anton 280
  cprintf("New periods: ");
691 anton 281
  for (i=0; i<MAX_PROC; i++) {
707 anton 282
    et = &lev->elist[i];
283
    if (et->flags & ELASTIC_PRESENT) {
284
      cprintf("%s:%d ", proc_table[i].name, (int)et->T);
691 anton 285
    }
286
  }
697 anton 287
  cprintf("\n");
707 anton 288
#endif
691 anton 289
 
697 anton 290
  return 0; // FEASIBLE
691 anton 291
 
673 giacomo 292
}
293
 
697 anton 294
 
671 giacomo 295
/* The on-line guarantee is enabled only if the appropriate flag is set... */
296
static int ELASTIC_public_guarantee(LEVEL l, bandwidth_t *freebandwidth)
297
{
298
  ELASTIC_level_des *lev = (ELASTIC_level_des *)(level_table[l]);
299
 
691 anton 300
  if (*freebandwidth >= lev->U) {
700 anton 301
    *freebandwidth -= (unsigned int)lev->U;
691 anton 302
    return 1;
303
  } else {
304
    return 0;
305
  }
737 anton 306
 
671 giacomo 307
}
308
 
691 anton 309
 
671 giacomo 310
static int ELASTIC_public_create(LEVEL l, PID p, TASK_MODEL *m)
311
{
312
  ELASTIC_level_des *lev = (ELASTIC_level_des *)(level_table[l]);
691 anton 313
  ELASTIC_TASK_MODEL *elastic = (ELASTIC_TASK_MODEL *)m;
707 anton 314
  ELASTIC_task_descr *et = &lev->elist[p];
671 giacomo 315
 
316
  if (m->pclass != ELASTIC_PCLASS) return -1;
317
  if (m->level != 0 && m->level != l) return -1;
318
 
691 anton 319
  if (elastic->C == 0) return -1;
673 giacomo 320
  if (elastic->Tmin > elastic->Tmax) return -1;
321
  if (elastic->Tmax == 0) return -1;
707 anton 322
  if (elastic->Tmin == 0) return -1;
673 giacomo 323
 
707 anton 324
  NULL_TIMESPEC(&(et->dline));
325
  et->Tmin = elastic->Tmin;
326
  et->Tmax = elastic->Tmax;
327
  et->C = elastic->C;
328
  et->E = elastic->E;
329
  et->beta = elastic->beta;
673 giacomo 330
 
707 anton 331
  et->Umax = ((long long)MAX_BANDWIDTH * (long long)elastic->C) / elastic->Tmin;
332
  et->Umin = ((long long)MAX_BANDWIDTH * (long long)elastic->C) / elastic->Tmax;
673 giacomo 333
 
707 anton 334
  et->U = et->Umax;
335
  et->oldU = 0;
336
  et->T = et->Tmin;
337
  et->dltimer = -1;
673 giacomo 338
 
691 anton 339
  proc_table[p].avail_time = elastic->C;
340
  proc_table[p].wcet       = elastic->C;
674 giacomo 341
  proc_table[p].control    |= CONTROL_CAP;
673 giacomo 342
 
697 anton 343
  return 0;
671 giacomo 344
}
345
 
697 anton 346
 
671 giacomo 347
static void ELASTIC_public_detach(LEVEL l, PID p)
348
{
707 anton 349
  //ELASTIC_level_des *lev = (ELASTIC_level_des *)(level_table[l]);
671 giacomo 350
 
351
}
352
 
353
static int ELASTIC_public_eligible(LEVEL l, PID p)
354
{
707 anton 355
  //ELASTIC_level_des *lev = (ELASTIC_level_des *)(level_table[l]);
671 giacomo 356
 
357
  return 0;
358
 
359
}
360
 
361
static void ELASTIC_public_dispatch(LEVEL l, PID p, int nostop)
362
{
363
  ELASTIC_level_des *lev = (ELASTIC_level_des *)(level_table[l]);
674 giacomo 364
 
671 giacomo 365
  level_table[ lev->scheduling_level ]->
366
    private_dispatch(lev->scheduling_level,p,nostop);
674 giacomo 367
 
671 giacomo 368
}
369
 
370
static void ELASTIC_public_epilogue(LEVEL l, PID p)
371
{
372
  ELASTIC_level_des *lev = (ELASTIC_level_des *)(level_table[l]);
373
 
674 giacomo 374
  /* check if the wcet is finished... */
375
  if (proc_table[p].avail_time <= 0) {
376
 
707 anton 377
    TRACER_LOGEVENT(FTrace_EVT_task_wcet_violation,
378
                    (unsigned short int)proc_table[p].context,0);
674 giacomo 379
    kern_raise(XWCET_VIOLATION,p);
380
 
381
  }
691 anton 382
 
707 anton 383
  level_table[lev->scheduling_level]->
674 giacomo 384
      private_epilogue(lev->scheduling_level,p);
385
 
671 giacomo 386
}
387
 
388
static void ELASTIC_public_activate(LEVEL l, PID p, struct timespec *t)
389
{
707 anton 390
 
671 giacomo 391
  ELASTIC_level_des *lev = (ELASTIC_level_des *)(level_table[l]);
707 anton 392
  ELASTIC_task_descr *et = &lev->elist[p];
671 giacomo 393
 
674 giacomo 394
  /* check if we are not in the SLEEP state */
395
  if (proc_table[p].status != SLEEP) {
396
    return;
397
  }
398
 
707 anton 399
  et->flags |= ELASTIC_PRESENT;
400
  if (ELASTIC_compress(lev) == -1) {
401
    et->flags &= ~ELASTIC_PRESENT;
402
#ifdef ELASTIC_DEBUG
403
    cprintf("ELASTIC_public_activate: compression failed!\n");
404
#endif
405
    return;
406
  }
407
 
674 giacomo 408
  ELASTIC_activation(lev,p,t);
409
 
410
  /* Next activation */
707 anton 411
  et->dltimer = kern_event_post(&et->dline, ELASTIC_timer_act, (void *)(p));
674 giacomo 412
 
671 giacomo 413
}
414
 
415
static void ELASTIC_public_unblock(LEVEL l, PID p)
416
{
417
  ELASTIC_level_des *lev = (ELASTIC_level_des *)(level_table[l]);
418
  struct timespec acttime;
419
 
420
  kern_gettime(&acttime);
421
 
422
  ELASTIC_activation(lev,p,&acttime);
423
 
424
}
425
 
426
static void ELASTIC_public_block(LEVEL l, PID p)
427
{
428
  ELASTIC_level_des *lev = (ELASTIC_level_des *)(level_table[l]);
707 anton 429
  ELASTIC_task_descr *et = &lev->elist[p];
671 giacomo 430
 
707 anton 431
  level_table[lev->scheduling_level]->
671 giacomo 432
    private_extract(lev->scheduling_level,p);
707 anton 433
  et->flags &= ~ELASTIC_JOB_PRESENT;
671 giacomo 434
 
435
}
436
 
437
static int ELASTIC_public_message(LEVEL l, PID p, void *m)
438
{
439
  ELASTIC_level_des *lev = (ELASTIC_level_des *)(level_table[l]);
737 anton 440
  ELASTIC_task_descr *et = &lev->elist[p];
671 giacomo 441
 
442
  switch((long)(m)) {
443
 
444
    case (long)(NULL):
445
 
707 anton 446
      level_table[lev->scheduling_level]->
676 giacomo 447
        private_extract(lev->scheduling_level,p);
737 anton 448
      et->flags &= ~ELASTIC_JOB_PRESENT;
676 giacomo 449
 
683 giacomo 450
      proc_table[p].status = ELASTIC_IDLE;
676 giacomo 451
 
671 giacomo 452
      jet_update_endcycle(); /* Update the Jet data... */
453
      TRACER_LOGEVENT(FTrace_EVT_task_end_cycle,(unsigned short int)proc_table[p].context,(unsigned int)l);
454
 
455
      break;
456
 
457
    case 1:
458
 
676 giacomo 459
      level_table[ lev->scheduling_level ]->
460
        private_extract(lev->scheduling_level,p);
737 anton 461
      et->flags &= ~ELASTIC_JOB_PRESENT;
676 giacomo 462
 
463
      proc_table[p].status = SLEEP;
464
 
671 giacomo 465
      TRACER_LOGEVENT(FTrace_EVT_task_disable,(unsigned short int)proc_table[p].context,(unsigned int)l);
466
 
467
      break;
468
 
469
  }
470
 
471
  return 0;
472
 
473
}
474
 
475
static void ELASTIC_public_end(LEVEL l, PID p)
476
{
477
  ELASTIC_level_des *lev = (ELASTIC_level_des *)(level_table[l]);
737 anton 478
  ELASTIC_task_descr *et = &lev->elist[p];
671 giacomo 479
 
480
  level_table[ lev->scheduling_level ]->
481
    private_extract(lev->scheduling_level,p);
737 anton 482
  et->flags &= ~ELASTIC_JOB_PRESENT;
671 giacomo 483
 
484
}
485
 
486
/*+ Registration function +*/
700 anton 487
LEVEL ELASTIC_register_level(int flags, LEVEL master, ext_bandwidth_t U)
671 giacomo 488
{
489
  LEVEL l;            /* the level that we register */
490
  ELASTIC_level_des *lev;  /* for readableness only */
491
  PID i;
492
 
493
  printk("ELASTIC_register_level\n");
494
 
495
  /* request an entry in the level_table */
496
  l = level_alloc_descriptor(sizeof(ELASTIC_level_des));
497
 
498
  lev = (ELASTIC_level_des *)level_table[l];
499
 
500
  /* fill the standard descriptor */
501
  if (flags & ELASTIC_ENABLE_GUARANTEE)
502
    lev->l.public_guarantee = ELASTIC_public_guarantee;
503
  else
504
    lev->l.public_guarantee = NULL;
505
  lev->l.public_create    = ELASTIC_public_create;
506
  lev->l.public_detach    = ELASTIC_public_detach;
507
  lev->l.public_end       = ELASTIC_public_end;
508
  lev->l.public_eligible  = ELASTIC_public_eligible;
509
  lev->l.public_dispatch  = ELASTIC_public_dispatch;
510
  lev->l.public_epilogue  = ELASTIC_public_epilogue;
511
  lev->l.public_activate  = ELASTIC_public_activate;
512
  lev->l.public_unblock   = ELASTIC_public_unblock;
513
  lev->l.public_block     = ELASTIC_public_block;
514
  lev->l.public_message   = ELASTIC_public_message;
515
 
676 giacomo 516
  /* fill the ELASTIC task descriptor part */
671 giacomo 517
  for (i=0; i<MAX_PROC; i++) {
518
     NULL_TIMESPEC(&(lev->elist[i].dline));
519
     lev->elist[i].Tmin = 0;
520
     lev->elist[i].Tmax = 0;
691 anton 521
     lev->elist[i].T = 0;
697 anton 522
     lev->elist[i].U = 0;
691 anton 523
     lev->elist[i].C = 0;
524
     lev->elist[i].E = 0;
671 giacomo 525
     lev->elist[i].beta = 0;
707 anton 526
     lev->elist[i].flags = 0;
671 giacomo 527
  }
528
 
691 anton 529
  lev->U = U;
671 giacomo 530
 
531
  lev->scheduling_level = master;
532
 
533
  lev->current_level = l;
534
 
707 anton 535
  lev->flags = 0;
671 giacomo 536
 
537
  return l;
538
}
539
 
707 anton 540
 
541
/* Force the period of task p to a given value */
542
 
543
int ELASTIC_set_period(PID p, TIME period) {
544
 
545
  SYS_FLAGS f;
546
  int saveE;          
547
  ext_bandwidth_t saveU;
548
 
549
  f = kern_fsave();
550
 
551
  ELASTIC_level_des *lev;
552
  lev = (ELASTIC_level_des *)level_table[proc_table[p].task_level];
553
  ELASTIC_task_descr *et = &lev->elist[p];
554
 
555
  saveE = et->E;
556
  saveU = et->U;
557
 
737 anton 558
  et->E = 0;  /* set elasticity to zero to force period */
707 anton 559
  et->U = ((long long)MAX_BANDWIDTH * (long long)et->C)/period;
560
 
561
  if (ELASTIC_compress(lev) == -1) {
562
#ifdef ELASTIC_DEBUG
563
    cprintf("ELASTIC_set_period failed: could not compress\n");
564
#endif
565
    et->E = saveE;
566
    et->U = saveU;
567
    kern_frestore(f);
568
    return -1;
569
  }
570
 
571
  et->E = saveE;     /* Restore E when compression is done */
572
  kern_frestore(f);
573
  return 0;
574
}
708 giacomo 575
 
576
int ELASTIC_get_period(PID p) {
577
 
578
  SYS_FLAGS f;
579
  ELASTIC_level_des *lev;
580
  lev = (ELASTIC_level_des *)level_table[proc_table[p].task_level];
737 anton 581
  TIME retval;
708 giacomo 582
 
583
  f = kern_fsave();
584
 
585
  if (lev->elist[p].flags & ELASTIC_PRESENT) {  
737 anton 586
    retval = lev->elist[p].T;
708 giacomo 587
    kern_frestore(f);
737 anton 588
    return retval;
708 giacomo 589
 
590
  } else {
591
 
592
    kern_frestore(f);
593
    return -1;
594
 
595
  }
596
 
597
}
598
 
737 anton 599
int ELASTIC_set_E(PID p, int E)
600
{
708 giacomo 601
  SYS_FLAGS f;
602
  ELASTIC_level_des *lev = (ELASTIC_level_des *)level_table[proc_table[p].task_level];
603
  ELASTIC_task_descr *et = &lev->elist[p];
604
  int saveE;
605
 
606
  f = kern_fsave();
737 anton 607
 
708 giacomo 608
  if (et->flags & ELASTIC_PRESENT) {
609
 
610
    saveE = et->E;
737 anton 611
 
612
    et->E = E;
708 giacomo 613
    if (ELASTIC_compress(lev) == -1) {
614
#ifdef ELASTIC_DEBUG
615
      cprintf("ELASTIC_set_E failed: could not compress\n");
616
#endif
617
      et->E = saveE;
618
      kern_frestore(f);
619
      return -1;
620
    }
737 anton 621
 
708 giacomo 622
    kern_frestore(f);
623
    return 0;
737 anton 624
 
708 giacomo 625
  } else {
737 anton 626
 
708 giacomo 627
    kern_frestore(f);
628
    return -1;
629
  }
630
}
631
 
632
int ELASTIC_get_E(PID p) {
737 anton 633
 
708 giacomo 634
  SYS_FLAGS f;
635
  ELASTIC_level_des *lev;
636
  lev = (ELASTIC_level_des *)level_table[proc_table[p].task_level];
737 anton 637
 
708 giacomo 638
  f = kern_fsave();
737 anton 639
 
708 giacomo 640
  if (lev->elist[p].flags & ELASTIC_PRESENT) {
737 anton 641
 
708 giacomo 642
    kern_frestore(f);
643
    return lev->elist[p].E;
737 anton 644
 
708 giacomo 645
  } else {
737 anton 646
 
708 giacomo 647
    kern_frestore(f);
648
    return -1;
649
  }
650
}
651
 
652
int ELASTIC_set_beta(PID p, int beta) {
737 anton 653
 
708 giacomo 654
  SYS_FLAGS f;
655
  ELASTIC_level_des *lev = (ELASTIC_level_des *)level_table[proc_table[p].task_level];
656
  ELASTIC_task_descr *et = &lev->elist[p];
657
  int saveBeta;
658
 
659
  f = kern_fsave();
737 anton 660
 
708 giacomo 661
  if (et->flags & ELASTIC_PRESENT) {
737 anton 662
 
708 giacomo 663
    saveBeta = et->beta;
737 anton 664
 
665
    et->beta = beta;
666
 
708 giacomo 667
    if (ELASTIC_compress(lev) == -1) {
668
#ifdef ELASTIC_DEBUG
669
      cprintf("ELASTIC_set_beta failed: could not compress\n");
670
#endif
671
      et->beta = saveBeta;
672
      kern_frestore(f);
673
      return -1;
674
    }
737 anton 675
 
708 giacomo 676
    kern_frestore(f);
677
    return 0;
737 anton 678
 
708 giacomo 679
  } else {
737 anton 680
 
708 giacomo 681
    kern_frestore(f);
682
    return -1;
737 anton 683
 
708 giacomo 684
  }
737 anton 685
 
708 giacomo 686
}
687
 
688
int ELASTIC_get_beta(PID p) {
737 anton 689
 
708 giacomo 690
  SYS_FLAGS f;
691
  ELASTIC_level_des *lev = (ELASTIC_level_des *)level_table[proc_table[p].task_level];
737 anton 692
  int retval;
693
 
708 giacomo 694
  f = kern_fsave();
737 anton 695
 
708 giacomo 696
  if (lev->elist[p].flags & ELASTIC_PRESENT) {
737 anton 697
    retval = lev->elist[p].beta;
708 giacomo 698
    kern_frestore(f);
737 anton 699
    return retval;
700
 
708 giacomo 701
  } else {
737 anton 702
 
708 giacomo 703
    kern_frestore(f);
704
    return -1;
737 anton 705
 
708 giacomo 706
  }
737 anton 707
 
708 giacomo 708
}
709
 
710
int ELASTIC_set_bandwidth(LEVEL level, ext_bandwidth_t U) {
737 anton 711
 
708 giacomo 712
  SYS_FLAGS f;
713
  ELASTIC_level_des *lev = (ELASTIC_level_des *)level_table[level];
714
 
715
  f = kern_fsave();
716
 
717
  lev->U = U;
718
 
719
  if (ELASTIC_compress(lev) == -1) {
720
#ifdef ELASTIC_DEBUG
721
    cprintf("ELASTIC_set_bandwidth failed: could not compress\n");
722
#endif
723
    kern_frestore(f);
724
    return -1;
725
  }
737 anton 726
 
708 giacomo 727
  kern_frestore(f);
728
  return 0;
737 anton 729
 
708 giacomo 730
}
731
 
732
ext_bandwidth_t ELASTIC_get_bandwidth(LEVEL level) {
737 anton 733
 
708 giacomo 734
  ELASTIC_level_des *lev = (ELASTIC_level_des *)level_table[level];;
735
 
736
  return lev->U;
737 anton 737
 
708 giacomo 738
}