2 * Copyright (c) 2004, 2005 Christophe Varoqui
3 * Copyright (c) 2005 Stefan Bader, IBM
4 * Copyright (c) 2005 Edward Goggin, EMC
19 merge_words (char ** dst, char * word, int space)
24 len = strlen(*dst) + strlen(word) + space;
25 *dst = REALLOC(*dst, len + 1);
40 strncpy(p, word, strlen(word) + 1);
46 * Transforms the path group vector into a proper device map string
49 assemble_map (struct multipath * mp)
55 struct pathgroup * pgp;
60 freechar = sizeof(mp->params);
62 shift = snprintf(p, freechar, "%s %s %i %i",
63 mp->features, mp->hwhandler,
64 VECTOR_SIZE(mp->pg), mp->bestpg);
66 if (shift >= freechar) {
67 fprintf(stderr, "mp->params too small\n");
73 vector_foreach_slot (mp->pg, pgp, i) {
74 pgp = VECTOR_SLOT(mp->pg, i);
75 shift = snprintf(p, freechar, " %s %i 1", mp->selector,
76 VECTOR_SIZE(pgp->paths));
77 if (shift >= freechar) {
78 fprintf(stderr, "mp->params too small\n");
84 vector_foreach_slot (pgp->paths, pp, j) {
85 if (mp->rr_weight == RR_WEIGHT_PRIO && pp->priority)
86 minio *= pp->priority;
88 shift = snprintf(p, freechar, " %s %d",
90 if (shift >= freechar) {
91 fprintf(stderr, "mp->params too small\n");
99 fprintf(stderr, "mp->params too small\n");
102 snprintf(p, 1, "\n");
107 disassemble_map (vector pathvec, char * params, struct multipath * mpp)
112 int num_features = 0;
113 int num_hwhandler = 0;
117 int num_paths_args = 0;
119 struct pathgroup * pgp;
126 p += get_word(p, &mpp->features);
131 num_features = atoi(mpp->features);
133 for (i = 0; i < num_features; i++) {
134 p += get_word(p, &word);
139 if (merge_words(&mpp->features, word, 1)) {
149 p += get_word(p, &mpp->hwhandler);
154 num_hwhandler = atoi(mpp->hwhandler);
156 for (i = 0; i < num_hwhandler; i++) {
157 p += get_word(p, &word);
162 if (merge_words(&mpp->hwhandler, word, 1)) {
172 p += get_word(p, &word);
180 if (num_pg > 0 && !mpp->pg)
181 mpp->pg = vector_alloc();
188 p += get_word(p, &word);
193 mpp->nextpg = atoi(word);
196 for (i = 0; i < num_pg; i++) {
201 if (!mpp->selector) {
202 p += get_word(p, &mpp->selector);
210 p += get_word(p, &word);
215 num_pg_args = atoi(word);
217 if (merge_words(&mpp->selector, word, 1)) {
223 p += get_word(p, NULL);
224 p += get_word(p, NULL);
227 for (j = 0; j < num_pg_args; j++)
228 p += get_word(p, NULL);
233 pgp = alloc_pathgroup();
238 if (store_pathgroup(mpp->pg, pgp))
241 p += get_word(p, &word);
246 num_paths = atoi(word);
249 p += get_word(p, &word);
254 num_paths_args = atoi(word);
257 for (j = 0; j < num_paths; j++) {
259 p += get_word(p, &word);
265 pp = find_path_by_devt(pathvec, word);
273 strncpy(pp->dev_t, word, BLK_DEV_SIZE);
276 if (store_path(pathvec, pp))
282 if (store_path(pgp->paths, pp))
286 * Update wwid for multipaths which are not setup
287 * in the get_dm_mpvec() code path
289 if (!strlen(mpp->wwid))
290 strncpy(mpp->wwid, pp->wwid, WWID_SIZE);
293 * Update wwid for paths which may not have been
294 * active at the time the getuid callout was run
296 else if (!strlen(pp->wwid))
297 strncpy(pp->wwid, mpp->wwid, WWID_SIZE);
302 for (k = 0; k < num_paths_args; k++)
303 if (k == 0 && !strncmp(mpp->selector,
304 "round-robin", 11)) {
305 p += get_word(p, &word);
306 mpp->minio = atoi(word);
309 mpp->minio /= mpp->rr_weight;
314 p += get_word(p, NULL);
322 free_pgvec(mpp->pg, KEEP_PATHS);
327 disassemble_status (char * params, struct multipath * mpp)
332 int num_feature_args;
333 int num_hwhandler_args;
338 struct pathgroup * pgp;
345 p += get_word(p, &word);
350 num_feature_args = atoi(word);
353 for (i = 0; i < num_feature_args; i++) {
355 p += get_word(p, &word);
360 mpp->queuedio = atoi(word);
365 p += get_word(p, NULL);
370 p += get_word(p, &word);
375 num_hwhandler_args = atoi(word);
378 for (i = 0; i < num_hwhandler_args; i++)
379 p += get_word(p, NULL);
384 p += get_word(p, &word);
395 p += get_word(p, NULL);
397 if (VECTOR_SIZE(mpp->pg) < num_pg)
400 for (i = 0; i < num_pg; i++) {
401 pgp = VECTOR_SLOT(mpp->pg, i);
405 p += get_word(p, &word);
412 pgp->status = PGSTATE_DISABLED;
415 pgp->status = PGSTATE_ACTIVE;
418 pgp->status = PGSTATE_ENABLED;
421 pgp->status = PGSTATE_UNDEF;
429 p += get_word(p, NULL);
431 p += get_word(p, &word);
436 num_paths = atoi(word);
439 p += get_word(p, &word);
444 num_pg_args = atoi(word);
447 if (VECTOR_SIZE(pgp->paths) < num_paths)
450 for (j = 0; j < num_paths; j++) {
451 pp = VECTOR_SLOT(pgp->paths, j);
455 p += get_word(p, NULL);
460 p += get_word(p, &word);
467 pp->dmstate = PSTATE_FAILED;
470 pp->dmstate = PSTATE_ACTIVE;
479 p += get_word(p, &word);
484 pp->failcount = atoi(word);
490 for (k = 0; k < num_pg_args; k++)
491 p += get_word(p, NULL);