fsstat.c revision 26fd77009b17f8c8fb32eb362584cfd635e87ad9
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * CDDL HEADER START
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * The contents of this file are subject to the terms of the
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * Common Development and Distribution License (the "License").
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * You may not use this file except in compliance with the License.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * See the License for the specific language governing permissions
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * and limitations under the License.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * When distributing Covered Code, include this CDDL HEADER in each
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * If applicable, add the following below this CDDL HEADER, with the
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * fields enclosed by brackets "[]" replaced with your own identifying
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * information: Portions Copyright [yyyy] [name of copyright owner]
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * CDDL HEADER END
4944376cd5de3dcd3b4feeaad9cbedbc024d1474John Levon * Copyright 2009 Sun Microsystems, Inc. All rights reserved.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * Use is subject to license terms.
3a401a6b073cd295066706e0825db167a9322c28rsb * For now, parsable output is turned off. Once we gather feedback and
3a401a6b073cd295066706e0825db167a9322c28rsb * stablize the output format, we'll turn it back on. This prevents
3a401a6b073cd295066706e0825db167a9322c28rsb * the situation where users build tools which depend on a specific
3a401a6b073cd295066706e0825db167a9322c28rsb * format before we declare the output stable.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb/* Time stamp values */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb#define UDATE 2 /* Internal representation of Unix time */
3a401a6b073cd295066706e0825db167a9322c28rsb#define HEADERLINES 12 /* Number of lines between display headers */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * The following are used for the nicenum() function
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb#define NENTITY_INIT 1 /* Initial number of entities to allocate */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * We need to have a mechanism for an old/previous and new/current vopstat
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * structure. We only need two per entity and we can swap between them.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb#define PREV_INDEX ((vs_i == 0) ? 1 : 0) /* Opposite of CUR_INDEX */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * An "entity" is anything we're collecting statistics on, it could
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * be a mountpoint or an FS-type.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * e_name is the name of the entity (e.g. mount point or FS-type)
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * e_ksname is the name of the associated kstat
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * e_vs is an array of vopstats. This is used to keep track of "previous"
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * and "current" vopstats.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsbtypedef struct entity {
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb/* Types of entities (e_type) */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb#define ENTYPE_UNKNOWN 0 /* UNKNOWN must be zero since we calloc() */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb/* If more sub-one units are added, make sure to adjust ONE_INDEX above */
26fd77009b17f8c8fb32eb362584cfd635e87ad9Krishnendu Sadhukhan - Sun Microsystemsstatic uint_t timestamp_fmt = NODATE; /* print timestamp with stats */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsbstatic void
3a401a6b073cd295066706e0825db167a9322c28rsb "Usage: %s [-a|f|i|n|v] [-T d|u] {-F | {fstype | fspath}...} "
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * Given a 64-bit number and a starting unit (e.g., n - nanoseconds),
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * convert the number to a 5-character representation including any
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * decimal point and single-character unit. Put that representation
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * into the array "buf" (which had better be big enough).
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* If the user passed in a NUL/zero unit, use the blank value for 1 */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb while (n >= KILO_VAL) {
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb n = (n + (KILO_VAL / 2)) / KILO_VAL; /* Round up or down */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb (newvsp->member.value.ui64 - (oldvsp ? oldvsp->member.value.ui64 : 0))
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb#define PRINTSTAT(isnice, nicestring, rawstring, rawval, unit, buf) \
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb (void) printf((nicestring), nicenum(rawval, unit, buf)) \
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb/* Values for display flag */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * The policy for dealing with multiple flags is dealt with here.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * Currently, if we are displaying raw output, then don't allow
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * headers to be printed.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* If we're not displaying raw output, then allow headers to print */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsbstatic void
5a59a8b3d86e67dbe75588879c46e3629f40efecrsbdflt_display(char *name, vopstats_t *oldvsp, vopstats_t *newvsp, int dispflag)
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb nnewfile = DELTA(ncreate) + DELTA(nmkdir) + DELTA(nsymlink);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb nnamechg = DELTA(nrename) + DELTA(nlink) + DELTA(nsymlink);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb nattrchg = DELTA(nsetattr) + DELTA(nsetsecattr) + DELTA(nspace);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb" new name name attr attr lookup rddir read read write write\n"
757bea67fc2c5b2af5e20d850267ce65984173bcrsb" file remov chng get set ops ops ops bytes ops bytes\n");
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", nnewfile, ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", nnamerm, ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", nnamechg, ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", nattrret, ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", nattrchg, ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, " %5s ", "%lld:", nlookup, ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", nreaddir, ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", ndataread, ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", readthruput, ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", ndatawrite, ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", writethruput, ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsbstatic void
5a59a8b3d86e67dbe75588879c46e3629f40efecrsbio_display(char *name, vopstats_t *oldvsp, vopstats_t *newvsp, int dispflag)
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb" read read write write rddir rddir rwlock rwulock\n"
757bea67fc2c5b2af5e20d850267ce65984173bcrsb" ops bytes ops bytes ops bytes ops ops\n");
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(nread), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(read_bytes), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(nwrite), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(write_bytes), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(nreaddir), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(readdir_bytes), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, " %5s ", "%lld:", DELTA(nrwlock), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(nrwunlock), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsbstatic void
5a59a8b3d86e67dbe75588879c46e3629f40efecrsbvm_display(char *name, vopstats_t *oldvsp, vopstats_t *newvsp, int dispflag)
757bea67fc2c5b2af5e20d850267ce65984173bcrsb (void) printf(" map addmap delmap getpag putpag pagio\n");
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(nmap), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, " %5s ", "%lld:", DELTA(naddmap), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, " %5s ", "%lld:", DELTA(ndelmap), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, " %5s ", "%lld:", DELTA(ngetpage), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, " %5s ", "%lld:", DELTA(nputpage), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(npageio), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsbstatic void
5a59a8b3d86e67dbe75588879c46e3629f40efecrsbattr_display(char *name, vopstats_t *oldvsp, vopstats_t *newvsp, int dispflag)
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, " %5s ", "%lld:", DELTA(ngetattr), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, " %5s ", "%lld:", DELTA(nsetattr), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, " %5s ", "%lld:", DELTA(ngetsecattr), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, " %5s ", "%lld:", DELTA(nsetsecattr), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsbstatic void
5a59a8b3d86e67dbe75588879c46e3629f40efecrsbnaming_display(char *name, vopstats_t *oldvsp, vopstats_t *newvsp, int dispflag)
757bea67fc2c5b2af5e20d850267ce65984173bcrsb "lookup creat remov link renam mkdir rmdir rddir symlnk rdlnk\n");
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(nlookup), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(ncreate), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(nremove), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(nlink), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(nrename), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(nmkdir), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(nrmdir), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(nreaddir), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, " %5s ", "%lld:", DELTA(nsymlink), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(nreadlink), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb PRINTSTAT(niceflag, "%5s ", "%lld:", DELTA(n##vop), ' ', buf);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsbstatic void
5a59a8b3d86e67dbe75588879c46e3629f40efecrsbvop_display(char *name, vopstats_t *oldvsp, vopstats_t *newvsp, int dispflag)
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* Make it easier on the eyes */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * Retrieve the vopstats. If kspp (pointer to kstat_t pointer) is non-NULL,
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * then pass it back to the caller.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * Returns 0 on success, non-zero on failure.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsbget_vopstats(kstat_ctl_t *kc, char *ksname, vopstats_t *vsp, kstat_t **kspp)
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (1);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* wait for a possibly up-to-date chain */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb if ((ksp = kstat_lookup(kc, NULL, -1, ksname)) == NULL) {
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (1);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (1);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (0);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * Given a file system type name, determine if it's part of the
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * exception list of file systems that are not to be displayed.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb static char *exception_list[] = {
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (1);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (0);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * Plain and simple, build an array of names for fstypes
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * Returns 0, if it encounters a problem.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (0);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb if ((*fstypep = calloc(nfstype, sizeof (char *))) == NULL) {
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (0);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (0);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb if (buf[0] == 0)
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* If this is part of the exception list, move on */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (0);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (i);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * After we're done with getopts(), process the rest of the
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * operands. We have three cases and this is the priority:
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * 1) [ operand... ] interval count
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * 2) [ operand... ] interval
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * 3) [ operand... ]
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * The trick is that any of the operands might start with a number or even
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * be made up exclusively of numbers (and we have to handle negative numbers
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * in case a user/script gets out of line). If we find two operands at the
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * end of the list then we claim case 1. If we find only one operand at the
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * end made up only of number, then we claim case 2. Otherwise, case 3.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * BTW, argc, argv don't change.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb int out_of_range; /* Set if 2nd-to-last operand out-of-range */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * We know exactly what the maximum number of entities is going
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * to be: argc - optind
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb if ((*entityp = calloc((argc - optind), sizeof (entity_t))) == NULL) {
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (-1);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* If we have more than two operands left to process */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* If we're here, then we only have one or two operands left */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* Operand was not a number */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* Operand was a number, just out of range */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * The last operand we saw was a number. If it happened to
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * be the last operand, then it is the interval...
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* ...but we need to check the range. */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb "interval must be between 1 and "
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (-1);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * The value of the interval is valid. Set
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * count to something really big so it goes
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * virtually forever.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * At this point, we *might* have the interval, but if the
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * next operand isn't a number, then we don't have either
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * the interval nor the count. Both must be set to the
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * defaults. In that case, both the current and the previous
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * operands are stat-able entities.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * Faked out! The last operand wasn't a number so
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * the current and previous operands should be
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * stat-able entities. We also need to reset interval.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb (*entityp)[nentities++].e_name = strdup(argv[optind++]);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb (*entityp)[nentities++].e_name = strdup(argv[optind++]);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb } else if (out_of_range || errno == ERANGE || *count <= 0) {
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb "Both interval and count must be between 1 "
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (-1);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb break; /* Done! */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * set_mntpt() looks at the entity's name (e_name) and finds its
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * mountpoint. To do this, we need to build a list of mountpoints
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * from /etc/mnttab. We only need to do this once and we don't do it
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * if we don't need to look at any mountpoints.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * Returns 0 on success, non-zero if it couldn't find a mount-point.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb static struct mnt {
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb ulong_t m_fsid; /* From statvfs(), set only as needed */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (1);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* We only set up mnt_list the first time this is called */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (1);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * We insert at the front of the list so that when we
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * search entries we'll have the last mounted entries
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * first in the list so that we can match the longest
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * mountpoint.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (1);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (1);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * Now that we have the path, walk through the mnt_list and
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * look for the first (best) match.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb if (strncmp(path, mntp->m_mntpt, strlen(mntp->m_mntpt)) == 0) {
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* Can't statvfs so no match */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* No match - Move on */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (1);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (0);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * We have an array of entities that are potentially stat-able. Using
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * the name (e_name) of the entity, attempt to construct a ksname suitable
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * for use by kstat_lookup(3kstat) and fill it into the e_ksname member.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * We check the e_name against the list of file system types. If there is
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * no match then test to see if the path is valid. If the path is valid,
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * then determine the mountpoint.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsbset_ksnames(entity_t *entities, int nentities, char **fstypes, int nfstypes)
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb for (i = 0; i < nentities; i++) {
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* Check the name against the list of fstypes */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* It's a file system type */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* Now allocate the vopstats array */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * If the entity in the exception list of fstypes, then
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * null out the entry so it isn't displayed and move along.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* If we didn't find it, see if it's a path */
06f33e8d08c75ccdc623b7f778570223d880eca4rsb if (ep->e_name == NULL || statvfs64(ep->e_name, &statvfsbuf)) {
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* Error - Make sure the entry is nulled out */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* Now allocate the vopstats array */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * The idea is that 'dspfunc' should only be modified from the default
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * once since the display options are mutually exclusive. If 'dspfunc'
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * only contains the default display function, then all is good and we
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * can set it to the new display function. Otherwise, bail.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb void (**dspfunc)(char *, vopstats_t *, vopstats_t *, int),
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb void (*newfunc)(char *, vopstats_t *, vopstats_t *, int))
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb "%s: Display options -{a|f|i|n|v} are mutually exclusive\n"),
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb int i, j; /* Generic counters */
4944376cd5de3dcd3b4feeaad9cbedbc024d1474John Levon int linesout = 0; /* Keeps track of lines printed */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb boolean_t fstypes_only = B_FALSE; /* Display fstypes only */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb void (*dfunc)(char *, vopstats_t *, vopstats_t *, int) = dflt_display;
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb extern int optind;
13c7b6ac430bc41eee84ba0b625cf5fde3241b10rsb#if !defined(TEXT_DOMAIN) /* Should be defined by cc -D */
13c7b6ac430bc41eee84ba0b625cf5fde3241b10rsb#define TEXT_DOMAIN "SYS_TEST" /* Use this only if it weren't */
f5cd957f512eb3fe078de1043418ae6acf52a4c6Robert Harris /* Don't let buffering interfere with piped output. */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb switch (c) {
3a401a6b073cd295066706e0825db167a9322c28rsb#endif /* PARSABLE_OUTPUT */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* If it was never set properly... */
f5cd957f512eb3fe078de1043418ae6acf52a4c6Robert Harris (void) fprintf(stderr, gettext("%s: -T option "
4944376cd5de3dcd3b4feeaad9cbedbc024d1474John Levon if ((dispflag & DISP_RAW) && (timestamp_fmt != NODATE)) {
f5cd957f512eb3fe078de1043418ae6acf52a4c6Robert Harris "-P and -T options are mutually exclusive\n"));
3a401a6b073cd295066706e0825db167a9322c28rsb#endif /* PARSABLE_OUTPUT */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* Gather the list of filesystem types */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb if (nentities == -1) /* Set of operands didn't parse properly */
3a401a6b073cd295066706e0825db167a9322c28rsb "Must specify -F or at least one fstype or mount point\n"));
3a401a6b073cd295066706e0825db167a9322c28rsb "Cannot use -F with fstypes or mount points\n"));
3a401a6b073cd295066706e0825db167a9322c28rsb * If we had no operands (except for interval/count) and we
3a401a6b073cd295066706e0825db167a9322c28rsb * requested FStypes only (-F), then fill in the entities[]
3a401a6b073cd295066706e0825db167a9322c28rsb * array with all available fstypes.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb if ((entities = calloc(nfstypes, sizeof (entity_t))) == NULL) {
00c76d6fcc0e3d5821ed5ac5165f1835f8151454tc /* Set start time */
4944376cd5de3dcd3b4feeaad9cbedbc024d1474John Levon /* Initial timestamp */
26fd77009b17f8c8fb32eb362584cfd635e87ad9Krishnendu Sadhukhan - Sun Microsystems print_timestamp(timestamp_fmt);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * The following loop walks through the entities[] list to "prime
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * the pump"
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * If we can't find it the first time through, then
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * get rid of it.
3a401a6b073cd295066706e0825db167a9322c28rsb * If we're only displaying FStypes (-F) then don't
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * complain about any file systems that might not
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * be loaded. Otherwise, let the user know that
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * he chose poorly.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb "No statistics available for %s\n"),
00c76d6fcc0e3d5821ed5ac5165f1835f8151454tc /* Set up signal handler for SIGCONT */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * No telling how many lines will be printed in any interval.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * There should be a minimum of HEADERLINES between any
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * header. If we exceed that, no big deal.
00c76d6fcc0e3d5821ed5ac5165f1835f8151454tc /* Have a kip */
26fd77009b17f8c8fb32eb362584cfd635e87ad9Krishnendu Sadhukhan - Sun Microsystems print_timestamp(timestamp_fmt);
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * If this entry has been cleared, don't attempt
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * to process it.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb "<<mount point no longer "
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb "<<file system module no longer "
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb "<<%s no longer available>>\n"),
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb /* Disable this so it doesn't print again */
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * If the entities we were observing are no longer there
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * (file system modules unloaded, file systems unmounted)
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb * then we're done.
5a59a8b3d86e67dbe75588879c46e3629f40efecrsb return (0);