Fix l-value indexing of memories and vectors so that

an unknown (x) index causes so cell to be addresses.

 Fix tangling of label identifiers in the fork-join
 code generator.
This commit is contained in:
steve 2002-08-27 05:39:57 +00:00
parent bd9e66d333
commit aa390f2a91
5 changed files with 115 additions and 26 deletions

View File

@ -17,7 +17,7 @@
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
*/ */
#ifdef HAVE_CVS_IDENT #ifdef HAVE_CVS_IDENT
#ident "$Id: eval_expr.c,v 1.70 2002/08/22 03:38:40 steve Exp $" #ident "$Id: eval_expr.c,v 1.71 2002/08/27 05:39:57 steve Exp $"
#endif #endif
# include "vvp_priv.h" # include "vvp_priv.h"
@ -1123,6 +1123,7 @@ void draw_memory_index_expr(ivl_memory_t mem, ivl_expr_t ae)
unsigned nbits = ivl_expr_width(ae); unsigned nbits = ivl_expr_width(ae);
const char*bits = ivl_expr_bits(ae); const char*bits = ivl_expr_bits(ae);
unsigned long v = 0; unsigned long v = 0;
int unknown_flag = 0;
unsigned idx; unsigned idx;
for (idx = 0 ; idx < nbits ; idx += 1) for (idx = 0 ; idx < nbits ; idx += 1)
switch (bits[idx]) { switch (bits[idx]) {
@ -1134,14 +1135,18 @@ void draw_memory_index_expr(ivl_memory_t mem, ivl_expr_t ae)
break; break;
default: default:
v = ~0UL; v = ~0UL;
unknown_flag = 1;
break; break;
} }
fprintf(vvp_out, " %%ix/load 3, %lu;\n", (v-root)*width); fprintf(vvp_out, " %%ix/load 3, %lu;\n", (v-root)*width);
fprintf(vvp_out, " %%mov 4, %c, 1;\n",
unknown_flag?'1':'0');
break; break;
} }
case IVL_EX_ULONG: { case IVL_EX_ULONG: {
unsigned v = ivl_expr_uvalue(ae); unsigned v = ivl_expr_uvalue(ae);
fprintf(vvp_out, " %%ix/load 3, %u;\n", (v-root)*width); fprintf(vvp_out, " %%ix/load 3, %u;\n", (v-root)*width);
fprintf(vvp_out, " %%mov 4, 0, 1;\n");
break; break;
} }
default: { default: {
@ -1745,6 +1750,13 @@ struct vector_info draw_eval_expr(ivl_expr_t exp)
/* /*
* $Log: eval_expr.c,v $ * $Log: eval_expr.c,v $
* Revision 1.71 2002/08/27 05:39:57 steve
* Fix l-value indexing of memories and vectors so that
* an unknown (x) index causes so cell to be addresses.
*
* Fix tangling of label identifiers in the fork-join
* code generator.
*
* Revision 1.70 2002/08/22 03:38:40 steve * Revision 1.70 2002/08/22 03:38:40 steve
* Fix behavioral eval of x?a:b expressions. * Fix behavioral eval of x?a:b expressions.
* *

View File

@ -19,7 +19,7 @@
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
*/ */
#ifdef HAVE_CVS_IDENT #ifdef HAVE_CVS_IDENT
#ident "$Id: vvp_priv.h,v 1.18 2002/08/12 01:35:04 steve Exp $" #ident "$Id: vvp_priv.h,v 1.19 2002/08/27 05:39:57 steve Exp $"
#endif #endif
# include "ivl_target.h" # include "ivl_target.h"
@ -91,6 +91,13 @@ struct vector_info {
extern struct vector_info draw_eval_expr(ivl_expr_t exp); extern struct vector_info draw_eval_expr(ivl_expr_t exp);
extern struct vector_info draw_eval_expr_wid(ivl_expr_t exp, unsigned w); extern struct vector_info draw_eval_expr_wid(ivl_expr_t exp, unsigned w);
/*
* This function draws code to evaluate the index expression exp for
* the memory mem. The result is loaded into index register i3, and
* the flag bit 4 is set to 0 if the numerical value is defined, or 1
* if not.
*/
extern void draw_memory_index_expr(ivl_memory_t mem, ivl_expr_t exp); extern void draw_memory_index_expr(ivl_memory_t mem, ivl_expr_t exp);
extern unsigned short allocate_vector(unsigned short wid); extern unsigned short allocate_vector(unsigned short wid);
@ -108,6 +115,13 @@ extern unsigned thread_count;
/* /*
* $Log: vvp_priv.h,v $ * $Log: vvp_priv.h,v $
* Revision 1.19 2002/08/27 05:39:57 steve
* Fix l-value indexing of memories and vectors so that
* an unknown (x) index causes so cell to be addresses.
*
* Fix tangling of label identifiers in the fork-join
* code generator.
*
* Revision 1.18 2002/08/12 01:35:04 steve * Revision 1.18 2002/08/12 01:35:04 steve
* conditional ident string using autoconfig. * conditional ident string using autoconfig.
* *

View File

@ -17,7 +17,7 @@
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
*/ */
#ifdef HAVE_CVS_IDENT #ifdef HAVE_CVS_IDENT
#ident "$Id: vvp_process.c,v 1.64 2002/08/19 00:06:12 steve Exp $" #ident "$Id: vvp_process.c,v 1.65 2002/08/27 05:39:57 steve Exp $"
#endif #endif
# include "vvp_priv.h" # include "vvp_priv.h"
@ -125,6 +125,10 @@ static void assign_to_memory(ivl_memory_t mem, unsigned idx,
vvp_memory_label(mem), delay, bit); vvp_memory_label(mem), delay, bit);
} }
/*
* This function, in addition to setting the value into index 0, sets
* bit 4 to 1 if the value is unknown.
*/
static void calculate_into_x0(ivl_expr_t expr) static void calculate_into_x0(ivl_expr_t expr)
{ {
struct vector_info vec = draw_eval_expr(expr); struct vector_info vec = draw_eval_expr(expr);
@ -156,39 +160,58 @@ static int show_stmt_assign(ivl_statement_t net)
unsigned cur_rbit = 0; unsigned cur_rbit = 0;
for (lidx = 0 ; lidx < ivl_stmt_lvals(net) ; lidx += 1) { for (lidx = 0 ; lidx < ivl_stmt_lvals(net) ; lidx += 1) {
unsigned skip_set = transient_id++;
unsigned skip_set_flag = 0;
unsigned idx; unsigned idx;
unsigned bit_limit = wid - cur_rbit; unsigned bit_limit = wid - cur_rbit;
lval = ivl_stmt_lval(net, lidx); lval = ivl_stmt_lval(net, lidx);
/* If there is a mux for the lval, calculate the /* If there is a mux for the lval, calculate the
value and write it into index0. */ value and write it into index0. */
if (ivl_lval_mux(lval)) if (ivl_lval_mux(lval)) {
calculate_into_x0(ivl_lval_mux(lval)); calculate_into_x0(ivl_lval_mux(lval));
fprintf(vvp_out, " %%jmp/1 t_%u, 4;\n", skip_set);
skip_set_flag = 1;
}
mem = ivl_lval_mem(lval); mem = ivl_lval_mem(lval);
if (mem) if (mem) {
draw_memory_index_expr(mem, ivl_lval_idx(lval)); draw_memory_index_expr(mem, ivl_lval_idx(lval));
fprintf(vvp_out, " %%jmp/1 t_%u, 4;\n", skip_set);
skip_set_flag = 1;
}
if (bit_limit > ivl_lval_pins(lval)) if (bit_limit > ivl_lval_pins(lval))
bit_limit = ivl_lval_pins(lval); bit_limit = ivl_lval_pins(lval);
if (mem) {
for (idx = 0 ; idx < bit_limit ; idx += 1) { for (idx = 0 ; idx < bit_limit ; idx += 1) {
if (mem)
set_to_memory(mem, idx, set_to_memory(mem, idx,
bitchar_to_idx(bits[cur_rbit])); bitchar_to_idx(bits[cur_rbit]));
else
cur_rbit += 1;
}
for (idx = bit_limit
; idx < ivl_lval_pins(lval) ; idx += 1)
set_to_memory(mem, idx, 0);
} else {
for (idx = 0 ; idx < bit_limit ; idx += 1) {
set_to_lvariable(lval, idx, set_to_lvariable(lval, idx,
bitchar_to_idx(bits[cur_rbit])); bitchar_to_idx(bits[cur_rbit]));
cur_rbit += 1; cur_rbit += 1;
} }
for (idx = bit_limit ; idx < ivl_lval_pins(lval) ; idx += 1) for (idx = bit_limit
if (mem) ; idx < ivl_lval_pins(lval) ; idx += 1)
set_to_memory(mem, idx, 0);
else
set_to_lvariable(lval, idx, 0); set_to_lvariable(lval, idx, 0);
}
if (skip_set_flag)
fprintf(vvp_out, "t_%u ;\n", skip_set);
} }
return 0; return 0;
@ -200,18 +223,26 @@ static int show_stmt_assign(ivl_statement_t net)
unsigned cur_rbit = 0; unsigned cur_rbit = 0;
for (lidx = 0 ; lidx < ivl_stmt_lvals(net) ; lidx += 1) { for (lidx = 0 ; lidx < ivl_stmt_lvals(net) ; lidx += 1) {
unsigned skip_set = transient_id++;
unsigned skip_set_flag = 0;
unsigned idx; unsigned idx;
unsigned bit_limit = wid - cur_rbit; unsigned bit_limit = wid - cur_rbit;
lval = ivl_stmt_lval(net, lidx); lval = ivl_stmt_lval(net, lidx);
/* If there is a mux for the lval, calculate the /* If there is a mux for the lval, calculate the
value and write it into index0. */ value and write it into index0. */
if (ivl_lval_mux(lval)) if (ivl_lval_mux(lval)) {
calculate_into_x0(ivl_lval_mux(lval)); calculate_into_x0(ivl_lval_mux(lval));
fprintf(vvp_out, " %%jmp/1 t_%u, 4;\n", skip_set);
skip_set_flag = 1;
}
mem = ivl_lval_mem(lval); mem = ivl_lval_mem(lval);
if (mem) if (mem) {
draw_memory_index_expr(mem, ivl_lval_idx(lval)); draw_memory_index_expr(mem, ivl_lval_idx(lval));
fprintf(vvp_out, " %%jmp/1 t_%u, 4;\n", skip_set);
skip_set_flag = 1;
}
if (bit_limit > ivl_lval_pins(lval)) if (bit_limit > ivl_lval_pins(lval))
bit_limit = ivl_lval_pins(lval); bit_limit = ivl_lval_pins(lval);
@ -234,6 +265,9 @@ static int show_stmt_assign(ivl_statement_t net)
else else
set_to_lvariable(lval, idx, 0); set_to_lvariable(lval, idx, 0);
if (skip_set_flag)
fprintf(vvp_out, "t_%u ;\n", skip_set);
} }
clr_vector(res); clr_vector(res);
@ -715,13 +749,16 @@ static int show_stmt_fork(ivl_statement_t net, ivl_scope_t sscope)
unsigned cnt = ivl_stmt_block_count(net); unsigned cnt = ivl_stmt_block_count(net);
unsigned out = transient_id++; unsigned out = transient_id++;
unsigned id_base = transient_id;
transient_id += cnt-1;
/* Draw a fork statement for all but one of the threads of the /* Draw a fork statement for all but one of the threads of the
fork/join. Send the threads off to a bit of code where they fork/join. Send the threads off to a bit of code where they
are implemented. */ are implemented. */
for (idx = 0 ; idx < cnt-1 ; idx += 1) { for (idx = 0 ; idx < cnt-1 ; idx += 1) {
fprintf(vvp_out, " %%fork t_%u, S_%s;\n", fprintf(vvp_out, " %%fork t_%u, S_%s;\n",
transient_id+idx, id_base+idx,
vvp_mangle_id(ivl_scope_name(sscope))); vvp_mangle_id(ivl_scope_name(sscope)));
} }
@ -735,7 +772,7 @@ static int show_stmt_fork(ivl_statement_t net, ivl_scope_t sscope)
fprintf(vvp_out, " %%jmp t_%u;\n", out); fprintf(vvp_out, " %%jmp t_%u;\n", out);
for (idx = 0 ; idx < cnt-1 ; idx += 1) { for (idx = 0 ; idx < cnt-1 ; idx += 1) {
fprintf(vvp_out, "t_%u ;\n", transient_id+idx); fprintf(vvp_out, "t_%u ;\n", id_base+idx);
rc += show_statement(ivl_stmt_block_stmt(net, idx), sscope); rc += show_statement(ivl_stmt_block_stmt(net, idx), sscope);
fprintf(vvp_out, " %%end;\n"); fprintf(vvp_out, " %%end;\n");
} }
@ -744,8 +781,6 @@ static int show_stmt_fork(ivl_statement_t net, ivl_scope_t sscope)
the implementations of all the child threads. */ the implementations of all the child threads. */
fprintf(vvp_out, "t_%u ;\n", out); fprintf(vvp_out, "t_%u ;\n", out);
transient_id += cnt-1;
return rc; return rc;
} }
@ -1232,6 +1267,13 @@ int draw_func_definition(ivl_scope_t scope)
/* /*
* $Log: vvp_process.c,v $ * $Log: vvp_process.c,v $
* Revision 1.65 2002/08/27 05:39:57 steve
* Fix l-value indexing of memories and vectors so that
* an unknown (x) index causes so cell to be addresses.
*
* Fix tangling of label identifiers in the fork-join
* code generator.
*
* Revision 1.64 2002/08/19 00:06:12 steve * Revision 1.64 2002/08/19 00:06:12 steve
* Allow release to handle removal of target net. * Allow release to handle removal of target net.
* *

View File

@ -1,7 +1,7 @@
/* /*
* Copyright (c) 2001 Stephen Williams (steve@icarus.com) * Copyright (c) 2001 Stephen Williams (steve@icarus.com)
* *
* $Id: opcodes.txt,v 1.37 2002/08/22 03:38:40 steve Exp $ * $Id: opcodes.txt,v 1.38 2002/08/27 05:39:57 steve Exp $
*/ */
@ -234,7 +234,16 @@ thread bit space, and <wid> is the width of the vector.
The function converts the 4-value bits into a binary number, without The function converts the 4-value bits into a binary number, without
sign extension. If any of the bits of the vector is x or z, then the sign extension. If any of the bits of the vector is x or z, then the
index register gets the value (-1). index register gets the value 0.
The function also writes into bit 4 a 1 if any of the bits of the
input vector are x or z. This is a flag that the 0 value written into
the index register is really the result of calculating from unknown
bits.
4: unknown value
5: (reserved)
6: (reserved)
* %ix/load <idx>, <value> * %ix/load <idx>, <value>

View File

@ -17,7 +17,7 @@
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
*/ */
#ifdef HAVE_CVS_IDENT #ifdef HAVE_CVS_IDENT
#ident "$Id: vthread.cc,v 1.81 2002/08/22 03:38:40 steve Exp $" #ident "$Id: vthread.cc,v 1.82 2002/08/27 05:39:57 steve Exp $"
#endif #endif
# include "vthread.h" # include "vthread.h"
@ -1260,21 +1260,26 @@ bool of_IX_LOAD(vthread_t thr, vvp_code_t cp)
* vector and <wid> is the width in bits. * vector and <wid> is the width in bits.
* *
* Index registers only hold binary values, so if any of the * Index registers only hold binary values, so if any of the
* bits of the vector are x or z, then set the value to 0 * bits of the vector are x or z, then set the value to 0,
* and give up. * set bit[4] to 1, and give up.
*/ */
bool of_IX_GET(vthread_t thr, vvp_code_t cp) bool of_IX_GET(vthread_t thr, vvp_code_t cp)
{ {
unsigned long v = 0; unsigned long v = 0;
bool unknown_flag = false;
for (unsigned i = 0; i<cp->number; i++) { for (unsigned i = 0; i<cp->number; i++) {
unsigned char vv = thr_get_bit(thr, cp->bit_idx[1] + i); unsigned char vv = thr_get_bit(thr, cp->bit_idx[1] + i);
if (vv&2) { if (vv&2) {
v = 0UL; v = 0UL;
unknown_flag = true;
break; break;
} }
v |= vv << i; v |= vv << i;
} }
thr->index[cp->bit_idx[0] & 3] = v; thr->index[cp->bit_idx[0] & 3] = v;
/* Set bit 4 as a flag if the input is unknown. */
thr_put_bit(thr, 4, unknown_flag? 1 : 0);
return true; return true;
} }
@ -2243,6 +2248,13 @@ bool of_CALL_UFUNC(vthread_t thr, vvp_code_t cp)
/* /*
* $Log: vthread.cc,v $ * $Log: vthread.cc,v $
* Revision 1.82 2002/08/27 05:39:57 steve
* Fix l-value indexing of memories and vectors so that
* an unknown (x) index causes so cell to be addresses.
*
* Fix tangling of label identifiers in the fork-join
* code generator.
*
* Revision 1.81 2002/08/22 03:38:40 steve * Revision 1.81 2002/08/22 03:38:40 steve
* Fix behavioral eval of x?a:b expressions. * Fix behavioral eval of x?a:b expressions.
* *