parent
cbf8d97a76
commit
b3a1a15e2b
|
|
@ -2713,6 +2713,26 @@ bool vl_check_format(const VerilatedVpioVarBase* vop, const p_vpi_value valuep,
|
|||
return status;
|
||||
}
|
||||
|
||||
// Get a VPI format that can be used to fully represent a signal of the given type
|
||||
PLI_INT32 vl_get_vltype_format(VerilatedVarType vlType) {
|
||||
switch (vlType) {
|
||||
case VLVT_UINT8:
|
||||
case VLVT_UINT16:
|
||||
case VLVT_UINT32:
|
||||
case VLVT_UINT64:
|
||||
case VLVT_WDATA: return vpiVectorVal;
|
||||
case VLVT_STRING:
|
||||
return vpiStringVal; // LCOV_EXCL_LINE - vl_get_vltype_format is only used in
|
||||
// vpi_put_value for releasing a forceable signal, and string signals
|
||||
// cannot be forced
|
||||
case VLVT_REAL: return vpiRealVal;
|
||||
default: // LCOV_EXCL_START - Cannot test, because vpi_put_value would already exit due to
|
||||
// failed vl_check_format before calling this
|
||||
VL_VPI_ERROR_(__FILE__, __LINE__, "%s: Unsupported vltype (%d)", __func__, vlType);
|
||||
return vpiUndefined;
|
||||
} // LCOV_EXCL_STOP
|
||||
}
|
||||
|
||||
static void vl_strprintf(std::string& buffer, char const* fmt, ...) {
|
||||
va_list args, args_copy;
|
||||
va_start(args, fmt);
|
||||
|
|
@ -3179,6 +3199,18 @@ vpiHandle vpi_put_value(vpiHandle object, p_vpi_value valuep, p_vpi_time /*time_
|
|||
if (baseSignalVop->varp()->isContinuously())
|
||||
VerilatedVpiImp::setAllBitsToValue(forceEnableSignalVop, 0);
|
||||
|
||||
// For writing back the forced value to a non-continuously assigned base signal in the
|
||||
// release case, need to get the forced signal's raw data, since valuep could have
|
||||
// a format that modifies the data (e.g. vpiStringVal which pads with spaces)
|
||||
const s_vpi_value forcedValue
|
||||
= baseSignalVop->varp()->isContinuously() ? s_vpi_value{} : [&baseSignalVop]() {
|
||||
s_vpi_value val{.format
|
||||
= vl_get_vltype_format(baseSignalVop->varp()->vltype()),
|
||||
.value{}};
|
||||
vl_vpi_get_value(baseSignalVop, &val);
|
||||
return val;
|
||||
}();
|
||||
|
||||
vl_vpi_get_value(baseSignalVop, valuep);
|
||||
|
||||
t_vpi_error_info baseValueGetError{};
|
||||
|
|
@ -3202,9 +3234,15 @@ vpiHandle vpi_put_value(vpiHandle object, p_vpi_value valuep, p_vpi_time /*time_
|
|||
VL_VPI_ERROR_RESET_();
|
||||
} // LCOV_EXCL_STOP
|
||||
|
||||
if (!baseSignalVop->varp()->isContinuously())
|
||||
if (!baseSignalVop->varp()->isContinuously()) {
|
||||
VerilatedVpiImp::setAllBitsToValue(forceEnableSignalVop, 0);
|
||||
|
||||
// If the signal is not continuously assigned, it should keep the forced value
|
||||
// until the next time it is assigned in the simulation, so the forced value is
|
||||
// written to the base signal
|
||||
vpi_put_value(object, const_cast<p_vpi_value>(&forcedValue), nullptr, vpiNoDelay);
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -360,6 +360,32 @@ extern "C" int checkValuesForced(void) {
|
|||
return 0;
|
||||
}
|
||||
|
||||
extern "C" int checkNonContinuousValuesForced(void) {
|
||||
// Non-continuously assigned (e.g. clocked) signals retain the forced value after releasing
|
||||
// until the they are updated again, so check that they are still at the forced value
|
||||
CHECK_RESULT_Z( // NOLINT(concurrency-mt-unsafe)
|
||||
std::any_of(TestSignals.begin(), TestSignals.end(), [](const TestSignal& signal) {
|
||||
CHECK_RESULT_Z( // NOLINT(concurrency-mt-unsafe)
|
||||
checkValue(scopeName, signal.signalName, signal.valueType, signal.forceValue));
|
||||
return 0;
|
||||
}));
|
||||
return 0;
|
||||
}
|
||||
|
||||
extern "C" int checkContinuousValuesReleased(void) {
|
||||
// Continuously assigned signals return to their original value immediately after releasing
|
||||
CHECK_RESULT_Z( // NOLINT(concurrency-mt-unsafe)
|
||||
std::any_of(TestSignals.begin(), TestSignals.end(), [](const TestSignal& signal) {
|
||||
const std::string continouslyAssignedSignal
|
||||
= std::string{signal.signalName} + "Continuously";
|
||||
CHECK_RESULT_Z( // NOLINT(concurrency-mt-unsafe)
|
||||
checkValue(scopeName, continouslyAssignedSignal, signal.valueType,
|
||||
signal.releaseValue));
|
||||
return 0;
|
||||
}));
|
||||
return 0;
|
||||
}
|
||||
|
||||
extern "C" int checkValuesPartiallyForced(void) {
|
||||
// Clocked signals
|
||||
CHECK_RESULT_Z( // NOLINT(concurrency-mt-unsafe)
|
||||
|
|
@ -383,6 +409,21 @@ extern "C" int checkValuesPartiallyForced(void) {
|
|||
return 0;
|
||||
}
|
||||
|
||||
extern "C" int checkNonContinuousValuesPartiallyForced(void) {
|
||||
// Non-continuously assigned (e.g. clocked) signals retain the partially forced value after
|
||||
// releasing until the they are updated again, so check that they are still at the partially
|
||||
// forced value
|
||||
CHECK_RESULT_Z( // NOLINT(concurrency-mt-unsafe)
|
||||
std::any_of(TestSignals.begin(), TestSignals.end(), [](const TestSignal& signal) {
|
||||
if (signal.partialForceValue.second)
|
||||
CHECK_RESULT_Z( // NOLINT(concurrency-mt-unsafe)
|
||||
checkValue(scopeName, signal.signalName, signal.valueType,
|
||||
signal.partialForceValue.first));
|
||||
return 0;
|
||||
}));
|
||||
return 0;
|
||||
}
|
||||
|
||||
extern "C" int checkValuesReleased(void) {
|
||||
// Clocked signals
|
||||
CHECK_RESULT_Z( // NOLINT(concurrency-mt-unsafe)
|
||||
|
|
@ -631,6 +672,28 @@ static int checkValuesForcedVpi() {
|
|||
return 0;
|
||||
}
|
||||
|
||||
static int checkNonContinuousValuesForcedVpi() {
|
||||
TestVpiHandle href = vpi_handle(vpiSysTfCall, 0);
|
||||
s_vpi_value vpi_value;
|
||||
|
||||
vpi_value.format = vpiIntVal;
|
||||
vpi_value.value.integer = checkNonContinuousValuesForced();
|
||||
vpi_put_value(href, &vpi_value, NULL, vpiNoDelay);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int checkContinuousValuesReleasedVpi() {
|
||||
TestVpiHandle href = vpi_handle(vpiSysTfCall, 0);
|
||||
s_vpi_value vpi_value;
|
||||
|
||||
vpi_value.format = vpiIntVal;
|
||||
vpi_value.value.integer = checkContinuousValuesReleased();
|
||||
vpi_put_value(href, &vpi_value, NULL, vpiNoDelay);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int checkValuesPartiallyForcedVpi() {
|
||||
TestVpiHandle href = vpi_handle(vpiSysTfCall, 0);
|
||||
s_vpi_value vpi_value;
|
||||
|
|
@ -642,6 +705,17 @@ static int checkValuesPartiallyForcedVpi() {
|
|||
return 0;
|
||||
}
|
||||
|
||||
static int checkNonContinuousValuesPartiallyForcedVpi() {
|
||||
TestVpiHandle href = vpi_handle(vpiSysTfCall, 0);
|
||||
s_vpi_value vpi_value;
|
||||
|
||||
vpi_value.format = vpiIntVal;
|
||||
vpi_value.value.integer = checkNonContinuousValuesPartiallyForced();
|
||||
vpi_put_value(href, &vpi_value, NULL, vpiNoDelay);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int checkValuesReleasedVpi() {
|
||||
TestVpiHandle href = vpi_handle(vpiSysTfCall, 0);
|
||||
s_vpi_value vpi_value;
|
||||
|
|
@ -686,7 +760,7 @@ static int releasePartiallyForcedValuesVpi() {
|
|||
return 0;
|
||||
}
|
||||
|
||||
std::array<s_vpi_systf_data, 6> vpi_systf_data
|
||||
std::array<s_vpi_systf_data, 9> vpi_systf_data
|
||||
= {s_vpi_systf_data{vpiSysFunc, vpiIntFunc, (PLI_BYTE8*)"$forceValues",
|
||||
(PLI_INT32(*)(PLI_BYTE8*))forceValuesVpi, 0, 0, 0},
|
||||
s_vpi_systf_data{vpiSysFunc, vpiIntFunc, (PLI_BYTE8*)"$releaseValues",
|
||||
|
|
@ -695,8 +769,15 @@ std::array<s_vpi_systf_data, 6> vpi_systf_data
|
|||
(PLI_INT32(*)(PLI_BYTE8*))releasePartiallyForcedValuesVpi, 0, 0, 0},
|
||||
s_vpi_systf_data{vpiSysFunc, vpiIntFunc, (PLI_BYTE8*)"$checkValuesForced",
|
||||
(PLI_INT32(*)(PLI_BYTE8*))checkValuesForcedVpi, 0, 0, 0},
|
||||
s_vpi_systf_data{vpiSysFunc, vpiIntFunc, (PLI_BYTE8*)"$checkNonContinuousValuesForced",
|
||||
(PLI_INT32(*)(PLI_BYTE8*))checkNonContinuousValuesForcedVpi, 0, 0, 0},
|
||||
s_vpi_systf_data{vpiSysFunc, vpiIntFunc, (PLI_BYTE8*)"$checkContinuousValuesReleased",
|
||||
(PLI_INT32(*)(PLI_BYTE8*))checkContinuousValuesReleasedVpi, 0, 0, 0},
|
||||
s_vpi_systf_data{vpiSysFunc, vpiIntFunc, (PLI_BYTE8*)"$checkValuesPartiallyForced",
|
||||
(PLI_INT32(*)(PLI_BYTE8*))checkValuesPartiallyForcedVpi, 0, 0, 0},
|
||||
s_vpi_systf_data{
|
||||
vpiSysFunc, vpiIntFunc, (PLI_BYTE8*)"$checkNonContinuousValuesPartiallyForced",
|
||||
(PLI_INT32(*)(PLI_BYTE8*))checkNonContinuousValuesPartiallyForcedVpi, 0, 0, 0},
|
||||
s_vpi_systf_data{vpiSysFunc, vpiIntFunc, (PLI_BYTE8*)"$checkValuesReleased",
|
||||
(PLI_INT32(*)(PLI_BYTE8*))checkValuesReleasedVpi, 0, 0, 0}};
|
||||
|
||||
|
|
|
|||
|
|
@ -4,6 +4,13 @@
|
|||
// SPDX-License-Identifier: CC0-1.0
|
||||
// ======================================================================
|
||||
|
||||
// verilog_format: off
|
||||
`define stop $stop
|
||||
`define checkh(gotv,expv) do if ((gotv) !== (expv)) begin $write("%%Error: %s:%0d: got='h%x exp='h%x\n", `__FILE__,`__LINE__, (gotv), (expv)); `stop; end while(0);
|
||||
`define checks(gotv,expv) do if ((gotv) != (expv)) begin $write("%%Error: %s:%0d: got='%s' exp='%s'\n", `__FILE__,`__LINE__, (gotv), (expv)); `stop; end while(0);
|
||||
`define checkr(gotv,expv) do if ((gotv) != (expv)) begin $write("%%Error: %s:%0d: got=%f exp=%f\n", `__FILE__,`__LINE__, (gotv), (expv)); `stop; end while(0);
|
||||
|
||||
// verilog_format: on
|
||||
`define STRINGIFY(x) `"x`"
|
||||
|
||||
`ifdef VERILATOR_COMMENTS
|
||||
|
|
@ -18,7 +25,7 @@ module t;
|
|||
|
||||
initial begin
|
||||
clk = 0;
|
||||
forever #1 clk = ~clk;
|
||||
forever #2 clk = ~clk;
|
||||
end
|
||||
|
||||
Test test (.clk(clk));
|
||||
|
|
@ -44,6 +51,9 @@ module Test (
|
|||
extern "C" int checkValuesForced();
|
||||
extern "C" int checkValuesPartiallyForced();
|
||||
extern "C" int checkValuesReleased();
|
||||
extern "C" int checkNonContinuousValuesForced();
|
||||
extern "C" int checkContinuousValuesReleased();
|
||||
extern "C" int checkNonContinuousValuesPartiallyForced();
|
||||
`verilog
|
||||
`endif
|
||||
`else
|
||||
|
|
@ -59,6 +69,9 @@ module Test (
|
|||
import "DPI-C" context function int checkValuesPartiallyForced();
|
||||
import "DPI-C" context function int checkValuesForced();
|
||||
import "DPI-C" context function int checkValuesReleased();
|
||||
import "DPI-C" context function int checkNonContinuousValuesForced();
|
||||
import "DPI-C" context function int checkContinuousValuesReleased();
|
||||
import "DPI-C" context function int checkNonContinuousValuesPartiallyForced();
|
||||
`endif
|
||||
|
||||
// Verify that vpi_put_value still works for strings
|
||||
|
|
@ -451,39 +464,39 @@ module Test (
|
|||
endtask
|
||||
|
||||
task automatic svCheckValuesForced();
|
||||
if(onebit != 0) $stop;
|
||||
if(intval != 32'h55555555) $stop;
|
||||
if(vectorC != 8'h55) $stop;
|
||||
if(vectorQ != 62'h15555555_55555555) $stop;
|
||||
if(vectorW != 128'h55555555_55555555_55555555_55555555) $stop;
|
||||
if(real1 != 123456.789) $stop;
|
||||
if(textHalf != "T2") $stop;
|
||||
if(textLong != "44Four44") $stop;
|
||||
if(text != "lorem ipsum") $stop;
|
||||
if(binString != 8'b01010101) $stop;
|
||||
if(octString != 15'o52525) $stop;
|
||||
if(hexString != 64'h5555555555555555) $stop;
|
||||
if(decStringC != 8'h55) $stop;
|
||||
if(decStringS != 16'h5555) $stop;
|
||||
if(decStringI != 32'h55555555) $stop;
|
||||
if(decStringQ != 64'd6148914691236517205) $stop;
|
||||
`checkh(onebit, 0);
|
||||
`checkh(intval, 32'h55555555);
|
||||
`checkh(vectorC, 8'h55);
|
||||
`checkh(vectorQ, 62'h15555555_55555555);
|
||||
`checkh(vectorW, 128'h55555555_55555555_55555555_55555555);
|
||||
`checkr(real1, 123456.789);
|
||||
`checks(textHalf, "T2");
|
||||
`checks(textLong, "44Four44");
|
||||
`checks(text, "lorem ipsum");
|
||||
`checkh(binString, 8'b01010101);
|
||||
`checkh(octString, 15'o52525);
|
||||
`checkh(hexString, 64'h5555555555555555);
|
||||
`checkh(decStringC, 8'h55);
|
||||
`checkh(decStringS, 16'h5555);
|
||||
`checkh(decStringI, 32'h55555555);
|
||||
`checkh(decStringQ, 64'd6148914691236517205);
|
||||
|
||||
if(onebitContinuously != 0) $stop;
|
||||
if(intvalContinuously != 32'h55555555) $stop;
|
||||
if(vectorCContinuously != 8'h55) $stop;
|
||||
if(vectorQContinuously != 62'h15555555_55555555) $stop;
|
||||
if(vectorWContinuously != 128'h55555555_55555555_55555555_55555555) $stop;
|
||||
if(real1Continuously != 123456.789) $stop;
|
||||
if(textHalfContinuously != "T2") $stop;
|
||||
if(textLongContinuously != "44Four44") $stop;
|
||||
if(textContinuously != "lorem ipsum") $stop;
|
||||
if(binStringContinuously != 8'b01010101) $stop;
|
||||
if(octStringContinuously != 15'o52525) $stop;
|
||||
if(hexStringContinuously != 64'h5555555555555555) $stop;
|
||||
if(decStringCContinuously != 8'h55) $stop;
|
||||
if(decStringSContinuously != 16'h5555) $stop;
|
||||
if(decStringIContinuously != 32'h55555555) $stop;
|
||||
if(decStringQContinuously != 64'd6148914691236517205) $stop;
|
||||
`checkh(onebitContinuously, 0);
|
||||
`checkh(intvalContinuously, 32'h55555555);
|
||||
`checkh(vectorCContinuously, 8'h55);
|
||||
`checkh(vectorQContinuously, 62'h15555555_55555555);
|
||||
`checkh(vectorWContinuously, 128'h55555555_55555555_55555555_55555555);
|
||||
`checkr(real1Continuously, 123456.789);
|
||||
`checks(textHalfContinuously, "T2");
|
||||
`checks(textLongContinuously, "44Four44");
|
||||
`checks(textContinuously, "lorem ipsum");
|
||||
`checkh(binStringContinuously, 8'b01010101);
|
||||
`checkh(octStringContinuously, 15'o52525);
|
||||
`checkh(hexStringContinuously, 64'h5555555555555555);
|
||||
`checkh(decStringCContinuously, 8'h55);
|
||||
`checkh(decStringSContinuously, 16'h5555);
|
||||
`checkh(decStringIContinuously, 32'h55555555);
|
||||
`checkh(decStringQContinuously, 64'd6148914691236517205);
|
||||
endtask
|
||||
|
||||
task automatic vpiCheckValuesForced();
|
||||
|
|
@ -509,36 +522,121 @@ module Test (
|
|||
end
|
||||
endtask
|
||||
|
||||
task automatic svCheckValuesPartiallyForced();
|
||||
if (intval != 32'hAAAA_5555) $stop;
|
||||
if (vectorC != 8'h A5) $stop;
|
||||
if (vectorQ != 62'h2AAAAAAAD5555555) $stop;
|
||||
if (vectorW != 128'hAAAAAAAA_AAAAAAAA_55555555_55555555) $stop;
|
||||
if (textHalf != "H2") $stop;
|
||||
if (textLong != "Lonur44") $stop;
|
||||
if (text != "Verilog Tesem ipsum") $stop;
|
||||
if (binString != 8'b1010_0101) $stop;
|
||||
if (octString != 15'b01010101_1010101) $stop;
|
||||
if (hexString != 64'hAAAAAAAA_55555555) $stop;
|
||||
if (decStringC != 8'hA5) $stop;
|
||||
if (decStringS != 16'hAA55) $stop;
|
||||
if (decStringI != 32'hAAAA_5555) $stop;
|
||||
if (decStringQ != 64'hAAAAAAAA_55555555) $stop;
|
||||
task automatic svCheckNonContinuousValuesForced();
|
||||
`checkh(onebit, 0);
|
||||
`checkh(intval, 32'h55555555);
|
||||
`checkh(vectorC, 8'h55);
|
||||
`checkh(vectorQ, 62'h15555555_55555555);
|
||||
`checkh(vectorW, 128'h55555555_55555555_55555555_55555555);
|
||||
`checkr(real1, 123456.789);
|
||||
`checks(textHalf, "T2");
|
||||
`checks(textLong, "44Four44");
|
||||
`checks(text, "lorem ipsum");
|
||||
`checkh(binString, 8'b01010101);
|
||||
`checkh(octString, 15'o52525);
|
||||
`checkh(hexString, 64'h5555555555555555);
|
||||
`checkh(decStringC, 8'h55);
|
||||
`checkh(decStringS, 16'h5555);
|
||||
`checkh(decStringI, 32'h55555555);
|
||||
`checkh(decStringQ, 64'd6148914691236517205);
|
||||
endtask
|
||||
|
||||
if (intvalContinuously != 32'hAAAA_5555) $stop;
|
||||
if (vectorCContinuously != 8'h A5) $stop;
|
||||
if (vectorQContinuously != 62'h2AAAAAAAD5555555) $stop;
|
||||
if (vectorWContinuously != 128'hAAAAAAAA_AAAAAAAA_55555555_55555555) $stop;
|
||||
if (textHalfContinuously != "H2") $stop;
|
||||
if (textLongContinuously != "Lonur44") $stop;
|
||||
if (textContinuously != "Verilog Tesem ipsum") $stop;
|
||||
if (binStringContinuously != 8'b1010_0101) $stop;
|
||||
if (octStringContinuously != 15'b01010101_1010101) $stop;
|
||||
if (hexStringContinuously != 64'hAAAAAAAA_55555555) $stop;
|
||||
if (decStringCContinuously != 8'hA5) $stop;
|
||||
if (decStringSContinuously != 16'hAA55) $stop;
|
||||
if (decStringIContinuously != 32'hAAAA_5555) $stop;
|
||||
if (decStringQContinuously != 64'hAAAAAAAA_55555555) $stop;
|
||||
// Check that the values *after releasing* still have the forced value
|
||||
task automatic vpiCheckNonContinuousValuesForced();
|
||||
integer vpiStatus = 1;
|
||||
`ifdef VERILATOR
|
||||
`ifdef USE_VPI_NOT_DPI
|
||||
vpiStatus = $c32("checkNonContinuousValuesForced()");
|
||||
`else
|
||||
vpiStatus = checkNonContinuousValuesForced();
|
||||
`endif
|
||||
`elsif IVERILOG
|
||||
vpiStatus = $checkNonContinuousValuesForced;
|
||||
`elsif USE_VPI_NOT_DPI
|
||||
vpiStatus = $checkNonContinuousValuesForced;
|
||||
`else
|
||||
vpiStatus = checkNonContinuousValuesForced();
|
||||
`endif
|
||||
|
||||
if (vpiStatus != 0) begin
|
||||
$write("%%Error: t_vpi_force.cpp:%0d:", vpiStatus);
|
||||
$display("C Test failed (value of non-continuously assigned signal after releasing does not match expectation)");
|
||||
$stop;
|
||||
end
|
||||
endtask
|
||||
|
||||
task automatic svCheckContinuousValuesReleased();
|
||||
`checkh(onebitContinuously, 1);
|
||||
`checkh(intvalContinuously, 32'hAAAAAAAA);
|
||||
`checkh(vectorCContinuously, 8'hAA);
|
||||
`checkh(vectorQContinuously, 62'h2AAAAAAA_AAAAAAAA);
|
||||
`checkh(vectorWContinuously, 128'hAAAAAAAA_AAAAAAAA_AAAAAAAA_AAAAAAAA);
|
||||
`checkr(real1Continuously, 1.0);
|
||||
`checks(textHalfContinuously, "Hf");
|
||||
`checks(textLongContinuously, "Long64b");
|
||||
`checks(textContinuously, "Verilog Test module");
|
||||
`checkh(binStringContinuously, 8'b10101010);
|
||||
`checkh(octStringContinuously, 15'o25252);
|
||||
`checkh(hexStringContinuously, 64'hAAAAAAAAAAAAAAAA);
|
||||
`checkh(decStringCContinuously, 8'hAA);
|
||||
`checkh(decStringSContinuously, 16'hAAAA);
|
||||
`checkh(decStringIContinuously, 32'hAAAAAAAA);
|
||||
`checkh(decStringQContinuously, 64'd12297829382473034410);
|
||||
endtask
|
||||
|
||||
task automatic vpiCheckContinuousValuesReleased();
|
||||
integer vpiStatus = 1;
|
||||
`ifdef VERILATOR
|
||||
`ifdef USE_VPI_NOT_DPI
|
||||
vpiStatus = $c32("checkContinuousValuesReleased()");
|
||||
`else
|
||||
vpiStatus = checkContinuousValuesReleased();
|
||||
`endif
|
||||
`elsif IVERILOG
|
||||
vpiStatus = $checkContinuousValuesReleased;
|
||||
`elsif USE_VPI_NOT_DPI
|
||||
vpiStatus = $checkContinuousValuesReleased;
|
||||
`else
|
||||
vpiStatus = checkContinuousValuesReleased();
|
||||
`endif
|
||||
|
||||
if (vpiStatus != 0) begin
|
||||
$write("%%Error: t_vpi_force.cpp:%0d:", vpiStatus);
|
||||
$display("C Test failed (value of continuously assigned signal after releasing does not match expectation)");
|
||||
$stop;
|
||||
end
|
||||
endtask
|
||||
|
||||
task automatic svCheckValuesPartiallyForced();
|
||||
`checkh(intval, 32'hAAAA_5555);
|
||||
`checkh(vectorC, 8'h A5);
|
||||
`checkh(vectorQ, 62'h2AAAAAAAD5555555);
|
||||
`checkh(vectorW, 128'hAAAAAAAA_AAAAAAAA_55555555_55555555);
|
||||
`checks(textHalf, "H2");
|
||||
`checks(textLong, "Lonur44");
|
||||
`checks(text, "Verilog Tesem ipsum");
|
||||
`checkh(binString, 8'b1010_0101);
|
||||
`checkh(octString, 15'b01010101_1010101);
|
||||
`checkh(hexString, 64'hAAAAAAAA_55555555);
|
||||
`checkh(decStringC, 8'hA5);
|
||||
`checkh(decStringS, 16'hAA55);
|
||||
`checkh(decStringI, 32'hAAAA_5555);
|
||||
`checkh(decStringQ, 64'hAAAAAAAA_55555555);
|
||||
|
||||
`checkh(intvalContinuously, 32'hAAAA_5555);
|
||||
`checkh(vectorCContinuously, 8'h A5);
|
||||
`checkh(vectorQContinuously, 62'h2AAAAAAAD5555555);
|
||||
`checkh(vectorWContinuously, 128'hAAAAAAAA_AAAAAAAA_55555555_55555555);
|
||||
`checks(textHalfContinuously, "H2");
|
||||
`checks(textLongContinuously, "Lonur44");
|
||||
`checks(textContinuously, "Verilog Tesem ipsum");
|
||||
`checkh(binStringContinuously, 8'b1010_0101);
|
||||
`checkh(octStringContinuously, 15'b01010101_1010101);
|
||||
`checkh(hexStringContinuously, 64'hAAAAAAAA_55555555);
|
||||
`checkh(decStringCContinuously, 8'hA5);
|
||||
`checkh(decStringSContinuously, 16'hAA55);
|
||||
`checkh(decStringIContinuously, 32'hAAAA_5555);
|
||||
`checkh(decStringQContinuously, 64'hAAAAAAAA_55555555);
|
||||
endtask
|
||||
|
||||
task automatic vpiCheckValuesPartiallyForced();
|
||||
|
|
@ -564,40 +662,81 @@ module Test (
|
|||
end
|
||||
endtask
|
||||
|
||||
task automatic svCheckValuesReleased();
|
||||
if (onebit != 1) $stop;
|
||||
if (intval != 32'hAAAAAAAA) $stop;
|
||||
if (vectorC != 8'hAA) $stop;
|
||||
if (vectorQ != 62'h2AAAAAAA_AAAAAAAA) $stop;
|
||||
if (vectorW != 128'hAAAAAAAA_AAAAAAAA_AAAAAAAA_AAAAAAAA) $stop;
|
||||
if (real1 != 1.0) $stop;
|
||||
if (textHalf != "Hf") $stop;
|
||||
if (textLong != "Long64b") $stop;
|
||||
if (text != "Verilog Test module") $stop;
|
||||
if (binString != 8'b10101010) $stop;
|
||||
if (octString != 15'o25252) $stop;
|
||||
if (hexString != 64'hAAAAAAAAAAAAAAAA) $stop;
|
||||
if (decStringC != 8'hAA) $stop;
|
||||
if (decStringS != 16'hAAAA) $stop;
|
||||
if (decStringI != 32'hAAAAAAAA) $stop;
|
||||
if (decStringQ != 64'd12297829382473034410) $stop;
|
||||
task automatic svCheckNonContinuousValuesPartiallyForced();
|
||||
`checkh(intval, 32'hAAAA_5555);
|
||||
`checkh(vectorC, 8'h A5);
|
||||
`checkh(vectorQ, 62'h2AAAAAAAD5555555);
|
||||
`checkh(vectorW, 128'hAAAAAAAA_AAAAAAAA_55555555_55555555);
|
||||
`checks(textHalf, "H2");
|
||||
`checks(textLong, "Lonur44");
|
||||
`checks(text, "Verilog Tesem ipsum");
|
||||
`checkh(binString, 8'b1010_0101);
|
||||
`checkh(octString, 15'b01010101_1010101);
|
||||
`checkh(hexString, 64'hAAAAAAAA_55555555);
|
||||
`checkh(decStringC, 8'hA5);
|
||||
`checkh(decStringS, 16'hAA55);
|
||||
`checkh(decStringI, 32'hAAAA_5555);
|
||||
`checkh(decStringQ, 64'hAAAAAAAA_55555555);
|
||||
endtask
|
||||
|
||||
if (onebitContinuously != 1) $stop;
|
||||
if (intvalContinuously != 32'hAAAAAAAA) $stop;
|
||||
if (vectorCContinuously != 8'hAA) $stop;
|
||||
if (vectorQContinuously != 62'h2AAAAAAA_AAAAAAAA) $stop;
|
||||
if (vectorWContinuously != 128'hAAAAAAAA_AAAAAAAA_AAAAAAAA_AAAAAAAA) $stop;
|
||||
if (real1Continuously != 1.0) $stop;
|
||||
if (textHalfContinuously != "Hf") $stop;
|
||||
if (textLongContinuously != "Long64b") $stop;
|
||||
if (textContinuously != "Verilog Test module") $stop;
|
||||
if (binStringContinuously != 8'b10101010) $stop;
|
||||
if (octStringContinuously != 15'o25252) $stop;
|
||||
if (hexStringContinuously != 64'hAAAAAAAAAAAAAAAA) $stop;
|
||||
if (decStringCContinuously != 8'hAA) $stop;
|
||||
if (decStringSContinuously != 16'hAAAA) $stop;
|
||||
if (decStringIContinuously != 32'hAAAAAAAA) $stop;
|
||||
if (decStringQContinuously != 64'd12297829382473034410) $stop;
|
||||
// Check that the values *after releasing* still have the partially forced value
|
||||
task automatic vpiCheckNonContinuousValuesPartiallyForced();
|
||||
integer vpiStatus = 1;
|
||||
`ifdef VERILATOR
|
||||
`ifdef USE_VPI_NOT_DPI
|
||||
vpiStatus = $c32("checkNonContinuousValuesPartiallyForced()");
|
||||
`else
|
||||
vpiStatus = checkNonContinuousValuesPartiallyForced();
|
||||
`endif
|
||||
`elsif IVERILOG
|
||||
vpiStatus = $checkNonContinuousValuesPartiallyForced;
|
||||
`elsif USE_VPI_NOT_DPI
|
||||
vpiStatus = $checkNonContinuousValuesPartiallyForced;
|
||||
`else
|
||||
vpiStatus = checkNonContinuousValuesPartiallyForced();
|
||||
`endif
|
||||
|
||||
if (vpiStatus != 0) begin
|
||||
$write("%%Error: t_vpi_force.cpp:%0d:", vpiStatus);
|
||||
$display("C Test failed (value of non-continuously assigned signal after releasing from partial force does not match expectation)");
|
||||
$stop;
|
||||
end
|
||||
endtask
|
||||
|
||||
task automatic svCheckValuesReleased();
|
||||
`checkh(onebit, 1);
|
||||
`checkh(intval, 32'hAAAAAAAA);
|
||||
`checkh(vectorC, 8'hAA);
|
||||
`checkh(vectorQ, 62'h2AAAAAAA_AAAAAAAA);
|
||||
`checkh(vectorW, 128'hAAAAAAAA_AAAAAAAA_AAAAAAAA_AAAAAAAA);
|
||||
`checkr(real1, 1.0);
|
||||
`checks(textHalf, "Hf");
|
||||
`checks(textLong, "Long64b");
|
||||
`checks(text, "Verilog Test module");
|
||||
`checkh(binString, 8'b10101010);
|
||||
`checkh(octString, 15'o25252);
|
||||
`checkh(hexString, 64'hAAAAAAAAAAAAAAAA);
|
||||
`checkh(decStringC, 8'hAA);
|
||||
`checkh(decStringS, 16'hAAAA);
|
||||
`checkh(decStringI, 32'hAAAAAAAA);
|
||||
`checkh(decStringQ, 64'd12297829382473034410);
|
||||
|
||||
`checkh(onebitContinuously, 1);
|
||||
`checkh(intvalContinuously, 32'hAAAAAAAA);
|
||||
`checkh(vectorCContinuously, 8'hAA);
|
||||
`checkh(vectorQContinuously, 62'h2AAAAAAA_AAAAAAAA);
|
||||
`checkh(vectorWContinuously, 128'hAAAAAAAA_AAAAAAAA_AAAAAAAA_AAAAAAAA);
|
||||
`checkr(real1Continuously, 1.0);
|
||||
`checks(textHalfContinuously, "Hf");
|
||||
`checks(textLongContinuously, "Long64b");
|
||||
`checks(textContinuously, "Verilog Test module");
|
||||
`checkh(binStringContinuously, 8'b10101010);
|
||||
`checkh(octStringContinuously, 15'o25252);
|
||||
`checkh(hexStringContinuously, 64'hAAAAAAAAAAAAAAAA);
|
||||
`checkh(decStringCContinuously, 8'hAA);
|
||||
`checkh(decStringSContinuously, 16'hAAAA);
|
||||
`checkh(decStringIContinuously, 32'hAAAAAAAA);
|
||||
`checkh(decStringQContinuously, 64'd12297829382473034410);
|
||||
endtask
|
||||
|
||||
task automatic vpiCheckValuesReleased();
|
||||
|
|
@ -636,54 +775,80 @@ $dumpfile(`STRINGIFY(`TEST_DUMPFILE));
|
|||
#1 vpiCheckInertialDelay();
|
||||
// Force and check non-public, but forceable signal
|
||||
force nonPublic = 0;
|
||||
#4 if(nonPublic != 0) $stop;
|
||||
#8 `checkh(nonPublic, 0);
|
||||
release nonPublic;
|
||||
#4 if (nonPublic != 1) $stop;
|
||||
#8 `checkh(nonPublic, 1);
|
||||
`endif
|
||||
|
||||
// Force through VPI, release through VPI
|
||||
vpiForceValues();
|
||||
|
||||
// Time delay to ensure setting and checking values does not happen
|
||||
// at the same time, so that the signals can have their values overwritten
|
||||
// by other processes
|
||||
#4 vpiCheckValuesForced();
|
||||
#8 vpiCheckValuesForced();
|
||||
svCheckValuesForced();
|
||||
#4 vpiReleaseValues();
|
||||
#4 vpiCheckValuesReleased();
|
||||
// Wait until negedge, then release
|
||||
@(negedge clk) vpiReleaseValues();
|
||||
// After release, but before posedge: Non-continuously assigned signals
|
||||
// should still have their forced value, because the posedge re-assigning
|
||||
// the non-continuously assigned signals has not happened yet, but
|
||||
// continuously assigned signals should have their non-forced value again
|
||||
#1 vpiCheckNonContinuousValuesForced();
|
||||
vpiCheckContinuousValuesReleased();
|
||||
svCheckNonContinuousValuesForced();
|
||||
svCheckContinuousValuesReleased();
|
||||
#8; // All signals should be released by now
|
||||
vpiCheckValuesReleased();
|
||||
svCheckValuesReleased();
|
||||
|
||||
// Force through VPI, release through Verilog
|
||||
#4 vpiForceValues();
|
||||
#4 vpiCheckValuesForced();
|
||||
#8 vpiForceValues();
|
||||
#8 vpiCheckValuesForced();
|
||||
svCheckValuesForced();
|
||||
#4 svReleaseValues();
|
||||
#4 vpiCheckValuesReleased();
|
||||
@(negedge clk) svReleaseValues();
|
||||
#1 vpiCheckNonContinuousValuesForced();
|
||||
vpiCheckContinuousValuesReleased();
|
||||
svCheckNonContinuousValuesForced();
|
||||
svCheckContinuousValuesReleased();
|
||||
#8 vpiCheckValuesReleased();
|
||||
svCheckValuesReleased();
|
||||
|
||||
// Force through Verilog, release through VPI
|
||||
#4 svForceValues();
|
||||
#4 vpiCheckValuesForced();
|
||||
#8 svForceValues();
|
||||
#8 vpiCheckValuesForced();
|
||||
svCheckValuesForced();
|
||||
#4 vpiReleaseValues();
|
||||
#4 vpiCheckValuesReleased();
|
||||
@(negedge clk) vpiReleaseValues();
|
||||
#1 vpiCheckNonContinuousValuesForced();
|
||||
vpiCheckContinuousValuesReleased();
|
||||
svCheckNonContinuousValuesForced();
|
||||
svCheckContinuousValuesReleased();
|
||||
#8 vpiCheckValuesReleased();
|
||||
svCheckValuesReleased();
|
||||
|
||||
// Force only some bits, check if __VforceRd yields correct signal,
|
||||
// release through VPI
|
||||
#4 svPartiallyForceValues();
|
||||
#4 vpiCheckValuesPartiallyForced();
|
||||
#8 svPartiallyForceValues();
|
||||
#8 vpiCheckValuesPartiallyForced();
|
||||
svCheckValuesPartiallyForced();
|
||||
#4 vpiReleasePartiallyForcedValues();
|
||||
#4 vpiCheckValuesReleased();
|
||||
@(negedge clk) vpiReleasePartiallyForcedValues();
|
||||
#1 vpiCheckNonContinuousValuesPartiallyForced();
|
||||
vpiCheckContinuousValuesReleased();
|
||||
svCheckNonContinuousValuesPartiallyForced();
|
||||
svCheckContinuousValuesReleased();
|
||||
#8 vpiCheckValuesReleased();
|
||||
svCheckValuesReleased();
|
||||
|
||||
// Force only some bits, check if __VforceRd yields correct signal,
|
||||
// release through Verilog
|
||||
#4 svPartiallyForceValues();
|
||||
#4 vpiCheckValuesPartiallyForced();
|
||||
#8 svPartiallyForceValues();
|
||||
#8 vpiCheckValuesPartiallyForced();
|
||||
svCheckValuesPartiallyForced();
|
||||
#4 svReleaseValues();
|
||||
#4 vpiCheckValuesReleased();
|
||||
@(negedge clk) svReleaseValues();
|
||||
#1 vpiCheckNonContinuousValuesPartiallyForced();
|
||||
vpiCheckContinuousValuesReleased();
|
||||
svCheckNonContinuousValuesPartiallyForced();
|
||||
svCheckContinuousValuesReleased();
|
||||
#8 vpiCheckValuesReleased();
|
||||
svCheckValuesReleased();
|
||||
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue