Skip to content

Commit e97b587

Browse files
authored
Merge pull request #219 from hreinecke/lookup-restart
Restart controller lookup
2 parents 47fd557 + 3785918 commit e97b587

4 files changed

Lines changed: 69 additions & 32 deletions

File tree

src/nvme/fabrics.c

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -581,9 +581,8 @@ nvme_ctrl_t nvmf_connect_disc_entry(nvme_host_t h,
581581
case NVMF_TRTYPE_FC:
582582
switch (e->adrfam) {
583583
case NVMF_ADDR_FAMILY_FC:
584-
nvme_chomp(e->traddr, NVMF_TRADDR_SIZE),
584+
nvme_chomp(e->traddr, NVMF_TRADDR_SIZE);
585585
traddr = e->traddr;
586-
trsvcid = NULL;
587586
break;
588587
default:
589588
nvme_msg(h->r, LOG_ERR,
@@ -593,6 +592,8 @@ nvme_ctrl_t nvmf_connect_disc_entry(nvme_host_t h,
593592
return NULL;
594593
}
595594
case NVMF_TRTYPE_LOOP:
595+
nvme_chomp(e->traddr, NVMF_TRADDR_SIZE);
596+
traddr = strlen(e->traddr) ? e->traddr : NULL;
596597
break;
597598
default:
598599
nvme_msg(h->r, LOG_ERR, "skipping unsupported transport %d\n",

src/nvme/json.c

Lines changed: 13 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -76,7 +76,7 @@ static void json_update_attributes(nvme_ctrl_t c,
7676

7777
static void json_parse_port(nvme_subsystem_t s, struct json_object *port_obj)
7878
{
79-
nvme_ctrl_t c;
79+
nvme_ctrl_t c, p;
8080
struct json_object *attr_obj;
8181
const char *transport, *traddr = NULL;
8282
const char *host_traddr = NULL, *host_iface = NULL, *trsvcid = NULL;
@@ -97,14 +97,18 @@ static void json_parse_port(nvme_subsystem_t s, struct json_object *port_obj)
9797
attr_obj = json_object_object_get(port_obj, "trsvcid");
9898
if (attr_obj)
9999
trsvcid = json_object_get_string(attr_obj);
100-
c = nvme_lookup_ctrl(s, transport, traddr, host_traddr,
101-
host_iface, trsvcid);
102-
if (c) {
103-
attr_obj = json_object_object_get(port_obj, "dhchap_key");
104-
if (attr_obj)
105-
nvme_ctrl_set_dhchap_key(c, json_object_get_string(attr_obj));
106-
json_update_attributes(c, port_obj);
107-
}
100+
p = NULL;
101+
do {
102+
c = nvme_lookup_ctrl(s, transport, traddr, host_traddr,
103+
host_iface, trsvcid, p);
104+
if (c) {
105+
attr_obj = json_object_object_get(port_obj, "dhchap_key");
106+
if (attr_obj)
107+
nvme_ctrl_set_dhchap_key(c, json_object_get_string(attr_obj));
108+
json_update_attributes(c, port_obj);
109+
}
110+
p = c;
111+
} while (c);
108112
}
109113

110114
static void json_parse_subsys(nvme_host_t h, struct json_object *subsys_obj)

src/nvme/tree.c

Lines changed: 46 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -669,7 +669,7 @@ const char *nvme_ctrl_get_subsysnqn(nvme_ctrl_t c)
669669

670670
const char *nvme_ctrl_get_address(nvme_ctrl_t c)
671671
{
672-
return c->address;
672+
return c->address ? c->address : "";
673673
}
674674

675675
const char *nvme_ctrl_get_firmware(nvme_ctrl_t c)
@@ -977,16 +977,18 @@ struct nvme_ctrl *nvme_create_ctrl(nvme_root_t r,
977977
return c;
978978
}
979979

980-
struct nvme_ctrl *nvme_lookup_ctrl(struct nvme_subsystem *s, const char *transport,
981-
const char *traddr, const char *host_traddr,
982-
const char *host_iface, const char *trsvcid)
980+
nvme_ctrl_t nvme_lookup_ctrl(nvme_subsystem_t s, const char *transport,
981+
const char *traddr, const char *host_traddr,
982+
const char *host_iface, const char *trsvcid,
983+
nvme_ctrl_t p)
983984
{
984985
nvme_root_t r = s->h ? s->h->r : NULL;
985986
struct nvme_ctrl *c;
986987

987988
if (!s || !transport)
988989
return NULL;
989-
nvme_subsystem_for_each_ctrl(s, c) {
990+
c = p ? nvme_subsystem_next_ctrl(s, p) : nvme_subsystem_first_ctrl(s);
991+
for (; c != NULL; c = nvme_subsystem_next_ctrl(s, c)) {
990992
if (strcmp(c->transport, transport))
991993
continue;
992994
if (traddr && c->traddr &&
@@ -1120,13 +1122,11 @@ int nvme_init_ctrl(nvme_host_t h, nvme_ctrl_t c, int instance)
11201122
goto out_free_name;
11211123
}
11221124

1123-
if (strcmp(c->transport, "loop")) {
1124-
c->address = nvme_get_attr(path, "address");
1125-
if (!c->address) {
1126-
errno = ENVME_CONNECT_INVAL_TR;
1127-
ret = -1;
1128-
goto out_free_name;
1129-
}
1125+
c->address = nvme_get_attr(path, "address");
1126+
if (!c->address && strcmp(c->transport, "loop")) {
1127+
errno = ENVME_CONNECT_INVAL_TR;
1128+
ret = -1;
1129+
goto out_free_name;
11301130
}
11311131

11321132
subsys_name = nvme_ctrl_lookup_subsystem_name(h->r, name);
@@ -1166,7 +1166,7 @@ int nvme_init_ctrl(nvme_host_t h, nvme_ctrl_t c, int instance)
11661166
static nvme_ctrl_t nvme_ctrl_alloc(nvme_root_t r, nvme_subsystem_t s,
11671167
const char *path, const char *name)
11681168
{
1169-
nvme_ctrl_t c;
1169+
nvme_ctrl_t c, p;
11701170
char *addr = NULL, *address = NULL, *a, *e;
11711171
char *transport, *traddr = NULL, *trsvcid = NULL;
11721172
char *host_traddr = NULL, *host_iface = NULL;
@@ -1177,13 +1177,15 @@ static nvme_ctrl_t nvme_ctrl_alloc(nvme_root_t r, nvme_subsystem_t s,
11771177
errno = ENXIO;
11781178
return NULL;
11791179
}
1180-
if (!strcmp(transport, "loop"))
1181-
goto skip_address;
11821180
/* Parse 'address' string into components */
11831181
addr = nvme_get_attr(path, "address");
11841182
if (!addr) {
11851183
char *rpath = NULL, *p = NULL, *_a = NULL;
11861184

1185+
/* loop transport might not have an address */
1186+
if (!strcmp(transport, "loop"))
1187+
goto skip_address;
1188+
11871189
/* Older kernel don't support pcie transport addresses */
11881190
if (strcmp(transport, "pcie")) {
11891191
free(transport);
@@ -1228,13 +1230,36 @@ static nvme_ctrl_t nvme_ctrl_alloc(nvme_root_t r, nvme_subsystem_t s,
12281230
}
12291231
}
12301232
skip_address:
1231-
c = nvme_lookup_ctrl(s, transport, traddr,
1232-
host_traddr, host_iface, trsvcid);
1233+
p = NULL;
1234+
do {
1235+
c = nvme_lookup_ctrl(s, transport, traddr,
1236+
host_traddr, host_iface, trsvcid, p);
1237+
if (c) {
1238+
if (!c->name)
1239+
break;
1240+
if (!strcmp(c->name, name)) {
1241+
nvme_msg(r, LOG_DEBUG,
1242+
"%s: found existing ctrl %s\n",
1243+
__func__, c->name);
1244+
break;
1245+
}
1246+
nvme_msg(r, LOG_DEBUG, "%s: skipping ctrl %s\n",
1247+
__func__, c->name);
1248+
p = c;
1249+
}
1250+
} while (c);
1251+
if (!c)
1252+
c = p;
12331253
free(transport);
12341254
if (address)
12351255
free(address);
12361256
if (!c) {
1237-
errno = ENOMEM;
1257+
if (!p) {
1258+
nvme_msg(r, LOG_ERR, "%s: failed to lookup ctrl\n",
1259+
__func__);
1260+
errno = ENODEV;
1261+
} else
1262+
errno = ENOMEM;
12381263
return NULL;
12391264
}
12401265
c->address = addr;
@@ -1287,7 +1312,10 @@ nvme_ctrl_t nvme_scan_ctrl(nvme_root_t r, const char *name)
12871312
return NULL;
12881313
}
12891314
subsysname = nvme_ctrl_lookup_subsystem_name(r, name);
1315+
/* subsysname might be NULL here */
12901316
s = nvme_lookup_subsystem(h, subsysname, subsysnqn);
1317+
if (subsysname)
1318+
free(subsysname);
12911319
free(subsysnqn);
12921320
if (!s) {
12931321
free(path);

src/nvme/tree.h

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -241,17 +241,20 @@ nvme_ctrl_t nvme_subsystem_next_ctrl(nvme_subsystem_t s, nvme_ctrl_t c);
241241
* @host_traddr: host transport address
242242
* @host_iface: host interface name
243243
* @trsvcid: transport service identifier
244+
* @p: previous nvme_ctrl_t object
244245
*
245246
* Lookup a nvme_ctrl_t object in @s based on @transport, @traddr,
246247
* @host_traddr, @host_iface, and @trsvcid. @transport must be specified,
247248
* other fields may be required depending on the transport. A new
248-
* object is created if none is found.
249+
* object is created if none is found. If @p is specified the lookup
250+
* will start at @p instead of the first controller.
249251
*
250252
* Return: nvme_ctrl_t object
251253
*/
252254
nvme_ctrl_t nvme_lookup_ctrl(nvme_subsystem_t s, const char *transport,
253255
const char *traddr, const char *host_traddr,
254-
const char *host_iface, const char *trsvcid);
256+
const char *host_iface, const char *trsvcid,
257+
nvme_ctrl_t p);
255258

256259

257260
/**
@@ -738,7 +741,8 @@ const char *nvme_ctrl_get_sysfs_dir(nvme_ctrl_t c);
738741
* nvme_ctrl_get_address() - Address string of an nvme_ctrl_t
739742
* @c: nvme_ctrl_t object
740743
*
741-
* Return: NVMe-over-Fabrics address string of @c
744+
* Return: NVMe-over-Fabrics address string of @c or empty string
745+
* of no address is present.
742746
*/
743747
const char *nvme_ctrl_get_address(nvme_ctrl_t c);
744748

0 commit comments

Comments
 (0)