>-----Original Message----- >From: Liu, Yi L <yi.l....@intel.com> >Subject: Re: [PATCH v1 05/15] intel_iommu: Introduce two helpers >vtd_as_from/to_iommu_pasid_locked > >On 2025/6/6 18:04, Zhenzhong Duan wrote: >> We already have vtd_find_add_as() to find an AS from BDF+pasid, but this >> pasid is passed from PCI subsystem. PCI device supports two request types, >> Requests-without-PASID and Requests-with-PASID. Requests-without-PASID >> doesn't include a PASID TLP prefix, IOMMU fetches rid_pasid from context >> entry and use it as IOMMU's pasid to index pasid table. > >When reading the first line, it makes me thinking why need the helpers >since there is already a helper to find. The key is the later part. We need >to translate the PCI_NO_PASID to ridpasid.
OK, presume you want me to delete first line. Let me know if you mean not. Thanks Zhenzhong > >> So we need to translate between PCI's pasid and IOMMU's pasid specially >> for Requests-without-PASID, e.g., PCI_NO_PASID(-1) <-> rid_pasid. >> For Requests-with-PASID, PCI's pasid and IOMMU's pasid are same value. >> >> vtd_as_from_iommu_pasid_locked() translates from BDF+iommu_pasid to >vtd_as >> which contains PCI's pasid vtd_as->pasid. >> >> vtd_as_to_iommu_pasid_locked() translates from BDF+vtd_as->pasid to >iommu_pasid. >> >> Signed-off-by: Zhenzhong Duan <zhenzhong.d...@intel.com> >> --- >> hw/i386/intel_iommu.c | 50 >+++++++++++++++++++++++++++++++++++++++++++ >> 1 file changed, 50 insertions(+) >> >> diff --git a/hw/i386/intel_iommu.c b/hw/i386/intel_iommu.c >> index 796b71605c..112e09e305 100644 >> --- a/hw/i386/intel_iommu.c >> +++ b/hw/i386/intel_iommu.c >> @@ -1617,6 +1617,56 @@ static int >vtd_as_to_context_entry(VTDAddressSpace *vtd_as, VTDContextEntry *ce) >> } >> } >> >> +static inline int vtd_as_to_iommu_pasid_locked(VTDAddressSpace *vtd_as, >> + uint32_t *pasid) >> +{ >> + VTDContextEntry ce; >> + int ret; >> + >> + ret = vtd_as_to_context_entry(vtd_as, &ce); >> + if (ret) { >> + return ret; >> + } >> + >> + /* Translate to iommu pasid if PCI_NO_PASID */ >> + if (vtd_as->pasid == PCI_NO_PASID) { >> + *pasid = VTD_CE_GET_RID2PASID(&ce); >> + } else { >> + *pasid = vtd_as->pasid; >> + } >> + >> + return 0; >> +} >> + >> +static gboolean vtd_find_as_by_sid_and_iommu_pasid(gpointer key, gpointer >value, >> + gpointer user_data) >> +{ >> + VTDAddressSpace *vtd_as = (VTDAddressSpace *)value; >> + struct vtd_as_raw_key *target = (struct vtd_as_raw_key *)user_data; >> + uint16_t sid = PCI_BUILD_BDF(pci_bus_num(vtd_as->bus), vtd_as->devfn); >> + uint32_t pasid; >> + >> + if (vtd_as_to_iommu_pasid_locked(vtd_as, &pasid)) { >> + return false; >> + } >> + >> + return (pasid == target->pasid) && (sid == target->sid); >> +} >> + >> +/* Translate iommu pasid to vtd_as */ >> +static inline >> +VTDAddressSpace *vtd_as_from_iommu_pasid_locked(IntelIOMMUState *s, >> + uint16_t sid, uint32_t >> pasid) >> +{ >> + struct vtd_as_raw_key key = { >> + .sid = sid, >> + .pasid = pasid >> + }; >> + >> + return g_hash_table_find(s->vtd_address_spaces, >> + vtd_find_as_by_sid_and_iommu_pasid, &key); >> +} >> + >> static int vtd_sync_shadow_page_hook(const IOMMUTLBEvent *event, >> void *private) >> { > >-- >Regards, >Yi Liu