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 */
25
26 #include <stdio.h>
27 #include <fcntl.h>
28 #include <ctype.h>
29 #include <string.h>
30 #include <stdlib.h>
31 #include <unistd.h>
32 #include <errno.h>
33 #include <limits.h>
34 #include <libintl.h>
35 #include <locale.h>
36 #include <sys/stat.h>
37 #include <sys/corectl.h>
38 #include <libproc.h>
39 #include <libscf.h>
40 #include <libscf_priv.h>
41 #include <assert.h>
42
43 #define E_SUCCESS 0 /* Exit status for success */
60 #define GLOBAL_PATTERN "global_pattern"
61 #define GLOBAL_CONTENT "global_content"
62 #define INIT_PATTERN "init_pattern"
63 #define INIT_CONTENT "init_content"
64
65 static char *command;
66 static uint64_t options;
67 static int alloptions;
68 static char *glob_pattern;
69 static char gpattern[PATH_MAX];
70 static core_content_t glob_content = CC_CONTENT_INVALID;
71 static char *init_pattern;
72 static char ipattern[PATH_MAX];
73 static core_content_t init_content = CC_CONTENT_INVALID;
74 static char *proc_pattern;
75 static size_t proc_size;
76 static core_content_t proc_content = CC_CONTENT_INVALID;
77
78 static int report_settings(void);
79 static int do_processes(int, char **);
80 static int do_modify(boolean_t);
81 static int do_update(void);
82 static int do_legacy(void);
83
84 static scf_propvec_t prop_gpattern = { GLOBAL_PATTERN, NULL, SCF_TYPE_ASTRING };
85 static scf_propvec_t prop_gcontent = { GLOBAL_CONTENT, NULL, SCF_TYPE_ASTRING };
86 static scf_propvec_t prop_ipattern = { INIT_PATTERN, NULL, SCF_TYPE_ASTRING };
87 static scf_propvec_t prop_icontent = { INIT_CONTENT, NULL, SCF_TYPE_ASTRING };
88 static scf_propvec_t prop_option[] = {
89 { GLOBAL_ENABLED, NULL, SCF_TYPE_BOOLEAN, NULL, CC_GLOBAL_PATH },
90 { PROCESS_ENABLED, NULL, SCF_TYPE_BOOLEAN, NULL, CC_PROCESS_PATH },
91 { GLOBAL_SETID_ENABLED, NULL, SCF_TYPE_BOOLEAN, NULL, CC_GLOBAL_SETID },
92 { PROCESS_SETID_ENABLED, NULL, SCF_TYPE_BOOLEAN, NULL, CC_PROCESS_SETID },
93 { GLOBAL_LOG_ENABLED, NULL, SCF_TYPE_BOOLEAN, NULL, CC_GLOBAL_LOG },
94 { NULL }
95 };
96 #define MAX_PROPS (4 + (sizeof (prop_option) / sizeof (scf_propvec_t)))
97
98 static void
99 usage(void)
100 {
101 (void) fprintf(stderr, gettext(
102 "usage:\n"));
103 (void) fprintf(stderr, gettext(
104 " %s [ -g pattern ] [ -i pattern ] [ -G content ] [ -I content ]\n"),
105 command);
106 (void) fprintf(stderr, gettext(
107 " [ -e {global | process | global-setid | proc-setid | log} ]\n"));
108 (void) fprintf(stderr, gettext(
109 " [ -d {global | process | global-setid | proc-setid | log} ]\n"));
110 (void) fprintf(stderr, gettext(
111 " %s [ -p pattern ] [ -P content ] [ pid ... ]\n"), command);
112 exit(E_USAGE);
226
227 if ((update || legacy_update) && (modify || proc_pattern != NULL ||
228 proc_content != CC_CONTENT_INVALID || npids != 0)) {
229 (void) fprintf(stderr,
230 gettext("%s: the -u option must stand alone\n"), command);
231 usage();
232 }
233 if (modify &&
234 (proc_pattern != NULL || proc_content != CC_CONTENT_INVALID)) {
235 (void) fprintf(stderr, gettext(
236 "%s: -[GIgied] and -[Pp] options are mutually exclusive\n"),
237 command);
238 usage();
239 }
240 if (modify && npids != 0) {
241 (void) fprintf(stderr, gettext(
242 "%s: -[GIgied] options cannot have a process-id list\n"),
243 command);
244 usage();
245 }
246 if ((proc_pattern != NULL || proc_content != CC_CONTENT_INVALID) &&
247 npids == 0) {
248 (void) sprintf(curpid, "%u", (uint_t)getppid());
249 npids = 1;
250 pidlist = &curpid_ptr;
251 }
252
253 if (legacy_update)
254 return (do_legacy());
255 if (update)
256 return (do_update());
257 if (modify)
258 return (do_modify(B_FALSE));
259 if (npids != 0)
260 return (do_processes(npids, pidlist));
261
262 return (report_settings());
263 }
264
265 static int
266 report_settings(void)
267 {
268 char content_str[PRCONTENTBUFSZ];
269
270 if ((options = core_get_options()) == -1) {
271 perror("core_get_options()");
272 return (E_ERROR);
273 }
274 if (core_get_global_path(gpattern, sizeof (gpattern)) != 0) {
275 perror("core_get_global_path()");
276 return (E_ERROR);
277 }
278 if (core_get_default_path(ipattern, sizeof (ipattern)) != 0) {
365 &proc_content, pid) != 0) {
366 perror(*pidlist);
367 rc = E_USAGE;
368 }
369 }
370 pidlist++;
371 }
372 }
373
374 return (rc);
375 }
376
377 static void
378 addprop(scf_propvec_t *props, int size, int count, scf_propvec_t *pv, void *ptr)
379 {
380 assert(count + 1 < size);
381 props[count] = *pv;
382 props[count].pv_ptr = ptr;
383 }
384
385 static boolean_t
386 is_online(const char *fmri)
387 {
388 char *state = smf_get_state(fmri);
389 boolean_t result = state != NULL &&
390 strcmp(state, SCF_STATE_STRING_ONLINE) == 0;
391
392 free(state);
393 return (result);
394 }
395
396 /*
397 * The user has specified the -g, -G, -i, -I, -d, or -e options to
398 * modify the given configuration parameter. Perform the modification
399 * in the smf repository and then perform a smf_refresh_instance which
400 * will cause a coreadm -u to occur which will transfer ALL coreadm
401 * configuration information from the repository to the kernel.
402 */
403 static int
404 do_modify(boolean_t method)
405 {
406 char gcontentstr[PRCONTENTBUFSZ];
407 char icontentstr[PRCONTENTBUFSZ];
408 scf_propvec_t *prop;
409 scf_propvec_t properties[MAX_PROPS + 1];
410 int count = 0;
411
412 if (!method && !is_online(COREADM_INST_FMRI)) {
413 (void) fprintf(stderr,
414 gettext("%s: coreadm service not online\n"), command);
415 return (E_ERROR);
416 }
417
418 if (glob_pattern != NULL)
419 addprop(properties, MAX_PROPS, count++, &prop_gpattern,
420 glob_pattern);
421
422 if (glob_content != CC_CONTENT_INVALID) {
423 (void) proc_content2str(glob_content, gcontentstr,
424 sizeof (gcontentstr));
425 addprop(properties, MAX_PROPS, count++, &prop_gcontent,
426 gcontentstr);
427 }
428
429 if (init_pattern != NULL)
430 addprop(properties, MAX_PROPS, count++, &prop_ipattern,
431 init_pattern);
432
433 if (init_content != CC_CONTENT_INVALID) {
434 (void) proc_content2str(init_content, icontentstr,
435 sizeof (icontentstr));
436 addprop(properties, MAX_PROPS, count++, &prop_icontent,
437 icontentstr);
441 if ((alloptions & prop->pv_aux) != 0)
442 addprop(properties, MAX_PROPS, count++, prop, &options);
443
444 properties[count].pv_prop = NULL;
445
446 prop = NULL;
447 if (scf_write_propvec(COREADM_INST_FMRI, CONFIG_PARAMS, properties,
448 &prop) == SCF_FAILED) {
449 if (prop != NULL) {
450 (void) fprintf(stderr, gettext(
451 "%s: Unable to write property '%s': %s"), command,
452 prop->pv_prop, scf_strerror(scf_error()));
453 } else {
454 (void) fprintf(stderr, gettext(
455 "%s: Unable to write configuration: %s\n"),
456 command, scf_strerror(scf_error()));
457 }
458 return (E_ERROR);
459 }
460
461 if (smf_refresh_instance(COREADM_INST_FMRI) != 0) {
462 (void) fprintf(stderr,
463 gettext("%s: Unable to refresh %s: %s\n"
464 "Configuration stored but not made active.\n"),
465 command, COREADM_INST_FMRI, scf_strerror(scf_error()));
466 return (E_ERROR);
467 }
468
469 return (E_SUCCESS);
470 }
471
472 static const char *
473 write_kernel(void)
474 {
475 if (core_set_global_path(glob_pattern, strlen(glob_pattern) + 1) != 0)
476 return ("core_set_global_path()");
477
478 if (core_set_global_content(&glob_content) != 0)
479 return ("core_set_global_content()");
480
481 if (core_set_default_path(init_pattern, strlen(init_pattern) + 1) != 0)
482 return ("core_set_default_path()");
483
484 if (core_set_default_content(&init_content) != 0)
485 return ("core_set_init_content()");
605
606 /*
607 * Loads and applies the coreadm configuration stored in the default
608 * coreadm instance. As this option is (only) used from within an SMF
609 * service method, this function must return an SMF_EXIT_* exit status
610 * to its caller.
611 */
612 static int
613 do_update(void)
614 {
615 char *gcstr, *icstr;
616 scf_propvec_t properties[MAX_PROPS + 1];
617 scf_propvec_t *prop;
618 int count = 0;
619 const char *errstr;
620
621 if (read_legacy()) {
622 if ((errstr = write_kernel()) != NULL)
623 goto error;
624
625 if (do_modify(B_TRUE) != 0 ||
626 rename(PATH_CONFIG, PATH_CONFIG_OLD) != 0) {
627 (void) fprintf(stderr, gettext(
628 "%s: failed to import legacy configuration.\n"),
629 command);
630 return (SMF_EXIT_ERR_FATAL);
631 }
632 return (SMF_EXIT_OK);
633 }
634
635 addprop(properties, MAX_PROPS, count++, &prop_gpattern, &glob_pattern);
636 addprop(properties, MAX_PROPS, count++, &prop_gcontent, &gcstr);
637 addprop(properties, MAX_PROPS, count++, &prop_ipattern, &init_pattern);
638 addprop(properties, MAX_PROPS, count++, &prop_icontent, &icstr);
639 for (prop = prop_option; prop->pv_prop != NULL; prop++)
640 addprop(properties, MAX_PROPS, count++, prop, &options);
641 properties[count].pv_prop = NULL;
642
643 alloptions = CC_OPTIONS;
644 if (scf_read_propvec(COREADM_INST_FMRI, CONFIG_PARAMS, B_TRUE,
645 properties, &prop) == SCF_FAILED) {
646 if (prop != NULL) {
647 (void) fprintf(stderr, gettext(
648 "%s: configuration property '%s' not found.\n"),
649 command, prop->pv_prop);
650 } else {
651 (void) fprintf(stderr, gettext(
652 "%s: unable to read configuration: %s\n"),
653 command, scf_strerror(scf_error()));
654 }
655 return (SMF_EXIT_ERR_FATAL);
656 }
657
658 (void) proc_str2content(gcstr, &glob_content);
659 (void) proc_str2content(icstr, &init_content);
660
661 errstr = write_kernel();
662 scf_clean_propvec(properties);
663 if (errstr == NULL)
664 return (SMF_EXIT_OK);
665
666 error:
667 if (errno == EPERM) {
668 (void) perm();
669 return (SMF_EXIT_ERR_PERM);
670 }
671 perror(errstr);
672 return (SMF_EXIT_ERR_FATAL);
673 }
674
675 static int do_legacy()
676 {
677 const char *errstr;
678
679 if (read_legacy() && (errstr = write_kernel()) != NULL) {
680 if (errno == EPERM)
681 return (perm());
682 perror(errstr);
683 return (E_ERROR);
684 }
685
686 return (E_SUCCESS);
687 }
|
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 *
25 * Copyright 2017 RackTop Systems.
26 */
27
28 #include <stdio.h>
29 #include <fcntl.h>
30 #include <ctype.h>
31 #include <string.h>
32 #include <stdlib.h>
33 #include <unistd.h>
34 #include <errno.h>
35 #include <limits.h>
36 #include <libintl.h>
37 #include <locale.h>
38 #include <sys/stat.h>
39 #include <sys/corectl.h>
40 #include <libproc.h>
41 #include <libscf.h>
42 #include <libscf_priv.h>
43 #include <assert.h>
44
45 #define E_SUCCESS 0 /* Exit status for success */
62 #define GLOBAL_PATTERN "global_pattern"
63 #define GLOBAL_CONTENT "global_content"
64 #define INIT_PATTERN "init_pattern"
65 #define INIT_CONTENT "init_content"
66
67 static char *command;
68 static uint64_t options;
69 static int alloptions;
70 static char *glob_pattern;
71 static char gpattern[PATH_MAX];
72 static core_content_t glob_content = CC_CONTENT_INVALID;
73 static char *init_pattern;
74 static char ipattern[PATH_MAX];
75 static core_content_t init_content = CC_CONTENT_INVALID;
76 static char *proc_pattern;
77 static size_t proc_size;
78 static core_content_t proc_content = CC_CONTENT_INVALID;
79
80 static int report_settings(void);
81 static int do_processes(int, char **);
82 static int do_modify(void);
83 static int do_update(void);
84 static int do_legacy(void);
85
86 static scf_propvec_t prop_gpattern = { GLOBAL_PATTERN, NULL, SCF_TYPE_ASTRING };
87 static scf_propvec_t prop_gcontent = { GLOBAL_CONTENT, NULL, SCF_TYPE_ASTRING };
88 static scf_propvec_t prop_ipattern = { INIT_PATTERN, NULL, SCF_TYPE_ASTRING };
89 static scf_propvec_t prop_icontent = { INIT_CONTENT, NULL, SCF_TYPE_ASTRING };
90 static scf_propvec_t prop_option[] = {
91 { GLOBAL_ENABLED, NULL, SCF_TYPE_BOOLEAN, NULL, CC_GLOBAL_PATH },
92 { PROCESS_ENABLED, NULL, SCF_TYPE_BOOLEAN, NULL, CC_PROCESS_PATH },
93 { GLOBAL_SETID_ENABLED, NULL, SCF_TYPE_BOOLEAN, NULL, CC_GLOBAL_SETID },
94 { PROCESS_SETID_ENABLED, NULL, SCF_TYPE_BOOLEAN, NULL,
95 CC_PROCESS_SETID },
96 { GLOBAL_LOG_ENABLED, NULL, SCF_TYPE_BOOLEAN, NULL, CC_GLOBAL_LOG },
97 { NULL }
98 };
99 #define MAX_PROPS (4 + (sizeof (prop_option) / sizeof (scf_propvec_t)))
100
101 static void
102 usage(void)
103 {
104 (void) fprintf(stderr, gettext(
105 "usage:\n"));
106 (void) fprintf(stderr, gettext(
107 " %s [ -g pattern ] [ -i pattern ] [ -G content ] [ -I content ]\n"),
108 command);
109 (void) fprintf(stderr, gettext(
110 " [ -e {global | process | global-setid | proc-setid | log} ]\n"));
111 (void) fprintf(stderr, gettext(
112 " [ -d {global | process | global-setid | proc-setid | log} ]\n"));
113 (void) fprintf(stderr, gettext(
114 " %s [ -p pattern ] [ -P content ] [ pid ... ]\n"), command);
115 exit(E_USAGE);
229
230 if ((update || legacy_update) && (modify || proc_pattern != NULL ||
231 proc_content != CC_CONTENT_INVALID || npids != 0)) {
232 (void) fprintf(stderr,
233 gettext("%s: the -u option must stand alone\n"), command);
234 usage();
235 }
236 if (modify &&
237 (proc_pattern != NULL || proc_content != CC_CONTENT_INVALID)) {
238 (void) fprintf(stderr, gettext(
239 "%s: -[GIgied] and -[Pp] options are mutually exclusive\n"),
240 command);
241 usage();
242 }
243 if (modify && npids != 0) {
244 (void) fprintf(stderr, gettext(
245 "%s: -[GIgied] options cannot have a process-id list\n"),
246 command);
247 usage();
248 }
249 if (glob_pattern != NULL && glob_pattern[0] != '/') {
250 (void) fprintf(stderr, gettext(
251 "%s: the -g option must specify an absolute path\n"),
252 command);
253 usage();
254 }
255 if ((proc_pattern != NULL || proc_content != CC_CONTENT_INVALID) &&
256 npids == 0) {
257 (void) sprintf(curpid, "%u", (uint_t)getppid());
258 npids = 1;
259 pidlist = &curpid_ptr;
260 }
261
262 if (legacy_update)
263 return (do_legacy());
264 if (update)
265 return (do_update());
266 if (modify)
267 return (do_modify());
268 if (npids != 0)
269 return (do_processes(npids, pidlist));
270
271 return (report_settings());
272 }
273
274 static int
275 report_settings(void)
276 {
277 char content_str[PRCONTENTBUFSZ];
278
279 if ((options = core_get_options()) == -1) {
280 perror("core_get_options()");
281 return (E_ERROR);
282 }
283 if (core_get_global_path(gpattern, sizeof (gpattern)) != 0) {
284 perror("core_get_global_path()");
285 return (E_ERROR);
286 }
287 if (core_get_default_path(ipattern, sizeof (ipattern)) != 0) {
374 &proc_content, pid) != 0) {
375 perror(*pidlist);
376 rc = E_USAGE;
377 }
378 }
379 pidlist++;
380 }
381 }
382
383 return (rc);
384 }
385
386 static void
387 addprop(scf_propvec_t *props, int size, int count, scf_propvec_t *pv, void *ptr)
388 {
389 assert(count + 1 < size);
390 props[count] = *pv;
391 props[count].pv_ptr = ptr;
392 }
393
394 static int
395 make_active(void)
396 {
397 char *state = smf_get_state(COREADM_INST_FMRI);
398
399 switch (state == NULL ? -1 : smf_state_from_string(state)) {
400 case SCF_STATE_ONLINE:
401 if (smf_refresh_instance_synchronous(COREADM_INST_FMRI) != 0) {
402 (void) fprintf(stderr,
403 gettext("%s: Unable to refresh %s: %s\n"),
404 command, COREADM_INST_FMRI,
405 scf_strerror(scf_error()));
406 return (-1);
407 }
408 break;
409 case SCF_STATE_DEGRADED:
410 case SCF_STATE_MAINT:
411 if (smf_restore_instance_synchronous(COREADM_INST_FMRI) != 0) {
412 (void) fprintf(stderr,
413 gettext("%s: Unable to clear %s: %s\n"),
414 command, COREADM_INST_FMRI,
415 scf_strerror(scf_error()));
416 return (-1);
417 }
418 break;
419 case SCF_STATE_DISABLED:
420 if (smf_enable_instance_synchronous(COREADM_INST_FMRI,
421 0) != 0) {
422 (void) fprintf(stderr,
423 gettext("%s: Unable to enable %s: %s\n"),
424 command, COREADM_INST_FMRI,
425 scf_strerror(scf_error()));
426 return (-1);
427 }
428 break;
429 case SCF_STATE_OFFLINE:
430 default:
431 (void) fprintf(stderr,
432 gettext("%s: coreadm service not online\n"), command);
433 return (-1);
434 }
435
436 return (0);
437 }
438
439 /*
440 * The user has specified the -g, -G, -i, -I, -d, or -e options to
441 * modify the given configuration parameter. Perform the modification
442 * in the smf repository and then perform a smf_refresh_instance which
443 * will cause a coreadm -u to occur which will transfer ALL coreadm
444 * configuration information from the repository to the kernel.
445 */
446 static int
447 do_modify(void)
448 {
449 char gcontentstr[PRCONTENTBUFSZ];
450 char icontentstr[PRCONTENTBUFSZ];
451 scf_propvec_t *prop;
452 scf_propvec_t properties[MAX_PROPS + 1];
453 int count = 0;
454
455 if (glob_pattern != NULL)
456 addprop(properties, MAX_PROPS, count++, &prop_gpattern,
457 glob_pattern);
458
459 if (glob_content != CC_CONTENT_INVALID) {
460 (void) proc_content2str(glob_content, gcontentstr,
461 sizeof (gcontentstr));
462 addprop(properties, MAX_PROPS, count++, &prop_gcontent,
463 gcontentstr);
464 }
465
466 if (init_pattern != NULL)
467 addprop(properties, MAX_PROPS, count++, &prop_ipattern,
468 init_pattern);
469
470 if (init_content != CC_CONTENT_INVALID) {
471 (void) proc_content2str(init_content, icontentstr,
472 sizeof (icontentstr));
473 addprop(properties, MAX_PROPS, count++, &prop_icontent,
474 icontentstr);
478 if ((alloptions & prop->pv_aux) != 0)
479 addprop(properties, MAX_PROPS, count++, prop, &options);
480
481 properties[count].pv_prop = NULL;
482
483 prop = NULL;
484 if (scf_write_propvec(COREADM_INST_FMRI, CONFIG_PARAMS, properties,
485 &prop) == SCF_FAILED) {
486 if (prop != NULL) {
487 (void) fprintf(stderr, gettext(
488 "%s: Unable to write property '%s': %s"), command,
489 prop->pv_prop, scf_strerror(scf_error()));
490 } else {
491 (void) fprintf(stderr, gettext(
492 "%s: Unable to write configuration: %s\n"),
493 command, scf_strerror(scf_error()));
494 }
495 return (E_ERROR);
496 }
497
498 if (make_active() != 0) {
499 (void) fprintf(stderr, gettext(
500 "Configuration stored but not made active.\n"));
501 return (E_ERROR);
502 }
503
504 return (E_SUCCESS);
505 }
506
507 static const char *
508 write_kernel(void)
509 {
510 if (core_set_global_path(glob_pattern, strlen(glob_pattern) + 1) != 0)
511 return ("core_set_global_path()");
512
513 if (core_set_global_content(&glob_content) != 0)
514 return ("core_set_global_content()");
515
516 if (core_set_default_path(init_pattern, strlen(init_pattern) + 1) != 0)
517 return ("core_set_default_path()");
518
519 if (core_set_default_content(&init_content) != 0)
520 return ("core_set_init_content()");
640
641 /*
642 * Loads and applies the coreadm configuration stored in the default
643 * coreadm instance. As this option is (only) used from within an SMF
644 * service method, this function must return an SMF_EXIT_* exit status
645 * to its caller.
646 */
647 static int
648 do_update(void)
649 {
650 char *gcstr, *icstr;
651 scf_propvec_t properties[MAX_PROPS + 1];
652 scf_propvec_t *prop;
653 int count = 0;
654 const char *errstr;
655
656 if (read_legacy()) {
657 if ((errstr = write_kernel()) != NULL)
658 goto error;
659
660 if (do_modify() != 0 ||
661 rename(PATH_CONFIG, PATH_CONFIG_OLD) != 0) {
662 (void) fprintf(stderr, gettext(
663 "%s: failed to import legacy configuration.\n"),
664 command);
665 return (SMF_EXIT_ERR_FATAL);
666 }
667 return (SMF_EXIT_OK);
668 }
669
670 addprop(properties, MAX_PROPS, count++, &prop_gpattern, &glob_pattern);
671 addprop(properties, MAX_PROPS, count++, &prop_gcontent, &gcstr);
672 addprop(properties, MAX_PROPS, count++, &prop_ipattern, &init_pattern);
673 addprop(properties, MAX_PROPS, count++, &prop_icontent, &icstr);
674 for (prop = prop_option; prop->pv_prop != NULL; prop++)
675 addprop(properties, MAX_PROPS, count++, prop, &options);
676 properties[count].pv_prop = NULL;
677
678 alloptions = CC_OPTIONS;
679 if (scf_read_propvec(COREADM_INST_FMRI, CONFIG_PARAMS, B_FALSE,
680 properties, &prop) == SCF_FAILED) {
681 if (prop != NULL) {
682 (void) fprintf(stderr, gettext(
683 "%s: configuration property '%s' not found.\n"),
684 command, prop->pv_prop);
685 } else {
686 (void) fprintf(stderr, gettext(
687 "%s: unable to read configuration: %s\n"),
688 command, scf_strerror(scf_error()));
689 }
690 return (SMF_EXIT_ERR_FATAL);
691 }
692
693 (void) proc_str2content(gcstr, &glob_content);
694 (void) proc_str2content(icstr, &init_content);
695
696 errstr = write_kernel();
697 scf_clean_propvec(properties);
698 if (errstr == NULL)
699 return (SMF_EXIT_OK);
700
701 error:
702 if (errno == EPERM) {
703 (void) perm();
704 return (SMF_EXIT_ERR_PERM);
705 }
706 perror(errstr);
707 return (errno == EINVAL ? SMF_EXIT_ERR_CONFIG : SMF_EXIT_ERR_FATAL);
708 }
709
710 static int do_legacy()
711 {
712 const char *errstr;
713
714 if (read_legacy() && (errstr = write_kernel()) != NULL) {
715 if (errno == EPERM)
716 return (perm());
717 perror(errstr);
718 return (E_ERROR);
719 }
720
721 return (E_SUCCESS);
722 }
|