String to std_logic_vector

S

Shannon

Guest
I've been searching here but all the hits were for converting SLV to
string for testbenches.

I'm looking to convert a string to an array of 8bit SLVs. The idea is
I have a revision string of fixed length- something like:

ver <= "005-0805300908x2"'

and I have an array of registers declared as such:

SUBTYPE hwid_type is STD_LOGIC_VECTOR(7 DOWNTO 0);
TYPE reg_type IS ARRAY (0 TO NUM_REGS-1) OF hwid_type;
SIGNAL regs : reg_type;

What I'm looking for is a loop shown here in psuedo code:

for i in 1 to 16 loop
regs(i) <= to_slv(ver(mid$(i,1)))
end loop

Note this is for synthesis so I don't know if any of this is even
legal. I am trying to create a version register that the
microprocessor can read. An ascii string is prefered - let's pretend
for a moment it is a requirement. This is also a learning exercise
for me to deal with strings in VHDL.

Any ideas?

Shannon
 
Shannon wrote:

Or something like that?
-- or this:

type char2std_t is array(character) of std_ulogic;

constant char2std_c : char2std_t := (
'U' => 'U',
'X' => 'X',
'0' => '0',
'1' => '1',
'Z' => 'Z',
'W' => 'W',
'L' => 'L',
'H' => 'H',
'-' => '-',
others => 'X');

function str2std(arg : string) return std_logic_vector is
variable result : std_logic_vector(arg'length - 1 downto 0);
variable j : integer;
begin
j := arg'length -1;
for i in arg'range loop
result(j) := char2std_c(arg(i));
j := j -1;
end loop;
return result;
end function;



-- Mike Treseler
 
Shannon wrote:

Mike -- Your answers are always amazing to me. You find super compact
ways of doing clever things. I confess I don't understand your
version this time but as usual, I will synthesize it and look at the
RTL viewer to see how yours does the same thing as mine in a tenth the
number of lines!
Thanks, but it is just a related example
of how to use a constant array for conversions.
It only covers the std_ulogic bits as is.
Your function looks fine for what you are doing.

-- Mike Treseler
 
On May 30, 12:16 pm, Shannon <sgo...@sbcglobal.net> wrote:
I've been searching here but all the hits were for converting SLV to
string for testbenches.

I'm looking to convert a string to an array of 8bit SLVs.  The idea is
I have a revision string of fixed length- something like:

ver <= "005-0805300908x2"'

and I have an array of registers declared as such:

SUBTYPE hwid_type is STD_LOGIC_VECTOR(7 DOWNTO 0);
TYPE reg_type IS ARRAY (0 TO NUM_REGS-1) OF hwid_type;
SIGNAL  regs : reg_type;

What I'm looking for is a loop shown here in psuedo code:

for i in 1 to 16 loop
    regs(i) <= to_slv(ver(mid$(i,1)))
end loop

Note this is for synthesis so I don't know if any of this is even
legal.  I am trying to create a version register that the
microprocessor can read.  An ascii string is prefered - let's pretend
for a moment it is a requirement.  This is also a learning exercise
for me to deal with strings in VHDL.

Any ideas?

Shannon
Since your input string has some non-numeric characters in it that you
presumably want to keep in the string, then the best approach would be
to simply write a function that parses the string however you'd like.

Below is an example that simply adds the 'value' of each input
character to produce an integer output. You should be able to easily
modify this to select out whichever characters you want and perform
whatever calculations you'd like.

function Version_String_To_integer(Some_String: STRING) return integer
is
variable Return_Value: integer := 0;
begin
for i in Some_String'range loop
Some_Char := Some_String(i)
case Some_Char is
when "0" => Return_Value := Return_Value + 0;
when "1" => Return_Value := Return_Value + 1;
...
when others => null;
end case;
end loop;
return(Return_Value);
end function Version_String_To_integer;

KJ
 
On May 30, 9:47 am, KJ <kkjenni...@sbcglobal.net> wrote:
On May 30, 12:16 pm, Shannon <sgo...@sbcglobal.net> wrote:





I've been searching here but all the hits were for converting SLV to
string for testbenches.

I'm looking to convert a string to an array of 8bit SLVs.  The idea is
I have a revision string of fixed length- something like:

ver <= "005-0805300908x2"'

and I have an array of registers declared as such:

SUBTYPE hwid_type is STD_LOGIC_VECTOR(7 DOWNTO 0);
TYPE reg_type IS ARRAY (0 TO NUM_REGS-1) OF hwid_type;
SIGNAL  regs : reg_type;

What I'm looking for is a loop shown here in psuedo code:

for i in 1 to 16 loop
    regs(i) <= to_slv(ver(mid$(i,1)))
end loop

Note this is for synthesis so I don't know if any of this is even
legal.  I am trying to create a version register that the
microprocessor can read.  An ascii string is prefered - let's pretend
for a moment it is a requirement.  This is also a learning exercise
for me to deal with strings in VHDL.

Any ideas?

Shannon

Since your input string has some non-numeric characters in it that you
presumably want to keep in the string, then the best approach would be
to simply write a function that parses the string however you'd like.

Below is an example that simply adds the 'value' of each input
character to produce an integer output.  You should be able to easily
modify this to select out whichever characters you want and perform
whatever calculations you'd like.

function Version_String_To_integer(Some_String: STRING) return integer
is
variable Return_Value: integer := 0;
begin
for i in Some_String'range loop
  Some_Char := Some_String(i)
  case Some_Char is
     when "0" => Return_Value := Return_Value + 0;
     when "1" => Return_Value := Return_Value + 1;
     ...
     when others => null;
  end case;
end loop;
return(Return_Value);
end function Version_String_To_integer;

KJ- Hide quoted text -

- Show quoted text -
As I suspected. So to flesh things out a bit....

function Version_Char_To_slv(Some_Char: character) return slv
is
variable Return_Value: slv(7 downto 0) := (others => 0);
begin
case Some_Char is
when "0" => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(0,8);
when "1" => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(1,8);
...
when "a" => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(97,8);
...
when "-" => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(45,8);
...
when others => null;
end case;
return(Return_Value);
end function Version_Char_To_slv;

and then back in my main process....

for i in 1 upto 16 loop
regs(i) <= Version_Char_To_slv(ver(i));
end loop;


Or something like that?
 
On May 30, 1:03 pm, Shannon <sgo...@sbcglobal.net> wrote:
On May 30, 9:47 am, KJ <kkjenni...@sbcglobal.net> wrote:


Or something like that?
Except that each character only returns a nibble not a byte.

KJ
 
On May 30, 10:31 am, KJ <kkjenni...@sbcglobal.net> wrote:
On May 30, 1:03 pm, Shannon <sgo...@sbcglobal.net> wrote:

On May 30, 9:47 am, KJ <kkjenni...@sbcglobal.net> wrote:

Or something like that?

Except that each character only returns a nibble not a byte.

KJ
My finished version:

FUNCTION char_to_slv (c : CHARACTER) RETURN STD_LOGIC_VECTOR IS
variable Return_Value : STD_LOGIC_VECTOR(7 downto 0);
BEGIN
case c is
when '0' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(0,8));
when '1' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(1,8));
when '2' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(2,8));
when '3' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(3,8));
when '4' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(4,8));
when '5' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(5,8));
when '6' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(6,8));
when '7' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(7,8));
when '8' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(8,8));
when '9' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(9,8));
when '-' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(45,8));
when others => Return_Value := (OTHERS => '1');
end case;

Later I will add the lowercase letters but this gets me through the
day. Thanks for you help everyone.

Mike -- Your answers are always amazing to me. You find super compact
ways of doing clever things. I confess I don't understand your
version this time but as usual, I will synthesize it and look at the
RTL viewer to see how yours does the same thing as mine in a tenth the
number of lines!

Shannon
return(Return_Value);

END char_to_slv;
 
Little mistake there. For clarity those should have been ascii
values:

FUNCTION char_to_slv (c : CHARACTER) RETURN STD_LOGIC_VECTOR IS
variable Return_Value : STD_LOGIC_VECTOR(7 downto 0);
BEGIN
case c is
when '0' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(48,8));
when '1' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(49,8));
when '2' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(50,8));
when '3' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(51,8));
when '4' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(52,8));
when '5' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(53,8));
when '6' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(54,8));
when '7' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(55,8));
when '8' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(56,8));
when '9' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(57,8));
when '-' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(45,8));
when others => Return_Value := (OTHERS => '1');
end case;
return(Return_Value);
END char_to_slv;

And it's working in hardware! yeah! Now...to figure out how to write
a TCL script or something to push my revision number into a constant
in my package. The fun never ends!

Shannon
 
On May 30, 2:06 pm, "KJ" <kkjenni...@sbcglobal.net> wrote:
"Shannon" <sgo...@sbcglobal.net> wrote in message

news:1e2083c0-63f4-4cf8-b41d-25e7c1f60212@x1g2000prh.googlegroups.com...





Little mistake there.  For clarity those should have been ascii
values:

FUNCTION char_to_slv (c : CHARACTER) RETURN STD_LOGIC_VECTOR IS
   variable Return_Value : STD_LOGIC_VECTOR(7 downto 0);
BEGIN
   case c is
when '0' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(48,8));
when '1' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(49,8));
when '2' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(50,8));
when '3' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(51,8));
when '4' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(52,8));
when '5' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(53,8));
when '6' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(54,8));
when '7' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(55,8));
when '8' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(56,8));
when '9' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(57,8));
when '-' => Return_Value := STD_LOGIC_VECTOR(TO_UNSIGNED(45,8));
when others => Return_Value := (OTHERS => '1');
   end case;
   return(Return_Value);
END char_to_slv;

And it's working in hardware!  yeah!  Now...to figure out how to write
a TCL script or something to push my revision number into a constant
in my package.  The fun never ends!

Shannon

Well if all you wanted was the ASCII value of the charcters in the string
(as it appears from your code that you do) then it's even simpler

for i in 1 to 16 loop
    Some_Slv_String(i) <> std_logic_vector(to_unsigned(character'pos(Some_String(i)),
8));
end loop;

KJ- Hide quoted text -

- Show quoted text -
Gee That's a bit more simple. Sigh.
 

Welcome to EDABoard.com

Sponsor

Back
Top