1*c3a558e7SSue Gleeson /*
2*c3a558e7SSue Gleeson * CDDL HEADER START
3*c3a558e7SSue Gleeson *
4*c3a558e7SSue Gleeson * The contents of this file are subject to the terms of the
5*c3a558e7SSue Gleeson * Common Development and Distribution License (the "License").
6*c3a558e7SSue Gleeson * You may not use this file except in compliance with the License.
7*c3a558e7SSue Gleeson *
8*c3a558e7SSue Gleeson * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9*c3a558e7SSue Gleeson * or http://www.opensolaris.org/os/licensing.
10*c3a558e7SSue Gleeson * See the License for the specific language governing permissions
11*c3a558e7SSue Gleeson * and limitations under the License.
12*c3a558e7SSue Gleeson *
13*c3a558e7SSue Gleeson * When distributing Covered Code, include this CDDL HEADER in each
14*c3a558e7SSue Gleeson * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15*c3a558e7SSue Gleeson * If applicable, add the following below this CDDL HEADER, with the
16*c3a558e7SSue Gleeson * fields enclosed by brackets "[]" replaced with your own identifying
17*c3a558e7SSue Gleeson * information: Portions Copyright [yyyy] [name of copyright owner]
18*c3a558e7SSue Gleeson *
19*c3a558e7SSue Gleeson * CDDL HEADER END
20*c3a558e7SSue Gleeson */
21*c3a558e7SSue Gleeson /*
22*c3a558e7SSue Gleeson * Copyright (c) 2010, Oracle and/or its affiliates. All rights reserved.
23*c3a558e7SSue Gleeson */
24*c3a558e7SSue Gleeson
25*c3a558e7SSue Gleeson #include <sys/types.h>
26*c3a558e7SSue Gleeson #include <sys/stat.h>
27*c3a558e7SSue Gleeson #include <limits.h>
28*c3a558e7SSue Gleeson #include <ctype.h>
29*c3a558e7SSue Gleeson #include <fcntl.h>
30*c3a558e7SSue Gleeson #include <errno.h>
31*c3a558e7SSue Gleeson #include <unistd.h>
32*c3a558e7SSue Gleeson #include <strings.h>
33*c3a558e7SSue Gleeson #include <libintl.h>
34*c3a558e7SSue Gleeson #include <libscf.h>
35*c3a558e7SSue Gleeson #include <libnvpair.h>
36*c3a558e7SSue Gleeson
37*c3a558e7SSue Gleeson #include <libstmf.h>
38*c3a558e7SSue Gleeson #include <libsrpt.h>
39*c3a558e7SSue Gleeson
40*c3a558e7SSue Gleeson #include "srpt_common.h"
41*c3a558e7SSue Gleeson
42*c3a558e7SSue Gleeson #define SRPT_PROV_NAME "srpt"
43*c3a558e7SSue Gleeson
44*c3a558e7SSue Gleeson /*
45*c3a558e7SSue Gleeson * Function: srpt_GetConfig()
46*c3a558e7SSue Gleeson *
47*c3a558e7SSue Gleeson * Parameters:
48*c3a558e7SSue Gleeson * cfg Current SRPT configuration in nvlist form
49*c3a558e7SSue Gleeson * token Configuration generation number. Use this token
50*c3a558e7SSue Gleeson * if updating the configuration with srpt_SetConfig.
51*c3a558e7SSue Gleeson *
52*c3a558e7SSue Gleeson * Return Values:
53*c3a558e7SSue Gleeson * 0 Success
54*c3a558e7SSue Gleeson * ENOMEM Could not allocate resources
55*c3a558e7SSue Gleeson * EINVAL Invalid parameter
56*c3a558e7SSue Gleeson */
57*c3a558e7SSue Gleeson int
srpt_GetConfig(nvlist_t ** cfg,uint64_t * token)58*c3a558e7SSue Gleeson srpt_GetConfig(nvlist_t **cfg, uint64_t *token)
59*c3a558e7SSue Gleeson {
60*c3a558e7SSue Gleeson int ret = 0;
61*c3a558e7SSue Gleeson nvlist_t *cfg_nv = NULL;
62*c3a558e7SSue Gleeson uint64_t stmf_token = 0;
63*c3a558e7SSue Gleeson nvlist_t *hcanv = NULL;
64*c3a558e7SSue Gleeson
65*c3a558e7SSue Gleeson if (!cfg) {
66*c3a558e7SSue Gleeson return (EINVAL);
67*c3a558e7SSue Gleeson }
68*c3a558e7SSue Gleeson
69*c3a558e7SSue Gleeson *cfg = NULL;
70*c3a558e7SSue Gleeson
71*c3a558e7SSue Gleeson ret = stmfGetProviderDataProt(SRPT_PROV_NAME, &cfg_nv,
72*c3a558e7SSue Gleeson STMF_PORT_PROVIDER_TYPE, &stmf_token);
73*c3a558e7SSue Gleeson
74*c3a558e7SSue Gleeson if (ret == STMF_STATUS_SUCCESS) {
75*c3a558e7SSue Gleeson ret = 0;
76*c3a558e7SSue Gleeson } else if (ret == STMF_ERROR_NOT_FOUND) {
77*c3a558e7SSue Gleeson /* Not initialized yet */
78*c3a558e7SSue Gleeson ret = nvlist_alloc(&cfg_nv, NV_UNIQUE_NAME, 0);
79*c3a558e7SSue Gleeson if (ret != 0) {
80*c3a558e7SSue Gleeson return (ret);
81*c3a558e7SSue Gleeson }
82*c3a558e7SSue Gleeson /* create the HCA list */
83*c3a558e7SSue Gleeson ret = nvlist_alloc(&hcanv, NV_UNIQUE_NAME, 0);
84*c3a558e7SSue Gleeson if (ret == 0) {
85*c3a558e7SSue Gleeson ret = nvlist_add_nvlist(cfg_nv, SRPT_PROP_HCALIST,
86*c3a558e7SSue Gleeson hcanv);
87*c3a558e7SSue Gleeson if (ret != 0) {
88*c3a558e7SSue Gleeson nvlist_free(hcanv);
89*c3a558e7SSue Gleeson }
90*c3a558e7SSue Gleeson }
91*c3a558e7SSue Gleeson if (ret != 0) {
92*c3a558e7SSue Gleeson nvlist_free(cfg_nv);
93*c3a558e7SSue Gleeson cfg_nv = NULL;
94*c3a558e7SSue Gleeson }
95*c3a558e7SSue Gleeson } else if (ret == STMF_ERROR_NOMEM) {
96*c3a558e7SSue Gleeson ret = ENOMEM;
97*c3a558e7SSue Gleeson } else {
98*c3a558e7SSue Gleeson ret = EINVAL;
99*c3a558e7SSue Gleeson }
100*c3a558e7SSue Gleeson
101*c3a558e7SSue Gleeson *cfg = cfg_nv;
102*c3a558e7SSue Gleeson *token = stmf_token;
103*c3a558e7SSue Gleeson
104*c3a558e7SSue Gleeson return (ret);
105*c3a558e7SSue Gleeson }
106*c3a558e7SSue Gleeson
107*c3a558e7SSue Gleeson /*
108*c3a558e7SSue Gleeson * Function: srpt_SetConfig()
109*c3a558e7SSue Gleeson *
110*c3a558e7SSue Gleeson * Parameters:
111*c3a558e7SSue Gleeson * cfg SRPT configuration in nvlist form
112*c3a558e7SSue Gleeson * token Configuration generation number from srpt_GetConfig.
113*c3a558e7SSue Gleeson * Use this token to ensure the configuration hasn't been
114*c3a558e7SSue Gleeson * updated by another user since the time it was fetched.
115*c3a558e7SSue Gleeson *
116*c3a558e7SSue Gleeson * Return Values:
117*c3a558e7SSue Gleeson * 0 Success
118*c3a558e7SSue Gleeson * ENOMEM Could not allocate resources
119*c3a558e7SSue Gleeson * EINVAL Invalid parameter
120*c3a558e7SSue Gleeson * ECANCELED Configuration updated by another user
121*c3a558e7SSue Gleeson */
122*c3a558e7SSue Gleeson int
srpt_SetConfig(nvlist_t * cfg,uint64_t token)123*c3a558e7SSue Gleeson srpt_SetConfig(nvlist_t *cfg, uint64_t token)
124*c3a558e7SSue Gleeson {
125*c3a558e7SSue Gleeson int ret = 0;
126*c3a558e7SSue Gleeson
127*c3a558e7SSue Gleeson ret = stmfSetProviderDataProt(SRPT_PROV_NAME, cfg,
128*c3a558e7SSue Gleeson STMF_PORT_PROVIDER_TYPE, &token);
129*c3a558e7SSue Gleeson
130*c3a558e7SSue Gleeson if (ret == STMF_STATUS_SUCCESS) {
131*c3a558e7SSue Gleeson ret = 0;
132*c3a558e7SSue Gleeson } else if (ret == STMF_ERROR_NOMEM) {
133*c3a558e7SSue Gleeson ret = ENOMEM;
134*c3a558e7SSue Gleeson } else if (ret == STMF_ERROR_PROV_DATA_STALE) {
135*c3a558e7SSue Gleeson ret = ECANCELED; /* could be a better errno */
136*c3a558e7SSue Gleeson } else {
137*c3a558e7SSue Gleeson ret = EINVAL;
138*c3a558e7SSue Gleeson }
139*c3a558e7SSue Gleeson
140*c3a558e7SSue Gleeson return (ret);
141*c3a558e7SSue Gleeson }
142*c3a558e7SSue Gleeson
143*c3a558e7SSue Gleeson /*
144*c3a558e7SSue Gleeson * Function: srpt_GetDefaultState()
145*c3a558e7SSue Gleeson *
146*c3a558e7SSue Gleeson * Parameters:
147*c3a558e7SSue Gleeson * enabled If B_TRUE, indicates that targets will be created for all
148*c3a558e7SSue Gleeson * discovered HCAs that have not been specifically disabled.
149*c3a558e7SSue Gleeson * If B_FALSE, targets will not be created unless the HCA has
150*c3a558e7SSue Gleeson * been specifically enabled. See also srpt_SetDefaultState().
151*c3a558e7SSue Gleeson *
152*c3a558e7SSue Gleeson * Return Values:
153*c3a558e7SSue Gleeson * 0 Success
154*c3a558e7SSue Gleeson * ENOMEM Could not allocate resources
155*c3a558e7SSue Gleeson * EINVAL Invalid parameter
156*c3a558e7SSue Gleeson */
157*c3a558e7SSue Gleeson int
srpt_GetDefaultState(boolean_t * enabled)158*c3a558e7SSue Gleeson srpt_GetDefaultState(boolean_t *enabled)
159*c3a558e7SSue Gleeson {
160*c3a558e7SSue Gleeson int ret;
161*c3a558e7SSue Gleeson nvlist_t *cfgnv;
162*c3a558e7SSue Gleeson uint64_t token;
163*c3a558e7SSue Gleeson boolean_t val = B_TRUE;
164*c3a558e7SSue Gleeson
165*c3a558e7SSue Gleeson if (enabled == NULL) {
166*c3a558e7SSue Gleeson return (EINVAL);
167*c3a558e7SSue Gleeson }
168*c3a558e7SSue Gleeson
169*c3a558e7SSue Gleeson ret = srpt_GetConfig(&cfgnv, &token);
170*c3a558e7SSue Gleeson if (ret != 0) {
171*c3a558e7SSue Gleeson return (ret);
172*c3a558e7SSue Gleeson }
173*c3a558e7SSue Gleeson
174*c3a558e7SSue Gleeson if (cfgnv != NULL) {
175*c3a558e7SSue Gleeson ret = nvlist_lookup_boolean_value(cfgnv,
176*c3a558e7SSue Gleeson SRPT_PROP_DEFAULT_ENABLED, &val);
177*c3a558e7SSue Gleeson
178*c3a558e7SSue Gleeson if (ret == ENOENT) {
179*c3a558e7SSue Gleeson ret = 0;
180*c3a558e7SSue Gleeson }
181*c3a558e7SSue Gleeson }
182*c3a558e7SSue Gleeson
183*c3a558e7SSue Gleeson *enabled = val;
184*c3a558e7SSue Gleeson return (ret);
185*c3a558e7SSue Gleeson }
186*c3a558e7SSue Gleeson
187*c3a558e7SSue Gleeson /*
188*c3a558e7SSue Gleeson * Function: srpt_SetDefaultState()
189*c3a558e7SSue Gleeson *
190*c3a558e7SSue Gleeson * Parameters:
191*c3a558e7SSue Gleeson * enabled If B_TRUE, indicates that targets will be created for all
192*c3a558e7SSue Gleeson * discovered HCAs that have not been specifically disabled.
193*c3a558e7SSue Gleeson * If B_FALSE, targets will not be created unless the HCA has
194*c3a558e7SSue Gleeson * been specifically enabled. See also srpt_SetDefaultState().
195*c3a558e7SSue Gleeson *
196*c3a558e7SSue Gleeson * Return Values:
197*c3a558e7SSue Gleeson * 0 Success
198*c3a558e7SSue Gleeson * ENOMEM Could not allocate resources
199*c3a558e7SSue Gleeson * EINVAL Invalid parameter
200*c3a558e7SSue Gleeson */
201*c3a558e7SSue Gleeson int
srpt_SetDefaultState(boolean_t enabled)202*c3a558e7SSue Gleeson srpt_SetDefaultState(boolean_t enabled)
203*c3a558e7SSue Gleeson {
204*c3a558e7SSue Gleeson int ret;
205*c3a558e7SSue Gleeson nvlist_t *cfgnv;
206*c3a558e7SSue Gleeson uint64_t token;
207*c3a558e7SSue Gleeson
208*c3a558e7SSue Gleeson ret = srpt_GetConfig(&cfgnv, &token);
209*c3a558e7SSue Gleeson if (ret != 0) {
210*c3a558e7SSue Gleeson return (ret);
211*c3a558e7SSue Gleeson }
212*c3a558e7SSue Gleeson
213*c3a558e7SSue Gleeson if (cfgnv == NULL) {
214*c3a558e7SSue Gleeson ret = nvlist_alloc(&cfgnv, NV_UNIQUE_NAME, 0);
215*c3a558e7SSue Gleeson if (ret != 0) {
216*c3a558e7SSue Gleeson return (ret);
217*c3a558e7SSue Gleeson }
218*c3a558e7SSue Gleeson }
219*c3a558e7SSue Gleeson
220*c3a558e7SSue Gleeson ret = nvlist_add_boolean_value(cfgnv, SRPT_PROP_DEFAULT_ENABLED,
221*c3a558e7SSue Gleeson enabled);
222*c3a558e7SSue Gleeson
223*c3a558e7SSue Gleeson if (ret == 0) {
224*c3a558e7SSue Gleeson ret = srpt_SetConfig(cfgnv, token);
225*c3a558e7SSue Gleeson }
226*c3a558e7SSue Gleeson
227*c3a558e7SSue Gleeson nvlist_free(cfgnv);
228*c3a558e7SSue Gleeson
229*c3a558e7SSue Gleeson return (ret);
230*c3a558e7SSue Gleeson }
231*c3a558e7SSue Gleeson
232*c3a558e7SSue Gleeson /*
233*c3a558e7SSue Gleeson * Function: srpt_SetTargetState()
234*c3a558e7SSue Gleeson *
235*c3a558e7SSue Gleeson * Parameters:
236*c3a558e7SSue Gleeson * hca_guid HCA GUID. See description of srpt_NormalizeGuid
237*c3a558e7SSue Gleeson * enabled If B_TRUE, indicates that a target will be created for
238*c3a558e7SSue Gleeson * this HCA when the SRPT SMF service is enabled. If B_FALSE,
239*c3a558e7SSue Gleeson * a target will not be created
240*c3a558e7SSue Gleeson *
241*c3a558e7SSue Gleeson * Return Values:
242*c3a558e7SSue Gleeson * 0 Success
243*c3a558e7SSue Gleeson * ENOMEM Could not allocate resources
244*c3a558e7SSue Gleeson * EINVAL Invalid parameter
245*c3a558e7SSue Gleeson */
246*c3a558e7SSue Gleeson int
srpt_SetTargetState(char * hca_guid,boolean_t enabled)247*c3a558e7SSue Gleeson srpt_SetTargetState(char *hca_guid, boolean_t enabled)
248*c3a558e7SSue Gleeson {
249*c3a558e7SSue Gleeson int ret;
250*c3a558e7SSue Gleeson nvlist_t *cfgnv;
251*c3a558e7SSue Gleeson uint64_t token;
252*c3a558e7SSue Gleeson nvlist_t *hcalist;
253*c3a558e7SSue Gleeson nvlist_t *hcanv;
254*c3a558e7SSue Gleeson char guid[32];
255*c3a558e7SSue Gleeson uint64_t hcaguid;
256*c3a558e7SSue Gleeson
257*c3a558e7SSue Gleeson if (hca_guid == NULL) {
258*c3a558e7SSue Gleeson return (EINVAL);
259*c3a558e7SSue Gleeson }
260*c3a558e7SSue Gleeson
261*c3a558e7SSue Gleeson ret = srpt_NormalizeGuid(hca_guid, guid, sizeof (guid), &hcaguid);
262*c3a558e7SSue Gleeson if (ret != 0) {
263*c3a558e7SSue Gleeson return (ret);
264*c3a558e7SSue Gleeson }
265*c3a558e7SSue Gleeson
266*c3a558e7SSue Gleeson ret = srpt_GetConfig(&cfgnv, &token);
267*c3a558e7SSue Gleeson if (ret != 0) {
268*c3a558e7SSue Gleeson return (ret);
269*c3a558e7SSue Gleeson }
270*c3a558e7SSue Gleeson
271*c3a558e7SSue Gleeson /* get the list of HCAs */
272*c3a558e7SSue Gleeson ret = nvlist_lookup_nvlist(cfgnv, SRPT_PROP_HCALIST, &hcalist);
273*c3a558e7SSue Gleeson if (ret != 0) {
274*c3a558e7SSue Gleeson nvlist_free(cfgnv);
275*c3a558e7SSue Gleeson return (ret);
276*c3a558e7SSue Gleeson }
277*c3a558e7SSue Gleeson
278*c3a558e7SSue Gleeson ret = nvlist_lookup_nvlist(hcalist, guid, &hcanv);
279*c3a558e7SSue Gleeson if (ret == ENOENT) {
280*c3a558e7SSue Gleeson /* no entry yet */
281*c3a558e7SSue Gleeson ret = nvlist_alloc(&hcanv, NV_UNIQUE_NAME, 0);
282*c3a558e7SSue Gleeson if (ret == 0) {
283*c3a558e7SSue Gleeson ret = nvlist_add_uint64(hcanv, SRPT_PROP_GUID, hcaguid);
284*c3a558e7SSue Gleeson }
285*c3a558e7SSue Gleeson }
286*c3a558e7SSue Gleeson
287*c3a558e7SSue Gleeson if (ret == 0) {
288*c3a558e7SSue Gleeson ret = nvlist_add_boolean_value(hcanv, SRPT_PROP_ENABLED,
289*c3a558e7SSue Gleeson enabled);
290*c3a558e7SSue Gleeson }
291*c3a558e7SSue Gleeson
292*c3a558e7SSue Gleeson if (ret == 0) {
293*c3a558e7SSue Gleeson ret = nvlist_add_nvlist(hcalist, guid, hcanv);
294*c3a558e7SSue Gleeson }
295*c3a558e7SSue Gleeson
296*c3a558e7SSue Gleeson if (ret == 0) {
297*c3a558e7SSue Gleeson ret = srpt_SetConfig(cfgnv, token);
298*c3a558e7SSue Gleeson }
299*c3a558e7SSue Gleeson
300*c3a558e7SSue Gleeson nvlist_free(cfgnv);
301*c3a558e7SSue Gleeson
302*c3a558e7SSue Gleeson return (ret);
303*c3a558e7SSue Gleeson }
304*c3a558e7SSue Gleeson
305*c3a558e7SSue Gleeson /*
306*c3a558e7SSue Gleeson * Function: srpt_GetTargetState()
307*c3a558e7SSue Gleeson *
308*c3a558e7SSue Gleeson * Parameters:
309*c3a558e7SSue Gleeson * hca_guid HCA GUID. See description of srpt_NormalizeGuid
310*c3a558e7SSue Gleeson * enabled If B_TRUE, indicates that a target will be created for
311*c3a558e7SSue Gleeson * this HCA when the SRPT SMF service is enabled. If B_FALSE,
312*c3a558e7SSue Gleeson * a target will not be created
313*c3a558e7SSue Gleeson *
314*c3a558e7SSue Gleeson * Return Values:
315*c3a558e7SSue Gleeson * 0 Success
316*c3a558e7SSue Gleeson * ENOMEM Could not allocate resources
317*c3a558e7SSue Gleeson * EINVAL Invalid parameter
318*c3a558e7SSue Gleeson */
319*c3a558e7SSue Gleeson int
srpt_GetTargetState(char * hca_guid,boolean_t * enabled)320*c3a558e7SSue Gleeson srpt_GetTargetState(char *hca_guid, boolean_t *enabled)
321*c3a558e7SSue Gleeson {
322*c3a558e7SSue Gleeson int ret;
323*c3a558e7SSue Gleeson nvlist_t *cfgnv;
324*c3a558e7SSue Gleeson uint64_t token;
325*c3a558e7SSue Gleeson nvlist_t *hcalist;
326*c3a558e7SSue Gleeson nvlist_t *hcanv;
327*c3a558e7SSue Gleeson boolean_t defaultState = B_TRUE;
328*c3a558e7SSue Gleeson char guid[32];
329*c3a558e7SSue Gleeson
330*c3a558e7SSue Gleeson if (hca_guid == NULL) {
331*c3a558e7SSue Gleeson return (EINVAL);
332*c3a558e7SSue Gleeson }
333*c3a558e7SSue Gleeson
334*c3a558e7SSue Gleeson ret = srpt_NormalizeGuid(hca_guid, guid, sizeof (guid), NULL);
335*c3a558e7SSue Gleeson if (ret != 0) {
336*c3a558e7SSue Gleeson return (ret);
337*c3a558e7SSue Gleeson }
338*c3a558e7SSue Gleeson
339*c3a558e7SSue Gleeson ret = srpt_GetConfig(&cfgnv, &token);
340*c3a558e7SSue Gleeson if (ret != 0) {
341*c3a558e7SSue Gleeson return (ret);
342*c3a558e7SSue Gleeson }
343*c3a558e7SSue Gleeson
344*c3a558e7SSue Gleeson /* get the list of HCAs */
345*c3a558e7SSue Gleeson ret = nvlist_lookup_nvlist(cfgnv, SRPT_PROP_HCALIST, &hcalist);
346*c3a558e7SSue Gleeson if (ret != 0) {
347*c3a558e7SSue Gleeson nvlist_free(cfgnv);
348*c3a558e7SSue Gleeson return (ret);
349*c3a558e7SSue Gleeson }
350*c3a558e7SSue Gleeson
351*c3a558e7SSue Gleeson /*
352*c3a558e7SSue Gleeson * Find the default, for the likely case that this HCA isn't
353*c3a558e7SSue Gleeson * explicitly set.
354*c3a558e7SSue Gleeson */
355*c3a558e7SSue Gleeson (void) nvlist_lookup_boolean_value(cfgnv, SRPT_PROP_DEFAULT_ENABLED,
356*c3a558e7SSue Gleeson &defaultState);
357*c3a558e7SSue Gleeson
358*c3a558e7SSue Gleeson ret = nvlist_lookup_nvlist(hcalist, guid, &hcanv);
359*c3a558e7SSue Gleeson if (ret == 0) {
360*c3a558e7SSue Gleeson ret = nvlist_lookup_boolean_value(hcanv, SRPT_PROP_ENABLED,
361*c3a558e7SSue Gleeson enabled);
362*c3a558e7SSue Gleeson }
363*c3a558e7SSue Gleeson
364*c3a558e7SSue Gleeson if (ret == ENOENT) {
365*c3a558e7SSue Gleeson /* not explicitly set, use the default */
366*c3a558e7SSue Gleeson *enabled = defaultState;
367*c3a558e7SSue Gleeson ret = 0;
368*c3a558e7SSue Gleeson }
369*c3a558e7SSue Gleeson
370*c3a558e7SSue Gleeson nvlist_free(cfgnv);
371*c3a558e7SSue Gleeson
372*c3a558e7SSue Gleeson return (ret);
373*c3a558e7SSue Gleeson
374*c3a558e7SSue Gleeson }
375*c3a558e7SSue Gleeson
376*c3a558e7SSue Gleeson /*
377*c3a558e7SSue Gleeson * Function: srpt_ResetTarget()
378*c3a558e7SSue Gleeson *
379*c3a558e7SSue Gleeson * Clears the HCA-specific configuration. Target creation will revert to
380*c3a558e7SSue Gleeson * the default.
381*c3a558e7SSue Gleeson *
382*c3a558e7SSue Gleeson * Parameters:
383*c3a558e7SSue Gleeson * hca_guid HCA GUID. See description of srpt_NormalizeGuid
384*c3a558e7SSue Gleeson *
385*c3a558e7SSue Gleeson * Return Values:
386*c3a558e7SSue Gleeson * 0 Success
387*c3a558e7SSue Gleeson * ENOMEM Could not allocate resources
388*c3a558e7SSue Gleeson * EINVAL Invalid parameter
389*c3a558e7SSue Gleeson */
390*c3a558e7SSue Gleeson int
srpt_ResetTarget(char * hca_guid)391*c3a558e7SSue Gleeson srpt_ResetTarget(char *hca_guid)
392*c3a558e7SSue Gleeson {
393*c3a558e7SSue Gleeson int ret;
394*c3a558e7SSue Gleeson nvlist_t *cfgnv;
395*c3a558e7SSue Gleeson nvlist_t *hcalist;
396*c3a558e7SSue Gleeson uint64_t token;
397*c3a558e7SSue Gleeson char guid[32];
398*c3a558e7SSue Gleeson
399*c3a558e7SSue Gleeson if (hca_guid == NULL) {
400*c3a558e7SSue Gleeson return (EINVAL);
401*c3a558e7SSue Gleeson }
402*c3a558e7SSue Gleeson
403*c3a558e7SSue Gleeson ret = srpt_NormalizeGuid(hca_guid, guid, sizeof (guid), NULL);
404*c3a558e7SSue Gleeson if (ret != 0) {
405*c3a558e7SSue Gleeson return (ret);
406*c3a558e7SSue Gleeson }
407*c3a558e7SSue Gleeson
408*c3a558e7SSue Gleeson ret = srpt_GetConfig(&cfgnv, &token);
409*c3a558e7SSue Gleeson if (ret != 0) {
410*c3a558e7SSue Gleeson return (ret);
411*c3a558e7SSue Gleeson }
412*c3a558e7SSue Gleeson
413*c3a558e7SSue Gleeson /* get the list of HCAs */
414*c3a558e7SSue Gleeson ret = nvlist_lookup_nvlist(cfgnv, SRPT_PROP_HCALIST, &hcalist);
415*c3a558e7SSue Gleeson if (ret != 0) {
416*c3a558e7SSue Gleeson nvlist_free(cfgnv);
417*c3a558e7SSue Gleeson return (ret);
418*c3a558e7SSue Gleeson }
419*c3a558e7SSue Gleeson
420*c3a558e7SSue Gleeson /* don't set config if we don't actually change anything */
421*c3a558e7SSue Gleeson if (nvlist_exists(hcalist, guid)) {
422*c3a558e7SSue Gleeson (void) nvlist_remove_all(hcalist, guid);
423*c3a558e7SSue Gleeson
424*c3a558e7SSue Gleeson if (ret == 0) {
425*c3a558e7SSue Gleeson ret = srpt_SetConfig(cfgnv, token);
426*c3a558e7SSue Gleeson }
427*c3a558e7SSue Gleeson }
428*c3a558e7SSue Gleeson
429*c3a558e7SSue Gleeson nvlist_free(cfgnv);
430*c3a558e7SSue Gleeson
431*c3a558e7SSue Gleeson return (ret);
432*c3a558e7SSue Gleeson }
433*c3a558e7SSue Gleeson
434*c3a558e7SSue Gleeson /*
435*c3a558e7SSue Gleeson * srpt_NormalizeGuid()
436*c3a558e7SSue Gleeson *
437*c3a558e7SSue Gleeson * Parameters:
438*c3a558e7SSue Gleeson * in HCA GUID. Must be in one of the following forms:
439*c3a558e7SSue Gleeson * 3BA000100CD18 - base hex form
440*c3a558e7SSue Gleeson * 0003BA000100CD18 - base hex form with leading zeroes
441*c3a558e7SSue Gleeson * hca:3BA000100CD18 - form from cfgadm and/or /dev/cfg
442*c3a558e7SSue Gleeson * eui.0003BA000100CD18 - EUI form
443*c3a558e7SSue Gleeson *
444*c3a558e7SSue Gleeson * buf Buffer to hold normalized guid string. Must be at least
445*c3a558e7SSue Gleeson * 17 chars long.
446*c3a558e7SSue Gleeson * buflen Length of provided buffer
447*c3a558e7SSue Gleeson * int_guid Optional. If not NULL, the integer form of the GUID will also
448*c3a558e7SSue Gleeson * be returned.
449*c3a558e7SSue Gleeson * Return Values:
450*c3a558e7SSue Gleeson * 0 Success
451*c3a558e7SSue Gleeson * EINVAL Invalid HCA GUID or invalid parameter.
452*c3a558e7SSue Gleeson */
453*c3a558e7SSue Gleeson int
srpt_NormalizeGuid(char * in,char * buf,size_t buflen,uint64_t * int_guid)454*c3a558e7SSue Gleeson srpt_NormalizeGuid(char *in, char *buf, size_t buflen, uint64_t *int_guid)
455*c3a558e7SSue Gleeson {
456*c3a558e7SSue Gleeson uint64_t guid;
457*c3a558e7SSue Gleeson char *bufp = in;
458*c3a558e7SSue Gleeson char *end = NULL;
459*c3a558e7SSue Gleeson
460*c3a558e7SSue Gleeson if ((in == NULL) || (buf == NULL)) {
461*c3a558e7SSue Gleeson return (EINVAL);
462*c3a558e7SSue Gleeson }
463*c3a558e7SSue Gleeson
464*c3a558e7SSue Gleeson if (strncasecmp(bufp, "eui.", 4) == 0) {
465*c3a558e7SSue Gleeson /* EUI form */
466*c3a558e7SSue Gleeson bufp += 4;
467*c3a558e7SSue Gleeson } else if (strncasecmp(bufp, "hca:", 4) == 0) {
468*c3a558e7SSue Gleeson /* cfgadm and /dev/hca form */
469*c3a558e7SSue Gleeson bufp += 4;
470*c3a558e7SSue Gleeson }
471*c3a558e7SSue Gleeson
472*c3a558e7SSue Gleeson /*
473*c3a558e7SSue Gleeson * strtoull() does not return EINVAL as documented. Lucky
474*c3a558e7SSue Gleeson * for us, neither 0 nor ULLONG_MAX will be valid. Trap on
475*c3a558e7SSue Gleeson * those and fail.
476*c3a558e7SSue Gleeson */
477*c3a558e7SSue Gleeson guid = strtoull(bufp, &end, 16);
478*c3a558e7SSue Gleeson if ((guid == 0) || (guid == ULLONG_MAX) ||
479*c3a558e7SSue Gleeson ((end != NULL) && (strlen(end) > 0))) {
480*c3a558e7SSue Gleeson return (EINVAL);
481*c3a558e7SSue Gleeson }
482*c3a558e7SSue Gleeson
483*c3a558e7SSue Gleeson #if 0
484*c3a558e7SSue Gleeson (void) snprintf(buf, buflen, "%llX", guid);
485*c3a558e7SSue Gleeson #endif
486*c3a558e7SSue Gleeson SRPT_FORMAT_HCAKEY(buf, buflen, guid);
487*c3a558e7SSue Gleeson
488*c3a558e7SSue Gleeson if (int_guid) {
489*c3a558e7SSue Gleeson *int_guid = guid;
490*c3a558e7SSue Gleeson }
491*c3a558e7SSue Gleeson
492*c3a558e7SSue Gleeson return (0);
493*c3a558e7SSue Gleeson }
494