xref: /illumos-gate/usr/src/cmd/isns/isnsadm/isnsadm.c (revision e9344627fd9b13a2a1fe91a37a88c0edbc4e5191)
1 /*
2  * CDDL HEADER START
3  *
4  * The contents of this file are subject to the terms of the
5  * Common Development and Distribution License (the "License").
6  * You may not use this file except in compliance with the License.
7  *
8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9  * or http://www.opensolaris.org/os/licensing.
10  * See the License for the specific language governing permissions
11  * and limitations under the License.
12  *
13  * When distributing Covered Code, include this CDDL HEADER in each
14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15  * If applicable, add the following below this CDDL HEADER, with the
16  * fields enclosed by brackets "[]" replaced with your own identifying
17  * information: Portions Copyright [yyyy] [name of copyright owner]
18  *
19  * CDDL HEADER END
20  */
21 /*
22  * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
23  * Use is subject to license terms.
24  * Copyright 2025 OmniOS Community Edition (OmniOSce) Association.
25  */
26 
27 /*
28  * isnsadm.c : isnsadm CL
29  *
30  */
31 
32 #include <sys/types.h>
33 #include <sys/stat.h>
34 #include <unistd.h>
35 #include <stdlib.h>
36 #include <devid.h>
37 #include <fcntl.h>
38 #include <door.h>
39 #include <errno.h>
40 #include <strings.h>
41 #include <libscf.h>
42 #include <libxml/xmlreader.h>
43 #include <libxml/xmlwriter.h>
44 #include <libxml/parser.h>
45 #include <libxml/xpath.h>
46 #include <libxml/tree.h>
47 #include <wchar.h>
48 #include <locale.h>
49 #include "isns_mgmt.h"
50 #include "isns_utils.h"
51 #include "isns_protocol.h"
52 #include "cmdparse.h"
53 #include "isnsadm.h"
54 
55 /* object functions per subcommand */
56 static int list_node_func(int, char **, cmdOptions_t *, void *);
57 static int list_dd_func(int, char **, cmdOptions_t *, void *);
58 static int list_ddset_func(int, char **, cmdOptions_t *, void *);
59 static int add_node_func(int, char **, cmdOptions_t *, void *);
60 static int add_dd_func(int, char **, cmdOptions_t *, void *);
61 static int delete_dd_func(int, char **, cmdOptions_t *, void *);
62 static int delete_ddset_func(int, char **, cmdOptions_t *, void *);
63 static int create_dd_func(int, char **, cmdOptions_t *, void *);
64 static int create_ddset_func(int, char **, cmdOptions_t *, void *);
65 static int remove_node_func(int, char **, cmdOptions_t *, void *);
66 static int remove_dd_func(int, char **, cmdOptions_t *, void *);
67 static int modify_dd_func(int, char **, cmdOptions_t *, void *);
68 static int modify_ddset_func(int, char **, cmdOptions_t *, void *);
69 static int enable_ddset_func(int, char **, cmdOptions_t *, void *);
70 static int disable_ddset_func(int, char **, cmdOptions_t *, void *);
71 static int show_config_func(int, char **, cmdOptions_t *, void *);
72 static int i_enableddset(int, char **, boolean_t);
73 static xmlTextReaderPtr lookup_next_matching_elem(xmlTextReaderPtr, int *,
74 	const char *, const char *);
75 static int handle_association_info(xmlChar *, association_t);
76 static int process_result_response(xmlChar *, int obj);
77 static int process_get_assoc_response(xmlChar *, association_t);
78 static int process_get_response(object_type, xmlChar *, uint32_t);
79 static int cvt_enumerate_rsp_to_get_req(xmlChar *, xmlChar **, object_type,
80 	uint32_t);
81 static int build_get_xml_doc(int, char **, object_type, xmlChar **);
82 static int build_delete_xml_doc(int, char **, object_type, char *, xmlChar **);
83 static int build_create_xml_doc(int, char **, object_type, char *, xmlChar **);
84 static int build_modify_xml_doc(int, char **, object_type, boolean_t,
85 	xmlChar **);
86 static int build_rename_xml_doc(char *, object_type, uint32_t, xmlChar **);
87 static int build_assoc_xml_doc(xmlChar *, association_t, xmlChar **);
88 static int build_assoc_xml_doc(xmlChar *, association_t, xmlChar **);
89 static int build_enumerate_xml_doc(object_type, xmlChar **);
90 
91 #define	NEW_XMLARGV(old, n) (xmlChar **)realloc((xmlChar *)old, \
92 	(unsigned)(n+2) * sizeof (xmlChar *))
93 
94 #define	XML_SFREE(x)	(((x) != NULL) ? (xmlFree(x), (x) = NULL) : (void *)0)
95 
96 #define	VERSION_STRING_MAX_LEN	10
97 
98 #define	OPTIONSTRING_NAME	"name"
99 #define	OPTIONSTRING_DDNAME	"Discovery Domain name"
100 #define	OPTIONSTRING_DDSETNAME	"Discovery Domain Set name"
101 #define	OPTIONSTRING_TARGET	"target"
102 #define	OPTIONSTRING_INITIATOR	"initiator"
103 #define	OPTIONSTRING_VERBOSE	"verbose"
104 
105 #define	VERBOSE		0x00000001
106 #define	INITIATOR_ONLY	0x00000010
107 #define	TARGET_ONLY	0x00000100
108 
109 #if LIBXML_VERSION >= 20904
110 #define	XMLSTRING_CAST (const char *)
111 #else
112 #define	XMLSTRING_CAST (const xmlChar *)
113 #endif
114 
115 /* object table based on definitions in isns_mgmt.h. */
116 static obj_table_entry_t obj_table[] = {
117 	{NODEOBJECT, Node},
118 	{DDOBJECT, DiscoveryDomain},
119 	{DDSETOBJECT, DiscoveryDomainSet},
120 	{DDOBJECTMEMBER, DiscoveryDomainMember},
121 	{DDSETOBJECTMEMBER, DiscoveryDomainSetMember},
122 	{ISNSSERVER, ServerConfig},
123 	{NULL, 0}
124 };
125 
126 /*
127  *  MAJOR - This should only change when there is an incompatible change made
128  *  to the interfaces or the output.
129  *
130  *  MINOR - This should change whenever there is a new command or new feature
131  *  with no incompatible change.
132  */
133 #define	VERSION_STRING_MAJOR	    "1"
134 #define	VERSION_STRING_MINOR	    "0"
135 static char *ISNS_FMRI = "network/isns_server:default";
136 
137 /*
138  * Add new options here
139  */
140 
141 /* tables set up based on cmdparse instructions */
142 optionTbl_t longOptions[] = {
143 	{"target", no_arg, 't', OPTIONSTRING_TARGET},
144 	{"initiator", no_arg, 'i', OPTIONSTRING_INITIATOR},
145 	{"verbose", no_arg, 'v', OPTIONSTRING_VERBOSE},
146 	{"name", required_arg, 'n', OPTIONSTRING_NAME},
147 	{"dd", required_arg, 'd', OPTIONSTRING_DDNAME},
148 	{"dd-set", required_arg, 's', OPTIONSTRING_DDSETNAME},
149 	{NULL, 0, 0, 0}
150 };
151 
152 
153 /*
154  * Add new subcommands here
155  */
156 subCommandProps_t subcommands[] = {
157 	{"list-node", LISTNODE, list_node_func, "itv", B_FALSE, NULL,
158 		OPERAND_OPTIONAL_MULTIPLE, "node-name"},
159 	{"list-dd", LISTDD, list_dd_func, "v", B_FALSE, NULL,
160 		OPERAND_OPTIONAL_MULTIPLE, OPTIONSTRING_DDNAME},
161 	{"list-dd-set", LISTDDSET, list_ddset_func, "v", B_FALSE, NULL,
162 		OPERAND_OPTIONAL_MULTIPLE, OPTIONSTRING_DDSETNAME},
163 	{"create-dd", CREATEDD, create_dd_func, NULL, B_FALSE, NULL,
164 		OPERAND_MANDATORY_MULTIPLE, OPTIONSTRING_DDNAME},
165 	{"create-dd-set", CREATEDDSET, create_ddset_func, NULL, B_FALSE, NULL,
166 		OPERAND_MANDATORY_MULTIPLE, OPTIONSTRING_DDSETNAME},
167 	{"delete-dd", DELETEDD, delete_dd_func, NULL, B_FALSE, NULL,
168 		OPERAND_MANDATORY_MULTIPLE, OPTIONSTRING_DDNAME},
169 	{"delete-dd-set", DELETEDDSET, delete_ddset_func, NULL, B_FALSE, NULL,
170 		OPERAND_MANDATORY_MULTIPLE, OPTIONSTRING_DDSETNAME},
171 	{"add-node", ADDNODE, add_node_func, "d", B_TRUE, NULL,
172 		OPERAND_MANDATORY_MULTIPLE, "node-name"},
173 	{"add-dd", ADDDD, add_dd_func, "s", B_TRUE, NULL,
174 		OPERAND_MANDATORY_MULTIPLE, OPTIONSTRING_DDNAME},
175 	{"remove-node", REMOVENODE, remove_node_func, "d", B_TRUE, NULL,
176 		OPERAND_MANDATORY_MULTIPLE, "node-name"},
177 	{"remove-dd", REMOVEDD, remove_dd_func, "s", B_TRUE, NULL,
178 		OPERAND_MANDATORY_MULTIPLE, OPTIONSTRING_DDNAME},
179 	{"modify-dd", MODIFYDD, modify_dd_func, "n", B_TRUE, NULL,
180 		OPERAND_MANDATORY_SINGLE, OPTIONSTRING_NAME},
181 	{"modify-dd-set", MODIFYDDSET, modify_ddset_func, "n", B_TRUE, NULL,
182 		OPERAND_MANDATORY_SINGLE, OPTIONSTRING_NAME},
183 	{"enable-dd-set", ENABLEDDSET, enable_ddset_func, NULL, B_FALSE, NULL,
184 		OPERAND_MANDATORY_MULTIPLE, OPTIONSTRING_DDSETNAME},
185 	{"disable-dd-set", DISABLEDDSET, disable_ddset_func, NULL, B_FALSE,
186 		NULL, OPERAND_MANDATORY_MULTIPLE, OPTIONSTRING_DDSETNAME},
187 	{"show-config", SHOWCONFIG, show_config_func, NULL, B_FALSE, NULL,
188 		OPERAND_NONE, NULL},
189 	{NULL, 0, NULL, NULL, 0, NULL, 0, NULL}
190 };
191 
192 /*
193  * ****************************************************************************
194  *
195  * check_door_error
196  *
197  * input:
198  *  errno from the door call.
199  *
200  * Returns:
201  *  either door error or smf service error.
202  *
203  * ****************************************************************************
204  */
205 static int
check_door_error(int door_err,int err)206 check_door_error(int door_err, int err)
207 {
208 	char	*state = NULL;
209 	int	ret;
210 
211 	if (((state = smf_get_state(ISNS_FMRI)) != NULL) &&
212 	    (strcmp(state, SCF_STATE_STRING_ONLINE) != 0)) {
213 		ret = ERROR_ISNS_SMF_SERVICE_NOT_ONLINE;
214 	} else {
215 	    (void) fprintf(stderr, "%s\n",
216 		(door_err == ERROR_DOOR_CALL_FAILED) ?
217 		getTextMessage(ERROR_DOOR_CALL_FAILED) :
218 		getTextMessage(ERROR_DOOR_OPEN_FAILED));
219 	    (void) fprintf(stderr, "\terrno: %s\n", strerror(err));
220 	    ret = door_err;
221 	}
222 
223 	if (state) free(state);
224 
225 	return (ret);
226 }
227 
228 /*
229  * ****************************************************************************
230  *
231  * lookup an element based on the element name.
232  *
233  * reader	- current xmlReaderReadPtr
234  * m_falg	- indicate lookup result
235  * elem		- name of element to look up.
236  * endelem	- name of end element to look up.
237  *
238  * ****************************************************************************
239  */
240 static	xmlTextReaderPtr
lookup_next_matching_elem(xmlTextReaderPtr reader,int * m_flag,const char * elem,const char * endelem)241 lookup_next_matching_elem(xmlTextReaderPtr reader, int *m_flag,
242 	const char *elem, const char *endelem)
243 {
244 
245 	if (reader == NULL) {
246 	    *m_flag = NO_MATCH;
247 	    return (NULL);
248 	}
249 
250 	do {
251 	/*
252 	 * if (xmlTextReaderName(reader) != NULL) {
253 	 * 	printf("%s ", xmlTextReaderName(reader));
254 	 * }
255 	 * printf("%d %d %d\n",
256 	 * xmlTextReaderDepth(reader),
257 	 * xmlTextReaderNodeType(reader),
258 	 * xmlTextReaderIsEmptyElement(reader));
259 	 */
260 		/*
261 		 * if match with elem, return the reader with READER_MATCH flag.
262 		 * if match with end elem, return the reader wtih
263 		 * END_READER_MATCH flag.
264 		 */
265 	    if (xmlTextReaderNodeType(reader) == XML_READER_TYPE_ELEMENT) {
266 		if (XMLNCMP(reader, elem) == 0) {
267 		    *m_flag = READER_MATCH;
268 		    return (reader);
269 		}
270 	    } else if (xmlTextReaderNodeType(reader) ==
271 		XML_READER_TYPE_END_ELEMENT) {
272 		if (XMLNCMP(reader, endelem) == 0) {
273 		    *m_flag = END_READER_MATCH;
274 		    return (reader);
275 		}
276 	    }
277 	} while (xmlTextReaderRead(reader) == 1);
278 
279 	*m_flag = NO_MATCH;
280 	return (NULL);
281 }
282 
283 /*
284  * ****************************************************************************
285  *
286  * Routine for getAssociated operation
287  *	Construct association request  based on the name and calls door
288  *	interface.
289  *
290  * name		- name attributes of an object for getting an association
291  * assoc	- association type
292  *
293  * ****************************************************************************
294  */
295 static int
handle_association_info(xmlChar * name,association_t assoc)296 handle_association_info(xmlChar *name, association_t assoc)
297 {
298 
299 	xmlChar *doc;
300 	door_arg_t darg;
301 	msg_code_t ret;
302 	int fd;
303 
304 	if ((ret = build_assoc_xml_doc(name, assoc, &doc)) != 0) {
305 	    return (ret);
306 	}
307 
308 	if ((fd = open(ISNS_DOOR_NAME, 0)) == -1) {
309 	    ret = check_door_error(ERROR_DOOR_OPEN_FAILED, errno);
310 	    return (ret);
311 	}
312 
313 	(void) bzero(&darg, sizeof (darg));
314 	bzero(&darg, sizeof (darg));
315 	darg.data_ptr = (char *)doc;
316 	darg.data_size = xmlStrlen(doc);
317 	darg.rbuf = NULL;
318 	darg.rsize = 0;
319 	if ((door_call(fd, &darg)) == -1) {
320 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
321 	    (void) close(fd);
322 	    (void) xmlFree(doc);
323 	    return (ret);
324 	}
325 
326 	if ((ret = process_get_assoc_response((xmlChar *)darg.rbuf,
327 	    assoc)) != 0) {
328 	/*
329 	 * door frame work allocated a buffer when the date lager
330 	 * that rbuf. indicate if munmap is required on rbuf.
331 	 */
332 	    (void) munmap(darg.rbuf, darg.rsize);
333 	    (void) close(fd);
334 	    (void) xmlFree(doc);
335 	    return (ret);
336 	}
337 
338 	(void) munmap(darg.rbuf, darg.rsize);
339 
340 	(void) close(fd);
341 	(void) xmlFree(doc);
342 
343 	return (0);
344 }
345 
346 /*
347  * ****************************************************************************
348  *
349  * process_error_status
350  *	The routine process non 0 status and print out error message.
351  *
352  * status	- status code
353  * reader	- reader that points to the message element.
354  *
355  * ****************************************************************************
356  */
357 static void
print_error_status(int status,int obj,xmlTextReaderPtr reader)358 print_error_status(int status, int obj, xmlTextReaderPtr reader)
359 {
360 	int m_flag = 0;
361 
362 	switch (status) {
363 	case ISNS_RSP_BUSY:
364 	    (void) fprintf(stderr, "%s\n",
365 		getTextMessage(ERROR_SERVER_BUSY));
366 	    break;
367 	case ISNS_RSP_INTERNAL_ERROR:
368 	    (void) fprintf(stderr, "%s\n",
369 		getTextMessage(ERROR_SERVER_INTERNAL_ERROR));
370 	    break;
371 	case ISNS_RSP_OPTION_NOT_UNDERSTOOD:
372 	    if ((obj == DiscoveryDomain) ||
373 		(obj == DiscoveryDomainMember)) {
374 		(void) fprintf(stderr, "%s\n",
375 		getTextMessage(ERROR_OPERATION_NOT_ALLOWED_FOR_DEFAULT_DD));
376 	    } else {
377 		(void) fprintf(stderr, "%s\n",
378 		getTextMessage(ERROR_OPERATION_NOT_ALLOWED_FOR_DEFAULT_DDSET));
379 	    }
380 	    break;
381 	case PARTIAL_FAILURE:
382 	    (void) fprintf(stderr, "%s\n",
383 		getTextMessage(ERROR_PARTIAL_FAILURE));
384 	    break;
385 	case ERR_NO_SUCH_ASSOCIATION:
386 	    if ((obj == DiscoveryDomain) ||
387 		(obj == DiscoveryDomainMember)) {
388 		(void) fprintf(stderr, "%s\n",
389 		getTextMessage(ERROR_DDMEMBER_NOT_FOUND));
390 	    } else {
391 		(void) fprintf(stderr, "%s\n",
392 		getTextMessage(ERROR_DDSETMEMBER_NOT_FOUND));
393 	    }
394 	    break;
395 	case ERR_ALREADY_ASSOCIATED:
396 	    if ((obj == DiscoveryDomain) ||
397 		(obj == DiscoveryDomainMember)) {
398 		(void) fprintf(stderr, "%s\n",
399 		getTextMessage(ERROR_DDMEMBER_ALREADY_EXIST));
400 	    } else {
401 		(void) fprintf(stderr, "%s\n",
402 		getTextMessage(ERROR_DDSETMEMBER_ALREADY_EXIST));
403 	    }
404 	    break;
405 	case ERR_NAME_IN_USE:
406 	    if ((obj == DiscoveryDomain) ||
407 		(obj == DiscoveryDomainMember)) {
408 		(void) fprintf(stderr, "%s\n",
409 		getTextMessage(ERROR_DD_NAME_IN_USE));
410 	    } else {
411 		(void) fprintf(stderr, "%s\n",
412 		getTextMessage(ERROR_DDSET_NAME_IN_USE));
413 	    }
414 	    break;
415 	default:
416 	    reader = lookup_next_matching_elem(reader, &m_flag,
417 		MESSAGEELEMENT, RESULTELEMENT);
418 	    if (m_flag == READER_MATCH) {
419 		(void) xmlTextReaderRead(reader);
420 		(void) fprintf(stderr, "Error: %s\n",
421 			(const char *) xmlTextReaderConstValue(reader));
422 	    } else {
423 		(void) fprintf(stderr, "Error: %s\n",
424 		getTextMessage(ERROR_XML_MESSAGE_ELEM_NOT_FOUND));
425 	    }
426 	}
427 }
428 
429 /*
430  * ****************************************************************************
431  *
432  * print_partial_failure_info
433  *	The routine prints partial failure info.
434  *
435  * status	- status code
436  * reader	- reader that points to the message element.
437  *
438  * ****************************************************************************
439  */
440 static void
print_partial_failure_info(xmlChar * doc)441 print_partial_failure_info(xmlChar *doc)
442 {
443 	xmlChar expr[ISNS_MAX_LABEL_LEN + 13];
444 	xmlDocPtr x_doc;
445 	xmlXPathContextPtr ctext = NULL;
446 	xmlXPathObjectPtr xpath_obj = NULL;
447 	xmlNodeSetPtr r_nodes = NULL;
448 	xmlAttrPtr attr = NULL;
449 	int i, cnt, obj = 0;
450 
451 	if ((x_doc = xmlParseMemory((const char *)doc, xmlStrlen(doc))) ==
452 	    NULL) {
453 	    (void) fprintf(stderr, "%s\n",
454 		getTextMessage(ERROR_NO_ADDITIONAL_PARTIAL_FAILIRE_INFO));
455 	}
456 
457 	ctext = xmlXPathNewContext(x_doc);
458 	if (ctext == NULL) {
459 	    (void) fprintf(stderr, "%s\n",
460 		getTextMessage(ERROR_NO_ADDITIONAL_PARTIAL_FAILIRE_INFO));
461 	}
462 
463 	for (i = 0; obj_table[i].obj_str != NULL; i++) {
464 	    (void) xmlStrPrintf(expr, ISNS_MAX_LABEL_LEN + 13,
465 		XMLSTRING_CAST "%s\"%s\"]", "//*[name()=",
466 		obj_table[i].obj_str);
467 	    xpath_obj = xmlXPathEvalExpression(expr, ctext);
468 	    if ((xpath_obj) && (xpath_obj->nodesetval) &&
469 		(xpath_obj->nodesetval->nodeNr > 0) &&
470 		(xpath_obj->nodesetval->nodeTab)) {
471 		obj = obj_table[i].obj_id;
472 		break;
473 	    }
474 	}
475 
476 	if (obj == 0) {
477 	    if (xpath_obj) xmlXPathFreeObject(xpath_obj);
478 	    (void) fprintf(stderr, "%s\n",
479 		getTextMessage(ERROR_NO_ADDITIONAL_PARTIAL_FAILIRE_INFO));
480 	}
481 
482 	switch (obj) {
483 	    case DiscoveryDomainMember:
484 		r_nodes = xpath_obj->nodesetval;
485 		cnt = r_nodes->nodeNr;
486 		for (i = 0; i < cnt; i++) {
487 		    attr = r_nodes->nodeTab[i]->properties;
488 		    for (; attr != NULL; attr = attr->next) {
489 			if (xmlStrncmp(attr->name, (xmlChar *)DDNAMEATTR,
490 			    xmlStrlen((xmlChar *)DDNAMEATTR)) == 0) {
491 				(void) fprintf(stderr, "DD Name: %s\t",
492 				xmlNodeGetContent(attr->children));
493 			}
494 			if (xmlStrncmp(attr->name, (xmlChar *)NODENAMEATTR,
495 			    xmlStrlen((xmlChar *)NODENAMEATTR)) == 0) {
496 				(void) fprintf(stderr, "Node Name: %s\t",
497 				xmlNodeGetContent(attr->children));
498 			}
499 		    }
500 		    (void) fprintf(stderr, "\n");
501 		}
502 		if (xpath_obj) xmlXPathFreeObject(xpath_obj);
503 		break;
504 	    case DiscoveryDomainSetMember:
505 		r_nodes = xpath_obj->nodesetval;
506 		cnt = r_nodes->nodeNr;
507 		for (i = 0; i < cnt; i++) {
508 		    attr = r_nodes->nodeTab[i]->properties;
509 		    for (; attr != NULL; attr = attr->next) {
510 			if (xmlStrncmp(attr->name, (xmlChar *)DDSETNAMEATTR,
511 			    xmlStrlen((xmlChar *)DDNAMEATTR)) == 0) {
512 				(void) fprintf(stderr, "DD Set Name: %s\t",
513 				xmlNodeGetContent(attr->children));
514 			}
515 			if (xmlStrncmp(attr->name, (xmlChar *)DDNAMEATTR,
516 			    xmlStrlen((xmlChar *)NODENAMEATTR)) == 0) {
517 				(void) fprintf(stderr, "DD Name: %s\t",
518 				xmlNodeGetContent(attr->children));
519 			}
520 		    }
521 		    (void) fprintf(stderr, "\n");
522 		}
523 		if (xpath_obj) xmlXPathFreeObject(xpath_obj);
524 		break;
525 	    case Node:
526 	    case DiscoveryDomain:
527 	    case DiscoveryDomainSet:
528 		r_nodes = xpath_obj->nodesetval;
529 		cnt = r_nodes->nodeNr;
530 		for (i = 0; i < cnt; i++) {
531 		    attr = r_nodes->nodeTab[i]->properties;
532 		    for (; attr != NULL; attr = attr->next) {
533 			if ((xmlStrncmp(attr->name, (xmlChar *)NAMEATTR,
534 			    xmlStrlen((xmlChar *)NAMEATTR))) == 0) {
535 				(void) fprintf(stderr, "Object Name: %s\n",
536 				xmlNodeGetContent(attr->children));
537 			}
538 		    }
539 		}
540 		if (xpath_obj) xmlXPathFreeObject(xpath_obj);
541 		break;
542 	}
543 }
544 
545 /*
546  * ****************************************************************************
547  *
548  * process_result_response
549  *	The routine process association data based on the association type.
550  *
551  * doc		- result
552  * obj		- associated object type
553  *
554  * ****************************************************************************
555  */
556 static int
process_result_response(xmlChar * doc,int obj)557 process_result_response(xmlChar *doc, int obj)
558 {
559 	xmlTextReaderPtr reader;
560 	int m_flag = 0, status;
561 
562 	if ((reader = (xmlTextReaderPtr)xmlReaderForMemory((const char *)doc,
563 	    xmlStrlen(doc), NULL, NULL, 0)) == NULL) {
564 		return (ERROR_XML_READER_NULL);
565 	}
566 
567 	/* if status is 0, continue on.  Otherwise return an error. */
568 	if (reader = lookup_next_matching_elem(reader, &m_flag, STATUSELEMENT,
569 	    RESULTELEMENT)) {
570 	    if (m_flag == READER_MATCH) {
571 		if (xmlTextReaderRead(reader) == 1) {
572 		    status =
573 		    atoi((const char *)xmlTextReaderConstValue(reader));
574 		    if (status != 0) {
575 			print_error_status(status, obj, reader);
576 			(void) xmlTextReaderClose(reader);
577 			(void) xmlFreeTextReader(reader);
578 			if (status == PARTIAL_FAILURE) {
579 			    print_partial_failure_info(doc);
580 			}
581 			return (status);
582 		    }
583 		} else {
584 		    (void) xmlTextReaderClose(reader);
585 		    (void) xmlFreeTextReader(reader);
586 		    return (ERROR_XML_STATUS_ELEM_NOT_FOUND);
587 		}
588 	    } else {
589 		(void) xmlTextReaderClose(reader);
590 		(void) xmlFreeTextReader(reader);
591 		return (ERROR_XML_STATUS_ELEM_NOT_FOUND);
592 	    }
593 	} else {
594 	    (void) fprintf(stderr, "%s\n",
595 		getTextMessage(ERROR_XML_READER_NULL));
596 	    return (ERROR_XML_READER_NULL);
597 	}
598 
599 	(void) xmlTextReaderClose(reader);
600 	(void) xmlFreeTextReader(reader);
601 	return (0);
602 }
603 
604 /*
605  * ****************************************************************************
606  *
607  * process_get_assoc_response
608  *	The routine process association data based on the association type.
609  *
610  * doc		- association data
611  * assoc	- associatiion type
612  *
613  * ****************************************************************************
614  */
615 static int
process_get_assoc_response(xmlChar * doc,association_t assoc)616 process_get_assoc_response(xmlChar *doc, association_t assoc)
617 {
618 	xmlTextReaderPtr reader;
619 	xmlChar *ddsname, *ddname, *nodename;
620 	wchar_t wc_name[ISNS_MAX_NAME_LEN];
621 	int m_flag = 0, h_printed = 0, status;
622 
623 	if ((reader = (xmlTextReaderPtr)xmlReaderForMemory((const char *)doc,
624 			xmlStrlen(doc), NULL, NULL, 0)) == NULL) {
625 	    return (ERROR_XML_READER_NULL);
626 	}
627 
628 	/* if status is 0, continue on.  Otherwise return an error. */
629 	if (reader = lookup_next_matching_elem(reader, &m_flag, STATUSELEMENT,
630 	    RESULTELEMENT)) {
631 	    if (m_flag == READER_MATCH) {
632 		if (xmlTextReaderRead(reader) == 1) {
633 		    status =
634 		    atoi((const char *)xmlTextReaderConstValue(reader));
635 		    if ((status != 0) && (status != PARTIAL_SUCCESS)) {
636 			/* not an error */
637 			if ((status !=  ERR_NO_SUCH_ASSOCIATION) &&
638 			    (status !=  ERR_NO_ASSOCIATED_DD_FOUND) &&
639 			    (status !=  ERR_NO_ASSOCIATED_DDSET_FOUND)) {
640 			    (void) xmlTextReaderClose(reader);
641 			    (void) xmlFreeTextReader(reader);
642 			    return (0);
643 			} else {
644 			    print_error_status(status,
645 				((assoc == node_to_dd) || (dd_to_node)) ?
646 				DiscoveryDomain : DiscoveryDomainSet, reader);
647 			    (void) xmlTextReaderClose(reader);
648 			    (void) xmlFreeTextReader(reader);
649 			    return (status);
650 			}
651 		    }
652 		} else {
653 		    (void) xmlTextReaderClose(reader);
654 		    (void) xmlFreeTextReader(reader);
655 		    return (ERROR_XML_STATUS_ELEM_NOT_FOUND);
656 		}
657 	    } else {
658 		return (ERROR_XML_STATUS_ELEM_NOT_FOUND);
659 	    }
660 	} else {
661 	    return (ERROR_XML_READER_NULL);
662 	}
663 
664 	m_flag = 0;
665 
666 	switch (assoc) {
667 	    case node_to_dd:
668 		/* process DD elements */
669 		while (reader = lookup_next_matching_elem(reader, &m_flag,
670 		    DDOBJECTMEMBER, ISNSRESPONSE)) {
671 		    if (m_flag == END_READER_MATCH) {
672 			(void) xmlTextReaderNext(reader);
673 			break;
674 		    } else if (m_flag == READER_MATCH) {
675 			if ((ddname = (xmlTextReaderGetAttribute(reader,
676 			    (const xmlChar *)DDNAMEATTR))) != NULL) {
677 			    if (mbstowcs(wc_name, (const char *)ddname,
678 				ISNS_MAX_NAME_LEN) == (size_t)-1) {
679 				(void) wcscpy(wc_name, L"-");
680 			    }
681 			    if (h_printed) {
682 				(void) printf("\tDD Name: %ws\n", wc_name);
683 			    } else {
684 				(void) printf("\tDD Name: %ws\n", wc_name);
685 				h_printed = 1;
686 			    }
687 			    xmlFree(ddname);
688 			} else {
689 			    if (h_printed) {
690 				(void) printf("\t         %s\n", "-");
691 			    } else {
692 				(void) printf("\tDD Name: %s\n", "-");
693 				h_printed = 1;
694 			    }
695 			}
696 		    }
697 		    m_flag = 0;
698 		    (void) xmlTextReaderRead(reader);
699 		}
700 	    break;
701 	case dd_to_node:
702 		/* process the DiscoveryDoamin elements */
703 	    while (reader = lookup_next_matching_elem(reader, &m_flag,
704 		    DDOBJECTMEMBER, ISNSRESPONSE)) {
705 		if (m_flag == END_READER_MATCH) {
706 		    (void) xmlTextReaderNext(reader);
707 		    break;
708 		} else if (m_flag == READER_MATCH) {
709 		    if ((nodename = (xmlTextReaderGetAttribute(reader,
710 			    (const xmlChar *)NODENAMEATTR))) != NULL) {
711 			if (mbstowcs(wc_name, (const char *)nodename,
712 			    ISNS_MAX_NAME_LEN) == (size_t)-1) {
713 			    (void) wcscpy(wc_name, L"-");
714 			}
715 			(void) printf("\tiSCSI name: %ws\n", wc_name);
716 			xmlFree(nodename);
717 		    } else {
718 			(void) printf("\tiSCSI name: %s\n", "-");
719 		    }
720 		}
721 		m_flag = 0;
722 		(void) xmlTextReaderRead(reader);
723 	    }
724 	    break;
725 	case dd_to_ddset:
726 		/* process the DiscoveryDoaminSet elements */
727 	    while (reader = lookup_next_matching_elem(reader, &m_flag,
728 		    DDSETOBJECTMEMBER, ISNSRESPONSE)) {
729 		if (m_flag == END_READER_MATCH) {
730 		    (void) xmlTextReaderNext(reader);
731 		    break;
732 		} else if (m_flag == READER_MATCH) {
733 		    if ((ddsname = (xmlTextReaderGetAttribute(reader,
734 			(const xmlChar *)DDSETNAMEATTR))) != NULL) {
735 			if (mbstowcs(wc_name, (const char *)ddsname,
736 			    ISNS_MAX_NAME_LEN) == (size_t)-1) {
737 			    (void) wcscpy(wc_name, L"-");
738 			}
739 			if (h_printed) {
740 			    (void) printf("\t           %ws\n", wc_name);
741 			} else {
742 			    (void) printf("\tDD set(s): %ws\n", wc_name);
743 			    h_printed = 1;
744 			}
745 			xmlFree(ddsname);
746 		    } else {
747 			(void) printf("\tDD set(s): %s\n", "-");
748 		    }
749 		}
750 		m_flag = 0;
751 		(void) xmlTextReaderRead(reader);
752 	    }
753 	    break;
754 	case ddset_to_dd:
755 		/* process the DiscoveryDoaminSet elements */
756 	    while (reader = lookup_next_matching_elem(reader, &m_flag,
757 		    DDSETOBJECTMEMBER, ISNSRESPONSE)) {
758 		if (m_flag == END_READER_MATCH) {
759 		    (void) xmlTextReaderNext(reader);
760 		    break;
761 		} else if (m_flag == READER_MATCH) {
762 			if ((ddname = (xmlTextReaderGetAttribute(reader,
763 			    (const xmlChar *)DDNAMEATTR))) != NULL) {
764 			    if (mbstowcs(wc_name, (const char *)ddname,
765 				ISNS_MAX_NAME_LEN) == (size_t)-1) {
766 				(void) wcscpy(wc_name, L"-");
767 			    }
768 			    (void) printf("\tDD Name: %ws\n", wc_name);
769 			    xmlFree(ddname);
770 			} else {
771 			    (void) printf("\tDD Name: %s\n", "-");
772 			}
773 		}
774 		m_flag = 0;
775 		(void) xmlTextReaderRead(reader);
776 	    }
777 	    break;
778 	default:
779 	    (void) xmlTextReaderClose(reader);
780 	    (void) xmlFreeTextReader(reader);
781 	    return (UNKNOWN);
782 	}
783 
784 	if (status == PARTIAL_SUCCESS) {
785 	    (void) fprintf(stderr, "%s\n",
786 		getTextMessage(ERROR_PARTIAL_SUCCESS));
787 	}
788 	(void) xmlTextReaderClose(reader);
789 	(void) xmlFreeTextReader(reader);
790 	return (status);
791 }
792 
793 /*
794  * ****************************************************************************
795  *
796  * process_get_response :
797  *	display data from the get response doc based on flag.
798  *
799  * obj		- object type
800  * doc		- docuemet to process
801  * flag		- options from the subcommand
802  *
803  * ****************************************************************************
804  */
805 static int
process_get_response(object_type obj,xmlChar * doc,uint32_t flag)806 process_get_response(object_type obj, xmlChar *doc, uint32_t flag)
807 {
808 	xmlTextReaderPtr reader;
809 	int m_flag = 0, ret = 0, status;
810 	xmlChar *name = NULL;
811 	wchar_t wc_name[ISNS_MAX_NAME_LEN];
812 	int tag_printed = 0;
813 
814 	if ((reader = (xmlTextReaderPtr)xmlReaderForMemory((const char *)doc,
815 	    xmlStrlen(doc), NULL, NULL, 0)) == NULL) {
816 		return (ERROR_XML_READER_NULL);
817 	}
818 
819 	/* if status is 0, continue on.  Otherwise return an error. */
820 	if (reader = lookup_next_matching_elem(reader, &m_flag, STATUSELEMENT,
821 	    RESULTELEMENT)) {
822 	    if (m_flag == READER_MATCH) {
823 		if (xmlTextReaderRead(reader) == 1) {
824 		    status =
825 		    atoi((const char *)xmlTextReaderConstValue(reader));
826 		    if ((status != 0) && (status != PARTIAL_SUCCESS)) {
827 			print_error_status(status, obj, reader);
828 			(void) xmlTextReaderClose(reader);
829 			(void) xmlFreeTextReader(reader);
830 			return (status);
831 		    }
832 		} else {
833 		    (void) xmlTextReaderClose(reader);
834 		    (void) xmlFreeTextReader(reader);
835 		    return (ERROR_XML_STATUS_ELEM_NOT_FOUND);
836 		}
837 	    } else {
838 		(void) xmlTextReaderClose(reader);
839 		(void) xmlFreeTextReader(reader);
840 		return (ERROR_XML_STATUS_ELEM_NOT_FOUND);
841 	    }
842 	} else {
843 	    return (ERROR_XML_READER_NULL);
844 	}
845 
846 	m_flag = 0;
847 
848 	switch (obj) {
849 	    case Node:
850 		/* process the node elements */
851 		while (reader = lookup_next_matching_elem(reader, &m_flag,
852 		    NODEOBJECT, ISNSRESPONSE)) {
853 		    if (m_flag == END_READER_MATCH) {
854 			break;
855 		    }
856 
857 		    /* check the type */
858 		    if ((xmlTextReaderMoveToAttribute(reader,
859 			(const xmlChar *)TYPEATTR)) == 1) {
860 			if (((flag & TARGET_ONLY) == TARGET_ONLY) &&
861 			    (XMLNCMPVAL(reader, TARGETTYPE) != 0)) {
862 			    /* move to next node object. */
863 			    (void) xmlTextReaderMoveToElement(reader);
864 			    (void) xmlTextReaderNext(reader);
865 			    continue;
866 			}
867 			if (((flag & INITIATOR_ONLY) == INITIATOR_ONLY) &&
868 			    (XMLNCMPVAL(reader, INITIATORTYPE) != 0)) {
869 			    /* move to next node object. */
870 			    (void) xmlTextReaderMoveToElement(reader);
871 			    (void) xmlTextReaderNext(reader);
872 			    continue;
873 			}
874 		    } else {
875 			ret = ERROR_XML_TYPE_ATTR_NOT_FOUND;
876 			goto out;
877 		    }
878 
879 		    if (((xmlTextReaderMoveToAttribute(reader,
880 			(const xmlChar *)NAMEATTR)) == 1) &&
881 			(const char *)xmlTextReaderConstValue(reader)) {
882 			if (mbstowcs(wc_name,
883 			    (const char *)xmlTextReaderConstValue(reader),
884 			    ISNS_MAX_NAME_LEN) == (size_t)-1) {
885 			    (void) wcscpy(wc_name, L"-");
886 			}
887 			if ((flag & VERBOSE) == VERBOSE) {
888 			    name = xmlTextReaderValue(reader);
889 			    (void) printf("iSCSI Name: %ws\n", wc_name);
890 			} else {
891 			    (void) printf("iSCSI Name: %ws\n", wc_name);
892 			}
893 		    } else {
894 			XML_SFREE(name);
895 			ret = ERROR_XML_TYPE_ATTR_NOT_FOUND;
896 			goto out;
897 		    }
898 		    if ((xmlTextReaderMoveToAttribute(reader,
899 			(const xmlChar *)ALIASATTR)) == 1) {
900 			if (xmlStrcmp(xmlTextReaderConstValue(reader),
901 			    (xmlChar *)"") == 0) {
902 			    (void) printf("\tAlias: %s\n", "-");
903 			} else {
904 			    if (mbstowcs(wc_name,
905 				(const char *)xmlTextReaderConstValue(reader),
906 				ISNS_MAX_NAME_LEN) == (size_t)-1) {
907 				(void) wcscpy(wc_name, L"-");
908 			    }
909 			    (void) printf("\tAlias: %ws\n", wc_name);
910 			}
911 		    }
912 
913 		    /* type attribute exist based on the previous checking. */
914 		    (void) xmlTextReaderMoveToAttribute(reader,
915 			(const xmlChar *)TYPEATTR);
916 		    (void) printf("\tType: %s\n",
917 			(const char *)xmlTextReaderConstValue(reader) ?
918 			(const char *)xmlTextReaderConstValue(reader) : "-");
919 
920 		    if ((flag & VERBOSE) == VERBOSE) {
921 			/* print more details */
922 			m_flag = 0;
923 			/*
924 			 * No details for deregistered node.
925 			 * skip to next isns object.
926 			 */
927 			if ((reader = lookup_next_matching_elem(reader,
928 			    &m_flag, ENTITYID, ISNSOBJECT))) {
929 			    if (m_flag == READER_MATCH) {
930 				/* move to entity id value. */
931 				if ((xmlTextReaderRead(reader) == 1) &&
932 				    xmlTextReaderConstValue(reader)) {
933 				    if (mbstowcs(wc_name,
934 					(const char *)
935 					xmlTextReaderConstValue(reader),
936 					ISNS_MAX_NAME_LEN) == (size_t)-1) {
937 					(void) wcscpy(wc_name,
938 					    L"-");
939 				    }
940 				    (void) printf("\tNetwork Entity: %ws\n",
941 					wc_name);
942 				} else {
943 				    (void) printf("\tNework Entity: -\n");
944 				}
945 			    } else if (m_flag == END_READER_MATCH) {
946 				(void) xmlTextReaderRead(reader);
947 				XML_SFREE(name);
948 				continue;
949 			    }
950 			}
951 
952 			/* print  portal info */
953 			m_flag = 0;
954 			while ((reader = lookup_next_matching_elem(reader,
955 			    &m_flag, IPADDR, NODEOBJECT))) {
956 			    if (m_flag == END_READER_MATCH) {
957 				(void) xmlTextReaderRead(reader);
958 				break;
959 			    }
960 			    /* move to the value of IP addr. */
961 			    if ((xmlTextReaderRead(reader) == 1) &&
962 				xmlTextReaderConstValue(reader)) {
963 				(void) printf("\tPortal: %s",
964 				xmlTextReaderConstValue(reader));
965 				/* get port number */
966 				m_flag = 0;
967 				if (reader = lookup_next_matching_elem(reader,
968 				    &m_flag, PORTNUMBER, UDPTCPPORT)) {
969 				    if ((xmlTextReaderRead(reader) == 1) &&
970 					xmlTextReaderConstValue(reader)) {
971 				    (void) printf(":%d\n",
972 					atoi((const char *)
973 					xmlTextReaderConstValue(reader)));
974 				    } else {
975 					(void) printf(":-\n");
976 				    }
977 				}
978 				m_flag = 0;
979 				if (reader = lookup_next_matching_elem(reader,
980 				    &m_flag, GROUPTAG, GROUPTAG)) {
981 				    if ((xmlTextReaderRead(reader) == 1) &&
982 					xmlTextReaderConstValue(reader)) {
983 				    (void) printf("\t\tPortal Group: %s\n",
984 					xmlTextReaderConstValue(reader));
985 				    } else {
986 					(void) printf(":-\n");
987 				    }
988 				}
989 			    }
990 			} /* Portal end */
991 			if ((ret = handle_association_info(name,
992 			    node_to_dd)) != 0) {
993 			    XML_SFREE(name);
994 			    goto out;
995 			}
996 		    } /* verbose end */
997 		    XML_SFREE(name);
998 		    (void) xmlTextReaderRead(reader);
999 		    m_flag = 0;
1000 		} /* end for node while */
1001 		break;
1002 	    case DiscoveryDomain:
1003 		/* process the DiscoveryDoamin elements */
1004 		while (reader = lookup_next_matching_elem(reader, &m_flag,
1005 		    DDOBJECT, ISNSRESPONSE)) {
1006 		    if (m_flag == END_READER_MATCH) {
1007 			(void) xmlTextReaderNext(reader);
1008 			break;
1009 		    }
1010 
1011 		    if (((xmlTextReaderMoveToAttribute(reader,
1012 			(const xmlChar *)NAMEATTR)) == 1) &&
1013 			(name = xmlTextReaderValue(reader))) {
1014 			if (mbstowcs(wc_name, (const char *)name,
1015 			    ISNS_MAX_NAME_LEN) == (size_t)-1) {
1016 			    (void) wcscpy(wc_name, L"-");
1017 			}
1018 			(void) printf("DD name: %ws\n", wc_name);
1019 		    } else {
1020 			ret = ERROR_XML_NAME_ATTR_NOT_FOUND;
1021 			XML_SFREE(name);
1022 			goto out;
1023 		    }
1024 		    if ((ret = handle_association_info(name, dd_to_ddset)) !=
1025 			0) {
1026 			XML_SFREE(name);
1027 			goto out;
1028 		    }
1029 		    /* handle verbose */
1030 		    if ((flag & VERBOSE) == VERBOSE) {
1031 			if ((ret = handle_association_info(name,
1032 			    dd_to_node)) != 0) {
1033 			    XML_SFREE(name);
1034 			    goto out;
1035 			}
1036 		    }
1037 		    XML_SFREE(name);
1038 		    m_flag = 0;
1039 		}
1040 		break;
1041 	    case DiscoveryDomainSet:
1042 		/* process the DiscoveryDoaminSet elements */
1043 		while (reader = lookup_next_matching_elem(reader, &m_flag,
1044 		    DDSETOBJECT, ISNSRESPONSE)) {
1045 		    if (m_flag == END_READER_MATCH) {
1046 			(void) xmlTextReaderNext(reader);
1047 			break;
1048 		    }
1049 
1050 		    if (((xmlTextReaderMoveToAttribute(reader,
1051 			(const xmlChar *)NAMEATTR)) == 1) &&
1052 			(const char *)xmlTextReaderConstValue(reader)) {
1053 			if (mbstowcs(wc_name,
1054 			    (const char *)xmlTextReaderConstValue(reader),
1055 			    ISNS_MAX_NAME_LEN) == (size_t)-1) {
1056 			    (void) wcscpy(wc_name, L"-");
1057 			}
1058 			if ((flag & VERBOSE) == VERBOSE) {
1059 			    name = xmlTextReaderValue(reader);
1060 			    (void) printf("DD Set name: %ws\n", wc_name);
1061 			} else {
1062 			    (void) printf("DD Set name: %ws\n", wc_name);
1063 			}
1064 		    } else {
1065 			ret = ERROR_XML_NAME_ATTR_NOT_FOUND;
1066 			XML_SFREE(name);
1067 			goto out;
1068 		    }
1069 		    m_flag = 0;
1070 		    if ((reader = lookup_next_matching_elem(reader,
1071 			&m_flag, ENABLEDELEM, ISNSOBJECT))) {
1072 			if (m_flag == READER_MATCH) {
1073 			    /* move to entity id value. */
1074 			    if ((xmlTextReaderRead(reader) == 1) &&
1075 				(XMLNCMPVAL(reader, XMLTRUE) == 0)) {
1076 				(void) printf("\tState: Enabled\n");
1077 			    } else {
1078 				(void) printf("\tState: Disabled\n");
1079 			    }
1080 			} else if (m_flag == END_READER_MATCH) {
1081 			    (void) xmlTextReaderRead(reader);
1082 			}
1083 		    }
1084 
1085 		    /* handle verbose */
1086 		    if ((flag & VERBOSE) == VERBOSE) {
1087 			if ((ret = handle_association_info(name,
1088 			    ddset_to_dd)) != 0) {
1089 			    XML_SFREE(name);
1090 			    goto out;
1091 			}
1092 		    }
1093 		    XML_SFREE(name);
1094 		    m_flag = 0;
1095 		}
1096 		break;
1097 	    case ServerConfig:
1098 		/* process the DiscoveryDoaminSet elements */
1099 		m_flag = 0;
1100 		reader = lookup_next_matching_elem(reader, &m_flag,
1101 		    ISNSSERVER, ISNSRESPONSE);
1102 		if (m_flag == END_READER_MATCH) {
1103 		    ret = ERROR_XML_ISNSSERVER_ELEM_NOT_FOUND;
1104 		    goto out;
1105 		}
1106 		m_flag = 0;
1107 		if ((reader = lookup_next_matching_elem(reader,
1108 		    &m_flag, DATASTORELOCATION, ISNSRESPONSE))) {
1109 		    if (m_flag == READER_MATCH) {
1110 			(void) xmlTextReaderRead(reader);
1111 			(void) printf("\tData Store Location: %s\n",
1112 			(const char *)xmlTextReaderConstValue(reader) ?
1113 			(const char *)xmlTextReaderConstValue(reader) : "-");
1114 		    }
1115 		}
1116 		m_flag = 0;
1117 		if ((reader = lookup_next_matching_elem(reader,
1118 		    &m_flag, ESIRETRYTHRESHOLD, ISNSRESPONSE))) {
1119 		    if (m_flag == READER_MATCH) {
1120 			(void) xmlTextReaderRead(reader);
1121 			(void) printf("\tEntity Status Inquiry Non-Response ");
1122 			(void) printf("Threshold: %d\n",
1123 			xmlTextReaderConstValue(reader) ?
1124 			atoi((const char *)xmlTextReaderConstValue(reader))
1125 			: 0);
1126 		    }
1127 		}
1128 		m_flag = 0;
1129 		if ((reader = lookup_next_matching_elem(reader,
1130 		    &m_flag, MANAGEMENTSCNENABLED, ISNSRESPONSE))) {
1131 		    if (m_flag == READER_MATCH) {
1132 			(void) xmlTextReaderRead(reader);
1133 			(void) printf("\tManagement SCN Enabled: %s\n",
1134 			(XMLNCMPVAL(reader, XMLTRUE) == 0) ?
1135 			"yes" : "no");
1136 		    }
1137 		}
1138 		m_flag = 0;
1139 		while ((reader = lookup_next_matching_elem(reader,
1140 		    &m_flag, CONTROLNODENAME, ISNSSERVER))) {
1141 		    if (m_flag == READER_MATCH) {
1142 			if (!xmlTextReaderIsEmptyElement(reader)) {
1143 			    (void) xmlTextReaderRead(reader);
1144 			    if (mbstowcs(wc_name,
1145 				(const char *)xmlTextReaderConstValue(reader),
1146 				ISNS_MAX_NAME_LEN) == (size_t)-1) {
1147 				(void) wcscpy(wc_name, L"-");
1148 			    }
1149 			    if (tag_printed) {
1150 				if (xmlTextReaderConstValue(reader)) {
1151 				    if (mbstowcs(wc_name,
1152 					(const char *)
1153 					xmlTextReaderConstValue(reader),
1154 					ISNS_MAX_NAME_LEN) == (size_t)-1) {
1155 					(void) wcscpy(wc_name, L"-");
1156 				    }
1157 				    (void) printf(
1158 				    "\t                               %ws\n",
1159 					wc_name);
1160 				} else {
1161 				    (void) printf(
1162 				    "\t                               %s\n",
1163 				    "-");
1164 				}
1165 			    } else {
1166 				if (xmlTextReaderConstValue(reader)) {
1167 				    if (mbstowcs(wc_name,
1168 					(const char *)
1169 					xmlTextReaderConstValue(reader),
1170 					ISNS_MAX_NAME_LEN) == (size_t)-1) {
1171 					(void) wcscpy(wc_name, L"-");
1172 				    }
1173 				    (void) printf(
1174 				    "\tAuthorized Control Node Names: %ws\n",
1175 					wc_name);
1176 				} else {
1177 				    (void) printf(
1178 				    "\tAuthorized Control Node Names: %s\n",
1179 				    "-");
1180 				}
1181 				tag_printed = 1;
1182 			    }
1183 			} else {
1184 			    (void) printf(
1185 				"\tAuthorized Control Node Names: %s\n", "-");
1186 			    break;
1187 			}
1188 		    } else {
1189 			break;
1190 		    }
1191 		}
1192 		break;
1193 	    default:
1194 		ret = UNKNOWN;
1195 	}
1196 
1197 out:
1198 	(void) xmlTextReaderClose(reader);
1199 	(void) xmlFreeTextReader(reader);
1200 	if (status == PARTIAL_SUCCESS) {
1201 	    (void) fprintf(stderr, "%s\n",
1202 		getTextMessage(ERROR_PARTIAL_SUCCESS));
1203 	    if (ret == 0) ret = status;
1204 	}
1205 	return (ret);
1206 
1207 }
1208 
1209 /*
1210  * ****************************************************************************
1211  *
1212  * cvt_enumerate_rsp_to_get_req:
1213  *	pull out object info from enumerate response and calls
1214  *	build_get_xml_doc based on object type.
1215  *
1216  * doc		- enumerate resonse from the server.
1217  * req_do	- pointer to get request doc.
1218  * object_type	- isns object type.
1219  * flag		- user options
1220  *
1221  * ****************************************************************************
1222  */
1223 static int
cvt_enumerate_rsp_to_get_req(xmlChar * doc,xmlChar ** req_doc,object_type obj,uint32_t flag)1224 cvt_enumerate_rsp_to_get_req(xmlChar *doc, xmlChar **req_doc,
1225 	object_type obj, uint32_t flag)
1226 {
1227 	xmlTextReaderPtr reader;
1228 	xmlChar **argxmlv;
1229 	int ret = 0, status;
1230 	int i, argxmlc = 0, m_flag = 0;
1231 
1232 	if ((reader = (xmlTextReaderPtr)xmlReaderForMemory((const char *)doc,
1233 	    xmlStrlen(doc), NULL, NULL, 0)) == NULL) {
1234 	    return (ERROR_XML_READER_NULL);
1235 	}
1236 
1237 	/* if status is 0, continue on.  Otherwise return an error. */
1238 	if (reader = lookup_next_matching_elem(reader, &m_flag, STATUSELEMENT,
1239 	    RESULTELEMENT)) {
1240 	    if (m_flag == READER_MATCH) {
1241 		if (xmlTextReaderRead(reader) == 1) {
1242 		    status =
1243 		    atoi((const char *)xmlTextReaderConstValue(reader));
1244 		    if (status != 0) {
1245 			print_error_status(status, obj, reader);
1246 			(void) xmlTextReaderClose(reader);
1247 			(void) xmlFreeTextReader(reader);
1248 			return (status);
1249 		    }
1250 		} else {
1251 		    (void) xmlTextReaderClose(reader);
1252 		    xmlFreeTextReader(reader);
1253 		    return (ERROR_XML_STATUS_ELEM_NOT_FOUND);
1254 		}
1255 	    } else {
1256 		return (ERROR_XML_STATUS_ELEM_NOT_FOUND);
1257 	    }
1258 	} else {
1259 	    return (ERROR_XML_READER_NULL);
1260 	}
1261 
1262 	m_flag = 0;
1263 
1264 	argxmlv = (xmlChar **)malloc(sizeof (xmlChar *));
1265 
1266 	/* XXX - validate isnsResponse element from response doc. */
1267 	switch (obj) {
1268 	    case Node:
1269 		/* process the node elements */
1270 		while (reader = lookup_next_matching_elem(reader, &m_flag,
1271 		    NODEOBJECT, ISNSRESPONSE)) {
1272 		    if (m_flag == END_READER_MATCH) {
1273 			(void) xmlTextReaderNext(reader);
1274 			break;
1275 		    }
1276 
1277 		    /* check the type */
1278 		    if ((xmlTextReaderMoveToAttribute(reader,
1279 			(const xmlChar *)TYPEATTR)) == 1) {
1280 			if (((flag & TARGET_ONLY) == TARGET_ONLY) &&
1281 			    (XMLNCMPVAL(reader, TARGETTYPE) != 0)) {
1282 			    /* move to next node object. */
1283 			    (void) xmlTextReaderMoveToElement(reader);
1284 			    (void) xmlTextReaderNext(reader);
1285 			    continue;
1286 			}
1287 			if (((flag & INITIATOR_ONLY) == INITIATOR_ONLY) &&
1288 			    (XMLNCMPVAL(reader, INITIATORTYPE) != 0)) {
1289 			    /* move to next node object. */
1290 			    (void) xmlTextReaderMoveToElement(reader);
1291 			    (void) xmlTextReaderNext(reader);
1292 			    continue;
1293 			}
1294 		    } else {
1295 			ret = ERROR_XML_TYPE_ATTR_NOT_FOUND;
1296 			goto out;
1297 		    }
1298 
1299 		    if (((xmlTextReaderMoveToAttribute(reader,
1300 			(const xmlChar *)NAMEATTR)) == 1) &&
1301 			xmlTextReaderConstValue(reader)) {
1302 			argxmlv = NEW_XMLARGV(argxmlv, argxmlc);
1303 			if (argxmlv == (xmlChar **)NULL) {
1304 			    ret = ERROR_MALLOC_FAILED;
1305 			    goto out;
1306 			}
1307 			argxmlv[argxmlc++] =
1308 			    xmlStrdup(xmlTextReaderConstValue(reader));
1309 			argxmlv[argxmlc] = NULL;
1310 		    } else {
1311 			ret = ERROR_XML_NAME_ATTR_NOT_FOUND;
1312 			goto out;
1313 		    }
1314 		    (void) xmlTextReaderRead(reader);
1315 		    m_flag = 0;
1316 		} /* end for node while */
1317 		break;
1318 	    case DiscoveryDomain:
1319 		/* process the DiscoveryDoamin elements */
1320 		while (reader = lookup_next_matching_elem(reader, &m_flag,
1321 		    DDOBJECT, ISNSRESPONSE)) {
1322 		    if (m_flag == END_READER_MATCH) {
1323 			(void) xmlTextReaderNext(reader);
1324 			break;
1325 		    }
1326 
1327 		    if (((xmlTextReaderMoveToAttribute(reader,
1328 			(const xmlChar *)NAMEATTR)) == 1) &&
1329 			xmlTextReaderConstValue(reader)) {
1330 			argxmlv = NEW_XMLARGV(argxmlv, argxmlc);
1331 			if (argxmlv == (xmlChar **)NULL) {
1332 			    ret = ERROR_MALLOC_FAILED;
1333 			    goto out;
1334 			}
1335 			argxmlv[argxmlc++] =
1336 			    xmlStrdup(xmlTextReaderConstValue(reader));
1337 			argxmlv[argxmlc] = NULL;
1338 		    } else {
1339 			    ret = ERROR_XML_NAME_ATTR_NOT_FOUND;
1340 			    goto out;
1341 		    }
1342 		    m_flag = 0;
1343 		    (void) xmlTextReaderRead(reader);
1344 		}
1345 		break;
1346 	    case DiscoveryDomainSet:
1347 		/* process the DiscoveryDoaminSet elements */
1348 		while (reader = lookup_next_matching_elem(reader, &m_flag,
1349 		    DDSETOBJECT, ISNSRESPONSE)) {
1350 		    if (m_flag == END_READER_MATCH) {
1351 			(void) xmlTextReaderNext(reader);
1352 			break;
1353 		    }
1354 
1355 		    if (((xmlTextReaderMoveToAttribute(reader,
1356 			(const xmlChar *)NAMEATTR)) == 1) &&
1357 			(const char *)xmlTextReaderConstValue(reader)) {
1358 			argxmlv = NEW_XMLARGV(argxmlv, argxmlc);
1359 			if (argxmlv == (xmlChar **)NULL) {
1360 			    ret = ERROR_MALLOC_FAILED;
1361 			    goto out;
1362 			}
1363 			argxmlv[argxmlc++] =
1364 			    xmlStrdup(xmlTextReaderConstValue(reader));
1365 			argxmlv[argxmlc] = NULL;
1366 		    } else {
1367 			ret = ERROR_XML_NAME_ATTR_NOT_FOUND;
1368 			goto out;
1369 		    }
1370 		    m_flag = 0;
1371 		    (void) xmlTextReaderRead(reader);
1372 		}
1373 		break;
1374 	    default:
1375 		ret = UNKNOWN;
1376 		goto out;
1377 	}
1378 
1379 	/* if no object found, stop here.  The status can be still 0. */
1380 	if (argxmlc != 0) {
1381 	    if ((ret = build_get_xml_doc(argxmlc, (char **)argxmlv, obj,
1382 		req_doc)) != 0) {
1383 		return (ret);
1384 	    }
1385 	} else {
1386 	    if (ret == 0) {
1387 		/* indicate there is no error but not object is found. */
1388 		ret = SUCCESS_WITH_NO_OBJECT;
1389 	    }
1390 	}
1391 
1392 out:
1393 	(void) xmlTextReaderClose(reader);
1394 	(void) xmlFreeTextReader(reader);
1395 	if (argxmlc != 0) {
1396 	    for (i = 0; i < argxmlc; i++) {
1397 		xmlFree(argxmlv[i]);
1398 	    }
1399 	    (void) free(argxmlv);
1400 	}
1401 	return (ret);
1402 
1403 }
1404 
1405 /*
1406  * ****************************************************************************
1407  *
1408  * build_delete_xml_doc -
1409  *	build remove request doc based the name.
1410  *	the resulted doc is passed in the doc ptr.
1411  *
1412  * name		- object type
1413  * assoc	- association type
1414  * doc		- ptr to the resulted doc
1415  *
1416  * ****************************************************************************
1417  */
1418 static int
build_delete_xml_doc(int operandLen,char ** operand,object_type obj,char * container,xmlChar ** doc)1419 build_delete_xml_doc(int operandLen, char **operand, object_type obj,
1420 	char *container, xmlChar **doc)
1421 {
1422 	xmlTextWriterPtr writer;
1423 	xmlBufferPtr xbuf;
1424 	const xmlChar *content;
1425 	int i, len;
1426 
1427 	if ((xbuf = xmlBufferCreate()) == NULL) {
1428 		return (ERROR_XML_CREATE_BUFFER_FAILED);
1429 	}
1430 
1431 	if ((writer = xmlNewTextWriterMemory(xbuf, 0)) == NULL) {
1432 		return (ERROR_XML_CREATE_WRITER_FAILED);
1433 	}
1434 
1435 	if (xmlTextWriterStartDocument(writer, "1.0", NULL, NULL) < 0) {
1436 		return (ERROR_XML_START_DOC_FAILED);
1437 	}
1438 
1439 	/* Start element "isnsRequest". */
1440 	if (xmlTextWriterStartElement(writer, (xmlChar *)ISNSREQUEST) < 0) {
1441 	    return (ERROR_XML_START_ELEMENT_FAILED);
1442 	}
1443 
1444 	if ((xmlTextWriterWriteAttribute(writer,
1445 	    (xmlChar *)XMLNSATTR, (xmlChar *)XMLNSATTRVAL)) < 0) {
1446 	    return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1447 	}
1448 
1449 	/* request delete operation to get the entire list of obejct. */
1450 	if (xmlTextWriterStartElement(writer, (xmlChar *)DELETE) < 0) {
1451 		return (ERROR_XML_START_ELEMENT_FAILED);
1452 	}
1453 
1454 	switch (obj) {
1455 	    case DiscoveryDomain:
1456 		for (i = 0; i < operandLen; i++) {
1457 		    /* start Discovery Domain element. */
1458 		    if (xmlTextWriterStartElement(writer,
1459 			(xmlChar *)DDOBJECT) < 0) {
1460 			return (ERROR_XML_START_ELEMENT_FAILED);
1461 		    }
1462 
1463 		    /* Start attr "name". */
1464 		    if ((xmlTextWriterWriteAttribute(writer,
1465 			(xmlChar *)NAMEATTR, (xmlChar *)operand[i])) < 0) {
1466 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1467 		    }
1468 
1469 		    /* End element "DiscoveryDomain". */
1470 		    if (xmlTextWriterEndElement(writer) < 0) {
1471 			return (ERROR_XML_END_ELEMENT_FAILED);
1472 		    }
1473 		}
1474 		break;
1475 	    case DiscoveryDomainSet:
1476 		for (i = 0; i < operandLen; i++) {
1477 		    /* start Discovery DomainSet element. */
1478 		    if (xmlTextWriterStartElement(writer,
1479 			(xmlChar *)DDSETOBJECT) < 0) {
1480 			return (ERROR_XML_START_ELEMENT_FAILED);
1481 		    }
1482 
1483 		    /* Start attr "name". */
1484 		    if (xmlTextWriterWriteAttribute(writer,
1485 			(xmlChar *)NAMEATTR, (xmlChar *)operand[i]) < 0) {
1486 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1487 		    }
1488 
1489 		    /* End element "DiscoveryDomainSet". */
1490 		    if (xmlTextWriterEndElement(writer) < 0) {
1491 			return (ERROR_XML_END_ELEMENT_FAILED);
1492 		    }
1493 		}
1494 		break;
1495 	    case DiscoveryDomainMember:
1496 		for (i = 0; i < operandLen; i++) {
1497 		    /* start Discovery Domain Member element. */
1498 		    if (xmlTextWriterStartElement(writer,
1499 			(xmlChar *)DDOBJECTMEMBER) < 0) {
1500 			return (ERROR_XML_START_ELEMENT_FAILED);
1501 		    }
1502 
1503 		    /* Start attr "DD Name". */
1504 		    if (xmlTextWriterWriteAttribute(writer,
1505 			(xmlChar *)DDNAMEATTR, (xmlChar *)container) < 0) {
1506 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1507 		    }
1508 
1509 		    /* Start attr "Node Name". */
1510 		    if (xmlTextWriterWriteAttribute(writer,
1511 			(xmlChar *)NODENAMEATTR, (xmlChar *)operand[i]) < 0) {
1512 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1513 		    }
1514 
1515 		    /* End element "DiscoveryDomainMember. */
1516 		    if (xmlTextWriterEndElement(writer) < 0) {
1517 			return (ERROR_XML_END_ELEMENT_FAILED);
1518 		    }
1519 		}
1520 		break;
1521 	    case DiscoveryDomainSetMember:
1522 		for (i = 0; i < operandLen; i++) {
1523 		    /* start Discovery Domain Member element. */
1524 		    if (xmlTextWriterStartElement(writer,
1525 			(xmlChar *)DDSETOBJECTMEMBER) < 0) {
1526 			return (ERROR_XML_START_ELEMENT_FAILED);
1527 		    }
1528 
1529 		    /* Start attr "DD Set Name". */
1530 		    if (xmlTextWriterWriteAttribute(writer,
1531 			(xmlChar *)DDSETNAMEATTR, (xmlChar *)(container)) < 0) {
1532 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1533 		    }
1534 
1535 		    /* Start attr "DD Name". */
1536 		    if (xmlTextWriterWriteAttribute(writer,
1537 			(xmlChar *)DDNAMEATTR, (xmlChar *)(operand[i])) < 0) {
1538 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1539 		    }
1540 
1541 		    /* End element "DiscoveryDomainSetMember. */
1542 		    if (xmlTextWriterEndElement(writer) < 0) {
1543 			return (ERROR_XML_END_ELEMENT_FAILED);
1544 		    }
1545 		}
1546 		break;
1547 	    default:
1548 		    xmlFreeTextWriter(writer);
1549 		    return (UNKNOWN);
1550 	}
1551 
1552 	/* end createModify */
1553 	if (xmlTextWriterEndElement(writer) < 0) {
1554 	    xmlFreeTextWriter(writer);
1555 	    return (ERROR_XML_END_ELEMENT_FAILED);
1556 	}
1557 
1558 	/* End element "isnsRequest". */
1559 	if (xmlTextWriterEndElement(writer) < 0) {
1560 	    xmlFreeTextWriter(writer);
1561 	    return (ERROR_XML_END_ELEMENT_FAILED);
1562 	}
1563 	if (xmlTextWriterEndDocument(writer) < 0) {
1564 	    xmlFreeTextWriter(writer);
1565 	    return (ERROR_XML_END_DOC_FAILED);
1566 	}
1567 
1568 	xmlFreeTextWriter(writer);
1569 
1570 	len = xmlBufferLength(xbuf);
1571 	content = xmlBufferContent(xbuf);
1572 	if ((*doc = xmlStrndup(content, len)) == NULL) {
1573 	    return (ERROR_XML_STRDUP_FAILED);
1574 	}
1575 
1576 	xmlBufferFree(xbuf);
1577 
1578 	return (0);
1579 }
1580 
1581 /*
1582  * ****************************************************************************
1583  *
1584  * build_modify_xml_doc -
1585  *	build create request doc based the name.
1586  *	the resulted doc is passed in the doc ptr.
1587  *
1588  * operannLen	- number of objects
1589  * operand	- object list
1590  * enabled	- indication of enable and disable boolean type element.
1591  * doc		- ptr to the resulted doc
1592  *
1593  * ****************************************************************************
1594  */
1595 static int
build_modify_xml_doc(int operandLen,char ** operand,object_type obj,boolean_t enabled,xmlChar ** doc)1596 build_modify_xml_doc(int operandLen, char **operand, object_type obj,
1597 	boolean_t enabled, xmlChar **doc)
1598 {
1599 	xmlTextWriterPtr writer;
1600 	xmlBufferPtr xbuf;
1601 	const xmlChar *content;
1602 	int i, len;
1603 
1604 	if ((xbuf = xmlBufferCreate()) == NULL) {
1605 		return (ERROR_XML_CREATE_BUFFER_FAILED);
1606 	}
1607 
1608 	if ((writer = xmlNewTextWriterMemory(xbuf, 0)) == NULL) {
1609 		return (ERROR_XML_CREATE_WRITER_FAILED);
1610 	}
1611 
1612 	if (xmlTextWriterStartDocument(writer, "1.0", NULL, NULL) < 0) {
1613 		return (ERROR_XML_START_DOC_FAILED);
1614 	}
1615 
1616 	/* Start element "isnsRequest". */
1617 	if (xmlTextWriterStartElement(writer, (xmlChar *)ISNSREQUEST) < 0) {
1618 	    return (ERROR_XML_START_ELEMENT_FAILED);
1619 	}
1620 
1621 	if ((xmlTextWriterWriteAttribute(writer,
1622 	    (xmlChar *)XMLNSATTR, (xmlChar *)XMLNSATTRVAL)) < 0) {
1623 	    return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1624 	}
1625 
1626 	/* request createModify operation to get the entire list of obejct. */
1627 	if (xmlTextWriterStartElement(writer, (xmlChar *)CREATEMODIFY) < 0) {
1628 		return (ERROR_XML_START_ELEMENT_FAILED);
1629 	}
1630 
1631 	switch (obj) {
1632 	    case DiscoveryDomain:
1633 		for (i = 0; i < operandLen; i++) {
1634 		    /* start Discovery Domain element. */
1635 		    if (xmlTextWriterStartElement(writer,
1636 			(xmlChar *)DDOBJECT) < 0) {
1637 			return (ERROR_XML_START_ELEMENT_FAILED);
1638 		    }
1639 
1640 		    /* write attr "name". */
1641 		    if ((xmlTextWriterWriteAttribute(writer,
1642 			(xmlChar *)NAMEATTR, (xmlChar *)operand[i])) < 0) {
1643 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1644 		    }
1645 
1646 		    /* write bootlist_enabled elem */
1647 		    if (xmlTextWriterWriteElement(writer,
1648 			(xmlChar *)BOOTLISTENABLEDELEM, (enabled)?
1649 			(xmlChar *)XMLTRUE : (xmlChar *)XMLFALSE) < 0) {
1650 			return (ERROR_XML_WRITE_ELEMENT_FAILED);
1651 		    }
1652 
1653 		    /* End element "DiscoveryDomain". */
1654 		    if (xmlTextWriterEndElement(writer) < 0) {
1655 			return (ERROR_XML_END_ELEMENT_FAILED);
1656 		    }
1657 		}
1658 		break;
1659 	    case DiscoveryDomainSet:
1660 		for (i = 0; i < operandLen; i++) {
1661 		    /* start Discovery DomainSet element. */
1662 		    if (xmlTextWriterStartElement(writer,
1663 			(xmlChar *)DDSETOBJECT) < 0) {
1664 			return (ERROR_XML_START_ELEMENT_FAILED);
1665 		    }
1666 
1667 		    /* Start attr "name". */
1668 		    if (xmlTextWriterWriteAttribute(writer,
1669 			(xmlChar *)NAMEATTR, (xmlChar *)operand[i]) < 0) {
1670 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1671 		    }
1672 
1673 		    /* write enabled elem */
1674 		    if (xmlTextWriterWriteElement(writer,
1675 			(xmlChar *)ENABLEDELEM, (enabled) ?
1676 			(xmlChar *)XMLTRUE : (xmlChar *)XMLFALSE) < 0) {
1677 			return (ERROR_XML_WRITE_ELEMENT_FAILED);
1678 		    }
1679 
1680 		    /* End element "DiscoveryDomainSet". */
1681 		    if (xmlTextWriterEndElement(writer) < 0) {
1682 			return (ERROR_XML_END_ELEMENT_FAILED);
1683 		    }
1684 		}
1685 		break;
1686 	    default:
1687 		    xmlFreeTextWriter(writer);
1688 		    return (UNKNOWN);
1689 	}
1690 
1691 	/* end createModify */
1692 	if (xmlTextWriterEndElement(writer) < 0) {
1693 	    xmlFreeTextWriter(writer);
1694 	    return (ERROR_XML_END_ELEMENT_FAILED);
1695 	}
1696 
1697 	/* End element "isnsRequest". */
1698 	if (xmlTextWriterEndElement(writer) < 0) {
1699 	    xmlFreeTextWriter(writer);
1700 	    return (ERROR_XML_END_ELEMENT_FAILED);
1701 	}
1702 	if (xmlTextWriterEndDocument(writer) < 0) {
1703 	    xmlFreeTextWriter(writer);
1704 	    return (ERROR_XML_END_DOC_FAILED);
1705 	}
1706 
1707 	xmlFreeTextWriter(writer);
1708 
1709 	len = xmlBufferLength(xbuf);
1710 	content = xmlBufferContent(xbuf);
1711 	if ((*doc = xmlStrndup(content, len)) == NULL) {
1712 	    return (ERROR_XML_STRDUP_FAILED);
1713 	}
1714 
1715 	xmlBufferFree(xbuf);
1716 
1717 	return (0);
1718 }
1719 
1720 /*
1721  * ****************************************************************************
1722  *
1723  * build_rename_xml_doc -
1724  *	build create request doc based the name.
1725  *	the resulted doc is passed in the doc ptr.
1726  *
1727  * assoc	- a new name
1728  * id		- index of the object of which name  to be changed
1729  * doc		- ptr to the resulted doc
1730  *
1731  * ****************************************************************************
1732  */
1733 static int
build_rename_xml_doc(char * name,object_type obj,uint32_t id,xmlChar ** doc)1734 build_rename_xml_doc(char *name, object_type obj, uint32_t id, xmlChar **doc)
1735 {
1736 	xmlTextWriterPtr writer;
1737 	xmlBufferPtr xbuf;
1738 	const xmlChar *content;
1739 	int len;
1740 	char namebuf[32];
1741 
1742 	if ((xbuf = xmlBufferCreate()) == NULL) {
1743 		return (ERROR_XML_CREATE_BUFFER_FAILED);
1744 	}
1745 
1746 	if ((writer = xmlNewTextWriterMemory(xbuf, 0)) == NULL) {
1747 		return (ERROR_XML_CREATE_WRITER_FAILED);
1748 	}
1749 
1750 	if (xmlTextWriterStartDocument(writer, "1.0", NULL, NULL) < 0) {
1751 		return (ERROR_XML_START_DOC_FAILED);
1752 	}
1753 
1754 	/* Start element "isnsRequest". */
1755 	if (xmlTextWriterStartElement(writer, (xmlChar *)ISNSREQUEST) < 0) {
1756 	    return (ERROR_XML_START_ELEMENT_FAILED);
1757 	}
1758 
1759 	if ((xmlTextWriterWriteAttribute(writer,
1760 	    (xmlChar *)XMLNSATTR, (xmlChar *)XMLNSATTRVAL)) < 0) {
1761 	    return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1762 	}
1763 
1764 	/* request createModify operation to get the entire list of obejct. */
1765 	if (xmlTextWriterStartElement(writer, (xmlChar *)CREATEMODIFY) < 0) {
1766 		return (ERROR_XML_START_ELEMENT_FAILED);
1767 	}
1768 
1769 	switch (obj) {
1770 	    case DiscoveryDomain:
1771 		    /* start Discovery Domain element. */
1772 		    if (xmlTextWriterStartElement(writer,
1773 			(xmlChar *)DDOBJECT) < 0) {
1774 			return (ERROR_XML_START_ELEMENT_FAILED);
1775 		    }
1776 
1777 		    /* write attr "name". */
1778 		    if ((xmlTextWriterWriteAttribute(writer,
1779 			(xmlChar *)NAMEATTR, (xmlChar *)name)) < 0) {
1780 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1781 		    }
1782 
1783 		    /* write attr "id". */
1784 		    (void) sprintf(namebuf, "%d", id);
1785 		    if ((xmlTextWriterWriteAttribute(writer,
1786 			(xmlChar *)IDATTR, (xmlChar *)namebuf)) < 0) {
1787 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1788 		    }
1789 
1790 		    /* End element "DiscoveryDomain". */
1791 		    if (xmlTextWriterEndElement(writer) < 0) {
1792 			return (ERROR_XML_END_ELEMENT_FAILED);
1793 		    }
1794 		break;
1795 	    case DiscoveryDomainSet:
1796 		    /* start Discovery DomainSet element. */
1797 		    if (xmlTextWriterStartElement(writer,
1798 			(xmlChar *)DDSETOBJECT) < 0) {
1799 			return (ERROR_XML_START_ELEMENT_FAILED);
1800 		    }
1801 
1802 		    /* Start attr "name". */
1803 		    if (xmlTextWriterWriteAttribute(writer,
1804 			(xmlChar *)NAMEATTR, (xmlChar *)name) < 0) {
1805 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1806 		    }
1807 
1808 		    /* write attr "id". */
1809 		    (void) sprintf(namebuf, "%d", id);
1810 		    if ((xmlTextWriterWriteAttribute(writer,
1811 			(xmlChar *)IDATTR, (xmlChar *)namebuf)) < 0) {
1812 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1813 		    }
1814 
1815 		    /* End element "DiscoveryDomainSet". */
1816 		    if (xmlTextWriterEndElement(writer) < 0) {
1817 			return (ERROR_XML_END_ELEMENT_FAILED);
1818 		    }
1819 		break;
1820 	    default:
1821 		    xmlFreeTextWriter(writer);
1822 		    return (UNKNOWN);
1823 	}
1824 
1825 	/* end createModify */
1826 	if (xmlTextWriterEndElement(writer) < 0) {
1827 	    xmlFreeTextWriter(writer);
1828 	    return (ERROR_XML_END_ELEMENT_FAILED);
1829 	}
1830 
1831 	/* End element "isnsRequest". */
1832 	if (xmlTextWriterEndElement(writer) < 0) {
1833 	    xmlFreeTextWriter(writer);
1834 	    return (ERROR_XML_END_ELEMENT_FAILED);
1835 	}
1836 	if (xmlTextWriterEndDocument(writer) < 0) {
1837 	    xmlFreeTextWriter(writer);
1838 	    return (ERROR_XML_END_DOC_FAILED);
1839 	}
1840 
1841 	xmlFreeTextWriter(writer);
1842 
1843 	len = xmlBufferLength(xbuf);
1844 	content = xmlBufferContent(xbuf);
1845 	if ((*doc = xmlStrndup(content, len)) == NULL) {
1846 	    return (ERROR_XML_STRDUP_FAILED);
1847 	}
1848 
1849 	xmlBufferFree(xbuf);
1850 
1851 	return (0);
1852 }
1853 
1854 /*
1855  * ****************************************************************************
1856  *
1857  * build_create_xml_doc -
1858  *	build create request doc based the name.
1859  *	the resulted doc is passed in the doc ptr.
1860  *
1861  * name		- object type
1862  * assoc	- association type
1863  * doc		- ptr to the resulted doc
1864  *
1865  * ****************************************************************************
1866  */
1867 static int
build_create_xml_doc(int operandLen,char ** operand,object_type obj,char * container,xmlChar ** doc)1868 build_create_xml_doc(int operandLen, char **operand, object_type obj,
1869 	char *container, xmlChar **doc)
1870 {
1871 	xmlTextWriterPtr writer;
1872 	xmlBufferPtr xbuf;
1873 	const xmlChar *content;
1874 	int i, len;
1875 
1876 	if ((xbuf = xmlBufferCreate()) == NULL) {
1877 		return (ERROR_XML_CREATE_BUFFER_FAILED);
1878 	}
1879 
1880 	if ((writer = xmlNewTextWriterMemory(xbuf, 0)) == NULL) {
1881 		return (ERROR_XML_CREATE_WRITER_FAILED);
1882 	}
1883 
1884 	if (xmlTextWriterStartDocument(writer, "1.0", NULL, NULL) < 0) {
1885 		return (ERROR_XML_START_DOC_FAILED);
1886 	}
1887 
1888 	/* Start element "isnsRequest". */
1889 	if (xmlTextWriterStartElement(writer, (xmlChar *)ISNSREQUEST) < 0) {
1890 	    return (ERROR_XML_START_ELEMENT_FAILED);
1891 	}
1892 
1893 	/* request createModify operation to get the entire list of obejct. */
1894 	if (xmlTextWriterStartElement(writer, (xmlChar *)CREATEMODIFY) < 0) {
1895 		return (ERROR_XML_START_ELEMENT_FAILED);
1896 	}
1897 
1898 	switch (obj) {
1899 	    case DiscoveryDomain:
1900 		for (i = 0; i < operandLen; i++) {
1901 		    /* start Discovery Domain element. */
1902 		    if (xmlTextWriterStartElement(writer,
1903 			(xmlChar *)DDOBJECT) < 0) {
1904 			return (ERROR_XML_START_ELEMENT_FAILED);
1905 		    }
1906 
1907 		    /* Start attr "name". */
1908 		    if ((xmlTextWriterWriteAttribute(writer,
1909 			(xmlChar *)NAMEATTR, (xmlChar *)operand[i])) < 0) {
1910 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1911 		    }
1912 
1913 		    /* End element "DiscoveryDomain". */
1914 		    if (xmlTextWriterEndElement(writer) < 0) {
1915 			return (ERROR_XML_END_ELEMENT_FAILED);
1916 		    }
1917 		}
1918 		break;
1919 	    case DiscoveryDomainSet:
1920 		for (i = 0; i < operandLen; i++) {
1921 		    /* start Discovery DomainSet element. */
1922 		    if (xmlTextWriterStartElement(writer,
1923 			(xmlChar *)DDSETOBJECT) < 0) {
1924 			return (ERROR_XML_START_ELEMENT_FAILED);
1925 		    }
1926 
1927 		    /* Start attr "name". */
1928 		    if (xmlTextWriterWriteAttribute(writer,
1929 			(xmlChar *)NAMEATTR, (xmlChar *)operand[i]) < 0) {
1930 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1931 		    }
1932 
1933 		    /* End element "DiscoveryDomainSet". */
1934 		    if (xmlTextWriterEndElement(writer) < 0) {
1935 			return (ERROR_XML_END_ELEMENT_FAILED);
1936 		    }
1937 		}
1938 		break;
1939 	    case DiscoveryDomainMember:
1940 		for (i = 0; i < operandLen; i++) {
1941 		    /* start Discovery Domain Member element. */
1942 		    if (xmlTextWriterStartElement(writer,
1943 			(xmlChar *)DDOBJECTMEMBER) < 0) {
1944 			return (ERROR_XML_START_ELEMENT_FAILED);
1945 		    }
1946 
1947 		    /* Start attr "DD Name". */
1948 		    if (xmlTextWriterWriteAttribute(writer,
1949 			(xmlChar *)DDNAMEATTR, (xmlChar *)container) < 0) {
1950 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1951 		    }
1952 
1953 		    /* Start attr "Node Name". */
1954 		    if (xmlTextWriterWriteAttribute(writer,
1955 			(xmlChar *)NODENAMEATTR, (xmlChar *)operand[i]) < 0) {
1956 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1957 		    }
1958 
1959 		    /* End element "DiscoveryDomainMember. */
1960 		    if (xmlTextWriterEndElement(writer) < 0) {
1961 			return (ERROR_XML_END_ELEMENT_FAILED);
1962 		    }
1963 		}
1964 		break;
1965 	    case DiscoveryDomainSetMember:
1966 		for (i = 0; i < operandLen; i++) {
1967 		    /* start Discovery Domain Member element. */
1968 		    if (xmlTextWriterStartElement(writer,
1969 			(xmlChar *)DDSETOBJECTMEMBER) < 0) {
1970 			return (ERROR_XML_START_ELEMENT_FAILED);
1971 		    }
1972 
1973 		    /* Start attr "DD Set Name". */
1974 		    if (xmlTextWriterWriteAttribute(writer,
1975 			(xmlChar *)DDSETNAMEATTR, (xmlChar *)(container)) < 0) {
1976 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1977 		    }
1978 
1979 		    /* Start attr "DD Name". */
1980 		    if (xmlTextWriterWriteAttribute(writer,
1981 			(xmlChar *)DDNAMEATTR, (xmlChar *)(operand[i])) < 0) {
1982 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
1983 		    }
1984 
1985 		    /* End element "DiscoveryDomainSetMember. */
1986 		    if (xmlTextWriterEndElement(writer) < 0) {
1987 			return (ERROR_XML_END_ELEMENT_FAILED);
1988 		    }
1989 		}
1990 		break;
1991 	    default:
1992 		    xmlFreeTextWriter(writer);
1993 		    return (UNKNOWN);
1994 	}
1995 
1996 	/* end createModify */
1997 	if (xmlTextWriterEndElement(writer) < 0) {
1998 	    xmlFreeTextWriter(writer);
1999 	    return (ERROR_XML_END_ELEMENT_FAILED);
2000 	}
2001 
2002 	/* End element "isnsRequest". */
2003 	if (xmlTextWriterEndElement(writer) < 0) {
2004 	    xmlFreeTextWriter(writer);
2005 	    return (ERROR_XML_END_ELEMENT_FAILED);
2006 	}
2007 	if (xmlTextWriterEndDocument(writer) < 0) {
2008 	    xmlFreeTextWriter(writer);
2009 	    return (ERROR_XML_END_DOC_FAILED);
2010 	}
2011 
2012 	xmlFreeTextWriter(writer);
2013 
2014 	len = xmlBufferLength(xbuf);
2015 	content = xmlBufferContent(xbuf);
2016 	if ((*doc = xmlStrndup(content, len)) == NULL) {
2017 	    return (ERROR_XML_STRDUP_FAILED);
2018 	}
2019 
2020 	xmlBufferFree(xbuf);
2021 
2022 	return (0);
2023 }
2024 
2025 /*
2026  * ****************************************************************************
2027  *
2028  * build_assoc_xml_doc -
2029  *	build association request doc based the name.
2030  *	the resulted doc is passed in the doc ptr.
2031  *
2032  * name		- object type
2033  * assoc	- association type
2034  * doc		- ptr to the resulted doc
2035  *
2036  * ****************************************************************************
2037  */
2038 static int
build_assoc_xml_doc(xmlChar * name,association_t assoc,xmlChar ** doc)2039 build_assoc_xml_doc(xmlChar *name, association_t assoc, xmlChar **doc)
2040 {
2041 	xmlTextWriterPtr writer;
2042 	xmlBufferPtr xbuf;
2043 	const xmlChar *content;
2044 	int len;
2045 
2046 	if ((xbuf = xmlBufferCreate()) == NULL) {
2047 		return (ERROR_XML_CREATE_BUFFER_FAILED);
2048 	}
2049 
2050 	if ((writer = xmlNewTextWriterMemory(xbuf, 0)) == NULL) {
2051 		return (ERROR_XML_CREATE_WRITER_FAILED);
2052 	}
2053 
2054 	if (xmlTextWriterStartDocument(writer, "1.0", NULL, NULL) < 0) {
2055 		return (ERROR_XML_START_DOC_FAILED);
2056 	}
2057 
2058 	/* Start element "isnsRequest". */
2059 	if (xmlTextWriterStartElement(writer, (xmlChar *)ISNSREQUEST) < 0) {
2060 	    return (ERROR_XML_START_ELEMENT_FAILED);
2061 	}
2062 
2063 	/* request getAssociated operation to get the entire list of obejct. */
2064 	if (xmlTextWriterStartElement(writer, (xmlChar *)GETASSOCIATED) < 0) {
2065 		return (ERROR_XML_START_ELEMENT_FAILED);
2066 	}
2067 
2068 	switch (assoc) {
2069 	    case (node_to_dd):
2070 		/* write association type. */
2071 		if (xmlTextWriterWriteElement(writer,
2072 		    (xmlChar *)ASSOCIATIONTYPE,
2073 		    (xmlChar *)DDOBJECTMEMBER) < 0) {
2074 		    return (ERROR_XML_WRITE_ELEMENT_FAILED);
2075 		}
2076 
2077 		if (xmlTextWriterStartElement(writer,
2078 		    (xmlChar *)ISNSOBJECT) < 0) {
2079 		    return (ERROR_XML_START_ELEMENT_FAILED);
2080 		}
2081 
2082 		if (xmlTextWriterStartElement(writer,
2083 		    (xmlChar *)NODEOBJECT) < 0) {
2084 		    return (ERROR_XML_START_ELEMENT_FAILED);
2085 		}
2086 
2087 		/* Start attr "name". */
2088 		if (xmlTextWriterWriteAttribute(writer,
2089 		    (xmlChar *)NAMEATTR, name) < 0) {
2090 		    return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
2091 		}
2092 		if (xmlTextWriterWriteAttribute(writer,
2093 		    (xmlChar *)TYPEATTR, (xmlChar *)EMPTYSTR) < 0) {
2094 		    return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
2095 		}
2096 		if (xmlTextWriterWriteAttribute(writer,
2097 		    (xmlChar *)ALIASATTR, (xmlChar *)EMPTYSTR) < 0) {
2098 		    return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
2099 		}
2100 
2101 		/* End element "Node". */
2102 		if (xmlTextWriterEndElement(writer) < 0) {
2103 		    return (ERROR_XML_END_ELEMENT_FAILED);
2104 		}
2105 
2106 		/* End element "isnsObject". */
2107 		if (xmlTextWriterEndElement(writer) < 0) {
2108 		    return (ERROR_XML_END_ELEMENT_FAILED);
2109 		}
2110 		break;
2111 	    case (dd_to_node):
2112 		/* write association type. */
2113 		if (xmlTextWriterWriteElement(writer,
2114 		    (xmlChar *)ASSOCIATIONTYPE,
2115 		    (xmlChar *)DDOBJECTMEMBER) < 0) {
2116 		    return (ERROR_XML_WRITE_ELEMENT_FAILED);
2117 		}
2118 
2119 		/* start isnsObject */
2120 		if (xmlTextWriterStartElement(writer,
2121 		    (xmlChar *)ISNSOBJECT) < 0) {
2122 		    return (ERROR_XML_START_ELEMENT_FAILED);
2123 		}
2124 
2125 		/* start DiscoveryDomain */
2126 		if (xmlTextWriterStartElement(writer,
2127 		    (xmlChar *)DDOBJECT) < 0) {
2128 		    return (ERROR_XML_START_ELEMENT_FAILED);
2129 		}
2130 
2131 		/* Start attr "name". */
2132 		if (xmlTextWriterWriteAttribute(writer,
2133 		    (xmlChar *)NAMEATTR, name) < 0) {
2134 		    return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
2135 		}
2136 
2137 		/* End element "DiscoveryDomain". */
2138 		if (xmlTextWriterEndElement(writer) < 0) {
2139 		    return (ERROR_XML_END_ELEMENT_FAILED);
2140 		}
2141 
2142 		/* End element "isnsObject". */
2143 		if (xmlTextWriterEndElement(writer) < 0) {
2144 		    return (ERROR_XML_END_ELEMENT_FAILED);
2145 		}
2146 		break;
2147 	    case (ddset_to_dd):
2148 		/* write association type. */
2149 		if (xmlTextWriterWriteElement(writer,
2150 		    (xmlChar *)ASSOCIATIONTYPE,
2151 		    (xmlChar *)DDSETOBJECTMEMBER) < 0) {
2152 		    return (ERROR_XML_WRITE_ELEMENT_FAILED);
2153 		}
2154 
2155 		/* start isnsObject */
2156 		if (xmlTextWriterStartElement(writer,
2157 		    (xmlChar *)ISNSOBJECT) < 0) {
2158 		    return (ERROR_XML_START_ELEMENT_FAILED);
2159 		}
2160 
2161 		/* start DiscoveryDomainSet */
2162 		if (xmlTextWriterStartElement(writer,
2163 		    (xmlChar *)DDSETOBJECT) < 0) {
2164 		    return (ERROR_XML_START_ELEMENT_FAILED);
2165 		}
2166 
2167 		/* Start attr "name". */
2168 		if (xmlTextWriterWriteAttribute(writer,
2169 		    (xmlChar *)NAMEATTR, name) < 0) {
2170 		    return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
2171 		}
2172 
2173 		/* End element "DiscoveryDomain". */
2174 		if (xmlTextWriterEndElement(writer) < 0) {
2175 		    return (ERROR_XML_END_ELEMENT_FAILED);
2176 		}
2177 
2178 		/* End element "isnsObject". */
2179 		if (xmlTextWriterEndElement(writer) < 0) {
2180 		    return (ERROR_XML_END_ELEMENT_FAILED);
2181 		}
2182 		break;
2183 	    case (dd_to_ddset):
2184 		/* write association type. */
2185 		if (xmlTextWriterWriteElement(writer,
2186 		    (xmlChar *)ASSOCIATIONTYPE,
2187 		    (xmlChar *)DDSETOBJECTMEMBER) < 0) {
2188 		    return (ERROR_XML_WRITE_ELEMENT_FAILED);
2189 		}
2190 
2191 		/* start isnsObject */
2192 		if (xmlTextWriterStartElement(writer,
2193 		    (xmlChar *)ISNSOBJECT) < 0) {
2194 		    return (ERROR_XML_START_ELEMENT_FAILED);
2195 		}
2196 
2197 		/* start DiscoveryDomain */
2198 		if (xmlTextWriterStartElement(writer,
2199 		    (xmlChar *)DDOBJECT) < 0) {
2200 		    return (ERROR_XML_START_ELEMENT_FAILED);
2201 		}
2202 
2203 		/* Start attr "name". */
2204 		if (xmlTextWriterWriteAttribute(writer,
2205 		    (xmlChar *)NAMEATTR, name) < 0) {
2206 		    return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
2207 		}
2208 
2209 		/* End element "DiscoveryDomain". */
2210 		if (xmlTextWriterEndElement(writer) < 0) {
2211 		    return (ERROR_XML_END_ELEMENT_FAILED);
2212 		}
2213 
2214 		/* End element "isnsObject". */
2215 		if (xmlTextWriterEndElement(writer) < 0) {
2216 		    return (ERROR_XML_END_ELEMENT_FAILED);
2217 		}
2218 		break;
2219 	    default:
2220 		return (UNKNOWN);
2221 	}
2222 
2223 	/* end getAssociated */
2224 	if (xmlTextWriterEndElement(writer) < 0) {
2225 		return (ERROR_XML_END_ELEMENT_FAILED);
2226 	}
2227 
2228 	/* End element "isnsRequest". */
2229 	if (xmlTextWriterEndElement(writer) < 0) {
2230 	    return (ERROR_XML_END_ELEMENT_FAILED);
2231 	}
2232 	if (xmlTextWriterEndDocument(writer) < 0) {
2233 	    return (ERROR_XML_END_DOC_FAILED);
2234 	}
2235 
2236 	xmlFreeTextWriter(writer);
2237 
2238 	len = xmlBufferLength(xbuf);
2239 	content = xmlBufferContent(xbuf);
2240 	if ((*doc = xmlStrndup(content, len)) == NULL) {
2241 	    return (ERROR_XML_STRDUP_FAILED);
2242 	}
2243 
2244 	xmlBufferFree(xbuf);
2245 	return (0);
2246 }
2247 
2248 /*
2249  * ****************************************************************************
2250  *
2251  * build_enumerate_xml_doc -
2252  *	build association request doc based the name.
2253  *	the resulted doc is passed in the doc ptr.
2254  *
2255  * name		- object type
2256  * doc		- ptr to the resulted doc
2257  *
2258  * ****************************************************************************
2259  */
2260 static int
build_enumerate_xml_doc(object_type obj,xmlChar ** doc)2261 build_enumerate_xml_doc(object_type obj, xmlChar **doc)
2262 {
2263 	xmlTextWriterPtr writer;
2264 	xmlBufferPtr xbuf;
2265 	const xmlChar *content;
2266 	int len;
2267 
2268 	if ((xbuf = xmlBufferCreate()) == NULL) {
2269 		return (ERROR_XML_CREATE_BUFFER_FAILED);
2270 	}
2271 
2272 	if ((writer = xmlNewTextWriterMemory(xbuf, 0)) == NULL) {
2273 		return (ERROR_XML_CREATE_WRITER_FAILED);
2274 	}
2275 
2276 	if (xmlTextWriterStartDocument(writer, "1.0", NULL, NULL) < 0) {
2277 		return (ERROR_XML_START_DOC_FAILED);
2278 	}
2279 
2280 	/* Start element "isnsRequest". */
2281 	if (xmlTextWriterStartElement(writer, (xmlChar *)ISNSREQUEST) < 0) {
2282 	    return (ERROR_XML_START_ELEMENT_FAILED);
2283 	}
2284 
2285 	/* Start attr "xmlns". */
2286 	if (xmlTextWriterWriteAttribute(writer,
2287 	    (xmlChar *)"xmlns",
2288 	    (xmlChar *)"http://www.sun.com/schema/isnsmanagement")) {
2289 	    return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
2290 	}
2291 
2292 	/* request enumerate operation to get the entire list of obejct. */
2293 	if (xmlTextWriterStartElement(writer, (xmlChar *)ENUMERATE) < 0) {
2294 	    return (ERROR_XML_START_ELEMENT_FAILED);
2295 	}
2296 
2297 	switch (obj) {
2298 	    case (Node):
2299 		if (xmlTextWriterWriteElement(writer,
2300 		    (xmlChar *)ISNSOBJECTTYPE, (xmlChar *)NODEOBJECT) < 0) {
2301 		    return (ERROR_XML_WRITE_ELEMENT_FAILED);
2302 		}
2303 		break;
2304 	    case (DiscoveryDomain):
2305 		if (xmlTextWriterWriteElement(writer,
2306 		    (xmlChar *)ISNSOBJECTTYPE,
2307 		    (xmlChar *)DDOBJECT) < 0) {
2308 		    return (ERROR_XML_WRITE_ELEMENT_FAILED);
2309 		}
2310 		break;
2311 	    case (DiscoveryDomainSet):
2312 		if (xmlTextWriterWriteElement(writer,
2313 		    (xmlChar *)ISNSOBJECTTYPE,
2314 		    (xmlChar *)DDSETOBJECT) < 0) {
2315 		    return (ERROR_XML_WRITE_ELEMENT_FAILED);
2316 		}
2317 		break;
2318 	    default:
2319 		return (UNKNOWN);
2320 	}
2321 
2322 	/* end isns object type */
2323 	if (xmlTextWriterEndElement(writer) < 0) {
2324 	    return (ERROR_XML_END_ELEMENT_FAILED);
2325 	}
2326 
2327 	/* End element "isnsRequest". */
2328 	if (xmlTextWriterEndElement(writer) < 0) {
2329 	    return (ERROR_XML_END_ELEMENT_FAILED);
2330 	}
2331 	if (xmlTextWriterEndDocument(writer) < 0) {
2332 	    return (ERROR_XML_END_DOC_FAILED);
2333 	}
2334 
2335 	xmlFreeTextWriter(writer);
2336 
2337 	len = xmlBufferLength(xbuf);
2338 	content = xmlBufferContent(xbuf);
2339 	if ((*doc = xmlStrndup(content, len)) == NULL) {
2340 	    return (ERROR_XML_STRDUP_FAILED);
2341 	}
2342 
2343 	xmlBufferFree(xbuf);
2344 	return (0);
2345 }
2346 
2347 /*
2348  * ****************************************************************************
2349  *
2350  * build_get_xml_doc -
2351  *	build association request doc based the name.
2352  *	the resulted doc is passed in the doc ptr.
2353  *
2354  * name		- object type
2355  * assoc	- association type
2356  * doc		- ptr to the resulted doc
2357  *
2358  * ****************************************************************************
2359  */
2360 static int
build_get_xml_doc(int operandLen,char ** operand,object_type obj,xmlChar ** doc)2361 build_get_xml_doc(int operandLen, char **operand, object_type obj,
2362 	xmlChar **doc)
2363 {
2364 	xmlTextWriterPtr writer;
2365 	xmlBufferPtr xbuf;
2366 	const xmlChar *content;
2367 	int i, len;
2368 
2369 	if ((xbuf = xmlBufferCreate()) == NULL) {
2370 		return (ERROR_XML_CREATE_BUFFER_FAILED);
2371 	}
2372 
2373 	if ((writer = xmlNewTextWriterMemory(xbuf, 0)) == NULL) {
2374 		return (ERROR_XML_CREATE_WRITER_FAILED);
2375 	}
2376 
2377 	if (xmlTextWriterStartDocument(writer, "1.0", NULL, NULL) < 0) {
2378 		return (ERROR_XML_START_DOC_FAILED);
2379 	}
2380 
2381 	/* Start element "isnsRequest". */
2382 	if (xmlTextWriterStartElement(writer, (xmlChar *)ISNSREQUEST) < 0) {
2383 	    return (ERROR_XML_START_ELEMENT_FAILED);
2384 	}
2385 
2386 	/* Start attr "xmlns". */
2387 	if (xmlTextWriterWriteAttribute(writer,
2388 	    (xmlChar *)"xmlns",
2389 	    (xmlChar *)"http://www.sun.com/schema/isnsmanagement")) {
2390 	    return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
2391 	}
2392 
2393 	/* Start element "get". */
2394 	if (xmlTextWriterStartElement(writer, (xmlChar *)GET) < 0) {
2395 	    return (ERROR_XML_START_ELEMENT_FAILED);
2396 	}
2397 
2398 	switch (obj) {
2399 	    case (Node):
2400 		for (i = 0; i < operandLen; i++) {
2401 		    /* Start element "isnsObject". */
2402 		    if (xmlTextWriterStartElement(writer,
2403 			(xmlChar *)ISNSOBJECT) < 0) {
2404 			return (ERROR_XML_START_ELEMENT_FAILED);
2405 		    }
2406 
2407 		    /* Start element Node. */
2408 		    if (xmlTextWriterStartElement(writer,
2409 			(xmlChar *)NODEOBJECT) < 0) {
2410 			return (ERROR_XML_START_ELEMENT_FAILED);
2411 		    }
2412 
2413 		    /* Start attr "name". */
2414 		    if (xmlTextWriterWriteAttribute(writer,
2415 			(xmlChar *)NAMEATTR, (xmlChar *)operand[i]) < 0) {
2416 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
2417 		    }
2418 		    if (xmlTextWriterWriteAttribute(writer,
2419 			(xmlChar *)TYPEATTR, (xmlChar *)EMPTYSTR) < 0) {
2420 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
2421 		    }
2422 		    if (xmlTextWriterWriteAttribute(writer,
2423 			(xmlChar *)ALIASATTR, (xmlChar *)EMPTYSTR) < 0) {
2424 			return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
2425 		    }
2426 
2427 		    /* End element "Node". */
2428 		    if (xmlTextWriterEndElement(writer) < 0) {
2429 			return (ERROR_XML_END_ELEMENT_FAILED);
2430 		    }
2431 
2432 		    /* End element "isnsObject". */
2433 		    if (xmlTextWriterEndElement(writer) < 0) {
2434 			return (ERROR_XML_END_ELEMENT_FAILED);
2435 		    }
2436 		}
2437 		break;
2438 	    case (DiscoveryDomain):
2439 		    for (i = 0; i < operandLen; i++) {
2440 			/* Start element "isnsObject". */
2441 			if (xmlTextWriterStartElement(writer,
2442 			    (xmlChar *)ISNSOBJECT) < 0) {
2443 			    return (ERROR_XML_START_ELEMENT_FAILED);
2444 			}
2445 
2446 			if (xmlTextWriterStartElement(writer,
2447 			    (xmlChar *)DDOBJECT) < 0) {
2448 			    return (ERROR_XML_START_ELEMENT_FAILED);
2449 			}
2450 
2451 			/* Start attr "name". */
2452 			if (xmlTextWriterWriteAttribute(writer,
2453 			    (xmlChar *)NAMEATTR, (xmlChar *)operand[i]) < 0) {
2454 			    return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
2455 			}
2456 
2457 			/* End element "DiscoveryDomain". */
2458 			if (xmlTextWriterEndElement(writer) < 0) {
2459 			    return (ERROR_XML_END_ELEMENT_FAILED);
2460 			}
2461 
2462 			/* End element "isnsObject". */
2463 			if (xmlTextWriterEndElement(writer) < 0) {
2464 			    return (ERROR_XML_END_ELEMENT_FAILED);
2465 			}
2466 		    }
2467 		    break;
2468 	    case (DiscoveryDomainSet):
2469 		    for (i = 0; i < operandLen; i++) {
2470 			/* Start element "isnsObject". */
2471 			if (xmlTextWriterStartElement(writer,
2472 			    (xmlChar *)ISNSOBJECT) < 0) {
2473 			    return (ERROR_XML_START_ELEMENT_FAILED);
2474 			}
2475 
2476 			if (xmlTextWriterStartElement(writer,
2477 			    (xmlChar *)DDSETOBJECT) < 0) {
2478 			    return (ERROR_XML_START_ELEMENT_FAILED);
2479 			}
2480 
2481 			/* Start attr "name". */
2482 			if (xmlTextWriterWriteAttribute(writer,
2483 			    (xmlChar *)NAMEATTR, (xmlChar *)operand[i]) < 0) {
2484 			    return (ERROR_XML_WRITE_ATTRIBUTE_FAILED);
2485 			}
2486 
2487 			/* End element "DiscoveryDomain". */
2488 			if (xmlTextWriterEndElement(writer) < 0) {
2489 			    return (ERROR_XML_END_ELEMENT_FAILED);
2490 			}
2491 
2492 			/* End element "isnsObject". */
2493 			if (xmlTextWriterEndElement(writer) < 0) {
2494 			    return (ERROR_XML_END_ELEMENT_FAILED);
2495 			}
2496 		    }
2497 		    break;
2498 	    case (ServerConfig):
2499 		if (xmlTextWriterStartElement(writer,
2500 		    (xmlChar *)ISNSSERVER) < 0) {
2501 		    return (ERROR_XML_START_ELEMENT_FAILED);
2502 		}
2503 		if (xmlTextWriterEndElement(writer) < 0) {
2504 		    return (ERROR_XML_END_ELEMENT_FAILED);
2505 		}
2506 		break;
2507 	    default:
2508 	    return (UNKNOWN);
2509 	}
2510 
2511 	/* End element "get". */
2512 	if (xmlTextWriterEndElement(writer) < 0) {
2513 	    return (ERROR_XML_END_ELEMENT_FAILED);
2514 	}
2515 	/* End element "isnsRequest". */
2516 	if (xmlTextWriterEndElement(writer) < 0) {
2517 	    return (ERROR_XML_END_ELEMENT_FAILED);
2518 	}
2519 	if (xmlTextWriterEndDocument(writer) < 0) {
2520 	    return (ERROR_XML_END_DOC_FAILED);
2521 	}
2522 
2523 	xmlFreeTextWriter(writer);
2524 
2525 	len = xmlBufferLength(xbuf);
2526 	content = xmlBufferContent(xbuf);
2527 	if ((*doc = xmlStrndup(content, len)) == NULL) {
2528 	    return (ERROR_XML_STRDUP_FAILED);
2529 	}
2530 
2531 	xmlBufferFree(xbuf);
2532 	return (0);
2533 }
2534 
2535 /*
2536  * ****************************************************************************
2537  *
2538  * list_node_func -
2539  * 	isnsadm list-node [options] [<node name>, ...]
2540  *
2541  * operandLen	- number of operands user passed into the cli
2542  * operand	- pointer to operand list from user
2543  * options	- pointer to option list from user
2544  *
2545  * ****************************************************************************
2546  */
2547 /*ARGSUSED*/
2548 static int
list_node_func(int operandLen,char * operand[],cmdOptions_t * options,void * addarg)2549 list_node_func(int operandLen, char *operand[], cmdOptions_t *options,
2550 	void *addarg)
2551 {
2552 
2553 	cmdOptions_t *optionList = options;
2554 	xmlChar *doc, *e_doc;
2555 	int ret;
2556 	door_arg_t		darg;
2557 	int			fd, flag = 0;
2558 
2559 	for (; optionList->optval; optionList++) {
2560 	    switch (optionList->optval) {
2561 		case 'i':
2562 		    flag |= INITIATOR_ONLY;
2563 		    break;
2564 		case 't':
2565 		    flag |= TARGET_ONLY;
2566 		    break;
2567 		case 'v':
2568 		    flag |= VERBOSE;
2569 		    break;
2570 		default:
2571 		    return (UNKNOWN);
2572 	    }
2573 	}
2574 
2575 	if ((fd = open(ISNS_DOOR_NAME, 0)) == -1) {
2576 	    ret = check_door_error(ERROR_DOOR_OPEN_FAILED, errno);
2577 	    return (ret);
2578 	}
2579 
2580 	/* No operand specified. Issue enumerate. */
2581 	if (operandLen == 0) {
2582 	    ret = build_enumerate_xml_doc(Node, &doc);
2583 	    if (ret != 0) {
2584 		(void) close(fd);
2585 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
2586 		return (ret);
2587 	    }
2588 	    bzero(&darg, sizeof (darg));
2589 	    darg.data_ptr = (char *)doc;
2590 	    darg.data_size = xmlStrlen(doc);
2591 	    darg.rbuf = NULL;
2592 	    darg.rsize = 0;
2593 
2594 	    if ((flag & VERBOSE) == VERBOSE) {
2595 		if ((door_call(fd, &darg)) == -1) {
2596 		    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
2597 		    (void) close(fd);
2598 		    (void) xmlFree(doc);
2599 		    return (ret);
2600 		}
2601 
2602 		if ((ret = cvt_enumerate_rsp_to_get_req((xmlChar *)darg.rbuf,
2603 		    &e_doc, Node, flag)) != 0) {
2604 		    (void) munmap(darg.rbuf, darg.rsize);
2605 		    (void) close(fd);
2606 		    (void) xmlFree(doc);
2607 		    if (ret != SUCCESS_WITH_NO_OBJECT) {
2608 			(void) fprintf(stderr, "%s\n", getTextMessage(ret));
2609 		    } else {
2610 			ret = SUBCOMMAND_SUCCESS;
2611 		    }
2612 		    return (ret);
2613 		} else {
2614 		    (void) munmap(darg.rbuf, darg.rsize);
2615 		    (void) xmlFree(doc);
2616 		    doc = e_doc;
2617 		    bzero(&darg, sizeof (door_arg_t));
2618 		    darg.data_ptr = (char *)doc;
2619 		    darg.data_size = xmlStrlen(doc);
2620 		    darg.rbuf = NULL;
2621 		    darg.rsize = 0;
2622 		}
2623 	    }
2624 	} else {
2625 	    if ((ret = build_get_xml_doc(operandLen, operand, Node, &doc)) ==
2626 		0) {
2627 		bzero(&darg, sizeof (darg));
2628 		darg.data_ptr = (char *)doc;
2629 		darg.data_size = xmlStrlen(doc);
2630 		darg.rbuf = NULL;
2631 		darg.rsize = 0;
2632 	    } else {
2633 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
2634 		(void) close(fd);
2635 		(void) xmlFree(doc);
2636 		return (ret);
2637 	    }
2638 	}
2639 
2640 	if ((door_call(fd, &darg)) == -1) {
2641 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
2642 	    (void) close(fd);
2643 	    (void) xmlFree(doc);
2644 	    return (ret);
2645 	}
2646 
2647 	if ((ret = process_get_response(Node, (xmlChar *)darg.rbuf, flag)) !=
2648 	    0) {
2649 	/*
2650 	 * door frame work allocated a buffer when the date lager that rbuf.
2651 	 * indicate if munmap is required on rbuf.
2652 	 */
2653 	    (void) munmap(darg.rbuf, darg.rsize);
2654 	    (void) xmlFree(doc);
2655 	    (void) close(fd);
2656 	    return (ret);
2657 	}
2658 
2659 	(void) munmap(darg.rbuf, darg.rsize);
2660 	(void) close(fd);
2661 	xmlFree(doc);
2662 
2663 	return (SUBCOMMAND_SUCCESS);
2664 }
2665 
2666 /*
2667  * ****************************************************************************
2668  *
2669  * list_dd_func -
2670  * 	isnsadm list-dd [options] [<dd name>, ...]
2671  *
2672  * operandLen	- number of operands user passed into the cli
2673  * operand	- pointer to operand list from user
2674  * options	- pointer to option list from user
2675  *
2676  * ****************************************************************************
2677  */
2678 /*ARGSUSED*/
2679 static int
list_dd_func(int operandLen,char * operand[],cmdOptions_t * options,void * addarg)2680 list_dd_func(int operandLen, char *operand[], cmdOptions_t *options,
2681 	void *addarg)
2682 {
2683 	cmdOptions_t *optionList = options;
2684 	xmlChar *doc, *e_doc;
2685 	int ret;
2686 	door_arg_t		darg;
2687 	int			fd, flag = 0;
2688 
2689 	for (; optionList->optval; optionList++) {
2690 	    switch (optionList->optval) {
2691 		case 'v':
2692 		    flag |= VERBOSE;
2693 		    break;
2694 	    }
2695 	}
2696 
2697 	if ((fd = open(ISNS_DOOR_NAME, 0)) == -1) {
2698 	    ret = check_door_error(ERROR_DOOR_OPEN_FAILED, errno);
2699 	    return (ret);
2700 	}
2701 
2702 	/* No operand specified. Issue enumerate. */
2703 	if (operandLen == 0) {
2704 	    ret = build_enumerate_xml_doc(DiscoveryDomain, &doc);
2705 	    if (ret != 0) {
2706 		(void) close(fd);
2707 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
2708 		return (ret);
2709 	    }
2710 	    /* get the enumerate resposne first. */
2711 	    bzero(&darg, sizeof (darg));
2712 	    darg.data_ptr = (char *)doc;
2713 	    darg.data_size = xmlStrlen(doc);
2714 	    darg.rbuf = NULL;
2715 	    darg.rsize = 0;
2716 	    if ((door_call(fd, &darg)) == -1) {
2717 		ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
2718 		(void) close(fd);
2719 		(void) xmlFree(doc);
2720 		return (ret);
2721 	    }
2722 	    if ((ret = cvt_enumerate_rsp_to_get_req((xmlChar *)darg.rbuf,
2723 		&e_doc, DiscoveryDomain, flag)) != 0) {
2724 		(void) munmap(darg.rbuf, darg.rsize);
2725 		(void) close(fd);
2726 		(void) xmlFree(doc);
2727 		if (ret != SUCCESS_WITH_NO_OBJECT) {
2728 		    (void) fprintf(stderr, "%s\n", getTextMessage(ret));
2729 		} else {
2730 		    ret = SUBCOMMAND_SUCCESS;
2731 		}
2732 		return (ret);
2733 	    } else {
2734 		(void) munmap(darg.rbuf, darg.rsize);
2735 		(void) xmlFree(doc);
2736 		doc = e_doc;
2737 	    }
2738 	} else {
2739 	    if ((ret = build_get_xml_doc(operandLen, operand,
2740 		DiscoveryDomain, &doc)) != 0) {
2741 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
2742 		(void) close(fd);
2743 		(void) xmlFree(doc);
2744 		return (ret);
2745 	    }
2746 	}
2747 
2748 	bzero(&darg, sizeof (darg));
2749 	darg.data_ptr = (char *)doc;
2750 	darg.data_size = xmlStrlen(doc);
2751 	darg.rbuf = NULL;
2752 	darg.rsize = 0;
2753 
2754 	if ((door_call(fd, &darg)) == -1) {
2755 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
2756 	    (void) close(fd);
2757 	    (void) xmlFree(doc);
2758 	    return (ret);
2759 	}
2760 
2761 	if ((ret = process_get_response(DiscoveryDomain, (xmlChar *)darg.rbuf,
2762 	    flag)) != 0) {
2763 	    (void) munmap(darg.rbuf, darg.rsize);
2764 	    (void) close(fd);
2765 	    (void) xmlFree(doc);
2766 	    return (ret);
2767 	}
2768 
2769 	(void) munmap(darg.rbuf, darg.rsize);
2770 
2771 	(void) close(fd);
2772 	xmlFree(doc);
2773 
2774 	return (SUBCOMMAND_SUCCESS);
2775 }
2776 
2777 /*
2778  * ****************************************************************************
2779  *
2780  * list_ddset_func -
2781  * 	isnsadm list-dd-set [options] [<dd set name>, ...]
2782  *
2783  * operandLen	- number of operands user passed into the cli
2784  * operand	- pointer to operand list from user
2785  * options	- pointer to option list from user
2786  *
2787  * ****************************************************************************
2788  */
2789 /*ARGSUSED*/
2790 static int
list_ddset_func(int operandLen,char * operand[],cmdOptions_t * options,void * addarg)2791 list_ddset_func(int operandLen, char *operand[], cmdOptions_t *options,
2792 	void *addarg)
2793 {
2794 	cmdOptions_t *optionList = options;
2795 	xmlChar *doc, *e_doc;
2796 	msg_code_t ret;
2797 	door_arg_t		darg;
2798 	int			fd, flag = 0;
2799 
2800 	for (; optionList->optval; optionList++) {
2801 	    switch (optionList->optval) {
2802 		case 'v':
2803 		    flag |= VERBOSE;
2804 		    break;
2805 	    }
2806 	}
2807 
2808 	if ((fd = open(ISNS_DOOR_NAME, 0)) == -1) {
2809 	    ret = check_door_error(ERROR_DOOR_OPEN_FAILED, errno);
2810 	    return (ret);
2811 	}
2812 
2813 	/* No operand specified. Issue enumerate. */
2814 	if (operandLen == 0) {
2815 	    ret = build_enumerate_xml_doc(DiscoveryDomainSet, &doc);
2816 	    if (ret != 0) {
2817 		(void) close(fd);
2818 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
2819 		return (ret);
2820 	    }
2821 	    /* get the enumerate resposne. */
2822 	    bzero(&darg, sizeof (darg));
2823 	    darg.data_ptr = (char *)doc;
2824 	    darg.data_size = xmlStrlen(doc);
2825 	    darg.rbuf = NULL;
2826 	    darg.rsize = 0;
2827 	    if ((door_call(fd, &darg)) == -1) {
2828 		ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
2829 		(void) close(fd);
2830 		(void) xmlFree(doc);
2831 		return (ret);
2832 	    }
2833 
2834 	    if ((ret = cvt_enumerate_rsp_to_get_req((xmlChar *)darg.rbuf,
2835 		&e_doc, DiscoveryDomainSet, flag)) != 0) {
2836 		(void) munmap(darg.rbuf, darg.rsize);
2837 		(void) close(fd);
2838 		(void) xmlFree(doc);
2839 		if (ret != SUCCESS_WITH_NO_OBJECT) {
2840 		    (void) fprintf(stderr, "%s\n", getTextMessage(ret));
2841 		} else {
2842 		    ret = SUBCOMMAND_SUCCESS;
2843 		}
2844 		return (ret);
2845 	    } else {
2846 		(void) munmap(darg.rbuf, darg.rsize);
2847 		(void) xmlFree(doc);
2848 		doc = e_doc;
2849 		bzero(&darg, sizeof (darg));
2850 		darg.data_ptr = (char *)doc;
2851 		darg.data_size = xmlStrlen(doc);
2852 		darg.rbuf = NULL;
2853 		darg.rsize = 0;
2854 	    }
2855 	} else {
2856 	    if ((ret = build_get_xml_doc(operandLen, operand,
2857 		DiscoveryDomainSet, &doc)) == 0) {
2858 		bzero(&darg, sizeof (darg));
2859 		darg.data_ptr = (char *)doc;
2860 		darg.data_size = xmlStrlen(doc);
2861 		darg.rbuf = NULL;
2862 		darg.rsize = 0;
2863 	    } else {
2864 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
2865 	    }
2866 	}
2867 
2868 	if ((door_call(fd, &darg)) == -1) {
2869 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
2870 	    (void) close(fd);
2871 	    (void) xmlFree(doc);
2872 	    return (ret);
2873 	}
2874 
2875 	/*
2876 	 * door frame work allocated a buffer when the date lager that rbuf.
2877 	 * indicate if munmap is required on rbuf.
2878 	 */
2879 	if ((ret = process_get_response(DiscoveryDomainSet,
2880 	    (xmlChar *)darg.rbuf, flag)) != 0) {
2881 	    (void) munmap(darg.rbuf, darg.rsize);
2882 	    (void) close(fd);
2883 	    (void) xmlFree(doc);
2884 	    return (ret);
2885 	}
2886 
2887 	(void) munmap(darg.rbuf, darg.rsize);
2888 	(void) close(fd);
2889 	(void) xmlFree(doc);
2890 
2891 	return (SUBCOMMAND_SUCCESS);
2892 }
2893 
2894 /*
2895  * ****************************************************************************
2896  *
2897  * create_dd_func -
2898  * 	create a DiscoveryDomain create-dd <dd name>, ...
2899  *
2900  * operandLen	- number of operands user passed into the cli
2901  * operand	- pointer to operand list from user
2902  * options	- pointer to option list from user
2903  *
2904  * ****************************************************************************
2905  */
2906 /*ARGSUSED*/
2907 static int
create_dd_func(int operandLen,char * operand[],cmdOptions_t * options,void * addarg)2908 create_dd_func(int operandLen, char *operand[], cmdOptions_t *options,
2909 	void *addarg)
2910 {
2911 	xmlChar *doc;
2912 	msg_code_t ret;
2913 	door_arg_t		darg;
2914 	int			fd;
2915 
2916 	if ((fd = open(ISNS_DOOR_NAME, 0)) == -1) {
2917 	    ret = check_door_error(ERROR_DOOR_OPEN_FAILED, errno);
2918 	    return (ret);
2919 	}
2920 
2921 	if ((ret = build_create_xml_doc(operandLen, operand,
2922 		DiscoveryDomain, NULL, &doc)) == 0) {
2923 		bzero(&darg, sizeof (darg));
2924 		darg.data_ptr = (char *)doc;
2925 		darg.data_size = xmlStrlen(doc);
2926 		darg.rbuf = NULL;
2927 		darg.rsize = 0;
2928 	} else {
2929 		(void) close(fd);
2930 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
2931 		return (ret);
2932 	}
2933 
2934 	if ((door_call(fd, &darg)) == -1) {
2935 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
2936 	    (void) close(fd);
2937 	    (void) xmlFree(doc);
2938 	    return (ret);
2939 	}
2940 
2941 	/*
2942 	 * door frame work allocated a buffer when the date lager that rbuf.
2943 	 * indicate if munmap is required on rbuf.
2944 	 */
2945 	if ((ret = process_result_response((xmlChar *)darg.rbuf,
2946 		DiscoveryDomain)) != 0) {
2947 	    (void) munmap(darg.rbuf, darg.rsize);
2948 	    (void) close(fd);
2949 	    (void) xmlFree(doc);
2950 	    return (ret);
2951 	}
2952 
2953 	(void) munmap(darg.rbuf, darg.rsize);
2954 	(void) close(fd);
2955 	xmlFree(doc);
2956 
2957 	return (SUBCOMMAND_SUCCESS);
2958 }
2959 
2960 /*
2961  * ****************************************************************************
2962  *
2963  * create_ddset_func -
2964  * 	create a DiscoveryDomainSet create-dd-set <dd set name>, ...
2965  *
2966  * operandLen	- number of operands user passed into the cli
2967  * operand	- pointer to operand list from user
2968  * options	- pointer to option list from user
2969  *
2970  * ****************************************************************************
2971  */
2972 /*ARGSUSED*/
2973 static int
create_ddset_func(int operandLen,char * operand[],cmdOptions_t * options,void * addarg)2974 create_ddset_func(int operandLen, char *operand[], cmdOptions_t *options,
2975     void *addarg)
2976 {
2977 	xmlChar *doc;
2978 	msg_code_t ret;
2979 	door_arg_t		darg;
2980 	int			fd;
2981 
2982 	if ((fd = open(ISNS_DOOR_NAME, 0)) == -1) {
2983 	    ret = check_door_error(ERROR_DOOR_OPEN_FAILED, errno);
2984 	    return (ret);
2985 	}
2986 
2987 	if ((ret = build_create_xml_doc(operandLen, operand,
2988 		DiscoveryDomainSet, NULL, &doc)) == 0) {
2989 		bzero(&darg, sizeof (darg));
2990 		darg.data_ptr = (char *)doc;
2991 		darg.data_size = xmlStrlen(doc);
2992 		darg.rbuf = NULL;
2993 		darg.rsize = 0;
2994 	} else {
2995 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
2996 		(void) close(fd);
2997 		return (ret);
2998 	}
2999 
3000 	if ((door_call(fd, &darg)) == -1) {
3001 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
3002 	    (void) close(fd);
3003 	    (void) xmlFree(doc);
3004 	    return (ret);
3005 	}
3006 
3007 	/*
3008 	 * door frame work allocated a buffer when the date lager that rbuf.
3009 	 * indicate if munmap is required on rbuf.
3010 	 */
3011 	if ((ret = process_result_response((xmlChar *)darg.rbuf,
3012 		DiscoveryDomainSet)) != 0) {
3013 	    (void) munmap(darg.rbuf, darg.rsize);
3014 	    (void) close(fd);
3015 	    (void) xmlFree(doc);
3016 	    return (ret);
3017 	}
3018 
3019 	(void) munmap(darg.rbuf, darg.rsize);
3020 
3021 	(void) close(fd);
3022 	xmlFree(doc);
3023 
3024 	return (SUBCOMMAND_SUCCESS);
3025 }
3026 
3027 /*
3028  * ****************************************************************************
3029  *
3030  * modify_dd_func -
3031  * 	Modify a dd attr. currently rename function is supported
3032  *	modify-dd -n name <dd name>
3033  *
3034  * operandLen	- number of operands user passed into the cli
3035  * operand	- pointer to operand list from user
3036  * options	- pointer to option list from user
3037  *
3038  * ****************************************************************************
3039  */
3040 /*ARGSUSED*/
3041 static int
modify_dd_func(int operandLen,char * operand[],cmdOptions_t * options,void * addarg)3042 modify_dd_func(int operandLen, char *operand[], cmdOptions_t *options,
3043 	void *addarg)
3044 {
3045 	xmlChar *doc;
3046 	xmlTextReaderPtr reader;
3047 	msg_code_t ret;
3048 	door_arg_t	darg;
3049 	int	fd, m_flag = 0;
3050 	uint32_t    id;
3051 
3052 	if ((fd = open(ISNS_DOOR_NAME, 0)) == -1) {
3053 	    ret = check_door_error(ERROR_DOOR_OPEN_FAILED, errno);
3054 	    return (ret);
3055 	}
3056 
3057 	if ((ret = build_get_xml_doc(operandLen, operand,
3058 		DiscoveryDomain, &doc)) == 0) {
3059 		bzero(&darg, sizeof (darg));
3060 		darg.data_ptr = (char *)doc;
3061 		darg.data_size = xmlStrlen(doc);
3062 		darg.rbuf = NULL;
3063 		darg.rsize = 0;
3064 	} else {
3065 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
3066 		(void) close(fd);
3067 		return (ret);
3068 	}
3069 
3070 	if ((door_call(fd, &darg)) == -1) {
3071 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
3072 	    (void) close(fd);
3073 	    (void) xmlFree(doc);
3074 	    return (ret);
3075 	}
3076 
3077 	/* Free the request that is created by xmlStrnDup. */
3078 	(void) xmlFree(doc);
3079 
3080 	/*
3081 	 * door frame work allocated a buffer when the date lager that rbuf.
3082 	 * indicate if munmap is required on rbuf.
3083 	 */
3084 	if ((ret = process_result_response((xmlChar *)darg.rbuf,
3085 		DiscoveryDomain)) != 0) {
3086 	    (void) munmap(darg.rbuf, darg.rsize);
3087 	    (void) close(fd);
3088 	    return (ret);
3089 	}
3090 
3091 	/* setup xml parser on the response. */
3092 	if ((reader = (xmlTextReaderPtr)xmlReaderForMemory
3093 	    ((const char *)darg.rbuf, xmlStrlen((xmlChar *)darg.rbuf),
3094 	    NULL, NULL, 0)) == NULL) {
3095 	    (void) munmap(darg.rbuf, darg.rsize);
3096 	    (void) close(fd);
3097 	    return (ERROR_XML_READER_NULL);
3098 	}
3099 
3100 	if (reader = lookup_next_matching_elem(reader, &m_flag, DDOBJECT,
3101 	    ISNSRESPONSE)) {
3102 	    if (m_flag == READER_MATCH) {
3103 		if ((xmlTextReaderMoveToAttribute(reader,
3104 			(const xmlChar *)IDATTR)) == 1) {
3105 		    id = atoi((const char *)xmlTextReaderConstValue(reader));
3106 		} else {
3107 			(void) xmlTextReaderClose(reader);
3108 			(void) xmlFreeTextReader(reader);
3109 			return (ERROR_XML_ID_ATTR_NOT_FOUND);
3110 		}
3111 	    } else {
3112 		(void) xmlTextReaderClose(reader);
3113 		(void) xmlFreeTextReader(reader);
3114 		return (ERROR_XML_DD_OBJECT_NOT_FOUND);
3115 	    }
3116 	} else {
3117 	    (void) fprintf(stderr, "%s\n",
3118 		getTextMessage(ERROR_XML_READER_NULL));
3119 	    return (ERROR_XML_READER_NULL);
3120 	}
3121 
3122 	(void) xmlTextReaderClose(reader);
3123 	(void) xmlFreeTextReader(reader);
3124 
3125 	if ((ret = build_rename_xml_doc(options->optarg, DiscoveryDomain,
3126 		id, &doc)) == 0) {
3127 		bzero(&darg, sizeof (darg));
3128 		darg.data_ptr = (char *)doc;
3129 		darg.data_size = xmlStrlen(doc);
3130 		darg.rbuf = NULL;
3131 		darg.rsize = 0;
3132 	} else {
3133 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
3134 		(void) close(fd);
3135 		return (ret);
3136 	}
3137 
3138 	if ((door_call(fd, &darg)) == -1) {
3139 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
3140 	    (void) close(fd);
3141 	    (void) xmlFree(doc);
3142 	    return (ret);
3143 	}
3144 
3145 	/*
3146 	 * door frame work allocated a buffer when the date lager that rbuf.
3147 	 * indicate if munmap is required on rbuf.
3148 	 */
3149 	if ((ret = process_result_response((xmlChar *)darg.rbuf,
3150 		DiscoveryDomain)) != 0) {
3151 	    (void) munmap(darg.rbuf, darg.rsize);
3152 	    (void) close(fd);
3153 	    (void) xmlFree(doc);
3154 	    return (ret);
3155 	}
3156 
3157 	(void) munmap(darg.rbuf, darg.rsize);
3158 	(void) close(fd);
3159 	xmlFree(doc);
3160 
3161 	return (SUBCOMMAND_SUCCESS);
3162 }
3163 
3164 /*
3165  * ****************************************************************************
3166  *
3167  * modify_ddset_func -
3168  * 	Modify a dd attr. currently rename function is supported
3169  *	modify-dd-set -n name <dd name>
3170  *
3171  * operandLen	- number of operands user passed into the cli
3172  * operand	- pointer to operand list from user
3173  * options	- pointer to option list from user
3174  *
3175  * ****************************************************************************
3176  */
3177 /*ARGSUSED*/
3178 static int
modify_ddset_func(int operandLen,char * operand[],cmdOptions_t * options,void * addarg)3179 modify_ddset_func(int operandLen, char *operand[], cmdOptions_t *options,
3180 	void *addarg)
3181 {
3182 	xmlChar *doc;
3183 	xmlTextReaderPtr reader;
3184 	msg_code_t ret;
3185 	door_arg_t	darg;
3186 	int	fd, m_flag = 0;
3187 	uint32_t    id;
3188 
3189 	if ((fd = open(ISNS_DOOR_NAME, 0)) == -1) {
3190 	    ret = check_door_error(ERROR_DOOR_OPEN_FAILED, errno);
3191 	    return (ret);
3192 	}
3193 
3194 	if ((ret = build_get_xml_doc(operandLen, operand,
3195 		DiscoveryDomainSet, &doc)) == 0) {
3196 		bzero(&darg, sizeof (darg));
3197 		darg.data_ptr = (char *)doc;
3198 		darg.data_size = xmlStrlen(doc);
3199 		darg.rbuf = NULL;
3200 		darg.rsize = 0;
3201 	} else {
3202 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
3203 		(void) close(fd);
3204 		return (ret);
3205 	}
3206 
3207 	if ((door_call(fd, &darg)) == -1) {
3208 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
3209 	    (void) close(fd);
3210 	    (void) xmlFree(doc);
3211 	    return (ret);
3212 	}
3213 
3214 	/* Free the request that is created by xmlStrnDup. */
3215 	(void) xmlFree(doc);
3216 
3217 	/*
3218 	 * door frame work allocated a buffer when the date lager that rbuf.
3219 	 * indicate if munmap is required on rbuf.
3220 	 */
3221 	if ((ret = process_result_response((xmlChar *)darg.rbuf,
3222 		DiscoveryDomainSet)) != 0) {
3223 	    (void) munmap(darg.rbuf, darg.rsize);
3224 	    (void) close(fd);
3225 	    return (ret);
3226 	}
3227 
3228 	/* setup xml parser on the response. */
3229 	if ((reader = (xmlTextReaderPtr)xmlReaderForMemory
3230 	    ((const char *)darg.rbuf, xmlStrlen((xmlChar *)darg.rbuf),
3231 	    NULL, NULL, 0)) == NULL) {
3232 	    (void) munmap(darg.rbuf, darg.rsize);
3233 	    (void) close(fd);
3234 	    return (ERROR_XML_READER_NULL);
3235 	}
3236 
3237 	if (reader = lookup_next_matching_elem(reader, &m_flag, DDSETOBJECT,
3238 	    ISNSRESPONSE)) {
3239 	    if (m_flag == READER_MATCH) {
3240 		if ((xmlTextReaderMoveToAttribute(reader,
3241 			(const xmlChar *)IDATTR)) == 1) {
3242 		    id = atoi((const char *)xmlTextReaderConstValue(reader));
3243 		} else {
3244 			(void) xmlTextReaderClose(reader);
3245 			(void) xmlFreeTextReader(reader);
3246 			return (ERROR_XML_ID_ATTR_NOT_FOUND);
3247 		}
3248 	    } else {
3249 		(void) xmlTextReaderClose(reader);
3250 		(void) xmlFreeTextReader(reader);
3251 		(void) fprintf(stderr, "%s\n",
3252 		    getTextMessage(ERROR_XML_NAME_ATTR_NOT_FOUND));
3253 		return (ERROR_XML_DD_SET_OBJECT_NOT_FOUND);
3254 	    }
3255 	}
3256 
3257 	(void) xmlTextReaderClose(reader);
3258 	(void) xmlFreeTextReader(reader);
3259 
3260 	if ((ret = build_rename_xml_doc(options->optarg, DiscoveryDomainSet,
3261 		id, &doc)) == 0) {
3262 		bzero(&darg, sizeof (darg));
3263 		darg.data_ptr = (char *)doc;
3264 		darg.data_size = xmlStrlen(doc);
3265 		darg.rbuf = NULL;
3266 		darg.rsize = 0;
3267 	} else {
3268 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
3269 		(void) close(fd);
3270 		return (ret);
3271 	}
3272 
3273 	if ((door_call(fd, &darg)) == -1) {
3274 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
3275 	    (void) close(fd);
3276 	    (void) xmlFree(doc);
3277 	    return (ret);
3278 	}
3279 
3280 	/*
3281 	 * door frame work allocated a buffer when the date lager that rbuf.
3282 	 * indicate if munmap is required on rbuf.
3283 	 */
3284 	if ((ret = process_result_response((xmlChar *)darg.rbuf,
3285 		DiscoveryDomainSet)) != 0) {
3286 	    (void) munmap(darg.rbuf, darg.rsize);
3287 	    (void) close(fd);
3288 	    (void) xmlFree(doc);
3289 	    return (ret);
3290 	}
3291 
3292 	(void) munmap(darg.rbuf, darg.rsize);
3293 	(void) close(fd);
3294 	xmlFree(doc);
3295 
3296 	return (SUBCOMMAND_SUCCESS);
3297 }
3298 
3299 /*
3300  * ****************************************************************************
3301  *
3302  * add_node_func -
3303  * 	Add a node to a DiscoveryDomain add-node -d dd-name <node name>, ...
3304  *
3305  * operandLen	- number of operands user passed into the cli
3306  * operand	- pointer to operand list from user
3307  * options	- pointer to option list from user
3308  *
3309  * ****************************************************************************
3310  */
3311 /*ARGSUSED*/
3312 static int
add_node_func(int operandLen,char * operand[],cmdOptions_t * options,void * addarg)3313 add_node_func(int operandLen, char *operand[], cmdOptions_t *options,
3314 	void *addarg)
3315 {
3316 	xmlChar *doc;
3317 	msg_code_t ret;
3318 	door_arg_t	darg;
3319 	int	fd;
3320 
3321 	if ((fd = open(ISNS_DOOR_NAME, 0)) == -1) {
3322 	    ret = check_door_error(ERROR_DOOR_OPEN_FAILED, errno);
3323 	    return (ret);
3324 	}
3325 
3326 	if ((ret = build_create_xml_doc(operandLen, operand,
3327 		DiscoveryDomainMember, options->optarg, &doc)) == 0) {
3328 		bzero(&darg, sizeof (darg));
3329 		darg.data_ptr = (char *)doc;
3330 		darg.data_size = xmlStrlen(doc);
3331 		darg.rbuf = NULL;
3332 		darg.rsize = 0;
3333 	} else {
3334 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
3335 		(void) close(fd);
3336 		return (ret);
3337 	}
3338 
3339 	if ((door_call(fd, &darg)) == -1) {
3340 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
3341 	    (void) close(fd);
3342 	    (void) xmlFree(doc);
3343 	    return (ret);
3344 	}
3345 
3346 	/*
3347 	 * door frame work allocated a buffer when the date lager that rbuf.
3348 	 * indicate if munmap is required on rbuf.
3349 	 */
3350 	if ((ret = process_result_response((xmlChar *)darg.rbuf,
3351 		DiscoveryDomainMember)) != 0) {
3352 	    (void) munmap(darg.rbuf, darg.rsize);
3353 	    (void) close(fd);
3354 	    (void) xmlFree(doc);
3355 	    return (ret);
3356 	}
3357 
3358 	(void) munmap(darg.rbuf, darg.rsize);
3359 	(void) close(fd);
3360 	xmlFree(doc);
3361 
3362 	return (SUBCOMMAND_SUCCESS);
3363 }
3364 
3365 /*
3366  * ****************************************************************************
3367  *
3368  * add_dd_func -
3369  * 	Add a dd to a DiscoveryDomainSet add-dd -s dd-set name <dd name>, ...
3370  *
3371  * operandLen	- number of operands user passed into the cli
3372  * operand	- pointer to operand list from user
3373  * options	- pointer to option list from user
3374  *
3375  * ****************************************************************************
3376  */
3377 /*ARGSUSED*/
3378 static int
add_dd_func(int operandLen,char * operand[],cmdOptions_t * options,void * addarg)3379 add_dd_func(int operandLen, char *operand[], cmdOptions_t *options,
3380 	void *addarg)
3381 {
3382 	xmlChar *doc;
3383 	msg_code_t ret;
3384 	door_arg_t	darg;
3385 	int	fd;
3386 
3387 	if ((fd = open(ISNS_DOOR_NAME, 0)) == -1) {
3388 	    ret = check_door_error(ERROR_DOOR_OPEN_FAILED, errno);
3389 	    return (ret);
3390 	}
3391 
3392 	if ((ret = build_create_xml_doc(operandLen, operand,
3393 		DiscoveryDomainSetMember, options->optarg, &doc)) == 0) {
3394 		bzero(&darg, sizeof (darg));
3395 		darg.data_ptr = (char *)doc;
3396 		darg.data_size = xmlStrlen(doc);
3397 		darg.rbuf = NULL;
3398 		darg.rsize = 0;
3399 	} else {
3400 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
3401 		(void) close(fd);
3402 		return (ret);
3403 	}
3404 
3405 	if ((door_call(fd, &darg)) == -1) {
3406 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
3407 	    (void) close(fd);
3408 	    (void) xmlFree(doc);
3409 	    return (ret);
3410 	}
3411 
3412 	/*
3413 	 * door frame work allocated a buffer when the date lager that rbuf.
3414 	 * indicate if munmap is required on rbuf.
3415 	 */
3416 	if ((ret = process_result_response((xmlChar *)darg.rbuf,
3417 		DiscoveryDomainSetMember)) != 0) {
3418 	    (void) munmap(darg.rbuf, darg.rsize);
3419 	    (void) close(fd);
3420 	    (void) xmlFree(doc);
3421 	    return (ret);
3422 	}
3423 
3424 	(void) munmap(darg.rbuf, darg.rsize);
3425 	(void) close(fd);
3426 	xmlFree(doc);
3427 
3428 	return (SUBCOMMAND_SUCCESS);
3429 }
3430 
3431 /*
3432  * ****************************************************************************
3433  *
3434  * remove_node_func -
3435  * 	Remove a node from DiscoveryDomain
3436  *	remov-node -d dd-name <node name>, ...
3437  *
3438  * operandLen	- number of operands user passed into the cli
3439  * operand	- pointer to operand list from user
3440  * options	- pointer to option list from user
3441  *
3442  * ****************************************************************************
3443  */
3444 /*ARGSUSED*/
3445 static int
remove_node_func(int operandLen,char * operand[],cmdOptions_t * options,void * addarg)3446 remove_node_func(int operandLen, char *operand[], cmdOptions_t *options,
3447 	void *addarg)
3448 {
3449 	xmlChar *doc;
3450 	msg_code_t ret;
3451 	door_arg_t	darg;
3452 	int	fd;
3453 
3454 	if ((fd = open(ISNS_DOOR_NAME, 0)) == -1) {
3455 	    ret = check_door_error(ERROR_DOOR_OPEN_FAILED, errno);
3456 	    return (ret);
3457 	}
3458 
3459 	if ((ret = build_delete_xml_doc(operandLen, operand,
3460 		DiscoveryDomainMember, options->optarg, &doc)) == 0) {
3461 		bzero(&darg, sizeof (darg));
3462 		darg.data_ptr = (char *)doc;
3463 		darg.data_size = xmlStrlen(doc);
3464 		darg.rbuf = NULL;
3465 		darg.rsize = 0;
3466 	} else {
3467 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
3468 		(void) close(fd);
3469 		return (ret);
3470 	}
3471 
3472 	if ((door_call(fd, &darg)) == -1) {
3473 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
3474 	    (void) close(fd);
3475 	    (void) xmlFree(doc);
3476 	    return (ret);
3477 	}
3478 
3479 	/*
3480 	 * door frame work allocated a buffer when the date lager that rbuf.
3481 	 * indicate if munmap is required on rbuf.
3482 	 */
3483 	if ((ret = process_result_response((xmlChar *)darg.rbuf,
3484 		DiscoveryDomainMember)) != 0) {
3485 	    (void) munmap(darg.rbuf, darg.rsize);
3486 	    (void) close(fd);
3487 	    (void) xmlFree(doc);
3488 	    return (ret);
3489 	}
3490 
3491 	(void) munmap(darg.rbuf, darg.rsize);
3492 	(void) close(fd);
3493 	xmlFree(doc);
3494 
3495 	return (SUBCOMMAND_SUCCESS);
3496 }
3497 
3498 /*
3499  * ****************************************************************************
3500  *
3501  * remove_dd_func -
3502  * 	Remove a dd from DiscoveryDomainSet
3503  *	remove-dd -s dd-set name <dd name>, ...
3504  *
3505  * operandLen	- number of operands user passed into the cli
3506  * operand	- pointer to operand list from user
3507  * options	- pointer to option list from user
3508  *
3509  * ****************************************************************************
3510  */
3511 /*ARGSUSED*/
3512 static int
remove_dd_func(int operandLen,char * operand[],cmdOptions_t * options,void * addarg)3513 remove_dd_func(int operandLen, char *operand[], cmdOptions_t *options,
3514 	void *addarg)
3515 {
3516 	xmlChar *doc;
3517 	msg_code_t ret;
3518 	door_arg_t	darg;
3519 	int	fd;
3520 
3521 	if ((fd = open(ISNS_DOOR_NAME, 0)) == -1) {
3522 	    ret = check_door_error(ERROR_DOOR_OPEN_FAILED, errno);
3523 	    return (ret);
3524 	}
3525 
3526 	if ((ret = build_delete_xml_doc(operandLen, operand,
3527 		DiscoveryDomainSetMember, options->optarg, &doc)) == 0) {
3528 		bzero(&darg, sizeof (darg));
3529 		darg.data_ptr = (char *)doc;
3530 		darg.data_size = xmlStrlen(doc);
3531 		darg.rbuf = NULL;
3532 		darg.rsize = 0;
3533 	} else {
3534 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
3535 		(void) close(fd);
3536 		return (ret);
3537 	}
3538 
3539 	if ((door_call(fd, &darg)) == -1) {
3540 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
3541 	    (void) close(fd);
3542 	    (void) xmlFree(doc);
3543 	    return (ret);
3544 	}
3545 
3546 	/*
3547 	 * door frame work allocated a buffer when the date lager that rbuf.
3548 	 * indicate if munmap is required on rbuf.
3549 	 */
3550 	if ((ret = process_result_response((xmlChar *)darg.rbuf,
3551 		DiscoveryDomainSetMember)) != 0) {
3552 	    (void) munmap(darg.rbuf, darg.rsize);
3553 	    (void) close(fd);
3554 	    (void) xmlFree(doc);
3555 	    return (ret);
3556 	}
3557 
3558 	(void) munmap(darg.rbuf, darg.rsize);
3559 	(void) close(fd);
3560 	xmlFree(doc);
3561 
3562 	return (SUBCOMMAND_SUCCESS);
3563 }
3564 
3565 /*
3566  * ****************************************************************************
3567  *
3568  * delete_dd_func -
3569  * 	remove a DiscoveryDomain remove-dd <dd name>, ...
3570  *
3571  * operandLen	- number of operands user passed into the cli
3572  * operand	- pointer to operand list from user
3573  * options	- pointer to option list from user
3574  *
3575  * ****************************************************************************
3576  */
3577 /*ARGSUSED*/
3578 static int
delete_dd_func(int operandLen,char * operand[],cmdOptions_t * options,void * addarg)3579 delete_dd_func(int operandLen, char *operand[], cmdOptions_t *options,
3580 	void *addarg)
3581 {
3582 	xmlChar *doc;
3583 	msg_code_t ret;
3584 	door_arg_t		darg;
3585 	int			fd;
3586 
3587 	if ((fd = open(ISNS_DOOR_NAME, 0)) == -1) {
3588 	    ret = check_door_error(ERROR_DOOR_OPEN_FAILED, errno);
3589 	    return (ret);
3590 	}
3591 
3592 	if ((ret = build_delete_xml_doc(operandLen, operand,
3593 		DiscoveryDomain, NULL, &doc)) == 0) {
3594 		bzero(&darg, sizeof (darg));
3595 		darg.data_ptr = (char *)doc;
3596 		darg.data_size = xmlStrlen(doc);
3597 		darg.rbuf = NULL;
3598 		darg.rsize = 0;
3599 	} else {
3600 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
3601 		(void) close(fd);
3602 		return (ret);
3603 	}
3604 
3605 	if ((door_call(fd, &darg)) == -1) {
3606 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
3607 	    (void) close(fd);
3608 	    (void) xmlFree(doc);
3609 	    return (ret);
3610 	}
3611 
3612 	/*
3613 	 * door frame work allocated a buffer when the date lager that rbuf.
3614 	 * indicate if munmap is required on rbuf.
3615 	 */
3616 	if ((ret = process_result_response((xmlChar *)darg.rbuf,
3617 		DiscoveryDomain)) != 0) {
3618 	    (void) munmap(darg.rbuf, darg.rsize);
3619 	    (void) close(fd);
3620 	    (void) xmlFree(doc);
3621 	    return (ret);
3622 	}
3623 
3624 	(void) munmap(darg.rbuf, darg.rsize);
3625 
3626 	(void) close(fd);
3627 	xmlFree(doc);
3628 
3629 	return (SUBCOMMAND_SUCCESS);
3630 }
3631 
3632 /*
3633  * ****************************************************************************
3634  *
3635  * delete_ddset_func -
3636  * 	delete DiscoveryDomainSet(s) delete-dd-set <dd set name>, ...
3637  *
3638  * operandLen	- number of operands user passed into the cli
3639  * operand	- pointer to operand list from user
3640  * options	- pointer to option list from user
3641  *
3642  * ****************************************************************************
3643  */
3644 /*ARGSUSED*/
3645 static int
delete_ddset_func(int operandLen,char * operand[],cmdOptions_t * options,void * addarg)3646 delete_ddset_func(int operandLen, char *operand[], cmdOptions_t *options,
3647     void *addarg)
3648 {
3649 	xmlChar *doc;
3650 	msg_code_t ret;
3651 	door_arg_t		darg;
3652 	int			fd;
3653 
3654 	if ((fd = open(ISNS_DOOR_NAME, 0)) == -1) {
3655 	    ret = check_door_error(ERROR_DOOR_OPEN_FAILED, errno);
3656 	    return (ret);
3657 	}
3658 
3659 	if ((ret = build_delete_xml_doc(operandLen, operand,
3660 		DiscoveryDomainSet, NULL, &doc)) == 0) {
3661 		bzero(&darg, sizeof (darg));
3662 		darg.data_ptr = (char *)doc;
3663 		darg.data_size = xmlStrlen(doc);
3664 		darg.rbuf = NULL;
3665 		darg.rsize = 0;
3666 	} else {
3667 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
3668 		(void) close(fd);
3669 		return (ret);
3670 	}
3671 
3672 	if ((door_call(fd, &darg)) == -1) {
3673 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
3674 	    (void) close(fd);
3675 	    (void) xmlFree(doc);
3676 	    return (ret);
3677 	}
3678 
3679 	/*
3680 	 * door frame work allocated a buffer when the date lager that rbuf.
3681 	 * indicate if munmap is required on rbuf.
3682 	 */
3683 	if ((ret = process_result_response((xmlChar *)darg.rbuf,
3684 		DiscoveryDomainSet)) != 0) {
3685 	    (void) munmap(darg.rbuf, darg.rsize);
3686 	    (void) close(fd);
3687 	    (void) xmlFree(doc);
3688 	    return (ret);
3689 	}
3690 
3691 	(void) munmap(darg.rbuf, darg.rsize);
3692 	(void) close(fd);
3693 	xmlFree(doc);
3694 
3695 	return (SUBCOMMAND_SUCCESS);
3696 }
3697 
3698 /*
3699  * ****************************************************************************
3700  *
3701  * i_enableddset
3702  * 	enables/disables DiscoveryDomainSet(s)
3703  *
3704  * operandLen	- number of operands user passed into the cli
3705  * operand	- pointer to operand list from user
3706  * enable	- indication of enable/disable
3707  *
3708  * ****************************************************************************
3709  */
3710 static int
i_enableddset(int operandLen,char * operand[],boolean_t enable)3711 i_enableddset(int operandLen, char *operand[], boolean_t enable)
3712 {
3713 	xmlChar *doc;
3714 	door_arg_t		darg;
3715 	int fd, ret = 0;
3716 
3717 	if ((fd = open(ISNS_DOOR_NAME, 0)) == -1) {
3718 	    ret = check_door_error(ERROR_DOOR_OPEN_FAILED, errno);
3719 	    return (ret);
3720 	}
3721 
3722 	if ((ret = build_modify_xml_doc(operandLen, operand,
3723 		DiscoveryDomainSet, enable, &doc)) == 0) {
3724 		bzero(&darg, sizeof (darg));
3725 		darg.data_ptr = (char *)doc;
3726 		darg.data_size = xmlStrlen(doc);
3727 		darg.rbuf = NULL;
3728 		darg.rsize = 0;
3729 	} else {
3730 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
3731 		(void) close(fd);
3732 		return (ret);
3733 	}
3734 
3735 	if ((door_call(fd, &darg)) == -1) {
3736 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
3737 	    (void) close(fd);
3738 	    (void) xmlFree(doc);
3739 	    return (ret);
3740 	}
3741 
3742 	xmlFree(doc);
3743 
3744 	if ((ret = process_result_response((xmlChar *)darg.rbuf,
3745 		DiscoveryDomainSet)) != 0) {
3746 	    (void) munmap(darg.rbuf, darg.rsize);
3747 	    (void) close(fd);
3748 	    return (ret);
3749 	}
3750 
3751 	(void) munmap(darg.rbuf, darg.rsize);
3752 	(void) close(fd);
3753 	return (SUBCOMMAND_SUCCESS);
3754 }
3755 
3756 /*
3757  * ****************************************************************************
3758  *
3759  * enable_ddset_func -
3760  * 	enables DiscoveryDomainSet(s) enable-dd-set <dd set name>, ...
3761  *
3762  * operandLen	- number of operands user passed into the cli
3763  * operand	- pointer to operand list from user
3764  * options	- pointer to option list from user
3765  *
3766  * ****************************************************************************
3767  */
3768 /*ARGSUSED*/
3769 static int
enable_ddset_func(int operandLen,char * operand[],cmdOptions_t * options,void * addarg)3770 enable_ddset_func(int operandLen, char *operand[], cmdOptions_t *options,
3771     void *addarg)
3772 {
3773 	return (i_enableddset(operandLen, operand, B_TRUE));
3774 }
3775 
3776 /*
3777  * ****************************************************************************
3778  *
3779  * disabledsetFunc -
3780  * 	disable DiscoveryDomainSet(s) disable-dd-set <dd set name>, ...
3781  *
3782  * operandLen	- number of operands user passed into the cli
3783  * operand	- pointer to operand list from user
3784  * options	- pointer to option list from user
3785  *
3786  * ****************************************************************************
3787  */
3788 /*ARGSUSED*/
3789 static int
disable_ddset_func(int operandLen,char * operand[],cmdOptions_t * options,void * addarg)3790 disable_ddset_func(int operandLen, char *operand[], cmdOptions_t *options,
3791     void *addarg)
3792 {
3793 	return (i_enableddset(operandLen, operand, B_FALSE));
3794 }
3795 
3796 /*
3797  * ****************************************************************************
3798  *
3799  * show_config_func -
3800  * 	isnsadm show-config
3801  *
3802  * operandLen	- number of operands user passed into the cli
3803  * operand	- pointer to operand list from user
3804  * options	- pointer to option list from user
3805  *
3806  * ****************************************************************************
3807  */
3808 /*ARGSUSED*/
3809 static int
show_config_func(int operandLen,char * operand[],cmdOptions_t * options,void * addarg)3810 show_config_func(int operandLen, char *operand[], cmdOptions_t *options,
3811 	void *addarg)
3812 {
3813 	xmlChar *doc;
3814 	int ret;
3815 	door_arg_t		darg;
3816 	int			fd, flag = 0;
3817 
3818 	if ((fd = open(ISNS_DOOR_NAME, 0)) == -1) {
3819 	    ret = check_door_error(ERROR_DOOR_OPEN_FAILED, errno);
3820 	    return (ret);
3821 	}
3822 
3823 	if ((ret = build_get_xml_doc(operandLen, operand,
3824 		ServerConfig, &doc)) == 0) {
3825 		bzero(&darg, sizeof (darg));
3826 		darg.data_ptr = (char *)doc;
3827 		darg.data_size = xmlStrlen(doc);
3828 		darg.rbuf = NULL;
3829 		darg.rsize = 0;
3830 	} else {
3831 		(void) fprintf(stderr, "%s\n", getTextMessage(ret));
3832 		(void) close(fd);
3833 		(void) xmlFree(doc);
3834 		return (ret);
3835 	}
3836 
3837 	if ((door_call(fd, &darg)) == -1) {
3838 	    ret = check_door_error(ERROR_DOOR_CALL_FAILED, errno);
3839 	    (void) close(fd);
3840 	    (void) xmlFree(doc);
3841 	    return (ret);
3842 	}
3843 
3844 	if ((ret = process_get_response(ServerConfig, (xmlChar *)darg.rbuf,
3845 	    flag)) != 0) {
3846 	    (void) munmap(darg.rbuf, darg.rsize);
3847 	    (void) close(fd);
3848 	    (void) xmlFree(doc);
3849 	    return (ret);
3850 	}
3851 
3852 	(void) munmap(darg.rbuf, darg.rsize);
3853 	(void) close(fd);
3854 	xmlFree(doc);
3855 
3856 	return (SUBCOMMAND_SUCCESS);
3857 }
3858 
3859 /*
3860  * *************************************************************************
3861  *
3862  * main
3863  *
3864  * *************************************************************************
3865  */
3866 int
main(int argc,char * argv[])3867 main(int argc, char *argv[])
3868 {
3869 	synTables_t 			synTables;
3870 	char 				versionString[VERSION_STRING_MAX_LEN];
3871 	int 				ret;
3872 	int 				funcRet;
3873 	void 				*subcommandArgs = NULL;
3874 
3875 	(void) setlocale(LC_ALL, "");
3876 
3877 	(void) sprintf(versionString, "%2s.%2s",
3878 	    VERSION_STRING_MAJOR, VERSION_STRING_MINOR);
3879 	synTables.versionString = versionString;
3880 	synTables.longOptionTbl = &longOptions[0];
3881 	synTables.subCommandPropsTbl = &subcommands[0];
3882 
3883 	ret = cmdParse(argc, argv, synTables, subcommandArgs, &funcRet);
3884 
3885 	if (ret == 1) {
3886 		return (COMMAND_SYNTAX_FAILED);
3887 	} else if (ret == -1) {
3888 		perror(argv[0]);
3889 		return (1);
3890 	} else if (ret == 0) {
3891 		/*
3892 		 * strawman way to sort out the error code.
3893 		 * isnsi server protocol error range 0 - 99
3894 		 * isns server maangement op error range 100 -199
3895 		 * isnsadm error range 200 -299
3896 		 */
3897 	    if (funcRet == SUBCOMMAND_SUCCESS) {
3898 		return (0);
3899 	    } else if (funcRet > SUBCOMMAND_SUCCESS) {
3900 		if (funcRet != ERROR_DOOR_CALL_FAILED &&
3901 		    funcRet != ERROR_DOOR_OPEN_FAILED) {
3902 		    (void) fprintf(stderr, "%s\n", getTextMessage(funcRet));
3903 		}
3904 		return (1);
3905 	    } else {
3906 		return (1);
3907 	    }
3908 	}
3909 
3910 	return (0);
3911 } /* end main */
3912