rtlil: add Const:: as_int_compressed function

This commit is contained in:
Philippe Sauter 2024-09-23 13:57:07 +02:00 committed by Emil J. Tywoniak
parent 07fb8af05b
commit c53c87e1f4
2 changed files with 29 additions and 3 deletions

View File

@ -28,6 +28,7 @@
#include <string.h>
#include <algorithm>
#include <optional>
YOSYS_NAMESPACE_BEGIN
@ -280,9 +281,9 @@ int RTLIL::Const::as_int(bool is_signed) const
return ret;
}
void RTLIL::Const::compress(bool is_signed)
size_t RTLIL::Const::get_min_size(bool is_signed) const
{
if (bits.empty()) return;
if (bits.empty()) return 0;
// back to front (MSB to LSB)
RTLIL::State leading_bit;
@ -301,11 +302,31 @@ void RTLIL::Const::compress(bool is_signed)
idx++;
}
// must be at least one bit
idx = (idx == 0) ? 1 : idx;
return (idx == 0) ? 1 : idx;
}
void RTLIL::Const::compress(bool is_signed)
{
size_t idx = get_min_size(is_signed);
bits.erase(bits.begin() + idx, bits.end());
}
std::optional<int> RTLIL::Const::as_int_compress(bool is_signed) const
{
size_t size = get_min_size(is_signed);
if(size == 0 || size > 32)
return std::nullopt;
int32_t ret = 0;
for (size_t i = 0; i < size && i < 32; i++)
if (bits[i] == State::S1)
ret |= 1 << i;
if (is_signed && bits[size-1] == State::S1)
for (size_t i = size; i < 32; i++)
ret |= 1 << i;
return ret;
}
std::string RTLIL::Const::as_string() const
{
std::string ret;

View File

@ -703,9 +703,14 @@ struct RTLIL::Const
return ret;
}
// find the MSB without redundant leading bits
size_t get_min_size(bool is_signed) const;
// compress representation to the minimum required bits
void compress(bool is_signed = false);
std::optional<int> as_int_compress(bool is_signed) const;
void extu(int width) {
bits.resize(width, RTLIL::State::S0);
}