powerpc-utils/powerpc-utils-1.3.12.drmgr-support-08.patch
Than Ngo dd69abbd9a - Add, multipath - drmgr support
- Fix, SMT state is not honored when new CPUs are added dynamically
Resolves: RHEL-62938
2024-11-18 15:25:58 +01:00

174 lines
5.0 KiB
Diff

commit f40a63b15c5639df93405b925a4dde740d9bfa23
Author: Haren Myneni <haren@linux.ibm.com>
Date: Fri Jun 21 15:45:58 2024 -0700
drmgr/pci: Add multipath partner device support for hotplug replace
If the PCI device has multipath partner device, its device node
contains "ibm,multipath-partner-drc" property which gives the DRC
index of the partner device.
So for the replace operation, the following steps will be executed:
- Find the device based on the partner DRC index of the requested
device
- Remove the requested device
- Remove the partner path
- Add the new device based on user input
- Find the device based on the partner DRC index of the new device
- Add the partner path of the new device
Since both paths will be using the same slot, LED indicators and
the slot identification will be done only for the primary device
in both removal and add operations.
Signed-off-by: Haren Myneni <haren@linux.ibm.com>
Signed-off-by: Tyrel Datwyler <tyreld@linux.ibm.com>
diff --git a/src/drmgr/drslot_chrp_pci.c b/src/drmgr/drslot_chrp_pci.c
index 2b8579b..ac078db 100644
--- a/src/drmgr/drslot_chrp_pci.c
+++ b/src/drmgr/drslot_chrp_pci.c
@@ -877,6 +877,44 @@ static int do_remove(struct dr_node *all_nodes)
return 0;
}
+static int replace_add_work(struct dr_node *node, bool partner_device)
+{
+
+ say(DEBUG, "repl_node:path=%s node:path=%s\n",
+ node->ofdt_path, node->children->ofdt_path);
+
+ /* Prompt user to replace card and to press
+ * Enter to continue or x to exit. Exiting here
+ * means the original card has been removed.
+ */
+ if (usr_prompt && !partner_device) {
+ if (process_led(node, LED_ACTION))
+ return -1;
+
+ printf("The visual indicator for the specified PCI slot <%s>\n"
+ "has been set to the action state. Replace the PCI\n"
+ "card in the identified slot and press Enter to "
+ "continue.\nEnter x to exit. Exiting now leaves the "
+ "PCI slot\nin the removed state.\n",
+ node->drc_name);
+
+ if (!(getchar() == '\n')) {
+ process_led(node, LED_OFF);
+ return 0;
+ }
+ }
+
+ if (add_work(node, partner_device))
+ return -1;
+
+ say(DEBUG, "CONFIGURING the card in node[name=%s, path=%s]\n",
+ node->drc_name, node->ofdt_path);
+
+ set_hp_adapter_status(PHP_CONFIG_ADAPTER, node->drc_name);
+
+ return 1;
+}
+
/**
* do_replace
* @brief Allows the replacement of an adapter connected to a
@@ -899,55 +937,43 @@ static int do_remove(struct dr_node *all_nodes)
*/
static int do_replace(struct dr_node *all_nodes)
{
- struct dr_node *repl_node;
+ struct dr_node *repl_node, *partner_node = NULL;
int rc;
repl_node = find_slot(usr_drc_name, 0, all_nodes, 0);
if (repl_node == NULL)
return -1;
+ partner_node = find_partner_node(repl_node, all_nodes);
+ if (partner_node)
+ printf("<%s> and <%s> are\nmultipath partner devices. "
+ "So <%s> will\nbe also replaced.\n",
+ repl_node->drc_name, partner_node->drc_name,
+ partner_node->drc_name);
+
/* Call the routine which does the work of getting the node info,
* then removing it from the OF device tree.
*/
if (remove_work(repl_node, false))
return -1;
+ if (partner_node) {
+ if (remove_work(partner_node, true))
+ return -1;
+ }
+
if (!repl_node->children) {
say(ERROR, "Bad node struct.\n");
return -1;
}
- say(DEBUG, "repl_node:path=%s node:path=%s\n",
- repl_node->ofdt_path, repl_node->children->ofdt_path);
-
- /* Prompt user to replace card and to press
- * Enter to continue or x to exit. Exiting here
- * means the original card has been removed.
- */
- if (usr_prompt) {
- if (process_led(repl_node, LED_ACTION))
- return -1;
-
- printf("The visual indicator for the specified PCI slot "
- "has\nbeen set to the action state. Replace the PCI "
- "card\nin the identified slot and press Enter to "
- "continue.\nEnter x to exit. Exiting now leaves the "
- "PCI slot\nin the removed state.\n");
-
- if (!(getchar() == '\n')) {
- process_led(repl_node, LED_OFF);
- return 0;
- }
- }
-
- rc = add_work(repl_node, false);
- if (rc)
+ rc = replace_add_work(repl_node, false);
+ if (rc <= 0)
return rc;
- say(DEBUG, "CONFIGURING the card in node[name=%s, path=%s]\n",
- repl_node->drc_name, repl_node->ofdt_path);
-
- set_hp_adapter_status(PHP_CONFIG_ADAPTER, repl_node->drc_name);
+ rc = replace_add_work(partner_node, true);
+ if (rc <= 0)
+ return rc;
if (repl_node->post_replace_processing) {
int prompt_save = usr_prompt;
@@ -961,11 +987,24 @@ static int do_replace(struct dr_node *all_nodes)
if (remove_work(repl_node, false))
return -1;
+ partner_node = find_partner_node(repl_node, node);
+ if (partner_node) {
+ if (remove_work(partner_node, true))
+ return -1;
+ }
+
rc = add_work(repl_node, false);
if (!rc)
set_hp_adapter_status(PHP_CONFIG_ADAPTER,
repl_node->drc_name);
+ if (partner_node) {
+ rc = add_work(partner_node, true);
+ if (!rc)
+ set_hp_adapter_status(PHP_CONFIG_ADAPTER,
+ partner_node->drc_name);
+ }
+
usr_prompt = prompt_save;
}