Message ID | 20220111131027.599784-5-danielhb413@gmail.com (mailing list archive) |
---|---|
State | New, archived |
Headers | show |
Series | user creatable pnv-phb4 devices | expand |
On 1/11/22 14:10, Daniel Henrique Barboza wrote: > This patch introduces pnv-phb4 user creatable devices that are created > in a similar manner as pnv-phb3 devices, allowing the user to interact > with the PHBs directly instead of creating PCI Express Controllers that > will create a certain amount of PHBs per controller index. > > We accomplish this by doing the following: > > - add a pnv_phb4_get_stack() helper to retrieve which stack an user > created phb4 would occupy; > > - when dealing with an user created pnv-phb4 (detected by checking if > phb->stack is NULL at the start of phb4_realize()), retrieve its stack > and initialize its properties as done in stk_realize(); > > - use 'defaults_enabled()' in stk_realize() to avoid creating and > initializing a 'stack->phb' qdev that might be overwritten by an user > created pnv-phb4 device. This process is wrapped into a new helper > called pnv_pec_stk_default_phb_realize(). > > Signed-off-by: Daniel Henrique Barboza <danielhb413@gmail.com> Reviewed-by: Cédric Le Goater <clg@kaod.org> Nothing is left in the stack model. I think the next cleanup is to get rid of it. Thanks, C. > --- > hw/pci-host/pnv_phb4.c | 74 ++++++++++++++++++++++++++++++++++++-- > hw/pci-host/pnv_phb4_pec.c | 17 +++++++-- > hw/ppc/pnv.c | 2 ++ > 3 files changed, 89 insertions(+), 4 deletions(-) > > diff --git a/hw/pci-host/pnv_phb4.c b/hw/pci-host/pnv_phb4.c > index ee046725ac..ca2f4078e5 100644 > --- a/hw/pci-host/pnv_phb4.c > +++ b/hw/pci-host/pnv_phb4.c > @@ -1487,15 +1487,85 @@ static void pnv_phb4_instance_init(Object *obj) > object_initialize_child(obj, "source", &phb->xsrc, TYPE_XIVE_SOURCE); > } > > +static PnvPhb4PecStack *pnv_phb4_get_stack(PnvChip *chip, PnvPHB4 *phb, > + Error **errp) > +{ > + Pnv9Chip *chip9 = PNV9_CHIP(chip); > + int chip_id = phb->chip_id; > + int index = phb->phb_id; > + int i, j; > + > + for (i = 0; i < chip->num_pecs; i++) { > + /* > + * For each PEC, check the amount of stacks it supports > + * and see if the given phb4 index matches a stack. > + */ > + PnvPhb4PecState *pec = &chip9->pecs[i]; > + > + for (j = 0; j < pec->num_stacks; j++) { > + if (index == pnv_phb4_pec_get_phb_id(pec, j)) { > + return &pec->stacks[j]; > + } > + } > + } > + > + error_setg(errp, > + "pnv-phb4 chip-id %d index %d didn't match any existing PEC", > + chip_id, index); > + > + return NULL; > +} > + > static void pnv_phb4_realize(DeviceState *dev, Error **errp) > { > PnvPHB4 *phb = PNV_PHB4(dev); > PCIHostState *pci = PCI_HOST_BRIDGE(dev); > XiveSource *xsrc = &phb->xsrc; > + Error *local_err = NULL; > int nr_irqs; > char name[32]; > > - assert(phb->stack); > + /* User created PHB */ > + if (!phb->stack) { > + PnvMachineState *pnv = PNV_MACHINE(qdev_get_machine()); > + PnvChip *chip = pnv_get_chip(pnv, phb->chip_id); > + PnvPhb4PecClass *pecc; > + BusState *s; > + > + if (!chip) { > + error_setg(errp, "invalid chip id: %d", phb->chip_id); > + return; > + } > + > + phb->stack = pnv_phb4_get_stack(chip, phb, &local_err); > + if (local_err) { > + error_propagate(errp, local_err); > + return; > + } > + > + /* All other phb properties but 'version' are already set */ > + pecc = PNV_PHB4_PEC_GET_CLASS(phb->stack->pec); > + object_property_set_int(OBJECT(phb), "version", pecc->version, > + &error_fatal); > + > + /* > + * Assign stack->phb since pnv_phb4_update_regions() uses it > + * to access the phb. > + */ > + phb->stack->phb = phb; > + > + /* > + * Reparent user created devices to the chip to build > + * correctly the device tree. > + */ > + pnv_chip_parent_fixup(chip, OBJECT(phb), phb->phb_id); > + > + s = qdev_get_parent_bus(DEVICE(chip)); > + if (!qdev_set_parent_bus(DEVICE(phb), s, &local_err)) { > + error_propagate(errp, local_err); > + return; > + } > + } > > /* Set the "big_phb" flag */ > phb->big_phb = phb->phb_id == 0 || phb->phb_id == 3; > @@ -1600,7 +1670,7 @@ static void pnv_phb4_class_init(ObjectClass *klass, void *data) > dc->realize = pnv_phb4_realize; > device_class_set_props(dc, pnv_phb4_properties); > set_bit(DEVICE_CATEGORY_BRIDGE, dc->categories); > - dc->user_creatable = false; > + dc->user_creatable = true; > > xfc->notify = pnv_phb4_xive_notify; > } > diff --git a/hw/pci-host/pnv_phb4_pec.c b/hw/pci-host/pnv_phb4_pec.c > index d4c52a5d28..7fe7f1f007 100644 > --- a/hw/pci-host/pnv_phb4_pec.c > +++ b/hw/pci-host/pnv_phb4_pec.c > @@ -19,6 +19,7 @@ > #include "hw/pci/pci_bus.h" > #include "hw/ppc/pnv.h" > #include "hw/qdev-properties.h" > +#include "sysemu/sysemu.h" > > #include <libfdt.h> > > @@ -275,9 +276,9 @@ static const TypeInfo pnv_pec_type_info = { > } > }; > > -static void pnv_pec_stk_realize(DeviceState *dev, Error **errp) > +static void pnv_pec_stk_default_phb_realize(PnvPhb4PecStack *stack, > + Error **errp) > { > - PnvPhb4PecStack *stack = PNV_PHB4_PEC_STACK(dev); > PnvPhb4PecState *pec = stack->pec; > PnvPhb4PecClass *pecc = PNV_PHB4_PEC_GET_CLASS(pec); > int phb_id = pnv_phb4_pec_get_phb_id(pec, stack->stack_no); > @@ -292,11 +293,23 @@ static void pnv_pec_stk_realize(DeviceState *dev, Error **errp) > &error_fatal); > object_property_set_link(OBJECT(stack->phb), "stack", OBJECT(stack), > &error_abort); > + > if (!sysbus_realize(SYS_BUS_DEVICE(stack->phb), errp)) { > return; > } > } > > +static void pnv_pec_stk_realize(DeviceState *dev, Error **errp) > +{ > + PnvPhb4PecStack *stack = PNV_PHB4_PEC_STACK(dev); > + > + if (!defaults_enabled()) { > + return; > + } > + > + pnv_pec_stk_default_phb_realize(stack, errp); > +} > + > static Property pnv_pec_stk_properties[] = { > DEFINE_PROP_UINT32("stack-no", PnvPhb4PecStack, stack_no, 0), > DEFINE_PROP_LINK("pec", PnvPhb4PecStack, pec, TYPE_PNV_PHB4_PEC, > diff --git a/hw/ppc/pnv.c b/hw/ppc/pnv.c > index fe7e67e73a..837146a2fb 100644 > --- a/hw/ppc/pnv.c > +++ b/hw/ppc/pnv.c > @@ -1960,6 +1960,8 @@ static void pnv_machine_power9_class_init(ObjectClass *oc, void *data) > pmc->compat = compat; > pmc->compat_size = sizeof(compat); > pmc->dt_power_mgt = pnv_dt_power_mgt; > + > + machine_class_allow_dynamic_sysbus_dev(mc, TYPE_PNV_PHB4); > } > > static void pnv_machine_power10_class_init(ObjectClass *oc, void *data) >
On 1/11/22 11:42, Cédric Le Goater wrote: > On 1/11/22 14:10, Daniel Henrique Barboza wrote: >> This patch introduces pnv-phb4 user creatable devices that are created >> in a similar manner as pnv-phb3 devices, allowing the user to interact >> with the PHBs directly instead of creating PCI Express Controllers that >> will create a certain amount of PHBs per controller index. >> >> We accomplish this by doing the following: >> >> - add a pnv_phb4_get_stack() helper to retrieve which stack an user >> created phb4 would occupy; >> >> - when dealing with an user created pnv-phb4 (detected by checking if >> phb->stack is NULL at the start of phb4_realize()), retrieve its stack >> and initialize its properties as done in stk_realize(); >> >> - use 'defaults_enabled()' in stk_realize() to avoid creating and >> initializing a 'stack->phb' qdev that might be overwritten by an user >> created pnv-phb4 device. This process is wrapped into a new helper >> called pnv_pec_stk_default_phb_realize(). >> >> Signed-off-by: Daniel Henrique Barboza <danielhb413@gmail.com> > > Reviewed-by: Cédric Le Goater <clg@kaod.org> > > Nothing is left in the stack model. I think the next cleanup is to > get rid of it. The first step would be to move some MemoryOps from the stack to the phb, then little by little we can get into a point where the stack will just be a pointer to its phb. This is something that we can keep working on in smaller bits here and there. I mean, assuming that we're not going to use this code base for PHB5. If that's the case then I can prioritize this cleanup. Thanks, Daniel > > Thanks, > > C. > > >> --- >> hw/pci-host/pnv_phb4.c | 74 ++++++++++++++++++++++++++++++++++++-- >> hw/pci-host/pnv_phb4_pec.c | 17 +++++++-- >> hw/ppc/pnv.c | 2 ++ >> 3 files changed, 89 insertions(+), 4 deletions(-) >> >> diff --git a/hw/pci-host/pnv_phb4.c b/hw/pci-host/pnv_phb4.c >> index ee046725ac..ca2f4078e5 100644 >> --- a/hw/pci-host/pnv_phb4.c >> +++ b/hw/pci-host/pnv_phb4.c >> @@ -1487,15 +1487,85 @@ static void pnv_phb4_instance_init(Object *obj) >> object_initialize_child(obj, "source", &phb->xsrc, TYPE_XIVE_SOURCE); >> } >> +static PnvPhb4PecStack *pnv_phb4_get_stack(PnvChip *chip, PnvPHB4 *phb, >> + Error **errp) >> +{ >> + Pnv9Chip *chip9 = PNV9_CHIP(chip); >> + int chip_id = phb->chip_id; >> + int index = phb->phb_id; >> + int i, j; >> + >> + for (i = 0; i < chip->num_pecs; i++) { >> + /* >> + * For each PEC, check the amount of stacks it supports >> + * and see if the given phb4 index matches a stack. >> + */ >> + PnvPhb4PecState *pec = &chip9->pecs[i]; >> + >> + for (j = 0; j < pec->num_stacks; j++) { >> + if (index == pnv_phb4_pec_get_phb_id(pec, j)) { >> + return &pec->stacks[j]; >> + } >> + } >> + } >> + >> + error_setg(errp, >> + "pnv-phb4 chip-id %d index %d didn't match any existing PEC", >> + chip_id, index); >> + >> + return NULL; >> +} >> + >> static void pnv_phb4_realize(DeviceState *dev, Error **errp) >> { >> PnvPHB4 *phb = PNV_PHB4(dev); >> PCIHostState *pci = PCI_HOST_BRIDGE(dev); >> XiveSource *xsrc = &phb->xsrc; >> + Error *local_err = NULL; >> int nr_irqs; >> char name[32]; >> - assert(phb->stack); >> + /* User created PHB */ >> + if (!phb->stack) { >> + PnvMachineState *pnv = PNV_MACHINE(qdev_get_machine()); >> + PnvChip *chip = pnv_get_chip(pnv, phb->chip_id); >> + PnvPhb4PecClass *pecc; >> + BusState *s; >> + >> + if (!chip) { >> + error_setg(errp, "invalid chip id: %d", phb->chip_id); >> + return; >> + } >> + >> + phb->stack = pnv_phb4_get_stack(chip, phb, &local_err); >> + if (local_err) { >> + error_propagate(errp, local_err); >> + return; >> + } >> + >> + /* All other phb properties but 'version' are already set */ >> + pecc = PNV_PHB4_PEC_GET_CLASS(phb->stack->pec); >> + object_property_set_int(OBJECT(phb), "version", pecc->version, >> + &error_fatal); >> + >> + /* >> + * Assign stack->phb since pnv_phb4_update_regions() uses it >> + * to access the phb. >> + */ >> + phb->stack->phb = phb; >> + >> + /* >> + * Reparent user created devices to the chip to build >> + * correctly the device tree. >> + */ >> + pnv_chip_parent_fixup(chip, OBJECT(phb), phb->phb_id); >> + >> + s = qdev_get_parent_bus(DEVICE(chip)); >> + if (!qdev_set_parent_bus(DEVICE(phb), s, &local_err)) { >> + error_propagate(errp, local_err); >> + return; >> + } >> + } >> /* Set the "big_phb" flag */ >> phb->big_phb = phb->phb_id == 0 || phb->phb_id == 3; >> @@ -1600,7 +1670,7 @@ static void pnv_phb4_class_init(ObjectClass *klass, void *data) >> dc->realize = pnv_phb4_realize; >> device_class_set_props(dc, pnv_phb4_properties); >> set_bit(DEVICE_CATEGORY_BRIDGE, dc->categories); >> - dc->user_creatable = false; >> + dc->user_creatable = true; >> xfc->notify = pnv_phb4_xive_notify; >> } >> diff --git a/hw/pci-host/pnv_phb4_pec.c b/hw/pci-host/pnv_phb4_pec.c >> index d4c52a5d28..7fe7f1f007 100644 >> --- a/hw/pci-host/pnv_phb4_pec.c >> +++ b/hw/pci-host/pnv_phb4_pec.c >> @@ -19,6 +19,7 @@ >> #include "hw/pci/pci_bus.h" >> #include "hw/ppc/pnv.h" >> #include "hw/qdev-properties.h" >> +#include "sysemu/sysemu.h" >> #include <libfdt.h> >> @@ -275,9 +276,9 @@ static const TypeInfo pnv_pec_type_info = { >> } >> }; >> -static void pnv_pec_stk_realize(DeviceState *dev, Error **errp) >> +static void pnv_pec_stk_default_phb_realize(PnvPhb4PecStack *stack, >> + Error **errp) >> { >> - PnvPhb4PecStack *stack = PNV_PHB4_PEC_STACK(dev); >> PnvPhb4PecState *pec = stack->pec; >> PnvPhb4PecClass *pecc = PNV_PHB4_PEC_GET_CLASS(pec); >> int phb_id = pnv_phb4_pec_get_phb_id(pec, stack->stack_no); >> @@ -292,11 +293,23 @@ static void pnv_pec_stk_realize(DeviceState *dev, Error **errp) >> &error_fatal); >> object_property_set_link(OBJECT(stack->phb), "stack", OBJECT(stack), >> &error_abort); >> + >> if (!sysbus_realize(SYS_BUS_DEVICE(stack->phb), errp)) { >> return; >> } >> } >> +static void pnv_pec_stk_realize(DeviceState *dev, Error **errp) >> +{ >> + PnvPhb4PecStack *stack = PNV_PHB4_PEC_STACK(dev); >> + >> + if (!defaults_enabled()) { >> + return; >> + } >> + >> + pnv_pec_stk_default_phb_realize(stack, errp); >> +} >> + >> static Property pnv_pec_stk_properties[] = { >> DEFINE_PROP_UINT32("stack-no", PnvPhb4PecStack, stack_no, 0), >> DEFINE_PROP_LINK("pec", PnvPhb4PecStack, pec, TYPE_PNV_PHB4_PEC, >> diff --git a/hw/ppc/pnv.c b/hw/ppc/pnv.c >> index fe7e67e73a..837146a2fb 100644 >> --- a/hw/ppc/pnv.c >> +++ b/hw/ppc/pnv.c >> @@ -1960,6 +1960,8 @@ static void pnv_machine_power9_class_init(ObjectClass *oc, void *data) >> pmc->compat = compat; >> pmc->compat_size = sizeof(compat); >> pmc->dt_power_mgt = pnv_dt_power_mgt; >> + >> + machine_class_allow_dynamic_sysbus_dev(mc, TYPE_PNV_PHB4); >> } >> static void pnv_machine_power10_class_init(ObjectClass *oc, void *data) >> >
On 1/11/22 15:57, Daniel Henrique Barboza wrote: > > > On 1/11/22 11:42, Cédric Le Goater wrote: >> On 1/11/22 14:10, Daniel Henrique Barboza wrote: >>> This patch introduces pnv-phb4 user creatable devices that are created >>> in a similar manner as pnv-phb3 devices, allowing the user to interact >>> with the PHBs directly instead of creating PCI Express Controllers that >>> will create a certain amount of PHBs per controller index. >>> >>> We accomplish this by doing the following: >>> >>> - add a pnv_phb4_get_stack() helper to retrieve which stack an user >>> created phb4 would occupy; >>> >>> - when dealing with an user created pnv-phb4 (detected by checking if >>> phb->stack is NULL at the start of phb4_realize()), retrieve its stack >>> and initialize its properties as done in stk_realize(); >>> >>> - use 'defaults_enabled()' in stk_realize() to avoid creating and >>> initializing a 'stack->phb' qdev that might be overwritten by an user >>> created pnv-phb4 device. This process is wrapped into a new helper >>> called pnv_pec_stk_default_phb_realize(). >>> >>> Signed-off-by: Daniel Henrique Barboza <danielhb413@gmail.com> >> >> Reviewed-by: Cédric Le Goater <clg@kaod.org> >> >> Nothing is left in the stack model. I think the next cleanup is to >> get rid of it. > > > The first step would be to move some MemoryOps from the stack to the phb, then > little by little we can get into a point where the stack will just be a pointer > to its phb. > > This is something that we can keep working on in smaller bits here and there. > I mean, assuming that we're not going to use this code base for PHB5. If that's > the case then I can prioritize this cleanup. PHB5 uses the same models. Only the PHB version and the root port model need some adaptation. On branch https://github.com/legoater/qemu/commits/powernv-7.0, I have merged : ppc/pnv: Move root port allocation under pnv_pec_stk_default_phb_realize() ppc/pnv: Add a 'rp_model' class attribute for the PHB4 PEC ppc/pnv: Remove PHB4 version property preparing ground for : ppc/pnv: Add model for POWER10 PHB5 PCIe Host bridge Should we rework slightly your patchset to include them ? Or we don't care may be. Please advise :) Thanks, C.
On 1/11/22 12:47, Cédric Le Goater wrote: > On 1/11/22 15:57, Daniel Henrique Barboza wrote: >> >> >> On 1/11/22 11:42, Cédric Le Goater wrote: >>> On 1/11/22 14:10, Daniel Henrique Barboza wrote: >>>> This patch introduces pnv-phb4 user creatable devices that are created >>>> in a similar manner as pnv-phb3 devices, allowing the user to interact >>>> with the PHBs directly instead of creating PCI Express Controllers that >>>> will create a certain amount of PHBs per controller index. >>>> >>>> We accomplish this by doing the following: >>>> >>>> - add a pnv_phb4_get_stack() helper to retrieve which stack an user >>>> created phb4 would occupy; >>>> >>>> - when dealing with an user created pnv-phb4 (detected by checking if >>>> phb->stack is NULL at the start of phb4_realize()), retrieve its stack >>>> and initialize its properties as done in stk_realize(); >>>> >>>> - use 'defaults_enabled()' in stk_realize() to avoid creating and >>>> initializing a 'stack->phb' qdev that might be overwritten by an user >>>> created pnv-phb4 device. This process is wrapped into a new helper >>>> called pnv_pec_stk_default_phb_realize(). >>>> >>>> Signed-off-by: Daniel Henrique Barboza <danielhb413@gmail.com> >>> >>> Reviewed-by: Cédric Le Goater <clg@kaod.org> >>> >>> Nothing is left in the stack model. I think the next cleanup is to >>> get rid of it. >> >> >> The first step would be to move some MemoryOps from the stack to the phb, then >> little by little we can get into a point where the stack will just be a pointer >> to its phb. >> >> This is something that we can keep working on in smaller bits here and there. >> I mean, assuming that we're not going to use this code base for PHB5. If that's >> the case then I can prioritize this cleanup. > > PHB5 uses the same models. Only the PHB version and the root port > model need some adaptation. > > > On branch https://github.com/legoater/qemu/commits/powernv-7.0, > I have merged : > > ppc/pnv: Move root port allocation under pnv_pec_stk_default_phb_realize() > ppc/pnv: Add a 'rp_model' class attribute for the PHB4 PEC > ppc/pnv: Remove PHB4 version property > > preparing ground for : > > ppc/pnv: Add model for POWER10 PHB5 PCIe Host bridge > > Should we rework slightly your patchset to include them ? Or we don't > care may be. Please advise :) I guess it's fine to add those 3 patches. Do you want me to re-send this series with them included? Daniel > > Thanks, > > C. >
>> On branch https://github.com/legoater/qemu/commits/powernv-7.0, >> I have merged : >> >> ppc/pnv: Move root port allocation under pnv_pec_stk_default_phb_realize() >> ppc/pnv: Add a 'rp_model' class attribute for the PHB4 PEC >> ppc/pnv: Remove PHB4 version property >> >> preparing ground for : >> >> ppc/pnv: Add model for POWER10 PHB5 PCIe Host bridge >> >> Should we rework slightly your patchset to include them ? Or we don't >> care may be. Please advise :) > > I guess it's fine to add those 3 patches. Do you want me to re-send this series with > them included? That would be interesting if you could merge the changes in your others patches. If not, then we will just send them before PHB5 as prereq cleanups. Thanks, C.
diff --git a/hw/pci-host/pnv_phb4.c b/hw/pci-host/pnv_phb4.c index ee046725ac..ca2f4078e5 100644 --- a/hw/pci-host/pnv_phb4.c +++ b/hw/pci-host/pnv_phb4.c @@ -1487,15 +1487,85 @@ static void pnv_phb4_instance_init(Object *obj) object_initialize_child(obj, "source", &phb->xsrc, TYPE_XIVE_SOURCE); } +static PnvPhb4PecStack *pnv_phb4_get_stack(PnvChip *chip, PnvPHB4 *phb, + Error **errp) +{ + Pnv9Chip *chip9 = PNV9_CHIP(chip); + int chip_id = phb->chip_id; + int index = phb->phb_id; + int i, j; + + for (i = 0; i < chip->num_pecs; i++) { + /* + * For each PEC, check the amount of stacks it supports + * and see if the given phb4 index matches a stack. + */ + PnvPhb4PecState *pec = &chip9->pecs[i]; + + for (j = 0; j < pec->num_stacks; j++) { + if (index == pnv_phb4_pec_get_phb_id(pec, j)) { + return &pec->stacks[j]; + } + } + } + + error_setg(errp, + "pnv-phb4 chip-id %d index %d didn't match any existing PEC", + chip_id, index); + + return NULL; +} + static void pnv_phb4_realize(DeviceState *dev, Error **errp) { PnvPHB4 *phb = PNV_PHB4(dev); PCIHostState *pci = PCI_HOST_BRIDGE(dev); XiveSource *xsrc = &phb->xsrc; + Error *local_err = NULL; int nr_irqs; char name[32]; - assert(phb->stack); + /* User created PHB */ + if (!phb->stack) { + PnvMachineState *pnv = PNV_MACHINE(qdev_get_machine()); + PnvChip *chip = pnv_get_chip(pnv, phb->chip_id); + PnvPhb4PecClass *pecc; + BusState *s; + + if (!chip) { + error_setg(errp, "invalid chip id: %d", phb->chip_id); + return; + } + + phb->stack = pnv_phb4_get_stack(chip, phb, &local_err); + if (local_err) { + error_propagate(errp, local_err); + return; + } + + /* All other phb properties but 'version' are already set */ + pecc = PNV_PHB4_PEC_GET_CLASS(phb->stack->pec); + object_property_set_int(OBJECT(phb), "version", pecc->version, + &error_fatal); + + /* + * Assign stack->phb since pnv_phb4_update_regions() uses it + * to access the phb. + */ + phb->stack->phb = phb; + + /* + * Reparent user created devices to the chip to build + * correctly the device tree. + */ + pnv_chip_parent_fixup(chip, OBJECT(phb), phb->phb_id); + + s = qdev_get_parent_bus(DEVICE(chip)); + if (!qdev_set_parent_bus(DEVICE(phb), s, &local_err)) { + error_propagate(errp, local_err); + return; + } + } /* Set the "big_phb" flag */ phb->big_phb = phb->phb_id == 0 || phb->phb_id == 3; @@ -1600,7 +1670,7 @@ static void pnv_phb4_class_init(ObjectClass *klass, void *data) dc->realize = pnv_phb4_realize; device_class_set_props(dc, pnv_phb4_properties); set_bit(DEVICE_CATEGORY_BRIDGE, dc->categories); - dc->user_creatable = false; + dc->user_creatable = true; xfc->notify = pnv_phb4_xive_notify; } diff --git a/hw/pci-host/pnv_phb4_pec.c b/hw/pci-host/pnv_phb4_pec.c index d4c52a5d28..7fe7f1f007 100644 --- a/hw/pci-host/pnv_phb4_pec.c +++ b/hw/pci-host/pnv_phb4_pec.c @@ -19,6 +19,7 @@ #include "hw/pci/pci_bus.h" #include "hw/ppc/pnv.h" #include "hw/qdev-properties.h" +#include "sysemu/sysemu.h" #include <libfdt.h> @@ -275,9 +276,9 @@ static const TypeInfo pnv_pec_type_info = { } }; -static void pnv_pec_stk_realize(DeviceState *dev, Error **errp) +static void pnv_pec_stk_default_phb_realize(PnvPhb4PecStack *stack, + Error **errp) { - PnvPhb4PecStack *stack = PNV_PHB4_PEC_STACK(dev); PnvPhb4PecState *pec = stack->pec; PnvPhb4PecClass *pecc = PNV_PHB4_PEC_GET_CLASS(pec); int phb_id = pnv_phb4_pec_get_phb_id(pec, stack->stack_no); @@ -292,11 +293,23 @@ static void pnv_pec_stk_realize(DeviceState *dev, Error **errp) &error_fatal); object_property_set_link(OBJECT(stack->phb), "stack", OBJECT(stack), &error_abort); + if (!sysbus_realize(SYS_BUS_DEVICE(stack->phb), errp)) { return; } } +static void pnv_pec_stk_realize(DeviceState *dev, Error **errp) +{ + PnvPhb4PecStack *stack = PNV_PHB4_PEC_STACK(dev); + + if (!defaults_enabled()) { + return; + } + + pnv_pec_stk_default_phb_realize(stack, errp); +} + static Property pnv_pec_stk_properties[] = { DEFINE_PROP_UINT32("stack-no", PnvPhb4PecStack, stack_no, 0), DEFINE_PROP_LINK("pec", PnvPhb4PecStack, pec, TYPE_PNV_PHB4_PEC, diff --git a/hw/ppc/pnv.c b/hw/ppc/pnv.c index fe7e67e73a..837146a2fb 100644 --- a/hw/ppc/pnv.c +++ b/hw/ppc/pnv.c @@ -1960,6 +1960,8 @@ static void pnv_machine_power9_class_init(ObjectClass *oc, void *data) pmc->compat = compat; pmc->compat_size = sizeof(compat); pmc->dt_power_mgt = pnv_dt_power_mgt; + + machine_class_allow_dynamic_sysbus_dev(mc, TYPE_PNV_PHB4); } static void pnv_machine_power10_class_init(ObjectClass *oc, void *data)
This patch introduces pnv-phb4 user creatable devices that are created in a similar manner as pnv-phb3 devices, allowing the user to interact with the PHBs directly instead of creating PCI Express Controllers that will create a certain amount of PHBs per controller index. We accomplish this by doing the following: - add a pnv_phb4_get_stack() helper to retrieve which stack an user created phb4 would occupy; - when dealing with an user created pnv-phb4 (detected by checking if phb->stack is NULL at the start of phb4_realize()), retrieve its stack and initialize its properties as done in stk_realize(); - use 'defaults_enabled()' in stk_realize() to avoid creating and initializing a 'stack->phb' qdev that might be overwritten by an user created pnv-phb4 device. This process is wrapped into a new helper called pnv_pec_stk_default_phb_realize(). Signed-off-by: Daniel Henrique Barboza <danielhb413@gmail.com> --- hw/pci-host/pnv_phb4.c | 74 ++++++++++++++++++++++++++++++++++++-- hw/pci-host/pnv_phb4_pec.c | 17 +++++++-- hw/ppc/pnv.c | 2 ++ 3 files changed, 89 insertions(+), 4 deletions(-)