10Sstevel@tonic-gate /*
20Sstevel@tonic-gate * CDDL HEADER START
30Sstevel@tonic-gate *
40Sstevel@tonic-gate * The contents of this file are subject to the terms of the
51864Sbustos * Common Development and Distribution License (the "License").
61864Sbustos * You may not use this file except in compliance with the License.
70Sstevel@tonic-gate *
80Sstevel@tonic-gate * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
90Sstevel@tonic-gate * or http://www.opensolaris.org/os/licensing.
100Sstevel@tonic-gate * See the License for the specific language governing permissions
110Sstevel@tonic-gate * and limitations under the License.
120Sstevel@tonic-gate *
130Sstevel@tonic-gate * When distributing Covered Code, include this CDDL HEADER in each
140Sstevel@tonic-gate * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
150Sstevel@tonic-gate * If applicable, add the following below this CDDL HEADER, with the
160Sstevel@tonic-gate * fields enclosed by brackets "[]" replaced with your own identifying
170Sstevel@tonic-gate * information: Portions Copyright [yyyy] [name of copyright owner]
180Sstevel@tonic-gate *
190Sstevel@tonic-gate * CDDL HEADER END
200Sstevel@tonic-gate */
21*13112STony.Q.Nguyen@oracle.com
220Sstevel@tonic-gate /*
23*13112STony.Q.Nguyen@oracle.com * Copyright (c) 2004, 2010, Oracle and/or its affiliates. All rights reserved.
240Sstevel@tonic-gate */
250Sstevel@tonic-gate
260Sstevel@tonic-gate #include <sys/types.h>
270Sstevel@tonic-gate
2811996SThomas.Whitten@Sun.COM #include <errno.h>
2911996SThomas.Whitten@Sun.COM #include <fcntl.h>
300Sstevel@tonic-gate #include <libintl.h>
31*13112STony.Q.Nguyen@oracle.com #include <libscf.h>
320Sstevel@tonic-gate #include <libuutil.h>
330Sstevel@tonic-gate #include <locale.h>
340Sstevel@tonic-gate #include <stdio.h>
350Sstevel@tonic-gate #include <stdlib.h>
360Sstevel@tonic-gate #include <string.h>
3711996SThomas.Whitten@Sun.COM #include <sys/stat.h>
380Sstevel@tonic-gate #include <unistd.h>
390Sstevel@tonic-gate
4011996SThomas.Whitten@Sun.COM #include "manifest_find.h"
410Sstevel@tonic-gate #include "manifest_hash.h"
420Sstevel@tonic-gate
430Sstevel@tonic-gate #define MAX_DEPTH 24
440Sstevel@tonic-gate
450Sstevel@tonic-gate /*
460Sstevel@tonic-gate * mfstscan - service manifest change detection utility
470Sstevel@tonic-gate *
480Sstevel@tonic-gate * mfstscan walks the given filesystem hierarchies, and reports those manifests
490Sstevel@tonic-gate * with changed or absent hash entries. Manifests are expected to end with a
500Sstevel@tonic-gate * .xml suffix--other files will be ignored.
510Sstevel@tonic-gate */
520Sstevel@tonic-gate
530Sstevel@tonic-gate static void
usage()540Sstevel@tonic-gate usage()
550Sstevel@tonic-gate {
560Sstevel@tonic-gate (void) fprintf(stderr, gettext("Usage: %s [-t] path ...\n"),
570Sstevel@tonic-gate uu_getpname());
580Sstevel@tonic-gate exit(UU_EXIT_USAGE);
590Sstevel@tonic-gate }
600Sstevel@tonic-gate
610Sstevel@tonic-gate int
main(int argc,char * argv[])620Sstevel@tonic-gate main(int argc, char *argv[])
630Sstevel@tonic-gate {
6411996SThomas.Whitten@Sun.COM manifest_info_t **entry;
6511996SThomas.Whitten@Sun.COM manifest_info_t **manifests;
66*13112STony.Q.Nguyen@oracle.com scf_handle_t *hndl = NULL;
670Sstevel@tonic-gate int i;
680Sstevel@tonic-gate int paths_walked = 0;
690Sstevel@tonic-gate struct stat sb;
7011996SThomas.Whitten@Sun.COM int status;
7111996SThomas.Whitten@Sun.COM int tflag = 0;
720Sstevel@tonic-gate
730Sstevel@tonic-gate (void) uu_setpname(argv[0]);
740Sstevel@tonic-gate
750Sstevel@tonic-gate while ((i = getopt(argc, argv, "t")) != -1) {
760Sstevel@tonic-gate switch (i) {
770Sstevel@tonic-gate case 't':
780Sstevel@tonic-gate tflag = 1;
790Sstevel@tonic-gate paths_walked = 1;
800Sstevel@tonic-gate break;
810Sstevel@tonic-gate case '?':
820Sstevel@tonic-gate default:
830Sstevel@tonic-gate usage();
840Sstevel@tonic-gate /*NOTREACHED*/
850Sstevel@tonic-gate }
860Sstevel@tonic-gate }
870Sstevel@tonic-gate
880Sstevel@tonic-gate if (optind >= argc)
890Sstevel@tonic-gate usage();
900Sstevel@tonic-gate
91*13112STony.Q.Nguyen@oracle.com if ((hndl = scf_handle_create(SCF_VERSION)) == NULL)
92*13112STony.Q.Nguyen@oracle.com uu_die(gettext("Unexpected libscf error: %s. Exiting.\n"),
93*13112STony.Q.Nguyen@oracle.com scf_strerror(scf_error()));
94*13112STony.Q.Nguyen@oracle.com
95*13112STony.Q.Nguyen@oracle.com if (scf_handle_bind(hndl) != SCF_SUCCESS)
96*13112STony.Q.Nguyen@oracle.com uu_die(gettext("Couldn't bind to svc.configd.\n"));
97*13112STony.Q.Nguyen@oracle.com
980Sstevel@tonic-gate for (i = optind; i < argc; i++) {
990Sstevel@tonic-gate if (tflag) {
1007475SPhilippe.Jung@Sun.COM char *pname = mhash_filename_to_propname(argv[i],
1017475SPhilippe.Jung@Sun.COM B_FALSE);
1021864Sbustos
1031864Sbustos if (pname != NULL)
1041864Sbustos (void) puts(pname);
1051864Sbustos else
1061864Sbustos uu_warn(gettext("cannot resolve pathname "
1071864Sbustos "for %s"), argv[i]);
1081864Sbustos
1090Sstevel@tonic-gate continue;
1100Sstevel@tonic-gate }
1110Sstevel@tonic-gate
1120Sstevel@tonic-gate if (stat(argv[i], &sb) == -1) {
1130Sstevel@tonic-gate uu_warn(gettext("cannot stat %s"), argv[i]);
1140Sstevel@tonic-gate continue;
1150Sstevel@tonic-gate }
1160Sstevel@tonic-gate
117*13112STony.Q.Nguyen@oracle.com status = find_manifests(hndl, argv[i], &manifests,
11811996SThomas.Whitten@Sun.COM CHECKHASH|CHECKEXT);
11911996SThomas.Whitten@Sun.COM if (status < 0) {
1200Sstevel@tonic-gate uu_warn(gettext("file tree walk of %s encountered "
12111996SThomas.Whitten@Sun.COM "error. %s\n"), argv[i], strerror(errno));
12211996SThomas.Whitten@Sun.COM } else {
1230Sstevel@tonic-gate paths_walked++;
12411996SThomas.Whitten@Sun.COM if (manifests != NULL) {
12511996SThomas.Whitten@Sun.COM for (entry = manifests;
12611996SThomas.Whitten@Sun.COM *entry != NULL;
12711996SThomas.Whitten@Sun.COM entry++) {
12811996SThomas.Whitten@Sun.COM (void) printf("%s\n",
12911996SThomas.Whitten@Sun.COM (*entry)->mi_path);
13011996SThomas.Whitten@Sun.COM }
13111996SThomas.Whitten@Sun.COM free_manifest_array(manifests);
13211996SThomas.Whitten@Sun.COM }
13311996SThomas.Whitten@Sun.COM }
1340Sstevel@tonic-gate
13511996SThomas.Whitten@Sun.COM }
1360Sstevel@tonic-gate
1370Sstevel@tonic-gate if (!paths_walked)
1380Sstevel@tonic-gate uu_die(gettext("no paths walked\n"));
1390Sstevel@tonic-gate
140*13112STony.Q.Nguyen@oracle.com if (hndl != NULL) {
141*13112STony.Q.Nguyen@oracle.com (void) scf_handle_unbind(hndl);
142*13112STony.Q.Nguyen@oracle.com (void) scf_handle_destroy(hndl);
143*13112STony.Q.Nguyen@oracle.com }
144*13112STony.Q.Nguyen@oracle.com
1450Sstevel@tonic-gate return (0);
1460Sstevel@tonic-gate }
147