]>
Commit | Line | Data |
---|---|---|
82094b55 AF |
1 | From: Mike Christie <michaelc@cs.wisc.edu> |
2 | Date: Wed, 13 May 2009 17:57:40 -0500 | |
3 | Subject: libiscsi: handle param allocation failures | |
4 | References: bnc#472432 | |
5 | X-Git: 5700b1af93388544843a453e3c68f8f928bd1e88 | |
6 | ||
7 | If we could not allocate the initiator name or some other id like | |
8 | the hwaddress or netdev, then userspace could deal with the failure | |
9 | by just running in a degraded mode. | |
10 | ||
11 | Now we want to be able to switch values for the params and we | |
12 | want some feedback, so this patch will check if a string like | |
13 | the initiatorname could not be allocated and return an error. | |
14 | ||
15 | Signed-off-by: Mike Christie <michaelc@cs.wisc.edu> | |
16 | Signed-off-by: James Bottomley <James.Bottomley@HansenPartnership.com> | |
17 | Signed-off-by: Hannes Reinecke <hare@suse.de> | |
18 | --- | |
19 | drivers/scsi/libiscsi.c | 108 ++++++++++++++-------------------------------- | |
20 | 1 files changed, 33 insertions(+), 75 deletions(-) | |
21 | ||
22 | diff --git a/drivers/scsi/libiscsi.c b/drivers/scsi/libiscsi.c | |
23 | index cc8d144..e7624db 100644 | |
24 | --- a/drivers/scsi/libiscsi.c | |
25 | +++ b/drivers/scsi/libiscsi.c | |
26 | @@ -2567,6 +2567,23 @@ int iscsi_conn_bind(struct iscsi_cls_session *cls_session, | |
27 | } | |
28 | EXPORT_SYMBOL_GPL(iscsi_conn_bind); | |
29 | ||
30 | +static int iscsi_switch_str_param(char **param, char *new_val_buf) | |
31 | +{ | |
32 | + char *new_val; | |
33 | + | |
34 | + if (*param) { | |
35 | + if (!strcmp(*param, new_val_buf)) | |
36 | + return 0; | |
37 | + } | |
38 | + | |
39 | + new_val = kstrdup(new_val_buf, GFP_NOIO); | |
40 | + if (!new_val) | |
41 | + return -ENOMEM; | |
42 | + | |
43 | + kfree(*param); | |
44 | + *param = new_val; | |
45 | + return 0; | |
46 | +} | |
47 | ||
48 | int iscsi_set_param(struct iscsi_cls_conn *cls_conn, | |
49 | enum iscsi_param param, char *buf, int buflen) | |
50 | @@ -2639,38 +2656,15 @@ int iscsi_set_param(struct iscsi_cls_conn *cls_conn, | |
51 | sscanf(buf, "%u", &conn->exp_statsn); | |
52 | break; | |
53 | case ISCSI_PARAM_USERNAME: | |
54 | - kfree(session->username); | |
55 | - session->username = kstrdup(buf, GFP_KERNEL); | |
56 | - if (!session->username) | |
57 | - return -ENOMEM; | |
58 | - break; | |
59 | + return iscsi_switch_str_param(&session->username, buf); | |
60 | case ISCSI_PARAM_USERNAME_IN: | |
61 | - kfree(session->username_in); | |
62 | - session->username_in = kstrdup(buf, GFP_KERNEL); | |
63 | - if (!session->username_in) | |
64 | - return -ENOMEM; | |
65 | - break; | |
66 | + return iscsi_switch_str_param(&session->username_in, buf); | |
67 | case ISCSI_PARAM_PASSWORD: | |
68 | - kfree(session->password); | |
69 | - session->password = kstrdup(buf, GFP_KERNEL); | |
70 | - if (!session->password) | |
71 | - return -ENOMEM; | |
72 | - break; | |
73 | + return iscsi_switch_str_param(&session->password, buf); | |
74 | case ISCSI_PARAM_PASSWORD_IN: | |
75 | - kfree(session->password_in); | |
76 | - session->password_in = kstrdup(buf, GFP_KERNEL); | |
77 | - if (!session->password_in) | |
78 | - return -ENOMEM; | |
79 | - break; | |
80 | + return iscsi_switch_str_param(&session->password_in, buf); | |
81 | case ISCSI_PARAM_TARGET_NAME: | |
82 | - /* this should not change between logins */ | |
83 | - if (session->targetname) | |
84 | - break; | |
85 | - | |
86 | - session->targetname = kstrdup(buf, GFP_KERNEL); | |
87 | - if (!session->targetname) | |
88 | - return -ENOMEM; | |
89 | - break; | |
90 | + return iscsi_switch_str_param(&session->targetname, buf); | |
91 | case ISCSI_PARAM_TPGT: | |
92 | sscanf(buf, "%d", &session->tpgt); | |
93 | break; | |
94 | @@ -2678,25 +2672,11 @@ int iscsi_set_param(struct iscsi_cls_conn *cls_conn, | |
95 | sscanf(buf, "%d", &conn->persistent_port); | |
96 | break; | |
97 | case ISCSI_PARAM_PERSISTENT_ADDRESS: | |
98 | - /* | |
99 | - * this is the address returned in discovery so it should | |
100 | - * not change between logins. | |
101 | - */ | |
102 | - if (conn->persistent_address) | |
103 | - break; | |
104 | - | |
105 | - conn->persistent_address = kstrdup(buf, GFP_KERNEL); | |
106 | - if (!conn->persistent_address) | |
107 | - return -ENOMEM; | |
108 | - break; | |
109 | + return iscsi_switch_str_param(&conn->persistent_address, buf); | |
110 | case ISCSI_PARAM_IFACE_NAME: | |
111 | - if (!session->ifacename) | |
112 | - session->ifacename = kstrdup(buf, GFP_KERNEL); | |
113 | - break; | |
114 | + return iscsi_switch_str_param(&session->ifacename, buf); | |
115 | case ISCSI_PARAM_INITIATOR_NAME: | |
116 | - if (!session->initiatorname) | |
117 | - session->initiatorname = kstrdup(buf, GFP_KERNEL); | |
118 | - break; | |
119 | + return iscsi_switch_str_param(&session->initiatorname, buf); | |
120 | default: | |
121 | return -ENOSYS; | |
122 | } | |
123 | @@ -2767,10 +2747,7 @@ int iscsi_session_get_param(struct iscsi_cls_session *cls_session, | |
124 | len = sprintf(buf, "%s\n", session->ifacename); | |
125 | break; | |
126 | case ISCSI_PARAM_INITIATOR_NAME: | |
127 | - if (!session->initiatorname) | |
128 | - len = sprintf(buf, "%s\n", "unknown"); | |
129 | - else | |
130 | - len = sprintf(buf, "%s\n", session->initiatorname); | |
131 | + len = sprintf(buf, "%s\n", session->initiatorname); | |
132 | break; | |
133 | default: | |
134 | return -ENOSYS; | |
135 | @@ -2836,29 +2813,16 @@ int iscsi_host_get_param(struct Scsi_Host *shost, enum iscsi_host_param param, | |
136 | ||
137 | switch (param) { | |
138 | case ISCSI_HOST_PARAM_NETDEV_NAME: | |
139 | - if (!ihost->netdev) | |
140 | - len = sprintf(buf, "%s\n", "default"); | |
141 | - else | |
142 | - len = sprintf(buf, "%s\n", ihost->netdev); | |
143 | + len = sprintf(buf, "%s\n", ihost->netdev); | |
144 | break; | |
145 | case ISCSI_HOST_PARAM_HWADDRESS: | |
146 | - if (!ihost->hwaddress) | |
147 | - len = sprintf(buf, "%s\n", "default"); | |
148 | - else | |
149 | - len = sprintf(buf, "%s\n", ihost->hwaddress); | |
150 | + len = sprintf(buf, "%s\n", ihost->hwaddress); | |
151 | break; | |
152 | case ISCSI_HOST_PARAM_INITIATOR_NAME: | |
153 | - if (!ihost->initiatorname) | |
154 | - len = sprintf(buf, "%s\n", "unknown"); | |
155 | - else | |
156 | - len = sprintf(buf, "%s\n", ihost->initiatorname); | |
157 | + len = sprintf(buf, "%s\n", ihost->initiatorname); | |
158 | break; | |
159 | case ISCSI_HOST_PARAM_IPADDRESS: | |
160 | - if (!strlen(ihost->local_address)) | |
161 | - len = sprintf(buf, "%s\n", "unknown"); | |
162 | - else | |
163 | - len = sprintf(buf, "%s\n", | |
164 | - ihost->local_address); | |
165 | + len = sprintf(buf, "%s\n", ihost->local_address); | |
166 | break; | |
167 | default: | |
168 | return -ENOSYS; | |
169 | @@ -2875,17 +2839,11 @@ int iscsi_host_set_param(struct Scsi_Host *shost, enum iscsi_host_param param, | |
170 | ||
171 | switch (param) { | |
172 | case ISCSI_HOST_PARAM_NETDEV_NAME: | |
173 | - if (!ihost->netdev) | |
174 | - ihost->netdev = kstrdup(buf, GFP_KERNEL); | |
175 | - break; | |
176 | + return iscsi_switch_str_param(&ihost->netdev, buf); | |
177 | case ISCSI_HOST_PARAM_HWADDRESS: | |
178 | - if (!ihost->hwaddress) | |
179 | - ihost->hwaddress = kstrdup(buf, GFP_KERNEL); | |
180 | - break; | |
181 | + return iscsi_switch_str_param(&ihost->hwaddress, buf); | |
182 | case ISCSI_HOST_PARAM_INITIATOR_NAME: | |
183 | - if (!ihost->initiatorname) | |
184 | - ihost->initiatorname = kstrdup(buf, GFP_KERNEL); | |
185 | - break; | |
186 | + return iscsi_switch_str_param(&ihost->initiatorname, buf); | |
187 | default: | |
188 | return -ENOSYS; | |
189 | } | |
190 | -- | |
191 | 1.6.0.2 | |
192 |