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