diff --git a/ieee1364-notes.txt b/ieee1364-notes.txt index 3b5427ed9..9253cb0e6 100644 --- a/ieee1364-notes.txt +++ b/ieee1364-notes.txt @@ -318,8 +318,32 @@ the right length, and will therefore flag instances u5 and u6 as errors. The IEEE1364 standard should be more specific one way or the other. -$Id: ieee1364-notes.txt,v 1.8 2001/08/01 05:17:31 steve Exp $ +* UNKNOWN VALUES IN L-VALUE BIT SELECTS + +Consider this example: + + reg [7:0] vec; + wire [4:0] idx = ; + [...] + vec[idx] = 1; + +So long as the value of idx is a valid bit select address, the +behavior of this assignment is obvious. However, there is no explicit +word in the standard as to what happens if the value is out of +range. The standard clearly states the value of an expression when the +bit-select or part select is out of range (the value is x) but does +not address the behavior when the expression is an l-value. + +Icarus Verilog will take the position that bit select expressions in +the l-value will select oblivion if it is out of range. That is, if +idx has a value that is not a valid bit select of vec, then the +assignment will have no effect. + +$Id: ieee1364-notes.txt,v 1.9 2002/01/26 02:08:07 steve Exp $ $Log: ieee1364-notes.txt,v $ +Revision 1.9 2002/01/26 02:08:07 steve + Handle x in l-value of set/x + Revision 1.8 2001/08/01 05:17:31 steve Accept empty port lists to module instantiation. diff --git a/vvp/opcodes.txt b/vvp/opcodes.txt index 0b6b53481..2cff04868 100644 --- a/vvp/opcodes.txt +++ b/vvp/opcodes.txt @@ -1,7 +1,7 @@ /* * Copyright (c) 2001 Stephen Williams (steve@icarus.com) * - * $Id: opcodes.txt,v 1.31 2001/11/01 03:00:19 steve Exp $ + * $Id: opcodes.txt,v 1.32 2002/01/26 02:08:07 steve Exp $ */ @@ -379,6 +379,10 @@ This sets the bit of a variable functor, the address calculated by using the index register (0, 1, 2 or 3) to index the functor address of . +If the index value in index register is <0 (for example if +%ix/get converted an unknown value into the register) then the set is +not performed. + * %shiftl/i0 , diff --git a/vvp/vthread.cc b/vvp/vthread.cc index 618a456d9..51429d27f 100644 --- a/vvp/vthread.cc +++ b/vvp/vthread.cc @@ -17,7 +17,7 @@ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA */ #if !defined(WINNT) -#ident "$Id: vthread.cc,v 1.65 2001/12/31 00:01:16 steve Exp $" +#ident "$Id: vthread.cc,v 1.66 2002/01/26 02:08:07 steve Exp $" #endif # include "vthread.h" @@ -275,6 +275,7 @@ void vthread_run(vthread_t thr) vvp_code_t cp = codespace_index(thr->pc); thr->pc += 1; + assert(cp); assert(cp->opcode); /* Run the opcode implementation. If the execution of @@ -1490,10 +1491,31 @@ bool of_SET_MEM(vthread_t thr, vvp_code_t cp) return true; } +/* + * Implement the %set/x instruction: + * + * %set/x , , + * + * The single bit goes into the indexed functor. Abort the instruction + * if the index is <0. + */ bool of_SET_X(vthread_t thr, vvp_code_t cp) { unsigned char bit_val = thr_get_bit(thr, cp->bit_idx[0]); - vvp_ipoint_t itmp = ipoint_index(cp->iptr, thr->index[cp->bit_idx[1]&3]); + long idx = thr->index[cp->bit_idx[1]&3]; + + /* If idx < 0, then the index value is probably generated from + an undefined value. At any rate, this is defined to have no + effect so quit now. */ + if (idx < 0) { + return true; + } + + /* Form the functor pointer from the base pointer and the + index from the index register. */ + vvp_ipoint_t itmp = ipoint_index(cp->iptr, idx); + + /* Set the value. */ functor_set(itmp, bit_val, strong_values[bit_val], true); return true; @@ -1696,6 +1718,9 @@ bool of_ZOMBIE(vthread_t thr, vvp_code_t) /* * $Log: vthread.cc,v $ + * Revision 1.66 2002/01/26 02:08:07 steve + * Handle x in l-value of set/x + * * Revision 1.65 2001/12/31 00:01:16 steve * Account for negatives in cmp/s *