Skip to content

Commit e4f7900

Browse files
committed
Merge tag 'powerpc-6.8-5' of git://git.kernel.org/pub/scm/linux/kernel/git/powerpc/linux
Pull powerpc fixes from Michael Ellerman: - Fix IOMMU table initialisation when doing kdump over SR-IOV - Fix incorrect RTAS function name for resetting TCE tables - Fix fpu_signal selftest failures since a recent change Thanks to Gaurav Batra and Nathan Lynch. * tag 'powerpc-6.8-5' of git://git.kernel.org/pub/scm/linux/kernel/git/powerpc/linux: selftests/powerpc: Fix fpu_signal failures powerpc/rtas: use correct function name for resetting TCE tables powerpc/pseries/iommu: IOMMU table is not initialized for kdump over SR-IOV
2 parents 73d35f8 + 380cb2f commit e4f7900

File tree

4 files changed

+120
-65
lines changed

4 files changed

+120
-65
lines changed

arch/powerpc/include/asm/rtas.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ enum rtas_function_index {
6969
RTAS_FNIDX__IBM_READ_SLOT_RESET_STATE,
7070
RTAS_FNIDX__IBM_READ_SLOT_RESET_STATE2,
7171
RTAS_FNIDX__IBM_REMOVE_PE_DMA_WINDOW,
72-
RTAS_FNIDX__IBM_RESET_PE_DMA_WINDOWS,
72+
RTAS_FNIDX__IBM_RESET_PE_DMA_WINDOW,
7373
RTAS_FNIDX__IBM_SCAN_LOG_DUMP,
7474
RTAS_FNIDX__IBM_SET_DYNAMIC_INDICATOR,
7575
RTAS_FNIDX__IBM_SET_EEH_OPTION,
@@ -164,7 +164,7 @@ typedef struct {
164164
#define RTAS_FN_IBM_READ_SLOT_RESET_STATE rtas_fn_handle(RTAS_FNIDX__IBM_READ_SLOT_RESET_STATE)
165165
#define RTAS_FN_IBM_READ_SLOT_RESET_STATE2 rtas_fn_handle(RTAS_FNIDX__IBM_READ_SLOT_RESET_STATE2)
166166
#define RTAS_FN_IBM_REMOVE_PE_DMA_WINDOW rtas_fn_handle(RTAS_FNIDX__IBM_REMOVE_PE_DMA_WINDOW)
167-
#define RTAS_FN_IBM_RESET_PE_DMA_WINDOWS rtas_fn_handle(RTAS_FNIDX__IBM_RESET_PE_DMA_WINDOWS)
167+
#define RTAS_FN_IBM_RESET_PE_DMA_WINDOW rtas_fn_handle(RTAS_FNIDX__IBM_RESET_PE_DMA_WINDOW)
168168
#define RTAS_FN_IBM_SCAN_LOG_DUMP rtas_fn_handle(RTAS_FNIDX__IBM_SCAN_LOG_DUMP)
169169
#define RTAS_FN_IBM_SET_DYNAMIC_INDICATOR rtas_fn_handle(RTAS_FNIDX__IBM_SET_DYNAMIC_INDICATOR)
170170
#define RTAS_FN_IBM_SET_EEH_OPTION rtas_fn_handle(RTAS_FNIDX__IBM_SET_EEH_OPTION)

arch/powerpc/kernel/rtas.c

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -375,8 +375,13 @@ static struct rtas_function rtas_function_table[] __ro_after_init = {
375375
[RTAS_FNIDX__IBM_REMOVE_PE_DMA_WINDOW] = {
376376
.name = "ibm,remove-pe-dma-window",
377377
},
378-
[RTAS_FNIDX__IBM_RESET_PE_DMA_WINDOWS] = {
379-
.name = "ibm,reset-pe-dma-windows",
378+
[RTAS_FNIDX__IBM_RESET_PE_DMA_WINDOW] = {
379+
/*
380+
* Note: PAPR+ v2.13 7.3.31.4.1 spells this as
381+
* "ibm,reset-pe-dma-windows" (plural), but RTAS
382+
* implementations use the singular form in practice.
383+
*/
384+
.name = "ibm,reset-pe-dma-window",
380385
},
381386
[RTAS_FNIDX__IBM_SCAN_LOG_DUMP] = {
382387
.name = "ibm,scan-log-dump",

arch/powerpc/platforms/pseries/iommu.c

Lines changed: 105 additions & 51 deletions
Original file line numberDiff line numberDiff line change
@@ -574,29 +574,6 @@ static void iommu_table_setparms(struct pci_controller *phb,
574574

575575
struct iommu_table_ops iommu_table_lpar_multi_ops;
576576

577-
/*
578-
* iommu_table_setparms_lpar
579-
*
580-
* Function: On pSeries LPAR systems, return TCE table info, given a pci bus.
581-
*/
582-
static void iommu_table_setparms_lpar(struct pci_controller *phb,
583-
struct device_node *dn,
584-
struct iommu_table *tbl,
585-
struct iommu_table_group *table_group,
586-
const __be32 *dma_window)
587-
{
588-
unsigned long offset, size, liobn;
589-
590-
of_parse_dma_window(dn, dma_window, &liobn, &offset, &size);
591-
592-
iommu_table_setparms_common(tbl, phb->bus->number, liobn, offset, size, IOMMU_PAGE_SHIFT_4K, NULL,
593-
&iommu_table_lpar_multi_ops);
594-
595-
596-
table_group->tce32_start = offset;
597-
table_group->tce32_size = size;
598-
}
599-
600577
struct iommu_table_ops iommu_table_pseries_ops = {
601578
.set = tce_build_pSeries,
602579
.clear = tce_free_pSeries,
@@ -724,44 +701,92 @@ struct iommu_table_ops iommu_table_lpar_multi_ops = {
724701
* dynamic 64bit DMA window, walking up the device tree.
725702
*/
726703
static struct device_node *pci_dma_find(struct device_node *dn,
727-
const __be32 **dma_window)
704+
struct dynamic_dma_window_prop *prop)
728705
{
729-
const __be32 *dw = NULL;
706+
const __be32 *default_prop = NULL;
707+
const __be32 *ddw_prop = NULL;
708+
struct device_node *rdn = NULL;
709+
bool default_win = false, ddw_win = false;
730710

731711
for ( ; dn && PCI_DN(dn); dn = dn->parent) {
732-
dw = of_get_property(dn, "ibm,dma-window", NULL);
733-
if (dw) {
734-
if (dma_window)
735-
*dma_window = dw;
736-
return dn;
712+
default_prop = of_get_property(dn, "ibm,dma-window", NULL);
713+
if (default_prop) {
714+
rdn = dn;
715+
default_win = true;
716+
}
717+
ddw_prop = of_get_property(dn, DIRECT64_PROPNAME, NULL);
718+
if (ddw_prop) {
719+
rdn = dn;
720+
ddw_win = true;
721+
break;
722+
}
723+
ddw_prop = of_get_property(dn, DMA64_PROPNAME, NULL);
724+
if (ddw_prop) {
725+
rdn = dn;
726+
ddw_win = true;
727+
break;
737728
}
738-
dw = of_get_property(dn, DIRECT64_PROPNAME, NULL);
739-
if (dw)
740-
return dn;
741-
dw = of_get_property(dn, DMA64_PROPNAME, NULL);
742-
if (dw)
743-
return dn;
729+
730+
/* At least found default window, which is the case for normal boot */
731+
if (default_win)
732+
break;
744733
}
745734

746-
return NULL;
735+
/* For PCI devices there will always be a DMA window, either on the device
736+
* or parent bus
737+
*/
738+
WARN_ON(!(default_win | ddw_win));
739+
740+
/* caller doesn't want to get DMA window property */
741+
if (!prop)
742+
return rdn;
743+
744+
/* parse DMA window property. During normal system boot, only default
745+
* DMA window is passed in OF. But, for kdump, a dedicated adapter might
746+
* have both default and DDW in FDT. In this scenario, DDW takes precedence
747+
* over default window.
748+
*/
749+
if (ddw_win) {
750+
struct dynamic_dma_window_prop *p;
751+
752+
p = (struct dynamic_dma_window_prop *)ddw_prop;
753+
prop->liobn = p->liobn;
754+
prop->dma_base = p->dma_base;
755+
prop->tce_shift = p->tce_shift;
756+
prop->window_shift = p->window_shift;
757+
} else if (default_win) {
758+
unsigned long offset, size, liobn;
759+
760+
of_parse_dma_window(rdn, default_prop, &liobn, &offset, &size);
761+
762+
prop->liobn = cpu_to_be32((u32)liobn);
763+
prop->dma_base = cpu_to_be64(offset);
764+
prop->tce_shift = cpu_to_be32(IOMMU_PAGE_SHIFT_4K);
765+
prop->window_shift = cpu_to_be32(order_base_2(size));
766+
}
767+
768+
return rdn;
747769
}
748770

749771
static void pci_dma_bus_setup_pSeriesLP(struct pci_bus *bus)
750772
{
751773
struct iommu_table *tbl;
752774
struct device_node *dn, *pdn;
753775
struct pci_dn *ppci;
754-
const __be32 *dma_window = NULL;
776+
struct dynamic_dma_window_prop prop;
755777

756778
dn = pci_bus_to_OF_node(bus);
757779

758780
pr_debug("pci_dma_bus_setup_pSeriesLP: setting up bus %pOF\n",
759781
dn);
760782

761-
pdn = pci_dma_find(dn, &dma_window);
783+
pdn = pci_dma_find(dn, &prop);
762784

763-
if (dma_window == NULL)
764-
pr_debug(" no ibm,dma-window property !\n");
785+
/* In PPC architecture, there will always be DMA window on bus or one of the
786+
* parent bus. During reboot, there will be ibm,dma-window property to
787+
* define DMA window. For kdump, there will at least be default window or DDW
788+
* or both.
789+
*/
765790

766791
ppci = PCI_DN(pdn);
767792

@@ -771,13 +796,24 @@ static void pci_dma_bus_setup_pSeriesLP(struct pci_bus *bus)
771796
if (!ppci->table_group) {
772797
ppci->table_group = iommu_pseries_alloc_group(ppci->phb->node);
773798
tbl = ppci->table_group->tables[0];
774-
if (dma_window) {
775-
iommu_table_setparms_lpar(ppci->phb, pdn, tbl,
776-
ppci->table_group, dma_window);
777799

778-
if (!iommu_init_table(tbl, ppci->phb->node, 0, 0))
779-
panic("Failed to initialize iommu table");
780-
}
800+
iommu_table_setparms_common(tbl, ppci->phb->bus->number,
801+
be32_to_cpu(prop.liobn),
802+
be64_to_cpu(prop.dma_base),
803+
1ULL << be32_to_cpu(prop.window_shift),
804+
be32_to_cpu(prop.tce_shift), NULL,
805+
&iommu_table_lpar_multi_ops);
806+
807+
/* Only for normal boot with default window. Doesn't matter even
808+
* if we set these with DDW which is 64bit during kdump, since
809+
* these will not be used during kdump.
810+
*/
811+
ppci->table_group->tce32_start = be64_to_cpu(prop.dma_base);
812+
ppci->table_group->tce32_size = 1 << be32_to_cpu(prop.window_shift);
813+
814+
if (!iommu_init_table(tbl, ppci->phb->node, 0, 0))
815+
panic("Failed to initialize iommu table");
816+
781817
iommu_register_group(ppci->table_group,
782818
pci_domain_nr(bus), 0);
783819
pr_debug(" created table: %p\n", ppci->table_group);
@@ -968,6 +1004,12 @@ static void find_existing_ddw_windows_named(const char *name)
9681004
continue;
9691005
}
9701006

1007+
/* If at the time of system initialization, there are DDWs in OF,
1008+
* it means this is during kexec. DDW could be direct or dynamic.
1009+
* We will just mark DDWs as "dynamic" since this is kdump path,
1010+
* no need to worry about perforance. ddw_list_new_entry() will
1011+
* set window->direct = false.
1012+
*/
9711013
window = ddw_list_new_entry(pdn, dma64);
9721014
if (!window) {
9731015
of_node_put(pdn);
@@ -1524,8 +1566,8 @@ static void pci_dma_dev_setup_pSeriesLP(struct pci_dev *dev)
15241566
{
15251567
struct device_node *pdn, *dn;
15261568
struct iommu_table *tbl;
1527-
const __be32 *dma_window = NULL;
15281569
struct pci_dn *pci;
1570+
struct dynamic_dma_window_prop prop;
15291571

15301572
pr_debug("pci_dma_dev_setup_pSeriesLP: %s\n", pci_name(dev));
15311573

@@ -1538,7 +1580,7 @@ static void pci_dma_dev_setup_pSeriesLP(struct pci_dev *dev)
15381580
dn = pci_device_to_OF_node(dev);
15391581
pr_debug(" node is %pOF\n", dn);
15401582

1541-
pdn = pci_dma_find(dn, &dma_window);
1583+
pdn = pci_dma_find(dn, &prop);
15421584
if (!pdn || !PCI_DN(pdn)) {
15431585
printk(KERN_WARNING "pci_dma_dev_setup_pSeriesLP: "
15441586
"no DMA window found for pci dev=%s dn=%pOF\n",
@@ -1551,8 +1593,20 @@ static void pci_dma_dev_setup_pSeriesLP(struct pci_dev *dev)
15511593
if (!pci->table_group) {
15521594
pci->table_group = iommu_pseries_alloc_group(pci->phb->node);
15531595
tbl = pci->table_group->tables[0];
1554-
iommu_table_setparms_lpar(pci->phb, pdn, tbl,
1555-
pci->table_group, dma_window);
1596+
1597+
iommu_table_setparms_common(tbl, pci->phb->bus->number,
1598+
be32_to_cpu(prop.liobn),
1599+
be64_to_cpu(prop.dma_base),
1600+
1ULL << be32_to_cpu(prop.window_shift),
1601+
be32_to_cpu(prop.tce_shift), NULL,
1602+
&iommu_table_lpar_multi_ops);
1603+
1604+
/* Only for normal boot with default window. Doesn't matter even
1605+
* if we set these with DDW which is 64bit during kdump, since
1606+
* these will not be used during kdump.
1607+
*/
1608+
pci->table_group->tce32_start = be64_to_cpu(prop.dma_base);
1609+
pci->table_group->tce32_size = 1 << be32_to_cpu(prop.window_shift);
15561610

15571611
iommu_init_table(tbl, pci->phb->node, 0, 0);
15581612
iommu_register_group(pci->table_group,

tools/testing/selftests/powerpc/math/fpu_signal.c

Lines changed: 6 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818
#include <pthread.h>
1919

2020
#include "utils.h"
21+
#include "fpu.h"
2122

2223
/* Number of times each thread should receive the signal */
2324
#define ITERATIONS 10
@@ -27,9 +28,7 @@
2728
*/
2829
#define THREAD_FACTOR 8
2930

30-
__thread double darray[] = {0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 0.9, 1.0,
31-
1.1, 1.2, 1.3, 1.4, 1.5, 1.6, 1.7, 1.8, 1.9, 2.0,
32-
2.1};
31+
__thread double darray[32];
3332

3433
bool bad_context;
3534
int threads_starting;
@@ -43,9 +42,9 @@ void signal_fpu_sig(int sig, siginfo_t *info, void *context)
4342
ucontext_t *uc = context;
4443
mcontext_t *mc = &uc->uc_mcontext;
4544

46-
/* Only the non volatiles were loaded up */
47-
for (i = 14; i < 32; i++) {
48-
if (mc->fp_regs[i] != darray[i - 14]) {
45+
// Don't check f30/f31, they're used as scratches in check_all_fprs()
46+
for (i = 0; i < 30; i++) {
47+
if (mc->fp_regs[i] != darray[i]) {
4948
bad_context = true;
5049
break;
5150
}
@@ -54,7 +53,6 @@ void signal_fpu_sig(int sig, siginfo_t *info, void *context)
5453

5554
void *signal_fpu_c(void *p)
5655
{
57-
int i;
5856
long rc;
5957
struct sigaction act;
6058
act.sa_sigaction = signal_fpu_sig;
@@ -64,9 +62,7 @@ void *signal_fpu_c(void *p)
6462
return p;
6563

6664
srand(pthread_self());
67-
for (i = 0; i < 21; i++)
68-
darray[i] = rand();
69-
65+
randomise_darray(darray, ARRAY_SIZE(darray));
7066
rc = preempt_fpu(darray, &threads_starting, &running);
7167

7268
return (void *) rc;

0 commit comments

Comments
 (0)