Revision 0ec9eabc
b/tcg/tcg.c | ||
---|---|---|
357 | 357 |
|
358 | 358 |
void tcg_func_start(TCGContext *s) |
359 | 359 |
{ |
360 |
int i; |
|
361 | 360 |
tcg_pool_reset(s); |
362 | 361 |
s->nb_temps = s->nb_globals; |
363 |
for(i = 0; i < (TCG_TYPE_COUNT * 2); i++) |
|
364 |
s->first_free_temp[i] = -1; |
|
362 |
|
|
363 |
/* No temps have been previously allocated for size or locality. */ |
|
364 |
memset(s->free_temps, 0, sizeof(s->free_temps)); |
|
365 |
|
|
365 | 366 |
s->labels = tcg_malloc(sizeof(TCGLabel) * TCG_MAX_LABELS); |
366 | 367 |
s->nb_labels = 0; |
367 | 368 |
s->current_frame_offset = s->frame_start; |
... | ... | |
503 | 504 |
TCGTemp *ts; |
504 | 505 |
int idx, k; |
505 | 506 |
|
506 |
k = type; |
|
507 |
if (temp_local) |
|
508 |
k += TCG_TYPE_COUNT; |
|
509 |
idx = s->first_free_temp[k]; |
|
510 |
if (idx != -1) { |
|
511 |
/* There is already an available temp with the |
|
512 |
right type */ |
|
507 |
k = type + (temp_local ? TCG_TYPE_COUNT : 0); |
|
508 |
idx = find_first_bit(s->free_temps[k].l, TCG_MAX_TEMPS); |
|
509 |
if (idx < TCG_MAX_TEMPS) { |
|
510 |
/* There is already an available temp with the right type. */ |
|
511 |
clear_bit(idx, s->free_temps[k].l); |
|
512 |
|
|
513 | 513 |
ts = &s->temps[idx]; |
514 |
s->first_free_temp[k] = ts->next_free_temp; |
|
515 | 514 |
ts->temp_allocated = 1; |
515 |
assert(ts->base_type == type); |
|
516 | 516 |
assert(ts->temp_local == temp_local); |
517 | 517 |
} else { |
518 | 518 |
idx = s->nb_temps; |
... | ... | |
568 | 568 |
return MAKE_TCGV_I64(idx); |
569 | 569 |
} |
570 | 570 |
|
571 |
static inline void tcg_temp_free_internal(int idx)
|
|
571 |
static void tcg_temp_free_internal(int idx) |
|
572 | 572 |
{ |
573 | 573 |
TCGContext *s = &tcg_ctx; |
574 | 574 |
TCGTemp *ts; |
... | ... | |
585 | 585 |
ts = &s->temps[idx]; |
586 | 586 |
assert(ts->temp_allocated != 0); |
587 | 587 |
ts->temp_allocated = 0; |
588 |
k = ts->base_type; |
|
589 |
if (ts->temp_local) |
|
590 |
k += TCG_TYPE_COUNT; |
|
591 |
ts->next_free_temp = s->first_free_temp[k]; |
|
592 |
s->first_free_temp[k] = idx; |
|
588 |
|
|
589 |
k = ts->type + (ts->temp_local ? TCG_TYPE_COUNT : 0); |
|
590 |
set_bit(idx, s->free_temps[k].l); |
|
593 | 591 |
} |
594 | 592 |
|
595 | 593 |
void tcg_temp_free_i32(TCGv_i32 arg) |
b/tcg/tcg.h | ||
---|---|---|
26 | 26 |
#define TCG_H |
27 | 27 |
|
28 | 28 |
#include "qemu-common.h" |
29 |
|
|
29 |
#include "qemu/bitops.h" |
|
30 | 30 |
#include "tcg-target.h" |
31 | 31 |
|
32 | 32 |
/* Default target word size to pointer size. */ |
... | ... | |
436 | 436 |
basic blocks. Otherwise, it is not |
437 | 437 |
preserved across basic blocks. */ |
438 | 438 |
unsigned int temp_allocated:1; /* never used for code gen */ |
439 |
/* index of next free temp of same base type, -1 if end */ |
|
440 |
int next_free_temp; |
|
441 | 439 |
const char *name; |
442 | 440 |
} TCGTemp; |
443 | 441 |
|
444 | 442 |
typedef struct TCGContext TCGContext; |
445 | 443 |
|
444 |
typedef struct TCGTempSet { |
|
445 |
unsigned long l[BITS_TO_LONGS(TCG_MAX_TEMPS)]; |
|
446 |
} TCGTempSet; |
|
447 |
|
|
446 | 448 |
struct TCGContext { |
447 | 449 |
uint8_t *pool_cur, *pool_end; |
448 | 450 |
TCGPool *pool_first, *pool_current, *pool_first_large; |
... | ... | |
450 | 452 |
int nb_labels; |
451 | 453 |
int nb_globals; |
452 | 454 |
int nb_temps; |
453 |
/* index of free temps, -1 if none */ |
|
454 |
int first_free_temp[TCG_TYPE_COUNT * 2]; |
|
455 | 455 |
|
456 | 456 |
/* goto_tb support */ |
457 | 457 |
uint8_t *code_buf; |
... | ... | |
477 | 477 |
|
478 | 478 |
uint8_t *code_ptr; |
479 | 479 |
TCGTemp temps[TCG_MAX_TEMPS]; /* globals first, temps after */ |
480 |
TCGTempSet free_temps[TCG_TYPE_COUNT * 2]; |
|
480 | 481 |
|
481 | 482 |
GHashTable *helpers; |
482 | 483 |
|
Also available in: Unified diff