NBA assignment of $random

Can $random be NBA assigned in a for loop to an unpacked array of variables?

int tmp [2] [8];
always @ (posedge clk) begin
foreach (tmp[0][i]) begin
tmp[0][i] <= $urandom();
end
end

Using Cadence tools (with a bit more code involved), I get all 8 of tmp[0] ints assigned the same value.

Can someone confirm whether this code is legal?

I have spoken to Cadence and been told this:
R&D’s response.

This use model of having $urandom call inside a non-blocking assignment is wrong.
The scheduling semantics of System Verilog dictates that the RHS is calculated and sampled once in the “inactive region” and then in the “NBA region” it’s assigned the ALL of the elements of the foreach at the same time!

Thanks,
Nachum

In reply to nachumk:

There is no difference in calling $urandom in a procedural loop versus serially calling $urandom multiple times. Your code gives the desired results in several tools, including Cadence’s on EDAPlayground.com. Perhaps you are not showing is part of your problem. It always helps to show an MCVE, like

module top;
  int tmp [2] [8];
  bit clk;

  initial begin
    #1 clk=1;

    #1 $display("%p",
                tmp[0]);
  end

always @ (posedge clk) begin
    foreach (tmp[,i]) begin
        tmp[0][i] <= $urandom();
    end
end

endmodule

In reply to dave_59:

So it is legal to assign NBA $urandom? That is the crux of Cadence’s response to me, that it is wrong to do.

This use model of having $urandom call inside a non-blocking assignment is wrong.
The scheduling semantics of System Verilog dictates that the RHS is calculated and sampled once in the “inactive region” and then in the “NBA region” it’s assigned the ALL of the elements of the foreach at the same time!

In reply to nachumk:

The RHS of a procedural assignment evaluates in the active region, regardless of whether it is blocking or non-blocking. A foreach-loop is just an easier way of writing a for-loop. There is nothing special or different regarding the statements inside the loop.