14b88c807SRodney W. Grimes /* 24b88c807SRodney W. Grimes * Copyright (c) 1989, 1993, 1994 34b88c807SRodney W. Grimes * The Regents of the University of California. All rights reserved. 44b88c807SRodney W. Grimes * 54b88c807SRodney W. Grimes * This code is derived from software contributed to Berkeley by 64b88c807SRodney W. Grimes * Michael Fischbein. 74b88c807SRodney W. Grimes * 84b88c807SRodney W. Grimes * Redistribution and use in source and binary forms, with or without 94b88c807SRodney W. Grimes * modification, are permitted provided that the following conditions 104b88c807SRodney W. Grimes * are met: 114b88c807SRodney W. Grimes * 1. Redistributions of source code must retain the above copyright 124b88c807SRodney W. Grimes * notice, this list of conditions and the following disclaimer. 134b88c807SRodney W. Grimes * 2. Redistributions in binary form must reproduce the above copyright 144b88c807SRodney W. Grimes * notice, this list of conditions and the following disclaimer in the 154b88c807SRodney W. Grimes * documentation and/or other materials provided with the distribution. 164b88c807SRodney W. Grimes * 3. All advertising materials mentioning features or use of this software 174b88c807SRodney W. Grimes * must display the following acknowledgement: 184b88c807SRodney W. Grimes * This product includes software developed by the University of 194b88c807SRodney W. Grimes * California, Berkeley and its contributors. 204b88c807SRodney W. Grimes * 4. Neither the name of the University nor the names of its contributors 214b88c807SRodney W. Grimes * may be used to endorse or promote products derived from this software 224b88c807SRodney W. Grimes * without specific prior written permission. 234b88c807SRodney W. Grimes * 244b88c807SRodney W. Grimes * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 254b88c807SRodney W. Grimes * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 264b88c807SRodney W. Grimes * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 274b88c807SRodney W. Grimes * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 284b88c807SRodney W. Grimes * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 294b88c807SRodney W. Grimes * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 304b88c807SRodney W. Grimes * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 314b88c807SRodney W. Grimes * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 324b88c807SRodney W. Grimes * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 334b88c807SRodney W. Grimes * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 344b88c807SRodney W. Grimes * SUCH DAMAGE. 354b88c807SRodney W. Grimes */ 364b88c807SRodney W. Grimes 374b88c807SRodney W. Grimes #ifndef lint 38d46c1a60SSteve Price static const char copyright[] = 394b88c807SRodney W. Grimes "@(#) Copyright (c) 1989, 1993, 1994\n\ 404b88c807SRodney W. Grimes The Regents of the University of California. All rights reserved.\n"; 41febad2fcSSteve Price #endif /* not lint */ 42febad2fcSSteve Price 43febad2fcSSteve Price #if 0 44c73d77ceSMark Murray #ifndef lint 45febad2fcSSteve Price static char sccsid[] = "@(#)ls.c 8.5 (Berkeley) 4/2/94"; 464b88c807SRodney W. Grimes #endif /* not lint */ 47c73d77ceSMark Murray #endif 485eb43ac2SDavid E. O'Brien #include <sys/cdefs.h> 495eb43ac2SDavid E. O'Brien __FBSDID("$FreeBSD$"); 504b88c807SRodney W. Grimes 514b88c807SRodney W. Grimes #include <sys/types.h> 524b88c807SRodney W. Grimes #include <sys/stat.h> 534b88c807SRodney W. Grimes #include <sys/ioctl.h> 544b88c807SRodney W. Grimes 554b88c807SRodney W. Grimes #include <dirent.h> 564b88c807SRodney W. Grimes #include <err.h> 574b88c807SRodney W. Grimes #include <errno.h> 584b88c807SRodney W. Grimes #include <fts.h> 59576541a9SWarner Losh #include <grp.h> 60008a4910SSheldon Hearn #include <limits.h> 61008a4910SSheldon Hearn #include <locale.h> 62576541a9SWarner Losh #include <pwd.h> 634b88c807SRodney W. Grimes #include <stdio.h> 644b88c807SRodney W. Grimes #include <stdlib.h> 654b88c807SRodney W. Grimes #include <string.h> 664b88c807SRodney W. Grimes #include <unistd.h> 67bd82d8abSAndrey A. Chernov #ifdef COLORLS 68bd82d8abSAndrey A. Chernov #include <termcap.h> 69bd82d8abSAndrey A. Chernov #include <signal.h> 70bd82d8abSAndrey A. Chernov #endif 714b88c807SRodney W. Grimes 724b88c807SRodney W. Grimes #include "ls.h" 734b88c807SRodney W. Grimes #include "extern.h" 747304f61fSBrian Feldman #include "lomac.h" 754b88c807SRodney W. Grimes 76008a4910SSheldon Hearn /* 77008a4910SSheldon Hearn * Upward approximation of the maximum number of characters needed to 78008a4910SSheldon Hearn * represent a value of integral type t as a string, excluding the 79008a4910SSheldon Hearn * NUL terminator, with provision for a sign. 80008a4910SSheldon Hearn */ 811f94b779SSheldon Hearn #define STRBUF_SIZEOF(t) (1 + CHAR_BIT * sizeof(t) / 3 + 1) 82008a4910SSheldon Hearn 8346251ddeSWarner Losh static void display(FTSENT *, FTSENT *); 8446251ddeSWarner Losh static u_quad_t makenines(u_long); 850d3bcc2eSGarrett Wollman static int mastercmp(const FTSENT * const *, const FTSENT * const *); 8646251ddeSWarner Losh static void traverse(int, char **, int); 874b88c807SRodney W. Grimes 8846251ddeSWarner Losh static void (*printfcn)(DISPLAY *); 8946251ddeSWarner Losh static int (*sortfcn)(const FTSENT *, const FTSENT *); 904b88c807SRodney W. Grimes 914b88c807SRodney W. Grimes long blocksize; /* block size units */ 924b88c807SRodney W. Grimes int termwidth = 80; /* default terminal width */ 934b88c807SRodney W. Grimes 944b88c807SRodney W. Grimes /* flags */ 954b88c807SRodney W. Grimes int f_accesstime; /* use time of last access */ 964b88c807SRodney W. Grimes int f_flags; /* show flags associated with a file */ 970e8d1551SJosef Karthauser int f_humanval; /* show human-readable file sizes */ 984b88c807SRodney W. Grimes int f_inode; /* print inode */ 999052855aSMark Murray static int f_kblocks; /* print size in kilobytes */ 1009052855aSMark Murray static int f_listdir; /* list actual directory, not contents */ 1019052855aSMark Murray static int f_listdot; /* list files beginning with . */ 1024b88c807SRodney W. Grimes int f_longform; /* long listing format */ 1034b88c807SRodney W. Grimes int f_nonprint; /* show unprintables as ? */ 1049052855aSMark Murray static int f_nosort; /* don't sort output */ 105008a4910SSheldon Hearn int f_notabs; /* don't use tab-separated multi-col output */ 1069052855aSMark Murray static int f_numericonly; /* don't convert uid/gid to name */ 1077ea30648SDag-Erling Smørgrav int f_octal; /* show unprintables as \xxx */ 1080d86878cSDag-Erling Smørgrav int f_octal_escape; /* like f_octal but use C escapes if possible */ 1099052855aSMark Murray static int f_recursive; /* ls subdirectories also */ 1109052855aSMark Murray static int f_reversesort; /* reverse whatever sort is used */ 1114b88c807SRodney W. Grimes int f_sectime; /* print the real time for all files */ 1129052855aSMark Murray static int f_singlecol; /* use single column output */ 1134b88c807SRodney W. Grimes int f_size; /* list size in short listing */ 11494274c73STim J. Robbins int f_slash; /* similar to f_type, but only for dirs */ 11594274c73STim J. Robbins int f_sortacross; /* sort across rows, not down columns */ 1164b88c807SRodney W. Grimes int f_statustime; /* use time of last mode change */ 1172b239dd1SJens Schweikhardt int f_stream; /* stream the output, separate with commas */ 1189052855aSMark Murray static int f_timesort; /* sort by time vice name */ 1194b88c807SRodney W. Grimes int f_type; /* add type character for non-regular files */ 1209052855aSMark Murray static int f_whiteout; /* show whiteout entries */ 1217304f61fSBrian Feldman int f_lomac; /* show LOMAC attributes */ 12274985094SJosef Karthauser #ifdef COLORLS 1233885812cSJosef Karthauser int f_color; /* add type in color for non-regular files */ 1245a890e22SJosef Karthauser 1255a890e22SJosef Karthauser char *ansi_bgcol; /* ANSI sequence to set background colour */ 1265a890e22SJosef Karthauser char *ansi_fgcol; /* ANSI sequence to set foreground colour */ 1275a890e22SJosef Karthauser char *ansi_coloff; /* ANSI sequence to reset colours */ 128c1499cf6SJosef Karthauser char *attrs_off; /* ANSI sequence to turn off attributes */ 129c1499cf6SJosef Karthauser char *enter_bold; /* ANSI sequence to set color to bold mode */ 13074985094SJosef Karthauser #endif 1314b88c807SRodney W. Grimes 1329052855aSMark Murray static int rval; 133fb1000d6SAdam David 1344b88c807SRodney W. Grimes int 13546251ddeSWarner Losh main(int argc, char *argv[]) 1364b88c807SRodney W. Grimes { 1374b88c807SRodney W. Grimes static char dot[] = ".", *dotav[] = {dot, NULL}; 1384b88c807SRodney W. Grimes struct winsize win; 1394b88c807SRodney W. Grimes int ch, fts_options, notused; 1404b88c807SRodney W. Grimes char *p; 1415a890e22SJosef Karthauser #ifdef COLORLS 1425a890e22SJosef Karthauser char termcapbuf[1024]; /* termcap definition buffer */ 1435a890e22SJosef Karthauser char tcapbuf[512]; /* capability buffer */ 1445a890e22SJosef Karthauser char *bp = tcapbuf; 1455a890e22SJosef Karthauser #endif 1465a890e22SJosef Karthauser 147f5bd01c6SAndrey A. Chernov (void)setlocale(LC_ALL, ""); 148f5bd01c6SAndrey A. Chernov 1494b88c807SRodney W. Grimes /* Terminal defaults to -Cq, non-terminal defaults to -1. */ 1504b88c807SRodney W. Grimes if (isatty(STDOUT_FILENO)) { 151a28edf9aSTim J. Robbins termwidth = 80; 152a28edf9aSTim J. Robbins if ((p = getenv("COLUMNS")) != NULL && *p != '\0') 1534b88c807SRodney W. Grimes termwidth = atoi(p); 154a28edf9aSTim J. Robbins else if (ioctl(STDOUT_FILENO, TIOCGWINSZ, &win) != -1 && 155a28edf9aSTim J. Robbins win.ws_col > 0) 1564b88c807SRodney W. Grimes termwidth = win.ws_col; 1579052855aSMark Murray f_nonprint = 1; 15834994fcdSJoerg Wunsch } else { 1594b88c807SRodney W. Grimes f_singlecol = 1; 16034994fcdSJoerg Wunsch /* retrieve environment variable, in case of explicit -C */ 1619052855aSMark Murray p = getenv("COLUMNS"); 1629052855aSMark Murray if (p) 16334994fcdSJoerg Wunsch termwidth = atoi(p); 16434994fcdSJoerg Wunsch } 1654b88c807SRodney W. Grimes 1664b88c807SRodney W. Grimes /* Root is -A automatically. */ 1674b88c807SRodney W. Grimes if (!getuid()) 1684b88c807SRodney W. Grimes f_listdot = 1; 1694b88c807SRodney W. Grimes 1704b88c807SRodney W. Grimes fts_options = FTS_PHYSICAL; 17194274c73STim J. Robbins while ((ch = getopt(argc, argv, "1ABCFGHLPRTWZabcdfghiklmnopqrstuwx")) 17294274c73STim J. Robbins != -1) { 1734b88c807SRodney W. Grimes switch (ch) { 1744b88c807SRodney W. Grimes /* 17594274c73STim J. Robbins * The -1, -C, -x and -l options all override each other so 17694274c73STim J. Robbins * shell aliasing works right. 1774b88c807SRodney W. Grimes */ 1784b88c807SRodney W. Grimes case '1': 1794b88c807SRodney W. Grimes f_singlecol = 1; 1809052855aSMark Murray f_longform = 0; 18194274c73STim J. Robbins f_stream = 0; 1824b88c807SRodney W. Grimes break; 1830d86878cSDag-Erling Smørgrav case 'B': 1840d86878cSDag-Erling Smørgrav f_nonprint = 0; 1850d86878cSDag-Erling Smørgrav f_octal = 1; 1860d86878cSDag-Erling Smørgrav f_octal_escape = 0; 1870d86878cSDag-Erling Smørgrav break; 1884b88c807SRodney W. Grimes case 'C': 18994274c73STim J. Robbins f_sortacross = f_longform = f_singlecol = 0; 1904b88c807SRodney W. Grimes break; 1914b88c807SRodney W. Grimes case 'l': 1924b88c807SRodney W. Grimes f_longform = 1; 1939052855aSMark Murray f_singlecol = 0; 19494274c73STim J. Robbins f_stream = 0; 19594274c73STim J. Robbins break; 19694274c73STim J. Robbins case 'x': 19794274c73STim J. Robbins f_sortacross = 1; 19894274c73STim J. Robbins f_longform = 0; 19994274c73STim J. Robbins f_singlecol = 0; 2004b88c807SRodney W. Grimes break; 2014b88c807SRodney W. Grimes /* The -c and -u options override each other. */ 2024b88c807SRodney W. Grimes case 'c': 2034b88c807SRodney W. Grimes f_statustime = 1; 2044b88c807SRodney W. Grimes f_accesstime = 0; 2054b88c807SRodney W. Grimes break; 2064b88c807SRodney W. Grimes case 'u': 2074b88c807SRodney W. Grimes f_accesstime = 1; 2084b88c807SRodney W. Grimes f_statustime = 0; 2094b88c807SRodney W. Grimes break; 2104b88c807SRodney W. Grimes case 'F': 2114b88c807SRodney W. Grimes f_type = 1; 21294274c73STim J. Robbins f_slash = 0; 2134b88c807SRodney W. Grimes break; 2143a34dbf7SDag-Erling Smørgrav case 'H': 2153a34dbf7SDag-Erling Smørgrav fts_options |= FTS_COMFOLLOW; 2163a34dbf7SDag-Erling Smørgrav break; 2173885812cSJosef Karthauser case 'G': 2183d2ddc9eSJosef Karthauser setenv("CLICOLOR", "", 1); 2193885812cSJosef Karthauser break; 2204b88c807SRodney W. Grimes case 'L': 2214b88c807SRodney W. Grimes fts_options &= ~FTS_PHYSICAL; 2224b88c807SRodney W. Grimes fts_options |= FTS_LOGICAL; 2234b88c807SRodney W. Grimes break; 2243a34dbf7SDag-Erling Smørgrav case 'P': 2253a34dbf7SDag-Erling Smørgrav fts_options &= ~FTS_COMFOLLOW; 2263a34dbf7SDag-Erling Smørgrav fts_options &= ~FTS_LOGICAL; 2273a34dbf7SDag-Erling Smørgrav fts_options |= FTS_PHYSICAL; 2283a34dbf7SDag-Erling Smørgrav break; 2294b88c807SRodney W. Grimes case 'R': 2304b88c807SRodney W. Grimes f_recursive = 1; 2314b88c807SRodney W. Grimes break; 2324b88c807SRodney W. Grimes case 'a': 2334b88c807SRodney W. Grimes fts_options |= FTS_SEEDOT; 2344b88c807SRodney W. Grimes /* FALLTHROUGH */ 2354b88c807SRodney W. Grimes case 'A': 2364b88c807SRodney W. Grimes f_listdot = 1; 2374b88c807SRodney W. Grimes break; 2384b88c807SRodney W. Grimes /* The -d option turns off the -R option. */ 2394b88c807SRodney W. Grimes case 'd': 2404b88c807SRodney W. Grimes f_listdir = 1; 2414b88c807SRodney W. Grimes f_recursive = 0; 2424b88c807SRodney W. Grimes break; 2434b88c807SRodney W. Grimes case 'f': 2444b88c807SRodney W. Grimes f_nosort = 1; 2454b88c807SRodney W. Grimes break; 2464b88c807SRodney W. Grimes case 'g': /* Compatibility with 4.3BSD. */ 2474b88c807SRodney W. Grimes break; 2480e8d1551SJosef Karthauser case 'h': 2490e8d1551SJosef Karthauser f_humanval = 1; 2500e8d1551SJosef Karthauser break; 2514b88c807SRodney W. Grimes case 'i': 2524b88c807SRodney W. Grimes f_inode = 1; 2534b88c807SRodney W. Grimes break; 254475727a0SPaul Traina case 'k': 255475727a0SPaul Traina f_kblocks = 1; 256475727a0SPaul Traina break; 25794274c73STim J. Robbins case 'm': 25894274c73STim J. Robbins f_stream = 1; 25994274c73STim J. Robbins f_singlecol = 0; 26094274c73STim J. Robbins f_longform = 0; 26194274c73STim J. Robbins break; 262f3a6a64eSSheldon Hearn case 'n': 263f3a6a64eSSheldon Hearn f_numericonly = 1; 264f3a6a64eSSheldon Hearn break; 2654b88c807SRodney W. Grimes case 'o': 2664b88c807SRodney W. Grimes f_flags = 1; 2674b88c807SRodney W. Grimes break; 26894274c73STim J. Robbins case 'p': 26994274c73STim J. Robbins f_slash = 1; 27094274c73STim J. Robbins f_type = 1; 27194274c73STim J. Robbins break; 2724b88c807SRodney W. Grimes case 'q': 2734b88c807SRodney W. Grimes f_nonprint = 1; 2747ea30648SDag-Erling Smørgrav f_octal = 0; 2750d86878cSDag-Erling Smørgrav f_octal_escape = 0; 2764b88c807SRodney W. Grimes break; 2774b88c807SRodney W. Grimes case 'r': 2784b88c807SRodney W. Grimes f_reversesort = 1; 2794b88c807SRodney W. Grimes break; 2804b88c807SRodney W. Grimes case 's': 2814b88c807SRodney W. Grimes f_size = 1; 2824b88c807SRodney W. Grimes break; 2834b88c807SRodney W. Grimes case 'T': 2844b88c807SRodney W. Grimes f_sectime = 1; 2854b88c807SRodney W. Grimes break; 2864b88c807SRodney W. Grimes case 't': 2874b88c807SRodney W. Grimes f_timesort = 1; 2884b88c807SRodney W. Grimes break; 289fb5cb208SSteve Price case 'W': 290fb5cb208SSteve Price f_whiteout = 1; 291fb5cb208SSteve Price break; 2927ea30648SDag-Erling Smørgrav case 'b': 2937ea30648SDag-Erling Smørgrav f_nonprint = 0; 2940d86878cSDag-Erling Smørgrav f_octal = 0; 2950d86878cSDag-Erling Smørgrav f_octal_escape = 1; 2967ea30648SDag-Erling Smørgrav break; 29747f884f0SJosef Karthauser case 'w': 29847f884f0SJosef Karthauser f_nonprint = 0; 29947f884f0SJosef Karthauser f_octal = 0; 30047f884f0SJosef Karthauser f_octal_escape = 0; 30147f884f0SJosef Karthauser break; 3027304f61fSBrian Feldman case 'Z': 3037304f61fSBrian Feldman f_lomac = 1; 3047304f61fSBrian Feldman break; 3054b88c807SRodney W. Grimes default: 3064b88c807SRodney W. Grimes case '?': 3074b88c807SRodney W. Grimes usage(); 3084b88c807SRodney W. Grimes } 3094b88c807SRodney W. Grimes } 3104b88c807SRodney W. Grimes argc -= optind; 3114b88c807SRodney W. Grimes argv += optind; 3124b88c807SRodney W. Grimes 3133d2ddc9eSJosef Karthauser /* Enabling of colours is conditional on the environment. */ 3143d2ddc9eSJosef Karthauser if (getenv("CLICOLOR") && 3153d2ddc9eSJosef Karthauser (isatty(STDOUT_FILENO) || getenv("CLICOLOR_FORCE"))) 316d4413063SJosef Karthauser #ifdef COLORLS 3173d2ddc9eSJosef Karthauser if (tgetent(termcapbuf, getenv("TERM")) == 1) { 3183d2ddc9eSJosef Karthauser ansi_fgcol = tgetstr("AF", &bp); 3193d2ddc9eSJosef Karthauser ansi_bgcol = tgetstr("AB", &bp); 320c1499cf6SJosef Karthauser attrs_off = tgetstr("me", &bp); 321c1499cf6SJosef Karthauser enter_bold = tgetstr("md", &bp); 3223d2ddc9eSJosef Karthauser 3233d2ddc9eSJosef Karthauser /* To switch colours off use 'op' if 3243d2ddc9eSJosef Karthauser * available, otherwise use 'oc', or 3253d2ddc9eSJosef Karthauser * don't do colours at all. */ 3263d2ddc9eSJosef Karthauser ansi_coloff = tgetstr("op", &bp); 3273d2ddc9eSJosef Karthauser if (!ansi_coloff) 3283d2ddc9eSJosef Karthauser ansi_coloff = tgetstr("oc", &bp); 3293d2ddc9eSJosef Karthauser if (ansi_fgcol && ansi_bgcol && ansi_coloff) 3303d2ddc9eSJosef Karthauser f_color = 1; 3313d2ddc9eSJosef Karthauser } 332d4413063SJosef Karthauser #else 333d4413063SJosef Karthauser (void)fprintf(stderr, "Color support not compiled in.\n"); 334d4413063SJosef Karthauser #endif /*COLORLS*/ 3353d2ddc9eSJosef Karthauser 336d4413063SJosef Karthauser #ifdef COLORLS 337bd82d8abSAndrey A. Chernov if (f_color) { 33822ff3e9eSAndrey A. Chernov /* 33922ff3e9eSAndrey A. Chernov * We can't put tabs and color sequences together: 34022ff3e9eSAndrey A. Chernov * column number will be incremented incorrectly 34122ff3e9eSAndrey A. Chernov * for "stty oxtabs" mode. 34222ff3e9eSAndrey A. Chernov */ 34322ff3e9eSAndrey A. Chernov f_notabs = 1; 344bd82d8abSAndrey A. Chernov (void)signal(SIGINT, colorquit); 345ab08444fSMartin Cracauer (void)signal(SIGQUIT, colorquit); 3463885812cSJosef Karthauser parsecolors(getenv("LSCOLORS")); 347bd82d8abSAndrey A. Chernov } 34874985094SJosef Karthauser #endif 3493885812cSJosef Karthauser 3504b88c807SRodney W. Grimes /* 3514b88c807SRodney W. Grimes * If not -F, -i, -l, -s or -t options, don't require stat 3523885812cSJosef Karthauser * information, unless in color mode in which case we do 3533885812cSJosef Karthauser * need this to determine which colors to display. 3544b88c807SRodney W. Grimes */ 3553885812cSJosef Karthauser if (!f_inode && !f_longform && !f_size && !f_timesort && !f_type 35674985094SJosef Karthauser #ifdef COLORLS 35774985094SJosef Karthauser && !f_color 35874985094SJosef Karthauser #endif 35974985094SJosef Karthauser ) 3604b88c807SRodney W. Grimes fts_options |= FTS_NOSTAT; 3614b88c807SRodney W. Grimes 3624b88c807SRodney W. Grimes /* 3634b88c807SRodney W. Grimes * If not -F, -d or -l options, follow any symbolic links listed on 3644b88c807SRodney W. Grimes * the command line. 3654b88c807SRodney W. Grimes */ 3664b88c807SRodney W. Grimes if (!f_longform && !f_listdir && !f_type) 3674b88c807SRodney W. Grimes fts_options |= FTS_COMFOLLOW; 3684b88c807SRodney W. Grimes 369fb5cb208SSteve Price /* 370fb5cb208SSteve Price * If -W, show whiteout entries 371fb5cb208SSteve Price */ 372fb5cb208SSteve Price #ifdef FTS_WHITEOUT 373fb5cb208SSteve Price if (f_whiteout) 374fb5cb208SSteve Price fts_options |= FTS_WHITEOUT; 375fb5cb208SSteve Price #endif 376fb5cb208SSteve Price 3774b88c807SRodney W. Grimes /* If -l or -s, figure out block size. */ 3784b88c807SRodney W. Grimes if (f_longform || f_size) { 37990b0ec31SPoul-Henning Kamp if (f_kblocks) 38090b0ec31SPoul-Henning Kamp blocksize = 2; 38190b0ec31SPoul-Henning Kamp else { 3824b88c807SRodney W. Grimes (void)getbsize(¬used, &blocksize); 3834b88c807SRodney W. Grimes blocksize /= 512; 38490b0ec31SPoul-Henning Kamp } 3854b88c807SRodney W. Grimes } 3864b88c807SRodney W. Grimes /* Select a sort function. */ 3874b88c807SRodney W. Grimes if (f_reversesort) { 3884b88c807SRodney W. Grimes if (!f_timesort) 3894b88c807SRodney W. Grimes sortfcn = revnamecmp; 3904b88c807SRodney W. Grimes else if (f_accesstime) 3914b88c807SRodney W. Grimes sortfcn = revacccmp; 3924b88c807SRodney W. Grimes else if (f_statustime) 3934b88c807SRodney W. Grimes sortfcn = revstatcmp; 3944b88c807SRodney W. Grimes else /* Use modification time. */ 3954b88c807SRodney W. Grimes sortfcn = revmodcmp; 3964b88c807SRodney W. Grimes } else { 3974b88c807SRodney W. Grimes if (!f_timesort) 3984b88c807SRodney W. Grimes sortfcn = namecmp; 3994b88c807SRodney W. Grimes else if (f_accesstime) 4004b88c807SRodney W. Grimes sortfcn = acccmp; 4014b88c807SRodney W. Grimes else if (f_statustime) 4024b88c807SRodney W. Grimes sortfcn = statcmp; 4034b88c807SRodney W. Grimes else /* Use modification time. */ 4044b88c807SRodney W. Grimes sortfcn = modcmp; 4054b88c807SRodney W. Grimes } 4064b88c807SRodney W. Grimes 4074b88c807SRodney W. Grimes /* Select a print function. */ 4084b88c807SRodney W. Grimes if (f_singlecol) 4094b88c807SRodney W. Grimes printfcn = printscol; 4104b88c807SRodney W. Grimes else if (f_longform) 4114b88c807SRodney W. Grimes printfcn = printlong; 41294274c73STim J. Robbins else if (f_stream) 41394274c73STim J. Robbins printfcn = printstream; 4144b88c807SRodney W. Grimes else 4154b88c807SRodney W. Grimes printfcn = printcol; 4164b88c807SRodney W. Grimes 4174b88c807SRodney W. Grimes if (argc) 4184b88c807SRodney W. Grimes traverse(argc, argv, fts_options); 4194b88c807SRodney W. Grimes else 4204b88c807SRodney W. Grimes traverse(1, dotav, fts_options); 421fb1000d6SAdam David exit(rval); 4224b88c807SRodney W. Grimes } 4234b88c807SRodney W. Grimes 4244b88c807SRodney W. Grimes static int output; /* If anything output. */ 4254b88c807SRodney W. Grimes 4264b88c807SRodney W. Grimes /* 4274b88c807SRodney W. Grimes * Traverse() walks the logical directory structure specified by the argv list 4284b88c807SRodney W. Grimes * in the order specified by the mastercmp() comparison function. During the 4294b88c807SRodney W. Grimes * traversal it passes linked lists of structures to display() which represent 4304b88c807SRodney W. Grimes * a superset (may be exact set) of the files to be displayed. 4314b88c807SRodney W. Grimes */ 4324b88c807SRodney W. Grimes static void 43346251ddeSWarner Losh traverse(int argc, char *argv[], int options) 4344b88c807SRodney W. Grimes { 4354b88c807SRodney W. Grimes FTS *ftsp; 4364b88c807SRodney W. Grimes FTSENT *p, *chp; 4374b88c807SRodney W. Grimes int ch_options; 4384b88c807SRodney W. Grimes 4394b88c807SRodney W. Grimes if ((ftsp = 4404b88c807SRodney W. Grimes fts_open(argv, options, f_nosort ? NULL : mastercmp)) == NULL) 4415ad9e45fSMatthew Dillon err(1, "fts_open"); 4424b88c807SRodney W. Grimes 4434b88c807SRodney W. Grimes display(NULL, fts_children(ftsp, 0)); 4444b88c807SRodney W. Grimes if (f_listdir) 4454b88c807SRodney W. Grimes return; 4464b88c807SRodney W. Grimes 4474b88c807SRodney W. Grimes /* 4484b88c807SRodney W. Grimes * If not recursing down this tree and don't need stat info, just get 4494b88c807SRodney W. Grimes * the names. 4504b88c807SRodney W. Grimes */ 4514b88c807SRodney W. Grimes ch_options = !f_recursive && options & FTS_NOSTAT ? FTS_NAMEONLY : 0; 4524b88c807SRodney W. Grimes 4534b88c807SRodney W. Grimes while ((p = fts_read(ftsp)) != NULL) 4544b88c807SRodney W. Grimes switch (p->fts_info) { 4554b88c807SRodney W. Grimes case FTS_DC: 4564b88c807SRodney W. Grimes warnx("%s: directory causes a cycle", p->fts_name); 4574b88c807SRodney W. Grimes break; 4584b88c807SRodney W. Grimes case FTS_DNR: 4594b88c807SRodney W. Grimes case FTS_ERR: 4604b88c807SRodney W. Grimes warnx("%s: %s", p->fts_name, strerror(p->fts_errno)); 461fb1000d6SAdam David rval = 1; 4624b88c807SRodney W. Grimes break; 4634b88c807SRodney W. Grimes case FTS_D: 4644b88c807SRodney W. Grimes if (p->fts_level != FTS_ROOTLEVEL && 4654b88c807SRodney W. Grimes p->fts_name[0] == '.' && !f_listdot) 4664b88c807SRodney W. Grimes break; 4674b88c807SRodney W. Grimes 4684b88c807SRodney W. Grimes /* 4694b88c807SRodney W. Grimes * If already output something, put out a newline as 4704b88c807SRodney W. Grimes * a separator. If multiple arguments, precede each 4714b88c807SRodney W. Grimes * directory with its name. 4724b88c807SRodney W. Grimes */ 4734b88c807SRodney W. Grimes if (output) 4744b88c807SRodney W. Grimes (void)printf("\n%s:\n", p->fts_path); 4754b88c807SRodney W. Grimes else if (argc > 1) { 4764b88c807SRodney W. Grimes (void)printf("%s:\n", p->fts_path); 4774b88c807SRodney W. Grimes output = 1; 4784b88c807SRodney W. Grimes } 4794b88c807SRodney W. Grimes chp = fts_children(ftsp, ch_options); 4804b88c807SRodney W. Grimes display(p, chp); 4814b88c807SRodney W. Grimes 4824b88c807SRodney W. Grimes if (!f_recursive && chp != NULL) 4834b88c807SRodney W. Grimes (void)fts_set(ftsp, p, FTS_SKIP); 4844b88c807SRodney W. Grimes break; 485568dcd5fSBill Fumerola default: 486568dcd5fSBill Fumerola break; 4874b88c807SRodney W. Grimes } 4884b88c807SRodney W. Grimes if (errno) 4894b88c807SRodney W. Grimes err(1, "fts_read"); 4904b88c807SRodney W. Grimes } 4914b88c807SRodney W. Grimes 4924b88c807SRodney W. Grimes /* 4934b88c807SRodney W. Grimes * Display() takes a linked list of FTSENT structures and passes the list 4944b88c807SRodney W. Grimes * along with any other necessary information to the print function. P 4954b88c807SRodney W. Grimes * points to the parent directory of the display list. 4964b88c807SRodney W. Grimes */ 4974b88c807SRodney W. Grimes static void 49846251ddeSWarner Losh display(FTSENT *p, FTSENT *list) 4994b88c807SRodney W. Grimes { 5004b88c807SRodney W. Grimes struct stat *sp; 5014b88c807SRodney W. Grimes DISPLAY d; 5024b88c807SRodney W. Grimes FTSENT *cur; 5034b88c807SRodney W. Grimes NAMES *np; 5049052855aSMark Murray off_t maxsize; 5059052855aSMark Murray u_long btotal, lattrlen, maxblock, maxinode, maxlen, maxnlink, maxlattr; 5069052855aSMark Murray int bcfile, maxflags; 5079052855aSMark Murray gid_t maxgroup; 5089052855aSMark Murray uid_t maxuser; 5099052855aSMark Murray size_t flen, ulen, glen; 510545f583cSTim Vanderhoek char *initmax; 5114b88c807SRodney W. Grimes int entries, needstats; 5120928a7f1SJuli Mallett const char *user, *group; 5130928a7f1SJuli Mallett char *flags, *lattr = NULL; 514008a4910SSheldon Hearn char buf[STRBUF_SIZEOF(u_quad_t) + 1]; 515008a4910SSheldon Hearn char ngroup[STRBUF_SIZEOF(uid_t) + 1]; 516008a4910SSheldon Hearn char nuser[STRBUF_SIZEOF(gid_t) + 1]; 5174b88c807SRodney W. Grimes 5184b88c807SRodney W. Grimes /* 5194b88c807SRodney W. Grimes * If list is NULL there are two possibilities: that the parent 5204b88c807SRodney W. Grimes * directory p has no children, or that fts_children() returned an 5214b88c807SRodney W. Grimes * error. We ignore the error case since it will be replicated 5224b88c807SRodney W. Grimes * on the next call to fts_read() on the post-order visit to the 52346be34b9SKris Kennaway * directory p, and will be signaled in traverse(). 5244b88c807SRodney W. Grimes */ 5254b88c807SRodney W. Grimes if (list == NULL) 5264b88c807SRodney W. Grimes return; 5274b88c807SRodney W. Grimes 5284b88c807SRodney W. Grimes needstats = f_inode || f_longform || f_size; 5294b88c807SRodney W. Grimes flen = 0; 530545f583cSTim Vanderhoek btotal = 0; 531545f583cSTim Vanderhoek initmax = getenv("LS_COLWIDTHS"); 532545f583cSTim Vanderhoek /* Fields match -lios order. New ones should be added at the end. */ 5339052855aSMark Murray maxlattr = maxblock = maxinode = maxlen = maxnlink = 5349052855aSMark Murray maxuser = maxgroup = maxflags = maxsize = 0; 535545f583cSTim Vanderhoek if (initmax != NULL && *initmax != '\0') { 536545f583cSTim Vanderhoek char *initmax2, *jinitmax; 537545f583cSTim Vanderhoek int ninitmax; 538545f583cSTim Vanderhoek 539545f583cSTim Vanderhoek /* Fill-in "::" as "0:0:0" for the sake of scanf. */ 540545f583cSTim Vanderhoek jinitmax = initmax2 = malloc(strlen(initmax) * 2 + 2); 541545f583cSTim Vanderhoek if (jinitmax == NULL) 5425ad9e45fSMatthew Dillon err(1, "malloc"); 543545f583cSTim Vanderhoek if (*initmax == ':') 544545f583cSTim Vanderhoek strcpy(initmax2, "0:"), initmax2 += 2; 545545f583cSTim Vanderhoek else 546545f583cSTim Vanderhoek *initmax2++ = *initmax, *initmax2 = '\0'; 547545f583cSTim Vanderhoek for (initmax++; *initmax != '\0'; initmax++) { 548545f583cSTim Vanderhoek if (initmax[-1] == ':' && initmax[0] == ':') { 549545f583cSTim Vanderhoek *initmax2++ = '0'; 550545f583cSTim Vanderhoek *initmax2++ = initmax[0]; 551545f583cSTim Vanderhoek initmax2[1] = '\0'; 552545f583cSTim Vanderhoek } else { 553545f583cSTim Vanderhoek *initmax2++ = initmax[0]; 554545f583cSTim Vanderhoek initmax2[1] = '\0'; 555545f583cSTim Vanderhoek } 556545f583cSTim Vanderhoek } 5575dda5d0dSJosef Karthauser if (initmax2[-1] == ':') 5585dda5d0dSJosef Karthauser strcpy(initmax2, "0"); 559545f583cSTim Vanderhoek 560545f583cSTim Vanderhoek ninitmax = sscanf(jinitmax, 5619052855aSMark Murray " %lu : %lu : %lu : %i : %i : %i : %llu : %lu : %lu ", 562545f583cSTim Vanderhoek &maxinode, &maxblock, &maxnlink, &maxuser, 5637304f61fSBrian Feldman &maxgroup, &maxflags, &maxsize, &maxlen, &maxlattr); 564545f583cSTim Vanderhoek f_notabs = 1; 565545f583cSTim Vanderhoek switch (ninitmax) { 5665dda5d0dSJosef Karthauser case 0: 5675dda5d0dSJosef Karthauser maxinode = 0; 5680d9f1a69SPhilippe Charnier /* FALLTHROUGH */ 5695dda5d0dSJosef Karthauser case 1: 5705dda5d0dSJosef Karthauser maxblock = 0; 5710d9f1a69SPhilippe Charnier /* FALLTHROUGH */ 5725dda5d0dSJosef Karthauser case 2: 5735dda5d0dSJosef Karthauser maxnlink = 0; 5740d9f1a69SPhilippe Charnier /* FALLTHROUGH */ 5755dda5d0dSJosef Karthauser case 3: 5765dda5d0dSJosef Karthauser maxuser = 0; 5770d9f1a69SPhilippe Charnier /* FALLTHROUGH */ 5785dda5d0dSJosef Karthauser case 4: 5795dda5d0dSJosef Karthauser maxgroup = 0; 5800d9f1a69SPhilippe Charnier /* FALLTHROUGH */ 5815dda5d0dSJosef Karthauser case 5: 5825dda5d0dSJosef Karthauser maxflags = 0; 5830d9f1a69SPhilippe Charnier /* FALLTHROUGH */ 5845dda5d0dSJosef Karthauser case 6: 5855dda5d0dSJosef Karthauser maxsize = 0; 5860d9f1a69SPhilippe Charnier /* FALLTHROUGH */ 5875dda5d0dSJosef Karthauser case 7: 5885dda5d0dSJosef Karthauser maxlen = 0; 5890d9f1a69SPhilippe Charnier /* FALLTHROUGH */ 5905dda5d0dSJosef Karthauser case 8: 5915dda5d0dSJosef Karthauser maxlattr = 0; 5920d9f1a69SPhilippe Charnier /* FALLTHROUGH */ 59318d8a22bSAndrey A. Chernov #ifdef COLORLS 59418d8a22bSAndrey A. Chernov if (!f_color) 59522ff3e9eSAndrey A. Chernov #endif 59618d8a22bSAndrey A. Chernov f_notabs = 0; 5970d9f1a69SPhilippe Charnier /* FALLTHROUGH */ 5989052855aSMark Murray default: 599568dcd5fSBill Fumerola break; 600545f583cSTim Vanderhoek } 601545f583cSTim Vanderhoek maxinode = makenines(maxinode); 602545f583cSTim Vanderhoek maxblock = makenines(maxblock); 603545f583cSTim Vanderhoek maxnlink = makenines(maxnlink); 604545f583cSTim Vanderhoek maxsize = makenines(maxsize); 6059052855aSMark Murray } 6067304f61fSBrian Feldman if (f_lomac) 6077304f61fSBrian Feldman lomac_start(); 6084b88c807SRodney W. Grimes bcfile = 0; 6090fd510b7SJoerg Wunsch flags = NULL; 6104b88c807SRodney W. Grimes for (cur = list, entries = 0; cur; cur = cur->fts_link) { 6114b88c807SRodney W. Grimes if (cur->fts_info == FTS_ERR || cur->fts_info == FTS_NS) { 6124b88c807SRodney W. Grimes warnx("%s: %s", 6134b88c807SRodney W. Grimes cur->fts_name, strerror(cur->fts_errno)); 6144b88c807SRodney W. Grimes cur->fts_number = NO_PRINT; 615fb1000d6SAdam David rval = 1; 6164b88c807SRodney W. Grimes continue; 6174b88c807SRodney W. Grimes } 6184b88c807SRodney W. Grimes /* 6194b88c807SRodney W. Grimes * P is NULL if list is the argv list, to which different rules 6204b88c807SRodney W. Grimes * apply. 6214b88c807SRodney W. Grimes */ 6224b88c807SRodney W. Grimes if (p == NULL) { 6234b88c807SRodney W. Grimes /* Directories will be displayed later. */ 6244b88c807SRodney W. Grimes if (cur->fts_info == FTS_D && !f_listdir) { 6254b88c807SRodney W. Grimes cur->fts_number = NO_PRINT; 6264b88c807SRodney W. Grimes continue; 6274b88c807SRodney W. Grimes } 6284b88c807SRodney W. Grimes } else { 6294b88c807SRodney W. Grimes /* Only display dot file if -a/-A set. */ 6304b88c807SRodney W. Grimes if (cur->fts_name[0] == '.' && !f_listdot) { 6314b88c807SRodney W. Grimes cur->fts_number = NO_PRINT; 6324b88c807SRodney W. Grimes continue; 6334b88c807SRodney W. Grimes } 6344b88c807SRodney W. Grimes } 6354b88c807SRodney W. Grimes if (cur->fts_namelen > maxlen) 6364b88c807SRodney W. Grimes maxlen = cur->fts_namelen; 6370d86878cSDag-Erling Smørgrav if (f_octal || f_octal_escape) { 6386bd042dfSJosef Karthauser u_long t = len_octal(cur->fts_name, cur->fts_namelen); 6395dda5d0dSJosef Karthauser 6405dda5d0dSJosef Karthauser if (t > maxlen) 6415dda5d0dSJosef Karthauser maxlen = t; 6427ea30648SDag-Erling Smørgrav } 6434b88c807SRodney W. Grimes if (needstats) { 6444b88c807SRodney W. Grimes sp = cur->fts_statp; 6454b88c807SRodney W. Grimes if (sp->st_blocks > maxblock) 6464b88c807SRodney W. Grimes maxblock = sp->st_blocks; 6474b88c807SRodney W. Grimes if (sp->st_ino > maxinode) 6484b88c807SRodney W. Grimes maxinode = sp->st_ino; 6494b88c807SRodney W. Grimes if (sp->st_nlink > maxnlink) 6504b88c807SRodney W. Grimes maxnlink = sp->st_nlink; 6514b88c807SRodney W. Grimes if (sp->st_size > maxsize) 6524b88c807SRodney W. Grimes maxsize = sp->st_size; 6534b88c807SRodney W. Grimes 6544b88c807SRodney W. Grimes btotal += sp->st_blocks; 6554b88c807SRodney W. Grimes if (f_longform) { 656f3a6a64eSSheldon Hearn if (f_numericonly) { 657f3a6a64eSSheldon Hearn (void)snprintf(nuser, sizeof(nuser), 658f3a6a64eSSheldon Hearn "%u", sp->st_uid); 659f3a6a64eSSheldon Hearn (void)snprintf(ngroup, sizeof(ngroup), 660f3a6a64eSSheldon Hearn "%u", sp->st_gid); 661f3a6a64eSSheldon Hearn user = nuser; 662f3a6a64eSSheldon Hearn group = ngroup; 663f3a6a64eSSheldon Hearn } else { 6644b88c807SRodney W. Grimes user = user_from_uid(sp->st_uid, 0); 665f3a6a64eSSheldon Hearn group = group_from_gid(sp->st_gid, 0); 666f3a6a64eSSheldon Hearn } 6674b88c807SRodney W. Grimes if ((ulen = strlen(user)) > maxuser) 6684b88c807SRodney W. Grimes maxuser = ulen; 6694b88c807SRodney W. Grimes if ((glen = strlen(group)) > maxgroup) 6704b88c807SRodney W. Grimes maxgroup = glen; 6714b88c807SRodney W. Grimes if (f_flags) { 672141d77b8SJosef Karthauser flags = fflagstostr(sp->st_flags); 673141d77b8SJosef Karthauser if (flags != NULL && *flags == '\0') { 674141d77b8SJosef Karthauser free(flags); 675141d77b8SJosef Karthauser flags = strdup("-"); 676141d77b8SJosef Karthauser } 677141d77b8SJosef Karthauser if (flags == NULL) 6785ad9e45fSMatthew Dillon err(1, "fflagstostr"); 6799052855aSMark Murray flen = strlen(flags); 6809052855aSMark Murray if (flen > (size_t)maxflags) 6814b88c807SRodney W. Grimes maxflags = flen; 6824b88c807SRodney W. Grimes } else 6834b88c807SRodney W. Grimes flen = 0; 684900021aeSWarner Losh lattr = NULL; 6857304f61fSBrian Feldman if (f_lomac) { 6867304f61fSBrian Feldman lattr = get_lattr(cur); 6877304f61fSBrian Feldman lattrlen = strlen(lattr); 6887304f61fSBrian Feldman if (lattrlen > maxlattr) 6897304f61fSBrian Feldman maxlattr = lattrlen; 6907304f61fSBrian Feldman } else 6917304f61fSBrian Feldman lattrlen = 0; 6924b88c807SRodney W. Grimes 6937304f61fSBrian Feldman if ((np = malloc(sizeof(NAMES) + lattrlen + 6947304f61fSBrian Feldman ulen + glen + flen + 4)) == NULL) 6955ad9e45fSMatthew Dillon err(1, "malloc"); 6964b88c807SRodney W. Grimes 6974b88c807SRodney W. Grimes np->user = &np->data[0]; 6984b88c807SRodney W. Grimes (void)strcpy(np->user, user); 6994b88c807SRodney W. Grimes np->group = &np->data[ulen + 1]; 7004b88c807SRodney W. Grimes (void)strcpy(np->group, group); 7014b88c807SRodney W. Grimes 7024b88c807SRodney W. Grimes if (S_ISCHR(sp->st_mode) || 7034b88c807SRodney W. Grimes S_ISBLK(sp->st_mode)) 7044b88c807SRodney W. Grimes bcfile = 1; 7054b88c807SRodney W. Grimes 7064b88c807SRodney W. Grimes if (f_flags) { 7074b88c807SRodney W. Grimes np->flags = &np->data[ulen + glen + 2]; 7084b88c807SRodney W. Grimes (void)strcpy(np->flags, flags); 709141d77b8SJosef Karthauser free(flags); 7104b88c807SRodney W. Grimes } 7117304f61fSBrian Feldman if (f_lomac) { 7127304f61fSBrian Feldman np->lattr = &np->data[ulen + glen + 2 7137304f61fSBrian Feldman + (f_flags ? flen + 1 : 0)]; 7147304f61fSBrian Feldman (void)strcpy(np->lattr, lattr); 7157304f61fSBrian Feldman free(lattr); 7167304f61fSBrian Feldman } 7174b88c807SRodney W. Grimes cur->fts_pointer = np; 7184b88c807SRodney W. Grimes } 7194b88c807SRodney W. Grimes } 7204b88c807SRodney W. Grimes ++entries; 7214b88c807SRodney W. Grimes } 7224b88c807SRodney W. Grimes 7234b88c807SRodney W. Grimes if (!entries) 7244b88c807SRodney W. Grimes return; 7254b88c807SRodney W. Grimes 7264b88c807SRodney W. Grimes d.list = list; 7274b88c807SRodney W. Grimes d.entries = entries; 7284b88c807SRodney W. Grimes d.maxlen = maxlen; 7294b88c807SRodney W. Grimes if (needstats) { 7304b88c807SRodney W. Grimes d.bcfile = bcfile; 7314b88c807SRodney W. Grimes d.btotal = btotal; 7324b88c807SRodney W. Grimes (void)snprintf(buf, sizeof(buf), "%lu", maxblock); 7334b88c807SRodney W. Grimes d.s_block = strlen(buf); 7344b88c807SRodney W. Grimes d.s_flags = maxflags; 7357304f61fSBrian Feldman d.s_lattr = maxlattr; 7364b88c807SRodney W. Grimes d.s_group = maxgroup; 7374b88c807SRodney W. Grimes (void)snprintf(buf, sizeof(buf), "%lu", maxinode); 7384b88c807SRodney W. Grimes d.s_inode = strlen(buf); 7394b88c807SRodney W. Grimes (void)snprintf(buf, sizeof(buf), "%lu", maxnlink); 7404b88c807SRodney W. Grimes d.s_nlink = strlen(buf); 7414b88c807SRodney W. Grimes (void)snprintf(buf, sizeof(buf), "%qu", maxsize); 7424b88c807SRodney W. Grimes d.s_size = strlen(buf); 7434b88c807SRodney W. Grimes d.s_user = maxuser; 7444b88c807SRodney W. Grimes } 7454b88c807SRodney W. Grimes printfcn(&d); 7464b88c807SRodney W. Grimes output = 1; 7474b88c807SRodney W. Grimes 7484b88c807SRodney W. Grimes if (f_longform) 7494b88c807SRodney W. Grimes for (cur = list; cur; cur = cur->fts_link) 7504b88c807SRodney W. Grimes free(cur->fts_pointer); 7517304f61fSBrian Feldman if (f_lomac) 7527304f61fSBrian Feldman lomac_stop(); 7534b88c807SRodney W. Grimes } 7544b88c807SRodney W. Grimes 7554b88c807SRodney W. Grimes /* 7564b88c807SRodney W. Grimes * Ordering for mastercmp: 7574b88c807SRodney W. Grimes * If ordering the argv (fts_level = FTS_ROOTLEVEL) return non-directories 7584b88c807SRodney W. Grimes * as larger than directories. Within either group, use the sort function. 7594b88c807SRodney W. Grimes * All other levels use the sort function. Error entries remain unsorted. 7604b88c807SRodney W. Grimes */ 7614b88c807SRodney W. Grimes static int 7620d3bcc2eSGarrett Wollman mastercmp(const FTSENT * const *a, const FTSENT * const *b) 7634b88c807SRodney W. Grimes { 7644b88c807SRodney W. Grimes int a_info, b_info; 7654b88c807SRodney W. Grimes 7664b88c807SRodney W. Grimes a_info = (*a)->fts_info; 7674b88c807SRodney W. Grimes if (a_info == FTS_ERR) 7684b88c807SRodney W. Grimes return (0); 7694b88c807SRodney W. Grimes b_info = (*b)->fts_info; 7704b88c807SRodney W. Grimes if (b_info == FTS_ERR) 7714b88c807SRodney W. Grimes return (0); 7724b88c807SRodney W. Grimes 7734b88c807SRodney W. Grimes if (a_info == FTS_NS || b_info == FTS_NS) 7744b88c807SRodney W. Grimes return (namecmp(*a, *b)); 7754b88c807SRodney W. Grimes 77651f26ac5SSean Eric Fagan if (a_info != b_info && 77751f26ac5SSean Eric Fagan (*a)->fts_level == FTS_ROOTLEVEL && !f_listdir) { 7784b88c807SRodney W. Grimes if (a_info == FTS_D) 7794b88c807SRodney W. Grimes return (1); 78051f26ac5SSean Eric Fagan if (b_info == FTS_D) 7814b88c807SRodney W. Grimes return (-1); 78251f26ac5SSean Eric Fagan } 7834b88c807SRodney W. Grimes return (sortfcn(*a, *b)); 7844b88c807SRodney W. Grimes } 785545f583cSTim Vanderhoek 786545f583cSTim Vanderhoek /* 787545f583cSTim Vanderhoek * Makenines() returns (10**n)-1. This is useful for converting a width 788545f583cSTim Vanderhoek * into a number that wide in decimal. 789545f583cSTim Vanderhoek */ 790545f583cSTim Vanderhoek static u_quad_t 79146251ddeSWarner Losh makenines(u_long n) 792545f583cSTim Vanderhoek { 793545f583cSTim Vanderhoek u_long i; 794545f583cSTim Vanderhoek u_quad_t reg; 795545f583cSTim Vanderhoek 796545f583cSTim Vanderhoek reg = 1; 797545f583cSTim Vanderhoek /* Use a loop instead of pow(), since all values of n are small. */ 798545f583cSTim Vanderhoek for (i = 0; i < n; i++) 799545f583cSTim Vanderhoek reg *= 10; 800545f583cSTim Vanderhoek reg--; 801545f583cSTim Vanderhoek 802545f583cSTim Vanderhoek return reg; 803545f583cSTim Vanderhoek } 804