use char in fabric bitstream to save memory footprint
This commit is contained in:
parent
405824081b
commit
9f19c36a89
|
@ -73,4 +73,34 @@ std::vector<size_t> itobin_vec(const size_t& in_int,
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/********************************************************************
|
||||||
|
* Converter an integer to a binary vector
|
||||||
|
* For example:
|
||||||
|
* Input integer: 4
|
||||||
|
* Binary length : 3
|
||||||
|
* Output:
|
||||||
|
* index | 0 | 1 | 2
|
||||||
|
* ret | 0 | 0 | 1
|
||||||
|
*
|
||||||
|
* This function is optimized to return a vector of char
|
||||||
|
* which has a smaller memory footprint than size_t
|
||||||
|
********************************************************************/
|
||||||
|
std::vector<char> itobin_charvec(const size_t& in_int,
|
||||||
|
const size_t& bin_len) {
|
||||||
|
std::vector<char> ret(bin_len, '0');
|
||||||
|
|
||||||
|
/* Make sure we do not have any overflow! */
|
||||||
|
VTR_ASSERT ( (in_int < pow(2., bin_len)) );
|
||||||
|
|
||||||
|
size_t temp = in_int;
|
||||||
|
for (size_t i = 0; i < bin_len; i++) {
|
||||||
|
if (1 == temp % 2) {
|
||||||
|
ret[i] = '1'; /* Keep a good sequence of bits */
|
||||||
|
}
|
||||||
|
temp = temp / 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
} /* end namespace openfpga */
|
} /* end namespace openfpga */
|
||||||
|
|
|
@ -18,6 +18,9 @@ std::vector<size_t> ito1hot_vec(const size_t& in_int,
|
||||||
std::vector<size_t> itobin_vec(const size_t& in_int,
|
std::vector<size_t> itobin_vec(const size_t& in_int,
|
||||||
const size_t& bin_len);
|
const size_t& bin_len);
|
||||||
|
|
||||||
|
std::vector<char> itobin_charvec(const size_t& in_int,
|
||||||
|
const size_t& bin_len);
|
||||||
|
|
||||||
} /* namespace openfpga ends */
|
} /* namespace openfpga ends */
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -158,11 +158,11 @@ void rec_build_module_fabric_dependent_memory_bank_bitstream(const BitstreamMana
|
||||||
|
|
||||||
/* Find BL address */
|
/* Find BL address */
|
||||||
size_t cur_bl_index = std::floor(cur_mem_index / num_bls);
|
size_t cur_bl_index = std::floor(cur_mem_index / num_bls);
|
||||||
std::vector<size_t> bl_addr_bits_vec = itobin_vec(cur_bl_index, bl_addr_size);
|
std::vector<char> bl_addr_bits_vec = itobin_charvec(cur_bl_index, bl_addr_size);
|
||||||
|
|
||||||
/* Find WL address */
|
/* Find WL address */
|
||||||
size_t cur_wl_index = cur_mem_index % num_wls;
|
size_t cur_wl_index = cur_mem_index % num_wls;
|
||||||
std::vector<size_t> wl_addr_bits_vec = itobin_vec(cur_wl_index, wl_addr_size);
|
std::vector<char> wl_addr_bits_vec = itobin_charvec(cur_wl_index, wl_addr_size);
|
||||||
|
|
||||||
/* Set BL address */
|
/* Set BL address */
|
||||||
fabric_bitstream.set_bit_bl_address(fabric_bit, bl_addr_bits_vec);
|
fabric_bitstream.set_bit_bl_address(fabric_bit, bl_addr_bits_vec);
|
||||||
|
@ -206,7 +206,7 @@ void rec_build_module_fabric_dependent_frame_bitstream(const BitstreamManager& b
|
||||||
const std::vector<ConfigBlockId>& parent_blocks,
|
const std::vector<ConfigBlockId>& parent_blocks,
|
||||||
const ModuleManager& module_manager,
|
const ModuleManager& module_manager,
|
||||||
const std::vector<ModuleId>& parent_modules,
|
const std::vector<ModuleId>& parent_modules,
|
||||||
const std::vector<size_t>& addr_code,
|
const std::vector<char>& addr_code,
|
||||||
FabricBitstream& fabric_bitstream) {
|
FabricBitstream& fabric_bitstream) {
|
||||||
|
|
||||||
/* Depth-first search: if we have any children in the parent_block,
|
/* Depth-first search: if we have any children in the parent_block,
|
||||||
|
@ -272,13 +272,13 @@ void rec_build_module_fabric_dependent_frame_bitstream(const BitstreamManager& b
|
||||||
child_modules.push_back(child_module);
|
child_modules.push_back(child_module);
|
||||||
|
|
||||||
/* Set address, apply binary conversion from the first to the last element in the address list */
|
/* Set address, apply binary conversion from the first to the last element in the address list */
|
||||||
std::vector<size_t> child_addr_code = addr_code;
|
std::vector<char> child_addr_code = addr_code;
|
||||||
|
|
||||||
if (true == add_addr_code) {
|
if (true == add_addr_code) {
|
||||||
/* Find the address port from the decoder module */
|
/* Find the address port from the decoder module */
|
||||||
const ModulePortId& decoder_addr_port_id = module_manager.find_module_port(decoder_module, std::string(DECODER_ADDRESS_PORT_NAME));
|
const ModulePortId& decoder_addr_port_id = module_manager.find_module_port(decoder_module, std::string(DECODER_ADDRESS_PORT_NAME));
|
||||||
const BasicPort& decoder_addr_port = module_manager.module_port(decoder_module, decoder_addr_port_id);
|
const BasicPort& decoder_addr_port = module_manager.module_port(decoder_module, decoder_addr_port_id);
|
||||||
std::vector<size_t> addr_bits_vec = itobin_vec(child_id, decoder_addr_port.get_width());
|
std::vector<char> addr_bits_vec = itobin_charvec(child_id, decoder_addr_port.get_width());
|
||||||
|
|
||||||
child_addr_code.insert(child_addr_code.begin(), addr_bits_vec.begin(), addr_bits_vec.end());
|
child_addr_code.insert(child_addr_code.begin(), addr_bits_vec.begin(), addr_bits_vec.end());
|
||||||
|
|
||||||
|
@ -316,7 +316,7 @@ void rec_build_module_fabric_dependent_frame_bitstream(const BitstreamManager& b
|
||||||
const ModulePortId& child_addr_port_id = module_manager.find_module_port(child_module, std::string(DECODER_ADDRESS_PORT_NAME));
|
const ModulePortId& child_addr_port_id = module_manager.find_module_port(child_module, std::string(DECODER_ADDRESS_PORT_NAME));
|
||||||
const BasicPort& child_addr_port = module_manager.module_port(child_module, child_addr_port_id);
|
const BasicPort& child_addr_port = module_manager.module_port(child_module, child_addr_port_id);
|
||||||
if (0 < max_child_addr_code_size - child_addr_port.get_width()) {
|
if (0 < max_child_addr_code_size - child_addr_port.get_width()) {
|
||||||
std::vector<size_t> dummy_codes(max_child_addr_code_size - child_addr_port.get_width(), 0);
|
std::vector<char> dummy_codes(max_child_addr_code_size - child_addr_port.get_width(), '0');
|
||||||
child_addr_code.insert(child_addr_code.begin(), dummy_codes.begin(), dummy_codes.end());
|
child_addr_code.insert(child_addr_code.begin(), dummy_codes.begin(), dummy_codes.end());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -349,9 +349,9 @@ void rec_build_module_fabric_dependent_frame_bitstream(const BitstreamManager& b
|
||||||
for (size_t ibit = 0; ibit < bitstream_manager.block_bits(parent_blocks.back()).size(); ++ibit) {
|
for (size_t ibit = 0; ibit < bitstream_manager.block_bits(parent_blocks.back()).size(); ++ibit) {
|
||||||
|
|
||||||
ConfigBitId config_bit = bitstream_manager.block_bits(parent_blocks.back())[ibit];
|
ConfigBitId config_bit = bitstream_manager.block_bits(parent_blocks.back())[ibit];
|
||||||
std::vector<size_t> addr_bits_vec = itobin_vec(ibit, decoder_addr_port.get_width());
|
std::vector<char> addr_bits_vec = itobin_charvec(ibit, decoder_addr_port.get_width());
|
||||||
|
|
||||||
std::vector<size_t> child_addr_code = addr_code;
|
std::vector<char> child_addr_code = addr_code;
|
||||||
|
|
||||||
child_addr_code.insert(child_addr_code.begin(), addr_bits_vec.begin(), addr_bits_vec.end());
|
child_addr_code.insert(child_addr_code.begin(), addr_bits_vec.begin(), addr_bits_vec.end());
|
||||||
|
|
||||||
|
@ -429,7 +429,7 @@ void build_module_fabric_dependent_bitstream(const ConfigProtocol& config_protoc
|
||||||
std::vector<ConfigBlockId>(1, top_block),
|
std::vector<ConfigBlockId>(1, top_block),
|
||||||
module_manager,
|
module_manager,
|
||||||
std::vector<ModuleId>(1, top_module),
|
std::vector<ModuleId>(1, top_module),
|
||||||
std::vector<size_t>(),
|
std::vector<char>(),
|
||||||
fabric_bitstream);
|
fabric_bitstream);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
|
@ -27,25 +27,25 @@ ConfigBitId FabricBitstream::config_bit(const FabricBitId& bit_id) const {
|
||||||
return config_bit_ids_[bit_id];
|
return config_bit_ids_[bit_id];
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<size_t> FabricBitstream::bit_address(const FabricBitId& bit_id) const {
|
std::vector<char> FabricBitstream::bit_address(const FabricBitId& bit_id) const {
|
||||||
/* Ensure a valid id */
|
/* Ensure a valid id */
|
||||||
VTR_ASSERT(true == valid_bit_id(bit_id));
|
VTR_ASSERT(true == valid_bit_id(bit_id));
|
||||||
|
|
||||||
return bit_addresses_[bit_id][0];
|
return bit_addresses_[bit_id][0];
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<size_t> FabricBitstream::bit_bl_address(const FabricBitId& bit_id) const {
|
std::vector<char> FabricBitstream::bit_bl_address(const FabricBitId& bit_id) const {
|
||||||
return bit_address(bit_id);
|
return bit_address(bit_id);
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<size_t> FabricBitstream::bit_wl_address(const FabricBitId& bit_id) const {
|
std::vector<char> FabricBitstream::bit_wl_address(const FabricBitId& bit_id) const {
|
||||||
/* Ensure a valid id */
|
/* Ensure a valid id */
|
||||||
VTR_ASSERT(true == valid_bit_id(bit_id));
|
VTR_ASSERT(true == valid_bit_id(bit_id));
|
||||||
|
|
||||||
return bit_addresses_[bit_id][1];
|
return bit_addresses_[bit_id][1];
|
||||||
}
|
}
|
||||||
|
|
||||||
bool FabricBitstream::bit_din(const FabricBitId& bit_id) const {
|
char FabricBitstream::bit_din(const FabricBitId& bit_id) const {
|
||||||
/* Ensure a valid id */
|
/* Ensure a valid id */
|
||||||
VTR_ASSERT(true == valid_bit_id(bit_id));
|
VTR_ASSERT(true == valid_bit_id(bit_id));
|
||||||
|
|
||||||
|
@ -74,24 +74,24 @@ FabricBitId FabricBitstream::add_bit(const ConfigBitId& config_bit_id) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void FabricBitstream::set_bit_address(const FabricBitId& bit_id,
|
void FabricBitstream::set_bit_address(const FabricBitId& bit_id,
|
||||||
const std::vector<size_t>& address) {
|
const std::vector<char>& address) {
|
||||||
VTR_ASSERT(true == valid_bit_id(bit_id));
|
VTR_ASSERT(true == valid_bit_id(bit_id));
|
||||||
bit_addresses_[bit_id][0] = address;
|
bit_addresses_[bit_id][0] = address;
|
||||||
}
|
}
|
||||||
|
|
||||||
void FabricBitstream::set_bit_bl_address(const FabricBitId& bit_id,
|
void FabricBitstream::set_bit_bl_address(const FabricBitId& bit_id,
|
||||||
const std::vector<size_t>& address) {
|
const std::vector<char>& address) {
|
||||||
set_bit_address(bit_id, address);
|
set_bit_address(bit_id, address);
|
||||||
}
|
}
|
||||||
|
|
||||||
void FabricBitstream::set_bit_wl_address(const FabricBitId& bit_id,
|
void FabricBitstream::set_bit_wl_address(const FabricBitId& bit_id,
|
||||||
const std::vector<size_t>& address) {
|
const std::vector<char>& address) {
|
||||||
VTR_ASSERT(true == valid_bit_id(bit_id));
|
VTR_ASSERT(true == valid_bit_id(bit_id));
|
||||||
bit_addresses_[bit_id][1] = address;
|
bit_addresses_[bit_id][1] = address;
|
||||||
}
|
}
|
||||||
|
|
||||||
void FabricBitstream::set_bit_din(const FabricBitId& bit_id,
|
void FabricBitstream::set_bit_din(const FabricBitId& bit_id,
|
||||||
const bool& din) {
|
const char& din) {
|
||||||
VTR_ASSERT(true == valid_bit_id(bit_id));
|
VTR_ASSERT(true == valid_bit_id(bit_id));
|
||||||
bit_dins_[bit_id] = din;
|
bit_dins_[bit_id] = din;
|
||||||
}
|
}
|
||||||
|
@ -105,7 +105,7 @@ void FabricBitstream::reverse() {
|
||||||
/******************************************************************************
|
/******************************************************************************
|
||||||
* Public Validators
|
* Public Validators
|
||||||
******************************************************************************/
|
******************************************************************************/
|
||||||
bool FabricBitstream::valid_bit_id(const FabricBitId& bit_id) const {
|
char FabricBitstream::valid_bit_id(const FabricBitId& bit_id) const {
|
||||||
return (size_t(bit_id) < bit_ids_.size()) && (bit_id == bit_ids_[bit_id]);
|
return (size_t(bit_id) < bit_ids_.size()) && (bit_id == bit_ids_[bit_id]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -52,12 +52,12 @@ class FabricBitstream {
|
||||||
ConfigBitId config_bit(const FabricBitId& bit_id) const;
|
ConfigBitId config_bit(const FabricBitId& bit_id) const;
|
||||||
|
|
||||||
/* Find the address of bitstream */
|
/* Find the address of bitstream */
|
||||||
std::vector<size_t> bit_address(const FabricBitId& bit_id) const;
|
std::vector<char> bit_address(const FabricBitId& bit_id) const;
|
||||||
std::vector<size_t> bit_bl_address(const FabricBitId& bit_id) const;
|
std::vector<char> bit_bl_address(const FabricBitId& bit_id) const;
|
||||||
std::vector<size_t> bit_wl_address(const FabricBitId& bit_id) const;
|
std::vector<char> bit_wl_address(const FabricBitId& bit_id) const;
|
||||||
|
|
||||||
/* Find the data-in of bitstream */
|
/* Find the data-in of bitstream */
|
||||||
bool bit_din(const FabricBitId& bit_id) const;
|
char bit_din(const FabricBitId& bit_id) const;
|
||||||
|
|
||||||
public: /* Public Mutators */
|
public: /* Public Mutators */
|
||||||
/* Reserve config bits */
|
/* Reserve config bits */
|
||||||
|
@ -67,16 +67,16 @@ class FabricBitstream {
|
||||||
FabricBitId add_bit(const ConfigBitId& config_bit_id);
|
FabricBitId add_bit(const ConfigBitId& config_bit_id);
|
||||||
|
|
||||||
void set_bit_address(const FabricBitId& bit_id,
|
void set_bit_address(const FabricBitId& bit_id,
|
||||||
const std::vector<size_t>& address);
|
const std::vector<char>& address);
|
||||||
|
|
||||||
void set_bit_bl_address(const FabricBitId& bit_id,
|
void set_bit_bl_address(const FabricBitId& bit_id,
|
||||||
const std::vector<size_t>& address);
|
const std::vector<char>& address);
|
||||||
|
|
||||||
void set_bit_wl_address(const FabricBitId& bit_id,
|
void set_bit_wl_address(const FabricBitId& bit_id,
|
||||||
const std::vector<size_t>& address);
|
const std::vector<char>& address);
|
||||||
|
|
||||||
void set_bit_din(const FabricBitId& bit_id,
|
void set_bit_din(const FabricBitId& bit_id,
|
||||||
const bool& din);
|
const char& din);
|
||||||
|
|
||||||
/* Reverse bit sequence of the fabric bitstream
|
/* Reverse bit sequence of the fabric bitstream
|
||||||
* This is required by configuration chain protocol
|
* This is required by configuration chain protocol
|
||||||
|
@ -84,7 +84,7 @@ class FabricBitstream {
|
||||||
void reverse();
|
void reverse();
|
||||||
|
|
||||||
public: /* Public Validators */
|
public: /* Public Validators */
|
||||||
bool valid_bit_id(const FabricBitId& bit_id) const;
|
char valid_bit_id(const FabricBitId& bit_id) const;
|
||||||
|
|
||||||
private: /* Internal data */
|
private: /* Internal data */
|
||||||
/* Unique id of a bit in the Bitstream */
|
/* Unique id of a bit in the Bitstream */
|
||||||
|
@ -97,10 +97,10 @@ class FabricBitstream {
|
||||||
*
|
*
|
||||||
* We use a 2-element array, as we may have a BL address and a WL address
|
* We use a 2-element array, as we may have a BL address and a WL address
|
||||||
*/
|
*/
|
||||||
vtr::vector<FabricBitId, std::array<std::vector<size_t>, 2>> bit_addresses_;
|
vtr::vector<FabricBitId, std::array<std::vector<char>, 2>> bit_addresses_;
|
||||||
|
|
||||||
/* Data input (Din) bits: this is designed for memory decoders */
|
/* Data input (Din) bits: this is designed for memory decoders */
|
||||||
vtr::vector<FabricBitId, bool> bit_dins_;
|
vtr::vector<FabricBitId, char> bit_dins_;
|
||||||
};
|
};
|
||||||
|
|
||||||
} /* end namespace openfpga */
|
} /* end namespace openfpga */
|
||||||
|
|
|
@ -50,11 +50,11 @@ int write_fabric_config_bit_to_text_file(std::fstream& fp,
|
||||||
fp << bitstream_manager.bit_value(fabric_bitstream.config_bit(fabric_bit));
|
fp << bitstream_manager.bit_value(fabric_bitstream.config_bit(fabric_bit));
|
||||||
break;
|
break;
|
||||||
case CONFIG_MEM_MEMORY_BANK: {
|
case CONFIG_MEM_MEMORY_BANK: {
|
||||||
for (const size_t& addr_bit : fabric_bitstream.bit_bl_address(fabric_bit)) {
|
for (const char& addr_bit : fabric_bitstream.bit_bl_address(fabric_bit)) {
|
||||||
fp << addr_bit;
|
fp << addr_bit;
|
||||||
}
|
}
|
||||||
write_space_to_file(fp, 1);
|
write_space_to_file(fp, 1);
|
||||||
for (const size_t& addr_bit : fabric_bitstream.bit_wl_address(fabric_bit)) {
|
for (const char& addr_bit : fabric_bitstream.bit_wl_address(fabric_bit)) {
|
||||||
fp << addr_bit;
|
fp << addr_bit;
|
||||||
}
|
}
|
||||||
write_space_to_file(fp, 1);
|
write_space_to_file(fp, 1);
|
||||||
|
@ -63,7 +63,7 @@ int write_fabric_config_bit_to_text_file(std::fstream& fp,
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case CONFIG_MEM_FRAME_BASED: {
|
case CONFIG_MEM_FRAME_BASED: {
|
||||||
for (const size_t& addr_bit : fabric_bitstream.bit_address(fabric_bit)) {
|
for (const char& addr_bit : fabric_bitstream.bit_address(fabric_bit)) {
|
||||||
fp << addr_bit;
|
fp << addr_bit;
|
||||||
}
|
}
|
||||||
write_space_to_file(fp, 1);
|
write_space_to_file(fp, 1);
|
||||||
|
|
|
@ -1223,14 +1223,14 @@ void print_verilog_top_testbench_memory_bank_bitstream(std::fstream& fp,
|
||||||
fp << "\t\t" << std::string(TOP_TESTBENCH_PROG_TASK_NAME);
|
fp << "\t\t" << std::string(TOP_TESTBENCH_PROG_TASK_NAME);
|
||||||
fp << "(" << bl_addr_port.get_width() << "'b";
|
fp << "(" << bl_addr_port.get_width() << "'b";
|
||||||
VTR_ASSERT(bl_addr_port.get_width() == fabric_bitstream.bit_bl_address(bit_id).size());
|
VTR_ASSERT(bl_addr_port.get_width() == fabric_bitstream.bit_bl_address(bit_id).size());
|
||||||
for (const size_t& addr_bit : fabric_bitstream.bit_bl_address(bit_id)) {
|
for (const char& addr_bit : fabric_bitstream.bit_bl_address(bit_id)) {
|
||||||
fp << addr_bit;
|
fp << addr_bit;
|
||||||
}
|
}
|
||||||
|
|
||||||
fp << ", ";
|
fp << ", ";
|
||||||
fp << wl_addr_port.get_width() << "'b";
|
fp << wl_addr_port.get_width() << "'b";
|
||||||
VTR_ASSERT(wl_addr_port.get_width() == fabric_bitstream.bit_wl_address(bit_id).size());
|
VTR_ASSERT(wl_addr_port.get_width() == fabric_bitstream.bit_wl_address(bit_id).size());
|
||||||
for (const size_t& addr_bit : fabric_bitstream.bit_wl_address(bit_id)) {
|
for (const char& addr_bit : fabric_bitstream.bit_wl_address(bit_id)) {
|
||||||
fp << addr_bit;
|
fp << addr_bit;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1319,7 +1319,7 @@ void print_verilog_top_testbench_frame_decoder_bitstream(std::fstream& fp,
|
||||||
fp << "\t\t" << std::string(TOP_TESTBENCH_PROG_TASK_NAME);
|
fp << "\t\t" << std::string(TOP_TESTBENCH_PROG_TASK_NAME);
|
||||||
fp << "(" << addr_port.get_width() << "'b";
|
fp << "(" << addr_port.get_width() << "'b";
|
||||||
VTR_ASSERT(addr_port.get_width() == fabric_bitstream.bit_address(bit_id).size());
|
VTR_ASSERT(addr_port.get_width() == fabric_bitstream.bit_address(bit_id).size());
|
||||||
for (const size_t& addr_bit : fabric_bitstream.bit_address(bit_id)) {
|
for (const char& addr_bit : fabric_bitstream.bit_address(bit_id)) {
|
||||||
fp << addr_bit;
|
fp << addr_bit;
|
||||||
}
|
}
|
||||||
fp << ", ";
|
fp << ", ";
|
||||||
|
|
Loading…
Reference in New Issue