1

In ModelSim, the following code works just fine:

string r;
string s;
// ...assign some string to s...
integer i;
r = "";
for (i=s.len()-1; i>=0; i=i-1) begin
    if (s[i] != "\n") begin
        r = {s[i], r};
    end
end

In Aldec Riviera, this causes a compilation error Incompatible types at assignment: .r<string> <- s[i]<byte>.

Reading the SystemVerilog LRM, I can see that the curly braces seem to be only supported to concatenate strings, not bytes. So either ModelSim is not as strict with the LRM or it implicitly converts the s[i] byte to a one-character string (which seems sensible in this context). In Riviera, it looks like I have to convert the byte s[i] to a one-character string manually. What is the most efficient and concise solution (if possible without having to introduce a temporary variable)?

2
  • I would expect s[i] to be treated as a string of length 1, not a byte. It seems to me that Riviera may not be doing the right thing. Do you have an LRM reference related to this? Also, curly braces can certainly be used to concatenate bits/logic/bytes - this is a hold over from Verilog and may not be explicit in the SystemVerilog LRM. Commented Nov 5, 2012 at 21:00
  • @dwikle, the SystemVerilog 3.1a LRM, under Table 3-2: String Operators on page 13 is what I was looking at. To me, this sounds like all operands have to be either a string or a string literal. Of course, concatenation of bits, logic and bytes using {} is ok too, but the result wouldn't be a string then. Commented Nov 5, 2012 at 23:27

4 Answers 4

3

You're right, ModelSim is accepting invalid code. The spec explicitly defines the types involved with indexing and assignments.

A single character of a string variable is of type byte.

...

Values of integral type can be assigned to a string variable, but require a cast.

The spec further details the result of the concatenation operator based on the operands:

Each operand can be a string literal or an expression of string type.

Using the cast:

string r;
string s;
// ...assign some string to s...
integer i;
r = "";
for (i=s.len()-1; i>=0; i=i-1) begin
    if (s[i] != "\n") begin
        r = {string'(s[i]), r};
    end
end
Sign up to request clarification or add additional context in comments.

Comments

1

I'm not sure about the following code is 100% OK in the simulator Aldec Riviera, because I try both yours and mine are ok in VCS. If you need to return string type of s, you may try the string method substr().

for (i=s.len()-1; i>=0; i=i-1) begin
    if (s[i] != "\n") begin
        r = {s.substr(i,i), r};
    end
end

Comments

0

Use atobin()/bintoa() functions for conversion between ASCII and Binary. Then you can use concatenation operator "{}" with either string/binary values.

1 Comment

Thanks for mentioning another option. Could you provide a code sample (maybe building on the code I gave in the question) by editing your answer?
0

Here a small example of code:

First, an example to create a byte dynamic array from a string. The dynamic array of bytes contains the ASCII CODE number representation of each character. The advantage is that this can be for example be randomized but strings cannot be randomized.

(created doing e.g.

for(i=0;i<stringvar.len(); i++) begin 
byte_din_array = {byte_din_array ,stringvar[i]}; //stringvar[i] will return empty byte if  the index would be beyond the string length
//The advantage of using stringvar[i] instead of stringvar.atoi(i) is that 
//the string can have all ASCII characters and not just numbers.
//Disadvantage is that the byte contains the ASCII CODE "number" 
//representation of the character and that is not human readable
end

).

Here is the example to convert the dynamic array of bytes back in a concatenated string. You may have used the previous dynamic array to be partly randomized (with constraints) inside an xfer or changed in post_randomize.

function string convert_byte_array2string(byte stringdescriptionholder[]);
    automatic string temp_str="";
    automatic byte byte_temp;
    automatic string str_test;
    for ( int unsigned i = 0; i<stringdescriptionholder.size(); i++)  begin
        i=i;//debug breakpoint
        byte_temp = stringdescriptionholder[i];
        str_test = string'(byte_temp); //the "string cast" will convert the numeric ASCII representation in a string character
        temp_str = {temp_str,str_test};
    end
    return temp_str;
endfunction

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.