Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

add missing Bare and Off check #301

Merged
merged 1 commit into from
Apr 25, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
35 changes: 23 additions & 12 deletions iommu_ref_model/libiommu/src/iommu_ats.c
Original file line number Diff line number Diff line change
Expand Up @@ -102,27 +102,43 @@ handle_page_request(
page_rec_t prec;
uint8_t L;
uint16_t PRGI;
uint32_t device_id, cause, status, response_code;
uint32_t device_id, cause, status, response_code, PRPR;
uint64_t prec_addr;
uint64_t pqb;
uint32_t pqh;
uint32_t pqt;

PRPR = 0;
device_id = ( pr->DSV == 1 ) ? (pr->RID | (pr->DSEG << 16)) : pr->RID;
if ( g_reg_file.ddtp.iommu_mode == Off ) {
cause = 256; // "All inbound transactions disallowed"
report_fault(cause, PAGE_REQ_MSG_CODE, 0, PCIE_MESSAGE_REQUEST, 0,
device_id, pr->PV, pr->PID, pr->PRIV);
response_code = RESPONSE_FAILURE;
goto send_prgr;
}
if ( g_reg_file.ddtp.iommu_mode == DDT_Bare ) {
cause = 260; // "Transaction type disallowed"
report_fault(cause, PAGE_REQ_MSG_CODE, 0, PCIE_MESSAGE_REQUEST, 0,
device_id, pr->PV, pr->PID, pr->PRIV);
response_code = INVALID_REQUEST;
goto send_prgr;
}
// To process a "Page Request" or "Stop Marker" message, the IOMMU first
// locates the device-context to determine if ATS and PRI are enabled for
// the requestor.
device_id = ( pr->DSV == 1 ) ? (pr->RID | (pr->DSEG << 16)) : pr->RID;
if ( locate_device_context(&DC, device_id, pr->PV, pr->PID, &cause) ) {
report_fault(cause, PAGE_REQ_MSG_CODE, 0, PCIE_MESSAGE_REQUEST, 0,
device_id, pr->PV, pr->PID, pr->PRIV);
response_code = RESPONSE_FAILURE;
goto send_prgr;
}
PRPR = DC.tc.PRPR;
if ( DC.tc.EN_PRI == 0 ) {
// 7. if any of the following conditions hold then stop and report
// "Transaction type disallowed" (cause = 260).
// * Transaction type is a PCIe "Page Request" Message and `DC.tc.EN_PRI` is 0.
report_fault(260, PAGE_REQ_MSG_CODE, 0, PCIE_MESSAGE_REQUEST, 0,
report_fault(260, PAGE_REQ_MSG_CODE, 0, PCIE_MESSAGE_REQUEST, DC.tc.DTF,
device_id, pr->PV, pr->PID, pr->PRIV);
response_code = INVALID_REQUEST;
goto send_prgr;
Expand Down Expand Up @@ -286,17 +302,12 @@ handle_page_request(
// the associated "Page Request" had a PASID. For IOMMU generated "Page Request
// Group Response" with response code set to Response Failure, if the "Page Request"
// had a PASID then response is generated with a PASID.
if ( response_code == INVALID_REQUEST || response_code == SUCCESS ) {
if ( DC.tc.PRPR == 1 ) {
prgr.PV = pr->PV;
prgr.PID = pr->PID;
} else {
prgr.PV = 0;
prgr.PID = 0;
}
} else {
if ( PRPR == 1 ) {
prgr.PV = pr->PV;
prgr.PID = pr->PID;
} else {
prgr.PV = 0;
prgr.PID = 0;
}
// PAYLOAD encoding of PRGR is as follows
// +0 | +1 | +2 | +3 |
Expand Down
52 changes: 50 additions & 2 deletions iommu_ref_model/test/test_app.c
Original file line number Diff line number Diff line change
Expand Up @@ -112,6 +112,29 @@ main(void) {
fail_if( ( check_rsp_and_faults(&req, &rsp, UNSUPPORTED_REQUEST, 256, 0) < 0 ) );
}
});
pr.MSGCODE = PAGE_REQ_MSG_CODE;
pr.TAG = 0;
pr.RID = 0x1234;
pr.PV = 1;
pr.PID = 0xbabec;
pr.PRIV = 1;
pr.EXEC_REQ = 0;
pr.DSV = 1;
pr.DSEG = 0x43;
pr.PAYLOAD = 0xdeadbeef00000007; // Set last, PRG index = 0
exp_msg.MSGCODE = PRGR_MSG_CODE;
exp_msg.TAG = 0;
exp_msg.RID = 0x1234;
exp_msg.PV = 0;
exp_msg.PID = 0;
exp_msg.PRIV = 0;
exp_msg.EXEC_REQ = 0;
exp_msg.DSV = 1;
exp_msg.DSEG = 0x43;
exp_msg.PAYLOAD = (0x1234UL << 48UL) | (RESPONSE_FAILURE << 44UL);
handle_page_request(&pr);
fail_if( ( exp_msg_received == 0 ) );
fail_if( ( check_msg_faults(256, pr.PV, pr.PID, pr.PRIV, 0x431234, PAGE_REQ_MSG_CODE) < 0 ) );
END_TEST();

START_TEST("Bare mode tests");
Expand All @@ -130,6 +153,29 @@ main(void) {
fail_if( ( check_rsp_and_faults(&req, &rsp, SUCCESS, 0, 0) < 0 ) );
}
});
pr.MSGCODE = PAGE_REQ_MSG_CODE;
pr.TAG = 0;
pr.RID = 0x1234;
pr.PV = 0;
pr.PID = 0;
pr.PRIV = 0;
pr.EXEC_REQ = 0;
pr.DSV = 1;
pr.DSEG = 0x43;
pr.PAYLOAD = 0xdeadbeef00000007; // Set last, PRG index = 0
exp_msg.MSGCODE = PRGR_MSG_CODE;
exp_msg.TAG = 0;
exp_msg.RID = 0x1234;
exp_msg.PV = 0;
exp_msg.PID = 0;
exp_msg.PRIV = 0;
exp_msg.EXEC_REQ = 0;
exp_msg.DSV = 1;
exp_msg.DSEG = 0x43;
exp_msg.PAYLOAD = (0x1234UL << 48UL) | (INVALID_REQUEST << 44UL);
handle_page_request(&pr);
fail_if( ( exp_msg_received == 0 ) );
fail_if( ( check_msg_faults(260, pr.PV, pr.PID, pr.PRIV, 0x431234, PAGE_REQ_MSG_CODE) < 0 ) );
// Turn it off
fail_if( ( enable_iommu(Off) < 0 ) );
END_TEST();
Expand Down Expand Up @@ -2847,8 +2893,8 @@ main(void) {
exp_msg.MSGCODE = PRGR_MSG_CODE;
exp_msg.TAG = 0;
exp_msg.RID = 0x1234;
exp_msg.PV = 1;
exp_msg.PID = 0xbabec;
exp_msg.PV = 0;
exp_msg.PID = 0;
exp_msg.PRIV = 0;
exp_msg.EXEC_REQ = 0;
exp_msg.DSV = 1;
Expand Down Expand Up @@ -2895,6 +2941,7 @@ main(void) {
fail_if( ( enable_disable_pq(4, 0) < 0 ) );
DC.tc.EN_ATS = 1;
DC.tc.EN_PRI = 1;
DC.tc.PRPR = 1;
write_memory((char *)&DC, DC_addr, 64);
iodir(INVAL_DDT, 1, 0x112233, 0);
exp_msg.RID = 0x2233;
Expand Down Expand Up @@ -2927,6 +2974,7 @@ main(void) {
pr.DSEG = 0x11;
DC.tc.EN_ATS = 1;
DC.tc.EN_PRI = 1;
DC.tc.PRPR = 0;
write_memory((char *)&DC, DC_addr, 64);
iodir(INVAL_DDT, 1, 0x112233, 0);
message_received = 0;
Expand Down
Loading