xref: /dragonfly/sbin/hammer/cmd_info.c (revision 4a65f651)
1 /*
2  * Copyright (c) 2009 The DragonFly Project.  All rights reserved.
3  *
4  * This code is derived from software contributed to The DragonFly Project
5  * by Antonio Huete <tuxillo@quantumachine.net>
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  *
11  * 1. Redistributions of source code must retain the above copyright
12  *    notice, this list of conditions and the following disclaimer.
13  * 2. Redistributions in binary form must reproduce the above copyright
14  *    notice, this list of conditions and the following disclaimer in
15  *    the documentation and/or other materials provided with the
16  *    distribution.
17  * 3. Neither the name of The DragonFly Project nor the names of its
18  *    contributors may be used to endorse or promote products derived
19  *    from this software without specific, prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
24  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE
25  * COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
26  * INCIDENTAL, SPECIAL, EXEMPLARY OR CONSEQUENTIAL DAMAGES (INCLUDING,
27  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
28  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
29  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
30  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
31  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
32  * SUCH DAMAGE.
33  *
34  */
35 #include "hammer.h"
36 #include <libutil.h>
37 
38 void	show_info(char *path);
39 double	percent(int64_t value, int64_t total);
40 
41 void
42 hammer_cmd_info(void)
43 {
44 	struct statfs *stfsbuf;
45 	int mntsize, i;
46 	char *fstype, *path;
47 
48 	tzset();
49 	mntsize = getmntinfo(&stfsbuf, MNT_NOWAIT);
50 	if (mntsize > 0) {
51 		for (i=0; i < mntsize; i++) {
52 			fstype = stfsbuf[i].f_fstypename;
53 			path = stfsbuf[i].f_mntonname;
54 			if ((strcmp(fstype, "hammer")) == 0)
55 				show_info(path);
56 		}
57 	}
58 	else
59 		fprintf(stdout, "No mounted filesystems found\n");
60 
61 }
62 
63 void show_info(char *path) {
64 
65 	int64_t	usedbigblocks, bytes;
66 	struct	hammer_ioc_info info;
67 	char	buf[6];
68 	int 	fd;
69 	char 	*fsid, *fstype;
70 
71 	fsid = fstype = NULL;
72 	usedbigblocks = 0;
73 	bytes = 0;
74 
75 	bzero(&info, sizeof(struct hammer_ioc_info));
76 
77 	/* Try to get a file descriptor based on the path given */
78 	fd = open(path, O_RDONLY);
79 	if (fd < 0) {
80 		perror("show_info");
81 		exit(EXIT_FAILURE);
82 	}
83 
84 	if ((ioctl(fd, HAMMERIOC_GET_INFO, &info)) < 0) {
85 		perror("show_info");
86 		exit(EXIT_FAILURE);
87 	}
88 
89 	/* Find out the UUID strings */
90 	uuid_to_string(&info.vol_fsid, &fsid, NULL);
91 
92 	/* Volume information */
93 	fprintf(stdout, "Volume identification\n");
94 	fprintf(stdout, "\tLabel          %s\n", info.vol_name);
95 	fprintf(stdout, "\tNo. Volumes    %d\n", info.nvolumes);
96 	fprintf(stdout, "\tFSID           %s\n", fsid);
97 
98 	/* Big blocks information */
99 	usedbigblocks = info.bigblocks - info.freebigblocks;
100 
101 	fprintf(stdout, "Big block information\n");
102 	fprintf(stdout, "\tTotal\t       %jd\n", (intmax_t)info.bigblocks);
103 	fprintf(stdout, "\tUsed\t       %jd (%.2lf%%)\n\tReserved       "
104 				       "%jd (%.2lf%%)\n\tFree\t       "
105 				       "%jd (%.2lf%%)\n",
106 			(intmax_t)usedbigblocks,
107 			percent(usedbigblocks, info.bigblocks),
108 			(intmax_t)info.rsvbigblocks,
109 			percent(info.rsvbigblocks, info.bigblocks),
110 			(intmax_t)(info.freebigblocks - info.rsvbigblocks),
111 			percent(info.freebigblocks - info.rsvbigblocks,
112 				info.bigblocks));
113 	fprintf(stdout, "Space information\n");
114 
115 	/* Space information */
116 	bytes = (info.bigblocks << HAMMER_LARGEBLOCK_BITS);
117 	humanize_number(buf, sizeof(buf)  - (bytes < 0 ? 0 : 1), bytes, "", HN_AUTOSCALE, HN_DECIMAL | HN_NOSPACE | HN_B);
118 	fprintf(stdout, "\tTotal size     %6s (%jd bytes)\n",
119 		buf, (intmax_t)bytes);
120 
121 	bytes = (usedbigblocks << HAMMER_LARGEBLOCK_BITS);
122 	humanize_number(buf, sizeof(buf)  - (bytes < 0 ? 0 : 1), bytes, "", HN_AUTOSCALE, HN_DECIMAL | HN_NOSPACE | HN_B);
123 	fprintf(stdout, "\tUsed space     %6s\n", buf);
124 
125 	bytes = (info.rsvbigblocks << HAMMER_LARGEBLOCK_BITS);
126 	humanize_number(buf, sizeof(buf)  - (bytes < 0 ? 0 : 1), bytes, "", HN_AUTOSCALE, HN_DECIMAL | HN_NOSPACE | HN_B);
127 	fprintf(stdout, "\tReserved space %6s\n", buf);
128 
129 	bytes = ((info.freebigblocks - info.rsvbigblocks) << HAMMER_LARGEBLOCK_BITS);
130 	humanize_number(buf, sizeof(buf)  - (bytes < 0 ? 0 : 1), bytes, "", HN_AUTOSCALE, HN_DECIMAL | HN_NOSPACE | HN_B);
131 	fprintf(stdout, "\tFree space     %6s\n\n", buf);
132 }
133 
134 double percent(int64_t value, int64_t total) {
135 
136 	/* Avoid divide-by-zero */
137 	if (value == 0)
138 		value = 1;
139 
140 	return ((value * 100.0) / (double)total);
141 }
142