Skip to content

Commit eaa18a1

Browse files
committed
Merge: KVM: Performance Enhanced Refresh PCI Translation
MR: https://gitlab.com/redhat/centos-stream/src/kernel/centos-stream-10/-/merge_requests/1137 JIRA: https://issues.redhat.com/browse/RHEL-52964 Commits: ``` 807c274 64af12c 0ed5967 d236843 6d52cb7 8124407 d5fbc5e 1fe3f3c a2392b8 83c1aec ``` Signed-off-by: Christoph Schlameuss <cschlame@redhat.com> Approved-by: Thomas Huth <thuth@redhat.com> Approved-by: Cornelia Huck <cohuck@redhat.com> Approved-by: Jerry Snitselaar <jsnitsel@redhat.com> Approved-by: CKI KWF Bot <cki-ci-bot+kwf-gitlab-com@redhat.com> Merged-by: Julio Faracco <jfaracco@redhat.com>
2 parents 33180d1 + c2c59d7 commit eaa18a1

File tree

9 files changed

+479
-100
lines changed

9 files changed

+479
-100
lines changed

arch/s390/include/asm/pci.h

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -144,7 +144,7 @@ struct zpci_dev {
144144
u8 util_str_avail : 1;
145145
u8 irqs_registered : 1;
146146
u8 tid_avail : 1;
147-
u8 reserved : 1;
147+
u8 rtr_avail : 1; /* Relaxed translation allowed */
148148
unsigned int devfn; /* DEVFN part of the RID*/
149149

150150
u8 pfip[CLP_PFIP_NR_SEGMENTS]; /* pci function internal path */
@@ -217,6 +217,7 @@ extern struct airq_iv *zpci_aif_sbv;
217217
struct zpci_dev *zpci_create_device(u32 fid, u32 fh, enum zpci_state state);
218218
int zpci_add_device(struct zpci_dev *zdev);
219219
int zpci_enable_device(struct zpci_dev *);
220+
int zpci_reenable_device(struct zpci_dev *zdev);
220221
int zpci_disable_device(struct zpci_dev *);
221222
int zpci_scan_configured_device(struct zpci_dev *zdev, u32 fh);
222223
int zpci_deconfigure_device(struct zpci_dev *zdev);
@@ -245,6 +246,7 @@ void update_uid_checking(bool new);
245246
/* IOMMU Interface */
246247
int zpci_init_iommu(struct zpci_dev *zdev);
247248
void zpci_destroy_iommu(struct zpci_dev *zdev);
249+
int zpci_iommu_register_ioat(struct zpci_dev *zdev, u8 *status);
248250

249251
#ifdef CONFIG_PCI
250252
static inline bool zpci_use_mio(struct zpci_dev *zdev)

arch/s390/include/asm/pci_clp.h

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -156,7 +156,9 @@ struct clp_rsp_query_pci_grp {
156156
u16 : 4;
157157
u16 noi : 12; /* number of interrupts */
158158
u8 version;
159-
u8 : 6;
159+
u8 : 2;
160+
u8 rtr : 1; /* Relaxed translation requirement */
161+
u8 : 3;
160162
u8 frame : 1;
161163
u8 refresh : 1; /* TLB refresh mode */
162164
u16 : 3;

arch/s390/include/asm/pci_dma.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ enum zpci_ioat_dtype {
2525
#define ZPCI_KEY (PAGE_DEFAULT_KEY << 5)
2626

2727
#define ZPCI_TABLE_SIZE_RT (1UL << 42)
28+
#define ZPCI_TABLE_SIZE_RS (1UL << 53)
2829

2930
#define ZPCI_IOTA_STO_FLAG (ZPCI_IOTA_IOT_ENABLED | ZPCI_KEY | ZPCI_IOTA_DT_ST)
3031
#define ZPCI_IOTA_RTTO_FLAG (ZPCI_IOTA_IOT_ENABLED | ZPCI_KEY | ZPCI_IOTA_DT_RT)
@@ -55,6 +56,8 @@ enum zpci_ioat_dtype {
5556
#define ZPCI_PT_BITS 8
5657
#define ZPCI_ST_SHIFT (ZPCI_PT_BITS + PAGE_SHIFT)
5758
#define ZPCI_RT_SHIFT (ZPCI_ST_SHIFT + ZPCI_TABLE_BITS)
59+
#define ZPCI_RS_SHIFT (ZPCI_RT_SHIFT + ZPCI_TABLE_BITS)
60+
#define ZPCI_RF_SHIFT (ZPCI_RS_SHIFT + ZPCI_TABLE_BITS)
5861

5962
#define ZPCI_RTE_FLAG_MASK 0x3fffUL
6063
#define ZPCI_RTE_ADDR_MASK (~ZPCI_RTE_FLAG_MASK)

arch/s390/kvm/pci.c

Lines changed: 2 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -433,7 +433,6 @@ static void kvm_s390_pci_dev_release(struct zpci_dev *zdev)
433433
static int kvm_s390_pci_register_kvm(void *opaque, struct kvm *kvm)
434434
{
435435
struct zpci_dev *zdev = opaque;
436-
u8 status;
437436
int rc;
438437

439438
if (!zdev)
@@ -480,13 +479,7 @@ static int kvm_s390_pci_register_kvm(void *opaque, struct kvm *kvm)
480479
*/
481480
zdev->gisa = (u32)virt_to_phys(&kvm->arch.sie_page2->gisa);
482481

483-
rc = zpci_enable_device(zdev);
484-
if (rc)
485-
goto clear_gisa;
486-
487-
/* Re-register the IOMMU that was already created */
488-
rc = zpci_register_ioat(zdev, 0, zdev->start_dma, zdev->end_dma,
489-
virt_to_phys(zdev->dma_table), &status);
482+
rc = zpci_reenable_device(zdev);
490483
if (rc)
491484
goto clear_gisa;
492485

@@ -516,7 +509,6 @@ static void kvm_s390_pci_unregister_kvm(void *opaque)
516509
{
517510
struct zpci_dev *zdev = opaque;
518511
struct kvm *kvm;
519-
u8 status;
520512

521513
if (!zdev)
522514
return;
@@ -550,12 +542,7 @@ static void kvm_s390_pci_unregister_kvm(void *opaque)
550542
goto out;
551543
}
552544

553-
if (zpci_enable_device(zdev))
554-
goto out;
555-
556-
/* Re-register the IOMMU that was already created */
557-
zpci_register_ioat(zdev, 0, zdev->start_dma, zdev->end_dma,
558-
virt_to_phys(zdev->dma_table), &status);
545+
zpci_reenable_device(zdev);
559546

560547
out:
561548
spin_lock(&kvm->arch.kzdev_list_lock);

arch/s390/pci/pci.c

Lines changed: 20 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -134,14 +134,13 @@ int zpci_register_ioat(struct zpci_dev *zdev, u8 dmaas,
134134
struct zpci_fib fib = {0};
135135
u8 cc;
136136

137-
WARN_ON_ONCE(iota & 0x3fff);
138137
fib.pba = base;
139138
/* Work around off by one in ISM virt device */
140139
if (zdev->pft == PCI_FUNC_TYPE_ISM && limit > base)
141140
fib.pal = limit + (1 << 12);
142141
else
143142
fib.pal = limit;
144-
fib.iota = iota | ZPCI_IOTA_RTTO_FLAG;
143+
fib.iota = iota;
145144
fib.gd = zdev->gisa;
146145
cc = zpci_mod_fc(req, &fib, status);
147146
if (cc)
@@ -700,6 +699,23 @@ int zpci_enable_device(struct zpci_dev *zdev)
700699
}
701700
EXPORT_SYMBOL_GPL(zpci_enable_device);
702701

702+
int zpci_reenable_device(struct zpci_dev *zdev)
703+
{
704+
u8 status;
705+
int rc;
706+
707+
rc = zpci_enable_device(zdev);
708+
if (rc)
709+
return rc;
710+
711+
rc = zpci_iommu_register_ioat(zdev, &status);
712+
if (rc)
713+
zpci_disable_device(zdev);
714+
715+
return rc;
716+
}
717+
EXPORT_SYMBOL_GPL(zpci_reenable_device);
718+
703719
int zpci_disable_device(struct zpci_dev *zdev)
704720
{
705721
u32 fh = zdev->fh;
@@ -749,7 +765,6 @@ EXPORT_SYMBOL_GPL(zpci_disable_device);
749765
*/
750766
int zpci_hot_reset_device(struct zpci_dev *zdev)
751767
{
752-
u8 status;
753768
int rc;
754769

755770
lockdep_assert_held(&zdev->state_lock);
@@ -768,19 +783,9 @@ int zpci_hot_reset_device(struct zpci_dev *zdev)
768783
return rc;
769784
}
770785

771-
rc = zpci_enable_device(zdev);
772-
if (rc)
773-
return rc;
774-
775-
if (zdev->dma_table)
776-
rc = zpci_register_ioat(zdev, 0, zdev->start_dma, zdev->end_dma,
777-
virt_to_phys(zdev->dma_table), &status);
778-
if (rc) {
779-
zpci_disable_device(zdev);
780-
return rc;
781-
}
786+
rc = zpci_reenable_device(zdev);
782787

783-
return 0;
788+
return rc;
784789
}
785790

786791
/**

arch/s390/pci/pci_bus.c

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@
1919
#include <linux/jump_label.h>
2020
#include <linux/pci.h>
2121
#include <linux/printk.h>
22+
#include <linux/dma-direct.h>
2223

2324
#include <asm/pci_clp.h>
2425
#include <asm/pci_dma.h>
@@ -283,10 +284,32 @@ static struct zpci_bus *zpci_bus_alloc(int topo, bool topo_is_tid)
283284
return zbus;
284285
}
285286

287+
static void pci_dma_range_setup(struct pci_dev *pdev)
288+
{
289+
struct zpci_dev *zdev = to_zpci(pdev);
290+
u64 aligned_end, size;
291+
dma_addr_t dma_start;
292+
int ret;
293+
294+
dma_start = PAGE_ALIGN(zdev->start_dma);
295+
aligned_end = PAGE_ALIGN_DOWN(zdev->end_dma + 1);
296+
if (aligned_end >= dma_start)
297+
size = aligned_end - dma_start;
298+
else
299+
size = 0;
300+
WARN_ON_ONCE(size == 0);
301+
302+
ret = dma_direct_set_offset(&pdev->dev, 0, dma_start, size);
303+
if (ret)
304+
pr_err("Failed to allocate DMA range map for %s\n", pci_name(pdev));
305+
}
306+
286307
void pcibios_bus_add_device(struct pci_dev *pdev)
287308
{
288309
struct zpci_dev *zdev = to_zpci(pdev);
289310

311+
pci_dma_range_setup(pdev);
312+
290313
/*
291314
* With pdev->no_vf_scan the common PCI probing code does not
292315
* perform PF/VF linking.

arch/s390/pci/pci_clp.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -112,6 +112,7 @@ static void clp_store_query_pci_fngrp(struct zpci_dev *zdev,
112112
zdev->version = response->version;
113113
zdev->maxstbl = response->maxstbl;
114114
zdev->dtsm = response->dtsm;
115+
zdev->rtr_avail = response->rtr;
115116

116117
switch (response->version) {
117118
case 1:

arch/s390/pci/pci_sysfs.c

Lines changed: 1 addition & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,6 @@ static DEVICE_ATTR_RO(mio_enabled);
5252

5353
static int _do_recover(struct pci_dev *pdev, struct zpci_dev *zdev)
5454
{
55-
u8 status;
5655
int ret;
5756

5857
pci_stop_and_remove_bus_device(pdev);
@@ -70,16 +69,8 @@ static int _do_recover(struct pci_dev *pdev, struct zpci_dev *zdev)
7069
return ret;
7170
}
7271

73-
ret = zpci_enable_device(zdev);
74-
if (ret)
75-
return ret;
72+
ret = zpci_reenable_device(zdev);
7673

77-
if (zdev->dma_table) {
78-
ret = zpci_register_ioat(zdev, 0, zdev->start_dma, zdev->end_dma,
79-
virt_to_phys(zdev->dma_table), &status);
80-
if (ret)
81-
zpci_disable_device(zdev);
82-
}
8374
return ret;
8475
}
8576

0 commit comments

Comments
 (0)