Skip to content

Commit 2fcf3ae

Browse files
mwbringmannmpe
authored andcommitted
hotplug/drc-info: Add code to search ibm,drc-info property
rpadlpar_core.c: Provide parallel routines to search the older device- tree properties ("ibm,drc-indexes", "ibm,drc-names", "ibm,drc-types" and "ibm,drc-power-domains"), or the new property "ibm,drc-info". The interface to examine the DRC information is changed from a "get" function that returns values for local verification elsewhere, to a "check" function that validates the 'name' and/or 'type' of a device node. This update hides the format of the underlying device-tree properties, and concentrates the value checks into a single function without requiring the user to verify whether a search was successful. Signed-off-by: Michael Bringmann <mwb@linux.vnet.ibm.com> Signed-off-by: Michael Ellerman <mpe@ellerman.id.au>
1 parent e83636a commit 2fcf3ae

File tree

4 files changed

+94
-37
lines changed

4 files changed

+94
-37
lines changed

drivers/pci/hotplug/rpadlpar_core.c

Lines changed: 5 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@
2727
#include <linux/mutex.h>
2828
#include <asm/rtas.h>
2929
#include <asm/vio.h>
30+
#include <linux/firmware.h>
3031

3132
#include "../pci.h"
3233
#include "rpaphp.h"
@@ -44,15 +45,14 @@ static struct device_node *find_vio_slot_node(char *drc_name)
4445
{
4546
struct device_node *parent = of_find_node_by_name(NULL, "vdevice");
4647
struct device_node *dn = NULL;
47-
char *name;
4848
int rc;
4949

5050
if (!parent)
5151
return NULL;
5252

5353
while ((dn = of_get_next_child(parent, dn))) {
54-
rc = rpaphp_get_drc_props(dn, NULL, &name, NULL, NULL);
55-
if ((rc == 0) && (!strcmp(drc_name, name)))
54+
rc = rpaphp_check_drc_props(dn, drc_name, NULL);
55+
if (rc == 0)
5656
break;
5757
}
5858

@@ -64,15 +64,12 @@ static struct device_node *find_php_slot_pci_node(char *drc_name,
6464
char *drc_type)
6565
{
6666
struct device_node *np = NULL;
67-
char *name;
68-
char *type;
6967
int rc;
7068

7169
while ((np = of_find_node_by_name(np, "pci"))) {
72-
rc = rpaphp_get_drc_props(np, NULL, &name, &type, NULL);
70+
rc = rpaphp_check_drc_props(np, drc_name, drc_type);
7371
if (rc == 0)
74-
if (!strcmp(drc_name, name) && !strcmp(drc_type, type))
75-
break;
72+
break;
7673
}
7774

7875
return np;

drivers/pci/hotplug/rpadlpar_sysfs.c

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@
1616
#include <linux/string.h>
1717
#include <linux/pci.h>
1818
#include <linux/pci_hotplug.h>
19+
#include "rpaphp.h"
1920
#include "rpadlpar.h"
2021
#include "../pci.h"
2122

@@ -27,8 +28,6 @@
2728
#define ADD_SLOT_ATTR_NAME add_slot
2829
#define REMOVE_SLOT_ATTR_NAME remove_slot
2930

30-
#define MAX_DRC_NAME_LEN 64
31-
3231
static ssize_t add_slot_store(struct kobject *kobj, struct kobj_attribute *attr,
3332
const char *buf, size_t nbytes)
3433
{

drivers/pci/hotplug/rpaphp.h

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,10 @@ extern bool rpaphp_debug;
6464
#define CONFIGURED 1
6565
#define EMPTY 0
6666

67+
/* DRC constants */
68+
69+
#define MAX_DRC_NAME_LEN 64
70+
6771
/*
6872
* struct slot - slot information for each *physical* slot
6973
*/
@@ -91,8 +95,8 @@ int rpaphp_get_sensor_state(struct slot *slot, int *state);
9195

9296
/* rpaphp_core.c */
9397
int rpaphp_add_slot(struct device_node *dn);
94-
int rpaphp_get_drc_props(struct device_node *dn, int *drc_index,
95-
char **drc_name, char **drc_type, int *drc_power_domain);
98+
int rpaphp_check_drc_props(struct device_node *dn, char *drc_name,
99+
char *drc_type);
96100

97101
/* rpaphp_slot.c */
98102
void dealloc_slot_struct(struct slot *slot);

drivers/pci/hotplug/rpaphp_core.c

Lines changed: 82 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@
3030
#include <linux/smp.h>
3131
#include <linux/init.h>
3232
#include <linux/vmalloc.h>
33+
#include <asm/firmware.h>
3334
#include <asm/eeh.h> /* for eeh_add_device() */
3435
#include <asm/rtas.h> /* rtas_call */
3536
#include <asm/pci-bridge.h> /* for pci_controller */
@@ -196,25 +197,21 @@ static int get_children_props(struct device_node *dn, const int **drc_indexes,
196197
return 0;
197198
}
198199

199-
/* To get the DRC props describing the current node, first obtain it's
200-
* my-drc-index property. Next obtain the DRC list from it's parent. Use
201-
* the my-drc-index for correlation, and obtain the requested properties.
200+
201+
/* Verify the existence of 'drc_name' and/or 'drc_type' within the
202+
* current node. First obtain it's my-drc-index property. Next,
203+
* obtain the DRC info from it's parent. Use the my-drc-index for
204+
* correlation, and obtain/validate the requested properties.
202205
*/
203-
int rpaphp_get_drc_props(struct device_node *dn, int *drc_index,
204-
char **drc_name, char **drc_type, int *drc_power_domain)
206+
207+
static int rpaphp_check_drc_props_v1(struct device_node *dn, char *drc_name,
208+
char *drc_type, unsigned int my_index)
205209
{
210+
char *name_tmp, *type_tmp;
206211
const int *indexes, *names;
207212
const int *types, *domains;
208-
const unsigned int *my_index;
209-
char *name_tmp, *type_tmp;
210213
int i, rc;
211214

212-
my_index = of_get_property(dn, "ibm,my-drc-index", NULL);
213-
if (!my_index) {
214-
/* Node isn't DLPAR/hotplug capable */
215-
return -EINVAL;
216-
}
217-
218215
rc = get_children_props(dn->parent, &indexes, &names, &types, &domains);
219216
if (rc < 0) {
220217
return -EINVAL;
@@ -225,24 +222,84 @@ int rpaphp_get_drc_props(struct device_node *dn, int *drc_index,
225222

226223
/* Iterate through parent properties, looking for my-drc-index */
227224
for (i = 0; i < be32_to_cpu(indexes[0]); i++) {
228-
if ((unsigned int) indexes[i + 1] == *my_index) {
229-
if (drc_name)
230-
*drc_name = name_tmp;
231-
if (drc_type)
232-
*drc_type = type_tmp;
233-
if (drc_index)
234-
*drc_index = be32_to_cpu(*my_index);
235-
if (drc_power_domain)
236-
*drc_power_domain = be32_to_cpu(domains[i+1]);
237-
return 0;
238-
}
225+
if ((unsigned int) indexes[i + 1] == my_index)
226+
break;
227+
239228
name_tmp += (strlen(name_tmp) + 1);
240229
type_tmp += (strlen(type_tmp) + 1);
241230
}
242231

232+
if (((drc_name == NULL) || (drc_name && !strcmp(drc_name, name_tmp))) &&
233+
((drc_type == NULL) || (drc_type && !strcmp(drc_type, type_tmp))))
234+
return 0;
235+
243236
return -EINVAL;
244237
}
245-
EXPORT_SYMBOL_GPL(rpaphp_get_drc_props);
238+
239+
static int rpaphp_check_drc_props_v2(struct device_node *dn, char *drc_name,
240+
char *drc_type, unsigned int my_index)
241+
{
242+
struct property *info;
243+
unsigned int entries;
244+
struct of_drc_info drc;
245+
const __be32 *value;
246+
char cell_drc_name[MAX_DRC_NAME_LEN];
247+
int j, fndit;
248+
249+
info = of_find_property(dn->parent, "ibm,drc-info", NULL);
250+
if (info == NULL)
251+
return -EINVAL;
252+
253+
value = of_prop_next_u32(info, NULL, &entries);
254+
if (!value)
255+
return -EINVAL;
256+
257+
for (j = 0; j < entries; j++) {
258+
of_read_drc_info_cell(&info, &value, &drc);
259+
260+
/* Should now know end of current entry */
261+
262+
if (my_index > drc.last_drc_index)
263+
continue;
264+
265+
fndit = 1;
266+
break;
267+
}
268+
/* Found it */
269+
270+
if (fndit)
271+
sprintf(cell_drc_name, "%s%d", drc.drc_name_prefix,
272+
my_index);
273+
274+
if (((drc_name == NULL) ||
275+
(drc_name && !strcmp(drc_name, cell_drc_name))) &&
276+
((drc_type == NULL) ||
277+
(drc_type && !strcmp(drc_type, drc.drc_type))))
278+
return 0;
279+
280+
return -EINVAL;
281+
}
282+
283+
int rpaphp_check_drc_props(struct device_node *dn, char *drc_name,
284+
char *drc_type)
285+
{
286+
const unsigned int *my_index;
287+
288+
my_index = of_get_property(dn, "ibm,my-drc-index", NULL);
289+
if (!my_index) {
290+
/* Node isn't DLPAR/hotplug capable */
291+
return -EINVAL;
292+
}
293+
294+
if (firmware_has_feature(FW_FEATURE_DRC_INFO))
295+
return rpaphp_check_drc_props_v2(dn, drc_name, drc_type,
296+
*my_index);
297+
else
298+
return rpaphp_check_drc_props_v1(dn, drc_name, drc_type,
299+
*my_index);
300+
}
301+
EXPORT_SYMBOL_GPL(rpaphp_check_drc_props);
302+
246303

247304
static int is_php_type(char *drc_type)
248305
{

0 commit comments

Comments
 (0)