3 * (C) Copyright 2008 Hewlett-Packard Development Company, L.P
5 * This file is released under the GPL
9 * Prioritizer for device mapper multipath, where specific paths and the
10 * corresponding priority values are provided as arguments.
12 * This prioritizer assigns the priority value provided in the configuration
13 * file based on the comparison made between the specified paths and the path
14 * instance for which this is called.
15 * Paths can be specified as a regular expression of devname of the path or
16 * as hbtl information of the path.
19 * prio "weightedpath hbtl 1:.:.:. 2 4:.:.:. 4"
20 * prio "weightedpath devname sda 10 sde 20"
22 * Returns zero as the default priority.
29 #include "weightedpath.h"
35 #include "structs_vec.h"
38 char *get_next_string(char **temp, char *split_char)
41 token = strsep(temp, split_char);
42 while (token != NULL && !strcmp(token, ""))
43 token = strsep(temp, split_char);
49 if ((p - str) >= (len - 1)) { \
50 condlog(0, "%s: %s - buffer size too small", pp->dev, pp->prio.name); \
56 build_serial_path(struct path *pp, char *str, int len)
60 p += snprint_path_serial(p, str + len - p, pp);
66 build_wwn_path(struct path *pp, char *str, int len)
70 p += snprint_host_wwnn(p, str + len - p, pp);
72 p += snprintf(p, str + len - p, ":");
74 p += snprint_host_wwpn(p, str + len - p, pp);
76 p += snprintf(p, str + len - p, ":");
78 p += snprint_tgt_wwnn(p, str + len - p, pp);
80 p += snprintf(p, str + len - p, ":");
82 p += snprint_tgt_wwpn(p, str + len - p, pp);
87 /* main priority routine */
88 int prio_path_weight(struct path *pp, char *prio_args)
90 char path[FILE_NAME_SIZE];
92 char *temp, *regex, *prio;
93 char split_char[] = " \t";
94 int priority = DEFAULT_PRIORITY, path_found = 0;
97 /* Return default priority if there is no argument */
101 arg = temp = STRDUP(prio_args);
103 regex = get_next_string(&temp, split_char);
105 /* Return default priority if the argument is not parseable */
111 if (!strcmp(regex, HBTL)) {
112 sprintf(path, "%d:%d:%d:%d", pp->sg_id.host_no,
113 pp->sg_id.channel, pp->sg_id.scsi_id, pp->sg_id.lun);
114 } else if (!strcmp(regex, DEV_NAME)) {
115 strcpy(path, pp->dev);
116 } else if (!strcmp(regex, SERIAL)) {
117 if (build_serial_path(pp, path, FILE_NAME_SIZE) != 0) {
121 } else if (!strcmp(regex, WWN)) {
122 if (build_wwn_path(pp, path, FILE_NAME_SIZE) != 0) {
127 condlog(0, "%s: %s - Invalid arguments", pp->dev,
133 while (!path_found) {
136 if (!(regex = get_next_string(&temp, split_char)))
138 if (!(prio = get_next_string(&temp, split_char)))
141 if (!regcomp(&pathe, regex, REG_EXTENDED|REG_NOSUB)) {
142 if (!regexec(&pathe, path, 0, NULL, 0)) {
144 priority = atoi(prio);
154 int getprio(struct path *pp, char *args)
156 return prio_path_weight(pp, args);