Add new %cast/vec2/dar and %cast/vec4/dar instructions to vvp.

This commit is contained in:
Martin Whitaker 2019-09-11 21:56:27 +01:00
parent 74ff44314e
commit 1aa22735ce
6 changed files with 153 additions and 2 deletions

View File

@ -66,6 +66,8 @@ extern bool of_CASSIGN_VEC4(vthread_t thr, vvp_code_t code);
extern bool of_CASSIGN_VEC4_OFF(vthread_t thr, vvp_code_t code);
extern bool of_CASSIGN_WR(vthread_t thr, vvp_code_t code);
extern bool of_CAST2(vthread_t thr, vvp_code_t code);
extern bool of_CAST_VEC2_DAR(vthread_t thr, vvp_code_t code);
extern bool of_CAST_VEC4_DAR(vthread_t thr, vvp_code_t code);
extern bool of_CAST_VEC4_STR(vthread_t thr, vvp_code_t code);
extern bool of_CMPE(vthread_t thr, vvp_code_t code);
extern bool of_CMPIE(vthread_t thr, vvp_code_t code);

View File

@ -117,6 +117,8 @@ static const struct opcode_table_s opcode_table[] = {
{ "%cassign/vec4", of_CASSIGN_VEC4, 1,{OA_FUNC_PTR,OA_NONE, OA_NONE} },
{ "%cassign/vec4/off",of_CASSIGN_VEC4_OFF,2,{OA_FUNC_PTR,OA_BIT1, OA_NONE} },
{ "%cassign/wr", of_CASSIGN_WR, 1,{OA_FUNC_PTR,OA_NONE, OA_NONE} },
{ "%cast/vec2/dar", of_CAST_VEC2_DAR, 1, {OA_NUMBER, OA_NONE, OA_NONE} },
{ "%cast/vec4/dar", of_CAST_VEC4_DAR, 1, {OA_NUMBER, OA_NONE, OA_NONE} },
{ "%cast/vec4/str", of_CAST_VEC4_STR, 1, {OA_NUMBER, OA_NONE, OA_NONE} },
{ "%cast2", of_CAST2, 0, {OA_NONE, OA_NONE, OA_NONE} },
{ "%cmp/e", of_CMPE, 0, {OA_NONE, OA_NONE, OA_NONE} },

View File

@ -258,6 +258,20 @@ value stack.
Pop a value from the vec4 stack, convert it using Verilog rules to a
vector2 (binary) value, and push the result.
* %cast/vec2/dar <wid>
Pop a dynamic array value from the object stack, convert it to a 2-state
vector that is <wid> bits wide, and push the result to the vec4 stack.
If the dynamic array does not fit exactly in <wid> bits, print an error
message and stop the simulation.
* %cast/vec4/dar <wid>
Pop a dynamic array value from the object stack, convert it to a 4-state
vector that is <wid> bits wide, and push the result to the vec4 stack.
If the dynamic array does not fit exactly in <wid> bits, print an error
message and stop the simulation.
* %cast/vec4/str <wid>
Pop a value from the string stack, convert it to a vector that is <wid>

View File

@ -1547,6 +1547,43 @@ bool of_CAST2(vthread_t thr, vvp_code_t)
return true;
}
bool do_cast_vec_dar(vthread_t thr, vvp_code_t cp, bool as_vec4)
{
unsigned wid = cp->number;
vvp_object_t obj;
thr->pop_object(obj);
vvp_darray*darray = obj.peek<vvp_darray>();
assert(darray);
vvp_vector4_t vec = darray->get_bitstream(as_vec4);
if (vec.size() != wid) {
cerr << "VVP error: size mismatch when casting dynamic array to vector." << endl;
thr->push_vec4(vvp_vector4_t(wid));
schedule_stop(0);
return false;
}
thr->push_vec4(vec);
return true;
}
/*
* %cast/vec2/dar <wid>
*/
bool of_CAST_VEC2_DAR(vthread_t thr, vvp_code_t cp)
{
return do_cast_vec_dar(thr, cp, false);
}
/*
* %cast/vec4/dar <wid>
*/
bool of_CAST_VEC4_DAR(vthread_t thr, vvp_code_t cp)
{
return do_cast_vec_dar(thr, cp, true);
}
/*
* %cast/vec4/str <wid>
*/

View File

@ -1,5 +1,5 @@
/*
* Copyright (c) 2012-2015 Stephen Williams (steve@icarus.com)
* Copyright (c) 2012-2019 Stephen Williams (steve@icarus.com)
*
* This source code is free software; you can redistribute it
* and/or modify it in source code form under the terms of the GNU
@ -72,6 +72,12 @@ void vvp_darray::shallow_copy(const vvp_object*)
cerr << "XXXX shallow_copy(vvp_object_t) not implemented for " << typeid(*this).name() << endl;
}
vvp_vector4_t vvp_darray::get_bitstream(bool)
{
cerr << "XXXX get_bitstream() not implemented for " << typeid(*this).name() << endl;
return vvp_vector4_t();
}
template <class TYPE> vvp_darray_atom<TYPE>::~vvp_darray_atom()
{
}
@ -116,6 +122,27 @@ template <class TYPE> void vvp_darray_atom<TYPE>::shallow_copy(const vvp_object*
array_[idx] = that->array_[idx];
}
template <class TYPE> vvp_vector4_t vvp_darray_atom<TYPE>::get_bitstream(bool)
{
const unsigned word_wid = sizeof(TYPE) * 8;
vvp_vector4_t vec(array_.size() * word_wid, BIT4_0);
unsigned adx = 0;
unsigned vdx = vec.size();
while (vdx > 0) {
TYPE word = array_[adx++];
vdx -= word_wid;
for (unsigned bdx = 0; bdx < word_wid; bdx += 1) {
if (word & 1)
vec.set_bit(vdx+bdx, BIT4_1);
word >>= 1;
}
}
return vec;
}
template class vvp_darray_atom<uint8_t>;
template class vvp_darray_atom<uint16_t>;
template class vvp_darray_atom<uint32_t>;
@ -165,6 +192,25 @@ void vvp_darray_vec4::shallow_copy(const vvp_object*obj)
array_[idx] = that->array_[idx];
}
vvp_vector4_t vvp_darray_vec4::get_bitstream(bool as_vec4)
{
vvp_vector4_t vec(array_.size() * word_wid_, BIT4_0);
unsigned adx = 0;
unsigned vdx = vec.size();
while (vdx > 0) {
vdx -= word_wid_;
for (unsigned bdx = 0; bdx < word_wid_; bdx += 1) {
vvp_bit4_t bit = array_[adx].value(bdx);
if (as_vec4 || (bit == BIT4_1))
vec.set_bit(vdx+bdx, bit);
}
adx++;
}
return vec;
}
vvp_darray_vec2::~vvp_darray_vec2()
{
}
@ -208,6 +254,24 @@ void vvp_darray_vec2::shallow_copy(const vvp_object*obj)
array_[idx] = that->array_[idx];
}
vvp_vector4_t vvp_darray_vec2::get_bitstream(bool)
{
vvp_vector4_t vec(array_.size() * word_wid_, BIT4_0);
unsigned adx = 0;
unsigned vdx = vec.size();
while (vdx > 0) {
vdx -= word_wid_;
for (unsigned bdx = 0; bdx < word_wid_; bdx += 1) {
if (array_[adx].value(bdx))
vec.set_bit(vdx+bdx, BIT4_1);
}
adx++;
}
return vec;
}
vvp_darray_object::~vvp_darray_object()
{
}
@ -280,6 +344,32 @@ void vvp_darray_real::shallow_copy(const vvp_object*obj)
array_[idx] = that->array_[idx];
}
vvp_vector4_t vvp_darray_real::get_bitstream(bool)
{
const unsigned word_wid = sizeof(double) * 8;
assert(word_wid == 64);
vvp_vector4_t vec(array_.size() * word_wid, BIT4_0);
unsigned adx = 0;
unsigned vdx = vec.size();
while (vdx > 0) {
union {
double value;
uint64_t bits;
} word;
word.value = array_[adx++];
vdx -= word_wid;
for (unsigned bdx = 0; bdx < word_wid; bdx += 1) {
if (word.bits & 1)
vec.set_bit(vdx+bdx, BIT4_1);
word.bits >>= 1;
}
}
return vec;
}
vvp_darray_string::~vvp_darray_string()
{
}

View File

@ -1,7 +1,7 @@
#ifndef IVL_vvp_darray_H
#define IVL_vvp_darray_H
/*
* Copyright (c) 2012-2015 Stephen Williams (steve@icarus.com)
* Copyright (c) 2012-2019 Stephen Williams (steve@icarus.com)
*
* This source code is free software; you can redistribute it
* and/or modify it in source code form under the terms of the GNU
@ -46,6 +46,8 @@ class vvp_darray : public vvp_object {
virtual void get_word(unsigned adr, vvp_object_t&value);
virtual void shallow_copy(const vvp_object*obj);
virtual vvp_vector4_t get_bitstream(bool as_vec4);
};
template <class TYPE> class vvp_darray_atom : public vvp_darray {
@ -58,6 +60,7 @@ template <class TYPE> class vvp_darray_atom : public vvp_darray {
void set_word(unsigned adr, const vvp_vector4_t&value);
void get_word(unsigned adr, vvp_vector4_t&value);
void shallow_copy(const vvp_object*obj);
vvp_vector4_t get_bitstream(bool as_vec4);
private:
std::vector<TYPE> array_;
@ -74,6 +77,7 @@ class vvp_darray_vec4 : public vvp_darray {
void set_word(unsigned adr, const vvp_vector4_t&value);
void get_word(unsigned adr, vvp_vector4_t&value);
void shallow_copy(const vvp_object*obj);
vvp_vector4_t get_bitstream(bool as_vec4);
private:
std::vector<vvp_vector4_t> array_;
@ -91,6 +95,7 @@ class vvp_darray_vec2 : public vvp_darray {
void set_word(unsigned adr, const vvp_vector4_t&value);
void get_word(unsigned adr, vvp_vector4_t&value);
void shallow_copy(const vvp_object*obj);
vvp_vector4_t get_bitstream(bool as_vec4);
private:
std::vector<vvp_vector2_t> array_;
@ -107,6 +112,7 @@ class vvp_darray_real : public vvp_darray {
void set_word(unsigned adr, double value);
void get_word(unsigned adr, double&value);
void shallow_copy(const vvp_object*obj);
vvp_vector4_t get_bitstream(bool as_vec4);
private:
std::vector<double> array_;