在 systemverilog 中使用 random 的随机 1 位和 2 位错误
Random 1-bit and 2-bit error using random in systemverilog
我正在使用错误检测块。我需要使用 SystemVerilig 随机翻转 1 位数据。我该怎么做呢?我也想在翻转 2 个随机数据位的地方做同样的事情。
正在使用海明码。因此需要翻转奇偶校验和数据中的随机位。
最直接的方法是使用 $urandom_range(0, msb)
到 select 您想要破坏的位。一个例子:
module test();
parameter DATA_WIDTH = 29;
parameter IDX_WIDTH = $clog2(DATA_WIDTH);
logic [DATA_WIDTH-1:0] data;
logic [IDX_WIDTH-1:0] idx_to_flip;
initial begin
data = $urandom();
$display("Original data = %x", data);
idx_to_flip = $urandom_range(0, DATA_WIDTH-1);
$display("Flipping data bit idx %d", idx_to_flip);
data[idx_to_flip] = !data[idx_to_flip];
$display("Corrupted data = %x", data);
end
endmodule
这对于一个位来说非常简单。如果你想破坏 2 位,你将需要更多的复杂性来确保第二位索引 selected 与第一个 selected 不同。有两种选择:
1) 循环调用第二个 $urandom_range() 直到它产生一个不同于第一个随机数的值。
2) 使用两个 'rand' 字段创建一个 class,并使用约束来确保值不相同:
class Corruption;
rand bit [IDX_WIDTH-1:0] corrupt_idx1;
rand bit [IDX_WIDTH-1:0] corrupt_idx2;
endclass
Corruption corr = new;
initial begin
corr.randomize() with {corrupt_idx1 != corrupt_idx2;};
$display("Bit indices to flip: %d and %d", corr.corrupt_idx1, corr.corrupt_idx2);
end
您可以声明一个位宽与您的“data”大小相同的变量。
假设您的“数据”大小为 8 位(例如 data_8b),您可以声明一个大小为 8 位的临时变量(例如 error_inject_8b),您可以使用简单的 EXOR 逻辑来插入多位错误。参考下面的片段
error_inject_8b[0] = 1;
error_inject_8b[1] = 1;
data_8b = data_8b ^ error_inject_8b; //injects error in 0th and 1st bits of data
error_inject_8b = 0;//Reset the errors
error_inject_8b = $random;
data_8b = data_8b ^ error_inject_8b;//Injects error in randomly selected bits
您还可以编写 constraints 或 randomize with 概念以根据您的要求随机化错误注入。
我正在使用错误检测块。我需要使用 SystemVerilig 随机翻转 1 位数据。我该怎么做呢?我也想在翻转 2 个随机数据位的地方做同样的事情。
正在使用海明码。因此需要翻转奇偶校验和数据中的随机位。
最直接的方法是使用 $urandom_range(0, msb)
到 select 您想要破坏的位。一个例子:
module test();
parameter DATA_WIDTH = 29;
parameter IDX_WIDTH = $clog2(DATA_WIDTH);
logic [DATA_WIDTH-1:0] data;
logic [IDX_WIDTH-1:0] idx_to_flip;
initial begin
data = $urandom();
$display("Original data = %x", data);
idx_to_flip = $urandom_range(0, DATA_WIDTH-1);
$display("Flipping data bit idx %d", idx_to_flip);
data[idx_to_flip] = !data[idx_to_flip];
$display("Corrupted data = %x", data);
end
endmodule
这对于一个位来说非常简单。如果你想破坏 2 位,你将需要更多的复杂性来确保第二位索引 selected 与第一个 selected 不同。有两种选择:
1) 循环调用第二个 $urandom_range() 直到它产生一个不同于第一个随机数的值。
2) 使用两个 'rand' 字段创建一个 class,并使用约束来确保值不相同:
class Corruption;
rand bit [IDX_WIDTH-1:0] corrupt_idx1;
rand bit [IDX_WIDTH-1:0] corrupt_idx2;
endclass
Corruption corr = new;
initial begin
corr.randomize() with {corrupt_idx1 != corrupt_idx2;};
$display("Bit indices to flip: %d and %d", corr.corrupt_idx1, corr.corrupt_idx2);
end
您可以声明一个位宽与您的“data”大小相同的变量。 假设您的“数据”大小为 8 位(例如 data_8b),您可以声明一个大小为 8 位的临时变量(例如 error_inject_8b),您可以使用简单的 EXOR 逻辑来插入多位错误。参考下面的片段
error_inject_8b[0] = 1;
error_inject_8b[1] = 1;
data_8b = data_8b ^ error_inject_8b; //injects error in 0th and 1st bits of data
error_inject_8b = 0;//Reset the errors
error_inject_8b = $random;
data_8b = data_8b ^ error_inject_8b;//Injects error in randomly selected bits
您还可以编写 constraints 或 randomize with 概念以根据您的要求随机化错误注入。