Remove `register' keyword.
[platform/upstream/coreutils.git] / src / ls.c
1 /* `dir', `vdir' and `ls' directory listing programs for GNU.
2    Copyright (C) 85, 88, 90, 91, 1995-2005 Free Software Foundation, Inc.
3
4    This program is free software; you can redistribute it and/or modify
5    it under the terms of the GNU General Public License as published by
6    the Free Software Foundation; either version 2, or (at your option)
7    any later version.
8
9    This program is distributed in the hope that it will be useful,
10    but WITHOUT ANY WARRANTY; without even the implied warranty of
11    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12    GNU General Public License for more details.
13
14    You should have received a copy of the GNU General Public License
15    along with this program; if not, write to the Free Software Foundation,
16    Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
17
18 /* If ls_mode is LS_MULTI_COL,
19    the multi-column format is the default regardless
20    of the type of output device.
21    This is for the `dir' program.
22
23    If ls_mode is LS_LONG_FORMAT,
24    the long format is the default regardless of the
25    type of output device.
26    This is for the `vdir' program.
27
28    If ls_mode is LS_LS,
29    the output format depends on whether the output
30    device is a terminal.
31    This is for the `ls' program.  */
32
33 /* Written by Richard Stallman and David MacKenzie.  */
34
35 /* Color support by Peter Anvin <Peter.Anvin@linux.org> and Dennis
36    Flaherty <dennisf@denix.elk.miles.com> based on original patches by
37    Greg Lee <lee@uhunix.uhcc.hawaii.edu>.  */
38
39 #include <config.h>
40 #include <sys/types.h>
41
42 #if HAVE_TERMIOS_H
43 # include <termios.h>
44 #endif
45
46 #ifdef GWINSZ_IN_SYS_IOCTL
47 # include <sys/ioctl.h>
48 #endif
49
50 #ifdef WINSIZE_IN_PTEM
51 # include <sys/stream.h>
52 # include <sys/ptem.h>
53 #endif
54
55 #include <stdio.h>
56 #include <assert.h>
57 #include <setjmp.h>
58 #include <grp.h>
59 #include <pwd.h>
60 #include <getopt.h>
61 #include <signal.h>
62
63 #ifndef SA_NOCLDSTOP
64 # define sigprocmask(How, Set, Oset) /* empty */
65 # define sigset_t int
66 #endif
67
68 /* Get mbstate_t, mbrtowc(), mbsinit(), wcwidth().  */
69 #if HAVE_WCHAR_H
70 # include <wchar.h>
71 #endif
72
73 /* Get iswprint().  */
74 #if HAVE_WCTYPE_H
75 # include <wctype.h>
76 #endif
77 #if !defined iswprint && !HAVE_ISWPRINT
78 # define iswprint(wc) 1
79 #endif
80
81 #ifndef HAVE_DECL_WCWIDTH
82 "this configure-time declaration test was not run"
83 #endif
84 #if !HAVE_DECL_WCWIDTH
85 int wcwidth ();
86 #endif
87
88 /* If wcwidth() doesn't exist, assume all printable characters have
89    width 1.  */
90 #ifndef wcwidth
91 # if !HAVE_WCWIDTH
92 #  define wcwidth(wc) ((wc) == 0 ? 0 : iswprint (wc) ? 1 : -1)
93 # endif
94 #endif
95
96 #include "system.h"
97 #include <fnmatch.h>
98
99 #include "acl.h"
100 #include "argmatch.h"
101 #include "dev-ino.h"
102 #include "dirname.h"
103 #include "dirfd.h"
104 #include "error.h"
105 #include "hard-locale.h"
106 #include "hash.h"
107 #include "human.h"
108 #include "filemode.h"
109 #include "inttostr.h"
110 #include "ls.h"
111 #include "mbswidth.h"
112 #include "obstack.h"
113 #include "path-concat.h"
114 #include "quote.h"
115 #include "quotearg.h"
116 #include "same.h"
117 #include "strftime.h"
118 #include "strverscmp.h"
119 #include "xstrtol.h"
120 #include "xreadlink.h"
121
122 #define PROGRAM_NAME (ls_mode == LS_LS ? "ls" \
123                       : (ls_mode == LS_MULTI_COL \
124                          ? "dir" : "vdir"))
125
126 #define AUTHORS "Richard Stallman", "David MacKenzie"
127
128 #define obstack_chunk_alloc malloc
129 #define obstack_chunk_free free
130
131 /* Return an int indicating the result of comparing two integers.
132    Subtracting doesn't always work, due to overflow.  */
133 #define longdiff(a, b) ((a) < (b) ? -1 : (a) > (b))
134
135 /* Arrange to make lstat calls go through the wrapper function
136    on systems with an lstat function that does not dereference symlinks
137    that are specified with a trailing slash.  */
138 #if ! LSTAT_FOLLOWS_SLASHED_SYMLINK
139 int rpl_lstat (const char *, struct stat *);
140 # undef lstat
141 # define lstat(Name, Stat_buf) rpl_lstat(Name, Stat_buf)
142 #endif
143
144 #if HAVE_STRUCT_DIRENT_D_TYPE && defined DTTOIF
145 # define DT_INIT(Val) = Val
146 #else
147 # define DT_INIT(Val) /* empty */
148 #endif
149
150 #if ! HAVE_STRUCT_STAT_ST_AUTHOR
151 # define st_author st_uid
152 #endif
153
154 /* Cray/Unicos DMF: use the file's migrated, not real, status */
155 #if HAVE_ST_DM_MODE
156 # define ST_DM_MODE(Stat_buf) ((Stat_buf).st_dm_mode)
157 #else
158 # define ST_DM_MODE(Stat_buf) ((Stat_buf).st_mode)
159 #endif
160
161 enum filetype
162   {
163     unknown DT_INIT (DT_UNKNOWN),
164     fifo DT_INIT (DT_FIFO),
165     chardev DT_INIT (DT_CHR),
166     directory DT_INIT (DT_DIR),
167     blockdev DT_INIT (DT_BLK),
168     normal DT_INIT (DT_REG),
169     symbolic_link DT_INIT (DT_LNK),
170     sock DT_INIT (DT_SOCK),
171     arg_directory DT_INIT (2 * (DT_UNKNOWN | DT_FIFO | DT_CHR | DT_DIR | DT_BLK
172                                 | DT_REG | DT_LNK | DT_SOCK))
173   };
174
175 struct fileinfo
176   {
177     /* The file name.  */
178     char *name;
179
180     struct stat stat;
181
182     /* For symbolic link, name of the file linked to, otherwise zero.  */
183     char *linkname;
184
185     /* For symbolic link and long listing, st_mode of file linked to, otherwise
186        zero.  */
187     mode_t linkmode;
188
189     /* For symbolic link and color printing, true if linked-to file
190        exists, otherwise false.  */
191     bool linkok;
192
193     enum filetype filetype;
194
195 #if HAVE_ACL
196     /* For long listings, true if the file has an access control list.  */
197     bool have_acl;
198 #endif
199   };
200
201 #if HAVE_ACL
202 # define FILE_HAS_ACL(F) ((F)->have_acl)
203 #else
204 # define FILE_HAS_ACL(F) 0
205 #endif
206
207 #define LEN_STR_PAIR(s) sizeof (s) - 1, s
208
209 /* Null is a valid character in a color indicator (think about Epson
210    printers, for example) so we have to use a length/buffer string
211    type.  */
212
213 struct bin_str
214   {
215     size_t len;                 /* Number of bytes */
216     const char *string;         /* Pointer to the same */
217   };
218
219 char *getgroup ();
220 char *getuser ();
221
222 #if ! HAVE_TCGETPGRP
223 # define tcgetpgrp(Fd) 0
224 #endif
225
226 static size_t quote_name (FILE *out, const char *name,
227                           struct quoting_options const *options,
228                           size_t *width);
229 static char *make_link_path (const char *path, const char *linkname);
230 static int decode_switches (int argc, char **argv);
231 static bool file_ignored (char const *name);
232 static uintmax_t gobble_file (char const *name, enum filetype type,
233                               bool command_line_arg, char const *dirname);
234 static void print_color_indicator (const char *name, mode_t mode, int linkok);
235 static void put_indicator (const struct bin_str *ind);
236 static void add_ignore_pattern (const char *pattern);
237 static void attach (char *dest, const char *dirname, const char *name);
238 static void clear_files (void);
239 static void extract_dirs_from_files (char const *dirname,
240                                      bool command_line_arg);
241 static void get_link_name (char const *filename, struct fileinfo *f,
242                            bool command_line_arg);
243 static void indent (size_t from, size_t to);
244 static size_t calculate_columns (bool by_columns);
245 static void print_current_files (void);
246 static void print_dir (char const *name, char const *realname,
247                        bool command_line_arg);
248 static void print_file_name_and_frills (const struct fileinfo *f);
249 static void print_horizontal (void);
250 static int format_user_width (uid_t u);
251 static int format_group_width (gid_t g);
252 static void print_long_format (const struct fileinfo *f);
253 static void print_many_per_line (void);
254 static void print_name_with_quoting (const char *p, mode_t mode,
255                                      int linkok,
256                                      struct obstack *stack);
257 static void prep_non_filename_text (void);
258 static void print_type_indicator (mode_t mode);
259 static void print_with_commas (void);
260 static void queue_directory (char const *name, char const *realname,
261                              bool command_line_arg);
262 static void sort_files (void);
263 static void parse_ls_color (void);
264 void usage (int status);
265
266 /* The name the program was run with, stripped of any leading path.  */
267 char *program_name;
268
269 /* Initial size of hash table.
270    Most hierarchies are likely to be shallower than this.  */
271 #define INITIAL_TABLE_SIZE 30
272
273 /* The set of `active' directories, from the current command-line argument
274    to the level in the hierarchy at which files are being listed.
275    A directory is represented by its device and inode numbers (struct dev_ino).
276    A directory is added to this set when ls begins listing it or its
277    entries, and it is removed from the set just after ls has finished
278    processing it.  This set is used solely to detect loops, e.g., with
279    mkdir loop; cd loop; ln -s ../loop sub; ls -RL  */
280 static Hash_table *active_dir_set;
281
282 #define LOOP_DETECT (!!active_dir_set)
283
284 /* The table of files in the current directory:
285
286    `files' points to a vector of `struct fileinfo', one per file.
287    `nfiles' is the number of elements space has been allocated for.
288    `files_index' is the number actually in use.  */
289
290 /* Address of block containing the files that are described.  */
291 static struct fileinfo *files;  /* FIXME: rename this to e.g. cwd_file */
292
293 /* Length of block that `files' points to, measured in files.  */
294 static size_t nfiles;  /* FIXME: rename this to e.g. cwd_n_alloc */
295
296 /* Index of first unused in `files'.  */
297 static size_t files_index;  /* FIXME: rename this to e.g. cwd_n_used */
298
299 /* When true, in a color listing, color each symlink name according to the
300    type of file it points to.  Otherwise, color them according to the `ln'
301    directive in LS_COLORS.  Dangling (orphan) symlinks are treated specially,
302    regardless.  This is set when `ln=target' appears in LS_COLORS.  */
303
304 static bool color_symlink_as_referent;
305
306 /* mode of appropriate file for colorization */
307 #define FILE_OR_LINK_MODE(File) \
308     ((color_symlink_as_referent & (File)->linkok) \
309      ? (File)->linkmode : (File)->stat.st_mode)
310
311
312 /* Record of one pending directory waiting to be listed.  */
313
314 struct pending
315   {
316     char *name;
317     /* If the directory is actually the file pointed to by a symbolic link we
318        were told to list, `realname' will contain the name of the symbolic
319        link, otherwise zero.  */
320     char *realname;
321     bool command_line_arg;
322     struct pending *next;
323   };
324
325 static struct pending *pending_dirs;
326
327 /* Current time in seconds and nanoseconds since 1970, updated as
328    needed when deciding whether a file is recent.  */
329
330 static time_t current_time = TYPE_MINIMUM (time_t);
331 static int current_time_ns = -1;
332
333 /* The number of columns to use for columns containing inode numbers,
334    block sizes, link counts, owners, groups, authors, major device
335    numbers, minor device numbers, and file sizes, respectively.  */
336
337 static int inode_number_width;
338 static int block_size_width;
339 static int nlink_width;
340 static int owner_width;
341 static int group_width;
342 static int author_width;
343 static int major_device_number_width;
344 static int minor_device_number_width;
345 static int file_size_width;
346
347 /* Option flags */
348
349 /* long_format for lots of info, one per line.
350    one_per_line for just names, one per line.
351    many_per_line for just names, many per line, sorted vertically.
352    horizontal for just names, many per line, sorted horizontally.
353    with_commas for just names, many per line, separated by commas.
354
355    -l (and other options that imply -l), -1, -C, -x and -m control
356    this parameter.  */
357
358 enum format
359   {
360     long_format,                /* -l and other options that imply -l */
361     one_per_line,               /* -1 */
362     many_per_line,              /* -C */
363     horizontal,                 /* -x */
364     with_commas                 /* -m */
365   };
366
367 static enum format format;
368
369 /* `full-iso' uses full ISO-style dates and times.  `long-iso' uses longer
370    ISO-style time stamps, though shorter than `full-iso'.  `iso' uses shorter
371    ISO-style time stamps.  `locale' uses locale-dependent time stamps.  */
372 enum time_style
373   {
374     full_iso_time_style,        /* --time-style=full-iso */
375     long_iso_time_style,        /* --time-style=long-iso */
376     iso_time_style,             /* --time-style=iso */
377     locale_time_style           /* --time-style=locale */
378   };
379
380 static char const *const time_style_args[] =
381 {
382   "full-iso", "long-iso", "iso", "locale", 0
383 };
384
385 static enum time_style const time_style_types[] =
386 {
387   full_iso_time_style, long_iso_time_style, iso_time_style,
388   locale_time_style, 0
389 };
390
391 /* Type of time to print or sort by.  Controlled by -c and -u.  */
392
393 enum time_type
394   {
395     time_mtime,                 /* default */
396     time_ctime,                 /* -c */
397     time_atime                  /* -u */
398   };
399
400 static enum time_type time_type;
401
402 /* The file characteristic to sort by.  Controlled by -t, -S, -U, -X, -v.  */
403
404 enum sort_type
405   {
406     sort_none,                  /* -U */
407     sort_name,                  /* default */
408     sort_extension,             /* -X */
409     sort_time,                  /* -t */
410     sort_size,                  /* -S */
411     sort_version                /* -v */
412   };
413
414 static enum sort_type sort_type;
415
416 /* Direction of sort.
417    false means highest first if numeric,
418    lowest first if alphabetic;
419    these are the defaults.
420    true means the opposite order in each case.  -r  */
421
422 static bool sort_reverse;
423
424 /* True means to display owner information.  -g turns this off.  */
425
426 static bool print_owner = true;
427
428 /* True means to display author information.  */
429
430 static bool print_author;
431
432 /* True means to display group information.  -G and -o turn this off.  */
433
434 static bool print_group = true;
435
436 /* True means print the user and group id's as numbers rather
437    than as names.  -n  */
438
439 static bool numeric_ids;
440
441 /* True means mention the size in blocks of each file.  -s  */
442
443 static bool print_block_size;
444
445 /* Human-readable options for output.  */
446 static int human_output_opts;
447
448 /* The units to use when printing sizes other than file sizes.  */
449 static uintmax_t output_block_size;
450
451 /* Likewise, but for file sizes.  */
452 static uintmax_t file_output_block_size = 1;
453
454 /* Follow the output with a special string.  Using this format,
455    Emacs' dired mode starts up twice as fast, and can handle all
456    strange characters in file names.  */
457 static bool dired;
458
459 /* `none' means don't mention the type of files.
460    `classify' means mention file types and mark executables.
461    `file_type' means mention only file types.
462
463    Controlled by -F, -p, and --indicator-style.  */
464
465 enum indicator_style
466   {
467     none,       /*     --indicator-style=none */
468     classify,   /* -F, --indicator-style=classify */
469     file_type   /* -p, --indicator-style=file-type */
470   };
471
472 static enum indicator_style indicator_style;
473
474 /* Names of indicator styles.  */
475 static char const *const indicator_style_args[] =
476 {
477   "none", "classify", "file-type", 0
478 };
479
480 static enum indicator_style const indicator_style_types[]=
481 {
482   none, classify, file_type
483 };
484
485 /* True means use colors to mark types.  Also define the different
486    colors as well as the stuff for the LS_COLORS environment variable.
487    The LS_COLORS variable is now in a termcap-like format.  */
488
489 static bool print_with_color;
490
491 enum color_type
492   {
493     color_never,                /* 0: default or --color=never */
494     color_always,               /* 1: --color=always */
495     color_if_tty                /* 2: --color=tty */
496   };
497
498 enum Dereference_symlink
499   {
500     DEREF_UNDEFINED = 1,
501     DEREF_NEVER,
502     DEREF_COMMAND_LINE_ARGUMENTS,       /* -H */
503     DEREF_COMMAND_LINE_SYMLINK_TO_DIR,  /* the default, in certain cases */
504     DEREF_ALWAYS                        /* -L */
505   };
506
507 enum indicator_no
508   {
509     C_LEFT, C_RIGHT, C_END, C_NORM, C_FILE, C_DIR, C_LINK, C_FIFO, C_SOCK,
510     C_BLK, C_CHR, C_MISSING, C_ORPHAN, C_EXEC, C_DOOR
511   };
512
513 static const char *const indicator_name[]=
514   {
515     "lc", "rc", "ec", "no", "fi", "di", "ln", "pi", "so",
516     "bd", "cd", "mi", "or", "ex", "do", NULL
517   };
518
519 struct color_ext_type
520   {
521     struct bin_str ext;         /* The extension we're looking for */
522     struct bin_str seq;         /* The sequence to output when we do */
523     struct color_ext_type *next;        /* Next in list */
524   };
525
526 static struct bin_str color_indicator[] =
527   {
528     { LEN_STR_PAIR ("\033[") },         /* lc: Left of color sequence */
529     { LEN_STR_PAIR ("m") },             /* rc: Right of color sequence */
530     { 0, NULL },                        /* ec: End color (replaces lc+no+rc) */
531     { LEN_STR_PAIR ("0") },             /* no: Normal */
532     { LEN_STR_PAIR ("0") },             /* fi: File: default */
533     { LEN_STR_PAIR ("01;34") },         /* di: Directory: bright blue */
534     { LEN_STR_PAIR ("01;36") },         /* ln: Symlink: bright cyan */
535     { LEN_STR_PAIR ("33") },            /* pi: Pipe: yellow/brown */
536     { LEN_STR_PAIR ("01;35") },         /* so: Socket: bright magenta */
537     { LEN_STR_PAIR ("01;33") },         /* bd: Block device: bright yellow */
538     { LEN_STR_PAIR ("01;33") },         /* cd: Char device: bright yellow */
539     { 0, NULL },                        /* mi: Missing file: undefined */
540     { 0, NULL },                        /* or: Orphaned symlink: undefined */
541     { LEN_STR_PAIR ("01;32") },         /* ex: Executable: bright green */
542     { LEN_STR_PAIR ("01;35") }          /* do: Door: bright magenta */
543   };
544
545 /* FIXME: comment  */
546 static struct color_ext_type *color_ext_list = NULL;
547
548 /* Buffer for color sequences */
549 static char *color_buf;
550
551 /* True means to check for orphaned symbolic link, for displaying
552    colors.  */
553
554 static bool check_symlink_color;
555
556 /* True means mention the inode number of each file.  -i  */
557
558 static bool print_inode;
559
560 /* What to do with symbolic links.  Affected by -d, -F, -H, -l (and
561    other options that imply -l), and -L.  */
562
563 static enum Dereference_symlink dereference;
564
565 /* True means when a directory is found, display info on its
566    contents.  -R  */
567
568 static bool recursive;
569
570 /* True means when an argument is a directory name, display info
571    on it itself.  -d  */
572
573 static bool immediate_dirs;
574
575 /* Which files to ignore.  */
576
577 static enum
578 {
579   /* Ignore files whose names start with `.', and files specified by
580      --hide and --ignore.  */
581   IGNORE_DEFAULT,
582
583   /* Ignore `.', `..', and files specified by --ignore.  */
584   IGNORE_DOT_AND_DOTDOT,
585
586   /* Ignore only files specified by --ignore.  */
587   IGNORE_MINIMAL
588 } ignore_mode;
589
590 /* A linked list of shell-style globbing patterns.  If a non-argument
591    file name matches any of these patterns, it is ignored.
592    Controlled by -I.  Multiple -I options accumulate.
593    The -B option adds `*~' and `.*~' to this list.  */
594
595 struct ignore_pattern
596   {
597     const char *pattern;
598     struct ignore_pattern *next;
599   };
600
601 static struct ignore_pattern *ignore_patterns;
602
603 /* Similar to IGNORE_PATTERNS, except that -a or -A causes this
604    variable itself to be ignored.  */
605 static struct ignore_pattern *hide_patterns;
606
607 /* True means output nongraphic chars in file names as `?'.
608    (-q, --hide-control-chars)
609    qmark_funny_chars and the quoting style (-Q, --quoting-style=WORD) are
610    independent.  The algorithm is: first, obey the quoting style to get a
611    string representing the file name;  then, if qmark_funny_chars is set,
612    replace all nonprintable chars in that string with `?'.  It's necessary
613    to replace nonprintable chars even in quoted strings, because we don't
614    want to mess up the terminal if control chars get sent to it, and some
615    quoting methods pass through control chars as-is.  */
616 static bool qmark_funny_chars;
617
618 /* Quoting options for file and dir name output.  */
619
620 static struct quoting_options *filename_quoting_options;
621 static struct quoting_options *dirname_quoting_options;
622
623 /* The number of chars per hardware tab stop.  Setting this to zero
624    inhibits the use of TAB characters for separating columns.  -T */
625 static size_t tabsize;
626
627 /* True means print each directory name before listing it.  */
628
629 static bool print_dir_name;
630
631 /* The line length to use for breaking lines in many-per-line format.
632    Can be set with -w.  */
633
634 static size_t line_length;
635
636 /* If true, the file listing format requires that stat be called on
637    each file.  */
638
639 static bool format_needs_stat;
640
641 /* Similar to `format_needs_stat', but set if only the file type is
642    needed.  */
643
644 static bool format_needs_type;
645
646 /* strftime formats for non-recent and recent files, respectively, in
647    -l output.  */
648
649 static char const *long_time_format[2] =
650   {
651     /* strftime format for non-recent files (older than 6 months), in
652        -l output when --time-style=locale is specified.  This should
653        contain the year, month and day (at least), in an order that is
654        understood by people in your locale's territory.
655        Please try to keep the number of used screen columns small,
656        because many people work in windows with only 80 columns.  But
657        make this as wide as the other string below, for recent files.  */
658     N_("%b %e  %Y"),
659     /* strftime format for recent files (younger than 6 months), in
660        -l output when --time-style=locale is specified.  This should
661        contain the month, day and time (at least), in an order that is
662        understood by people in your locale's territory.
663        Please try to keep the number of used screen columns small,
664        because many people work in windows with only 80 columns.  But
665        make this as wide as the other string above, for non-recent files.  */
666     N_("%b %e %H:%M")
667   };
668
669 /* The set of signals that are caught.  */
670
671 static sigset_t caught_signals;
672
673 /* If nonzero, the value of the pending fatal signal.  */
674
675 static sig_atomic_t volatile interrupt_signal;
676
677 /* A count of the number of pending stop signals that have been received.  */
678
679 static sig_atomic_t volatile stop_signal_count;
680
681 /* Desired exit status.  */
682
683 static int exit_status;
684
685 /* Exit statuses.  */
686 enum
687   {
688     /* "ls" had a minor problem (e.g., it could not stat a directory
689        entry).  */
690     LS_MINOR_PROBLEM = 1,
691
692     /* "ls" had more serious trouble.  */
693     LS_FAILURE = 2
694   };
695
696 /* For long options that have no equivalent short option, use a
697    non-character as a pseudo short option, starting with CHAR_MAX + 1.  */
698 enum
699 {
700   AUTHOR_OPTION = CHAR_MAX + 1,
701   BLOCK_SIZE_OPTION,
702   COLOR_OPTION,
703   DEREFERENCE_COMMAND_LINE_SYMLINK_TO_DIR_OPTION,
704   FORMAT_OPTION,
705   FULL_TIME_OPTION,
706   HIDE_OPTION,
707   INDICATOR_STYLE_OPTION,
708   QUOTING_STYLE_OPTION,
709   SHOW_CONTROL_CHARS_OPTION,
710   SI_OPTION,
711   SORT_OPTION,
712   TIME_OPTION,
713   TIME_STYLE_OPTION
714 };
715
716 static struct option const long_options[] =
717 {
718   {"all", no_argument, 0, 'a'},
719   {"escape", no_argument, 0, 'b'},
720   {"directory", no_argument, 0, 'd'},
721   {"dired", no_argument, 0, 'D'},
722   {"full-time", no_argument, 0, FULL_TIME_OPTION},
723   {"human-readable", no_argument, 0, 'h'},
724   {"inode", no_argument, 0, 'i'},
725   {"kilobytes", no_argument, 0, 'k'}, /* long form is obsolescent */
726   {"numeric-uid-gid", no_argument, 0, 'n'},
727   {"no-group", no_argument, 0, 'G'},
728   {"hide-control-chars", no_argument, 0, 'q'},
729   {"reverse", no_argument, 0, 'r'},
730   {"size", no_argument, 0, 's'},
731   {"width", required_argument, 0, 'w'},
732   {"almost-all", no_argument, 0, 'A'},
733   {"ignore-backups", no_argument, 0, 'B'},
734   {"classify", no_argument, 0, 'F'},
735   {"file-type", no_argument, 0, 'p'},
736   {"si", no_argument, 0, SI_OPTION},
737   {"dereference-command-line", no_argument, 0, 'H'},
738   {"dereference-command-line-symlink-to-dir", no_argument, 0,
739    DEREFERENCE_COMMAND_LINE_SYMLINK_TO_DIR_OPTION},
740   {"hide", required_argument, 0, HIDE_OPTION},
741   {"ignore", required_argument, 0, 'I'},
742   {"indicator-style", required_argument, 0, INDICATOR_STYLE_OPTION},
743   {"dereference", no_argument, 0, 'L'},
744   {"literal", no_argument, 0, 'N'},
745   {"quote-name", no_argument, 0, 'Q'},
746   {"quoting-style", required_argument, 0, QUOTING_STYLE_OPTION},
747   {"recursive", no_argument, 0, 'R'},
748   {"format", required_argument, 0, FORMAT_OPTION},
749   {"show-control-chars", no_argument, 0, SHOW_CONTROL_CHARS_OPTION},
750   {"sort", required_argument, 0, SORT_OPTION},
751   {"tabsize", required_argument, 0, 'T'},
752   {"time", required_argument, 0, TIME_OPTION},
753   {"time-style", required_argument, 0, TIME_STYLE_OPTION},
754   {"color", optional_argument, 0, COLOR_OPTION},
755   {"block-size", required_argument, 0, BLOCK_SIZE_OPTION},
756   {"author", no_argument, 0, AUTHOR_OPTION},
757   {GETOPT_HELP_OPTION_DECL},
758   {GETOPT_VERSION_OPTION_DECL},
759   {NULL, 0, NULL, 0}
760 };
761
762 static char const *const format_args[] =
763 {
764   "verbose", "long", "commas", "horizontal", "across",
765   "vertical", "single-column", 0
766 };
767
768 static enum format const format_types[] =
769 {
770   long_format, long_format, with_commas, horizontal, horizontal,
771   many_per_line, one_per_line
772 };
773
774 static char const *const sort_args[] =
775 {
776   "none", "time", "size", "extension", "version", 0
777 };
778
779 static enum sort_type const sort_types[] =
780 {
781   sort_none, sort_time, sort_size, sort_extension, sort_version
782 };
783
784 static char const *const time_args[] =
785 {
786   "atime", "access", "use", "ctime", "status", 0
787 };
788
789 static enum time_type const time_types[] =
790 {
791   time_atime, time_atime, time_atime, time_ctime, time_ctime
792 };
793
794 static char const *const color_args[] =
795 {
796   /* force and none are for compatibility with another color-ls version */
797   "always", "yes", "force",
798   "never", "no", "none",
799   "auto", "tty", "if-tty", 0
800 };
801
802 static enum color_type const color_types[] =
803 {
804   color_always, color_always, color_always,
805   color_never, color_never, color_never,
806   color_if_tty, color_if_tty, color_if_tty
807 };
808
809 /* Information about filling a column.  */
810 struct column_info
811 {
812   bool valid_len;
813   size_t line_len;
814   size_t *col_arr;
815 };
816
817 /* Array with information about column filledness.  */
818 static struct column_info *column_info;
819
820 /* Maximum number of columns ever possible for this display.  */
821 static size_t max_idx;
822
823 /* The minimum width of a column is 3: 1 character for the name and 2
824    for the separating white space.  */
825 #define MIN_COLUMN_WIDTH        3
826
827
828 /* This zero-based index is used solely with the --dired option.
829    When that option is in effect, this counter is incremented for each
830    byte of output generated by this program so that the beginning
831    and ending indices (in that output) of every file name can be recorded
832    and later output themselves.  */
833 static size_t dired_pos;
834
835 #define DIRED_PUTCHAR(c) do {putchar ((c)); ++dired_pos;} while (0)
836
837 /* Write S to STREAM and increment DIRED_POS by S_LEN.  */
838 #define DIRED_FPUTS(s, stream, s_len) \
839     do {fputs ((s), (stream)); dired_pos += s_len;} while (0)
840
841 /* Like DIRED_FPUTS, but for use when S is a literal string.  */
842 #define DIRED_FPUTS_LITERAL(s, stream) \
843     do {fputs ((s), (stream)); dired_pos += sizeof((s)) - 1;} while (0)
844
845 #define DIRED_INDENT()                                                  \
846     do                                                                  \
847       {                                                                 \
848         if (dired)                                                      \
849           DIRED_FPUTS_LITERAL ("  ", stdout);                           \
850       }                                                                 \
851     while (0)
852
853 /* With --dired, store pairs of beginning and ending indices of filenames.  */
854 static struct obstack dired_obstack;
855
856 /* With --dired, store pairs of beginning and ending indices of any
857    directory names that appear as headers (just before `total' line)
858    for lists of directory entries.  Such directory names are seen when
859    listing hierarchies using -R and when a directory is listed with at
860    least one other command line argument.  */
861 static struct obstack subdired_obstack;
862
863 /* Save the current index on the specified obstack, OBS.  */
864 #define PUSH_CURRENT_DIRED_POS(obs)                                     \
865   do                                                                    \
866     {                                                                   \
867       if (dired)                                                        \
868         obstack_grow ((obs), &dired_pos, sizeof (dired_pos));           \
869     }                                                                   \
870   while (0)
871
872 /* With -R, this stack is used to help detect directory cycles.
873    The device/inode pairs on this stack mirror the pairs in the
874    active_dir_set hash table.  */
875 static struct obstack dev_ino_obstack;
876
877 /* Push a pair onto the device/inode stack.  */
878 #define DEV_INO_PUSH(Dev, Ino)                                          \
879   do                                                                    \
880     {                                                                   \
881       struct dev_ino *di;                                               \
882       obstack_blank (&dev_ino_obstack, sizeof (struct dev_ino));        \
883       di = -1 + (struct dev_ino *) obstack_next_free (&dev_ino_obstack); \
884       di->st_dev = (Dev);                                               \
885       di->st_ino = (Ino);                                               \
886     }                                                                   \
887   while (0)
888
889 /* Pop a dev/ino struct off the global dev_ino_obstack
890    and return that struct.  */
891 static struct dev_ino
892 dev_ino_pop (void)
893 {
894   assert (sizeof (struct dev_ino) <= obstack_object_size (&dev_ino_obstack));
895   obstack_blank (&dev_ino_obstack, -(int) (sizeof (struct dev_ino)));
896   return *(struct dev_ino*) obstack_next_free (&dev_ino_obstack);
897 }
898
899 #define ASSERT_MATCHING_DEV_INO(Name, Di)       \
900   do                                            \
901     {                                           \
902       struct stat sb;                           \
903       assert (Name);                            \
904       assert (0 <= stat (Name, &sb));           \
905       assert (sb.st_dev == Di.st_dev);          \
906       assert (sb.st_ino == Di.st_ino);          \
907     }                                           \
908   while (0)
909
910
911 /* Write to standard output PREFIX, followed by the quoting style and
912    a space-separated list of the integers stored in OS all on one line.  */
913
914 static void
915 dired_dump_obstack (const char *prefix, struct obstack *os)
916 {
917   size_t n_pos;
918
919   n_pos = obstack_object_size (os) / sizeof (dired_pos);
920   if (n_pos > 0)
921     {
922       size_t i;
923       size_t *pos;
924
925       pos = (size_t *) obstack_finish (os);
926       fputs (prefix, stdout);
927       for (i = 0; i < n_pos; i++)
928         printf (" %lu", (unsigned long int) pos[i]);
929       putchar ('\n');
930     }
931 }
932
933 static size_t
934 dev_ino_hash (void const *x, size_t table_size)
935 {
936   struct dev_ino const *p = x;
937   return (uintmax_t) p->st_ino % table_size;
938 }
939
940 static bool
941 dev_ino_compare (void const *x, void const *y)
942 {
943   struct dev_ino const *a = x;
944   struct dev_ino const *b = y;
945   return SAME_INODE (*a, *b) ? true : false;
946 }
947
948 static void
949 dev_ino_free (void *x)
950 {
951   free (x);
952 }
953
954 /* Add the device/inode pair (P->st_dev/P->st_ino) to the set of
955    active directories.  Return true if there is already a matching
956    entry in the table.  */
957
958 static bool
959 visit_dir (dev_t dev, ino_t ino)
960 {
961   struct dev_ino *ent;
962   struct dev_ino *ent_from_table;
963   bool found_match;
964
965   ent = xmalloc (sizeof *ent);
966   ent->st_ino = ino;
967   ent->st_dev = dev;
968
969   /* Attempt to insert this entry into the table.  */
970   ent_from_table = hash_insert (active_dir_set, ent);
971
972   if (ent_from_table == NULL)
973     {
974       /* Insertion failed due to lack of memory.  */
975       xalloc_die ();
976     }
977
978   found_match = (ent_from_table != ent);
979
980   if (found_match)
981     {
982       /* ent was not inserted, so free it.  */
983       free (ent);
984     }
985
986   return found_match;
987 }
988
989 static void
990 free_pending_ent (struct pending *p)
991 {
992   if (p->name)
993     free (p->name);
994   if (p->realname)
995     free (p->realname);
996   free (p);
997 }
998
999 static bool
1000 is_colored (enum indicator_no type)
1001 {
1002   size_t len = color_indicator[type].len;
1003   char const *s = color_indicator[type].string;
1004   return ! (len == 0
1005             || (len == 1 && strncmp (s, "0", 1) == 0)
1006             || (len == 2 && strncmp (s, "00", 2) == 0));
1007 }
1008
1009 static void
1010 restore_default_color (void)
1011 {
1012   put_indicator (&color_indicator[C_LEFT]);
1013   put_indicator (&color_indicator[C_RIGHT]);
1014 }
1015
1016 /* An ordinary signal was received; arrange for the program to exit.  */
1017
1018 static void
1019 sighandler (int sig)
1020 {
1021 #ifndef SA_NOCLDSTOP
1022   signal (sig, SIG_IGN);
1023 #endif
1024
1025   if (! interrupt_signal)
1026     interrupt_signal = sig;
1027 }
1028
1029 /* A SIGTSTP was received; arrange for the program to suspend itself.  */
1030
1031 static void
1032 stophandler (int sig)
1033 {
1034 #ifndef SA_NOCLDSTOP
1035   signal (sig, stophandler);
1036 #endif
1037
1038   if (! interrupt_signal)
1039     stop_signal_count++;
1040 }
1041
1042 /* Process any pending signals.  If signals are caught, this function
1043    should be called periodically.  Ideally there should never be an
1044    unbounded amount of time when signals are not being processed.
1045    Signal handling can restore the default colors, so callers must
1046    immediately change colors after invoking this function.  */
1047
1048 static void
1049 process_signals (void)
1050 {
1051   while (interrupt_signal | stop_signal_count)
1052     {
1053       int sig;
1054       int stops;
1055       sigset_t oldset;
1056
1057       restore_default_color ();
1058       fflush (stdout);
1059
1060       sigprocmask (SIG_BLOCK, &caught_signals, &oldset);
1061
1062       /* Reload interrupt_signal and stop_signal_count, in case a new
1063          signal was handled before sigprocmask took effect.  */
1064       sig = interrupt_signal;
1065       stops = stop_signal_count;
1066
1067       /* SIGTSTP is special, since the application can receive that signal
1068          more than once.  In this case, don't set the signal handler to the
1069          default.  Instead, just raise the uncatchable SIGSTOP.  */
1070       if (stops)
1071         {
1072           stop_signal_count = stops - 1;
1073           sig = SIGSTOP;
1074         }
1075       else
1076         signal (sig, SIG_DFL);
1077
1078       /* Exit or suspend the program.  */
1079       raise (sig);
1080       sigprocmask (SIG_SETMASK, &oldset, NULL);
1081
1082       /* If execution reaches here, then the program has been
1083          continued (after being suspended).  */
1084     }
1085 }
1086
1087 int
1088 main (int argc, char **argv)
1089 {
1090   int i;
1091   struct pending *thispend;
1092   int n_files;
1093
1094   /* The signals that are trapped, and the number of such signals.  */
1095   static int const sig[] = { SIGHUP, SIGINT, SIGPIPE,
1096                              SIGQUIT, SIGTERM, SIGTSTP };
1097   enum { nsigs = sizeof sig / sizeof sig[0] };
1098
1099 #ifndef SA_NOCLDSTOP
1100   bool caught_sig[nsigs];
1101 #endif
1102
1103   initialize_main (&argc, &argv);
1104   program_name = argv[0];
1105   setlocale (LC_ALL, "");
1106   bindtextdomain (PACKAGE, LOCALEDIR);
1107   textdomain (PACKAGE);
1108
1109   initialize_exit_failure (LS_FAILURE);
1110   atexit (close_stdout);
1111
1112 #define N_ENTRIES(Array) (sizeof Array / sizeof *(Array))
1113   assert (N_ENTRIES (color_indicator) + 1 == N_ENTRIES (indicator_name));
1114
1115   exit_status = EXIT_SUCCESS;
1116   print_dir_name = true;
1117   pending_dirs = NULL;
1118
1119   i = decode_switches (argc, argv);
1120
1121   if (print_with_color)
1122     parse_ls_color ();
1123
1124   /* Test print_with_color again, because the call to parse_ls_color
1125      may have just reset it -- e.g., if LS_COLORS is invalid.  */
1126   if (print_with_color)
1127     {
1128       /* Avoid following symbolic links when possible.  */
1129       if (is_colored (C_ORPHAN)
1130           || is_colored (C_EXEC)
1131           || (is_colored (C_MISSING) && format == long_format))
1132         check_symlink_color = true;
1133
1134       /* If the standard output is a controlling terminal, watch out
1135          for signals, so that the colors can be restored to the
1136          default state if "ls" is suspended or interrupted.  */
1137
1138       if (0 <= tcgetpgrp (STDOUT_FILENO))
1139         {
1140           int j;
1141 #ifdef SA_NOCLDSTOP
1142           struct sigaction act;
1143
1144           sigemptyset (&caught_signals);
1145           for (j = 0; j < nsigs; j++)
1146             {
1147               sigaction (sig[j], NULL, &act);
1148               if (act.sa_handler != SIG_IGN)
1149                 sigaddset (&caught_signals, sig[j]);
1150             }
1151
1152           act.sa_mask = caught_signals;
1153           act.sa_flags = SA_RESTART;
1154
1155           for (j = 0; j < nsigs; j++)
1156             if (sigismember (&caught_signals, sig[j]))
1157               {
1158                 act.sa_handler = sig[j] == SIGTSTP ? stophandler : sighandler;
1159                 sigaction (sig[j], &act, NULL);
1160               }
1161 #else
1162           for (j = 0; j < nsigs; j++)
1163             {
1164               caught_sig[j] = (signal (sig[j], SIG_IGN) != SIG_IGN);
1165               if (caught_sig[j])
1166                 signal (sig[j], sig[j] == SIGTSTP ? stophandler : sighandler);
1167             }
1168 #endif
1169         }
1170
1171       prep_non_filename_text ();
1172     }
1173
1174   if (dereference == DEREF_UNDEFINED)
1175     dereference = ((immediate_dirs
1176                     || indicator_style == classify
1177                     || format == long_format)
1178                    ? DEREF_NEVER
1179                    : DEREF_COMMAND_LINE_SYMLINK_TO_DIR);
1180
1181   /* When using -R, initialize a data structure we'll use to
1182      detect any directory cycles.  */
1183   if (recursive)
1184     {
1185       active_dir_set = hash_initialize (INITIAL_TABLE_SIZE, NULL,
1186                                         dev_ino_hash,
1187                                         dev_ino_compare,
1188                                         dev_ino_free);
1189       if (active_dir_set == NULL)
1190         xalloc_die ();
1191
1192       obstack_init (&dev_ino_obstack);
1193     }
1194
1195   format_needs_stat = sort_type == sort_time || sort_type == sort_size
1196     || format == long_format
1197     || dereference == DEREF_ALWAYS
1198     || print_block_size || print_inode;
1199   format_needs_type = (!format_needs_stat
1200                        && (recursive || print_with_color
1201                            || indicator_style != none));
1202
1203   if (dired)
1204     {
1205       obstack_init (&dired_obstack);
1206       obstack_init (&subdired_obstack);
1207     }
1208
1209   nfiles = 100;
1210   files = xnmalloc (nfiles, sizeof *files);
1211   files_index = 0;
1212
1213   clear_files ();
1214
1215   n_files = argc - i;
1216
1217   if (n_files <= 0)
1218     {
1219       if (immediate_dirs)
1220         gobble_file (".", directory, true, "");
1221       else
1222         queue_directory (".", NULL, true);
1223     }
1224   else
1225     do
1226       gobble_file (argv[i++], unknown, true, "");
1227     while (i < argc);
1228
1229   if (files_index)
1230     {
1231       sort_files ();
1232       if (!immediate_dirs)
1233         extract_dirs_from_files (NULL, true);
1234       /* `files_index' might be zero now.  */
1235     }
1236
1237   /* In the following if/else blocks, it is sufficient to test `pending_dirs'
1238      (and not pending_dirs->name) because there may be no markers in the queue
1239      at this point.  A marker may be enqueued when extract_dirs_from_files is
1240      called with a non-empty string or via print_dir.  */
1241   if (files_index)
1242     {
1243       print_current_files ();
1244       if (pending_dirs)
1245         DIRED_PUTCHAR ('\n');
1246     }
1247   else if (n_files <= 1 && pending_dirs && pending_dirs->next == 0)
1248     print_dir_name = false;
1249
1250   while (pending_dirs)
1251     {
1252       thispend = pending_dirs;
1253       pending_dirs = pending_dirs->next;
1254
1255       if (LOOP_DETECT)
1256         {
1257           if (thispend->name == NULL)
1258             {
1259               /* thispend->name == NULL means this is a marker entry
1260                  indicating we've finished processing the directory.
1261                  Use its dev/ino numbers to remove the corresponding
1262                  entry from the active_dir_set hash table.  */
1263               struct dev_ino di = dev_ino_pop ();
1264               struct dev_ino *found = hash_delete (active_dir_set, &di);
1265               /* ASSERT_MATCHING_DEV_INO (thispend->realname, di); */
1266               assert (found);
1267               dev_ino_free (found);
1268               free_pending_ent (thispend);
1269               continue;
1270             }
1271         }
1272
1273       print_dir (thispend->name, thispend->realname,
1274                  thispend->command_line_arg);
1275
1276       free_pending_ent (thispend);
1277       print_dir_name = true;
1278     }
1279
1280   if (print_with_color)
1281     {
1282       int j;
1283
1284       restore_default_color ();
1285       fflush (stdout);
1286
1287       /* Restore the default signal handling.  */
1288 #ifdef SA_NOCLDSTOP
1289       for (j = 0; j < nsigs; j++)
1290         if (sigismember (&caught_signals, sig[j]))
1291           signal (sig[j], SIG_DFL);
1292 #else
1293       for (j = 0; j < nsigs; j++)
1294         if (caught_sig[j])
1295           signal (sig[j], SIG_DFL);
1296 #endif
1297
1298       /* Act on any signals that arrived before the default was restored.
1299          This can process signals out of order, but there doesn't seem to
1300          be an easy way to do them in order, and the order isn't that
1301          important anyway.  */
1302       for (j = stop_signal_count; j; j--)
1303         raise (SIGSTOP);
1304       j = interrupt_signal;
1305       if (j)
1306         raise (j);
1307     }
1308
1309   if (dired)
1310     {
1311       /* No need to free these since we're about to exit.  */
1312       dired_dump_obstack ("//DIRED//", &dired_obstack);
1313       dired_dump_obstack ("//SUBDIRED//", &subdired_obstack);
1314       printf ("//DIRED-OPTIONS// --quoting-style=%s\n",
1315               quoting_style_args[get_quoting_style (filename_quoting_options)]);
1316     }
1317
1318   if (LOOP_DETECT)
1319     {
1320       assert (hash_get_n_entries (active_dir_set) == 0);
1321       hash_free (active_dir_set);
1322     }
1323
1324   exit (exit_status);
1325 }
1326
1327 /* Set all the option flags according to the switches specified.
1328    Return the index of the first non-option argument.  */
1329
1330 static int
1331 decode_switches (int argc, char **argv)
1332 {
1333   int c;
1334   char *time_style_option = 0;
1335
1336   /* Record whether there is an option specifying sort type.  */
1337   bool sort_type_specified = false;
1338
1339   qmark_funny_chars = false;
1340
1341   /* initialize all switches to default settings */
1342
1343   switch (ls_mode)
1344     {
1345     case LS_MULTI_COL:
1346       /* This is for the `dir' program.  */
1347       format = many_per_line;
1348       set_quoting_style (NULL, escape_quoting_style);
1349       break;
1350
1351     case LS_LONG_FORMAT:
1352       /* This is for the `vdir' program.  */
1353       format = long_format;
1354       set_quoting_style (NULL, escape_quoting_style);
1355       break;
1356
1357     case LS_LS:
1358       /* This is for the `ls' program.  */
1359       if (isatty (STDOUT_FILENO))
1360         {
1361           format = many_per_line;
1362           /* See description of qmark_funny_chars, above.  */
1363           qmark_funny_chars = true;
1364         }
1365       else
1366         {
1367           format = one_per_line;
1368           qmark_funny_chars = false;
1369         }
1370       break;
1371
1372     default:
1373       abort ();
1374     }
1375
1376   time_type = time_mtime;
1377   sort_type = sort_name;
1378   sort_reverse = false;
1379   numeric_ids = false;
1380   print_block_size = false;
1381   indicator_style = none;
1382   print_inode = false;
1383   dereference = DEREF_UNDEFINED;
1384   recursive = false;
1385   immediate_dirs = false;
1386   ignore_mode = IGNORE_DEFAULT;
1387   ignore_patterns = NULL;
1388   hide_patterns = NULL;
1389
1390   /* FIXME: put this in a function.  */
1391   {
1392     char const *q_style = getenv ("QUOTING_STYLE");
1393     if (q_style)
1394       {
1395         int i = ARGMATCH (q_style, quoting_style_args, quoting_style_vals);
1396         if (0 <= i)
1397           set_quoting_style (NULL, quoting_style_vals[i]);
1398         else
1399           error (0, 0,
1400          _("ignoring invalid value of environment variable QUOTING_STYLE: %s"),
1401                  quotearg (q_style));
1402       }
1403   }
1404
1405   {
1406     char const *ls_block_size = getenv ("LS_BLOCK_SIZE");
1407     human_output_opts = human_options (ls_block_size, false,
1408                                        &output_block_size);
1409     if (ls_block_size || getenv ("BLOCK_SIZE"))
1410       file_output_block_size = output_block_size;
1411   }
1412
1413   line_length = 80;
1414   {
1415     char const *p = getenv ("COLUMNS");
1416     if (p && *p)
1417       {
1418         unsigned long int tmp_ulong;
1419         if (xstrtoul (p, NULL, 0, &tmp_ulong, NULL) == LONGINT_OK
1420             && 0 < tmp_ulong && tmp_ulong <= SIZE_MAX)
1421           {
1422             line_length = tmp_ulong;
1423           }
1424         else
1425           {
1426             error (0, 0,
1427                _("ignoring invalid width in environment variable COLUMNS: %s"),
1428                    quotearg (p));
1429           }
1430       }
1431   }
1432
1433 #ifdef TIOCGWINSZ
1434   {
1435     struct winsize ws;
1436
1437     if (ioctl (STDOUT_FILENO, TIOCGWINSZ, &ws) != -1
1438         && 0 < ws.ws_col && ws.ws_col == (size_t) ws.ws_col)
1439       line_length = ws.ws_col;
1440   }
1441 #endif
1442
1443   {
1444     char const *p = getenv ("TABSIZE");
1445     tabsize = 8;
1446     if (p)
1447       {
1448         unsigned long int tmp_ulong;
1449         if (xstrtoul (p, NULL, 0, &tmp_ulong, NULL) == LONGINT_OK
1450             && tmp_ulong <= SIZE_MAX)
1451           {
1452             tabsize = tmp_ulong;
1453           }
1454         else
1455           {
1456             error (0, 0,
1457              _("ignoring invalid tab size in environment variable TABSIZE: %s"),
1458                    quotearg (p));
1459           }
1460       }
1461   }
1462
1463   while ((c = getopt_long (argc, argv,
1464                            "abcdfghiklmnopqrstuvw:xABCDFGHI:LNQRST:UX1",
1465                            long_options, NULL)) != -1)
1466     {
1467       switch (c)
1468         {
1469         case 'a':
1470           ignore_mode = IGNORE_MINIMAL;
1471           break;
1472
1473         case 'b':
1474           set_quoting_style (NULL, escape_quoting_style);
1475           break;
1476
1477         case 'c':
1478           time_type = time_ctime;
1479           break;
1480
1481         case 'd':
1482           immediate_dirs = true;
1483           break;
1484
1485         case 'f':
1486           /* Same as enabling -a -U and disabling -l -s.  */
1487           ignore_mode = IGNORE_MINIMAL;
1488           sort_type = sort_none;
1489           sort_type_specified = true;
1490           /* disable -l */
1491           if (format == long_format)
1492             format = (isatty (STDOUT_FILENO) ? many_per_line : one_per_line);
1493           print_block_size = false;     /* disable -s */
1494           print_with_color = false;     /* disable --color */
1495           break;
1496
1497         case 'g':
1498           format = long_format;
1499           print_owner = false;
1500           break;
1501
1502         case 'h':
1503           human_output_opts = human_autoscale | human_SI | human_base_1024;
1504           file_output_block_size = output_block_size = 1;
1505           break;
1506
1507         case 'i':
1508           print_inode = true;
1509           break;
1510
1511         case 'k':
1512           human_output_opts = 0;
1513           file_output_block_size = output_block_size = 1024;
1514           break;
1515
1516         case 'l':
1517           format = long_format;
1518           break;
1519
1520         case 'm':
1521           format = with_commas;
1522           break;
1523
1524         case 'n':
1525           numeric_ids = true;
1526           format = long_format;
1527           break;
1528
1529         case 'o':  /* Just like -l, but don't display group info.  */
1530           format = long_format;
1531           print_group = false;
1532           break;
1533
1534         case 'p':
1535           indicator_style = file_type;
1536           break;
1537
1538         case 'q':
1539           qmark_funny_chars = true;
1540           break;
1541
1542         case 'r':
1543           sort_reverse = true;
1544           break;
1545
1546         case 's':
1547           print_block_size = true;
1548           break;
1549
1550         case 't':
1551           sort_type = sort_time;
1552           sort_type_specified = true;
1553           break;
1554
1555         case 'u':
1556           time_type = time_atime;
1557           break;
1558
1559         case 'v':
1560           sort_type = sort_version;
1561           sort_type_specified = true;
1562           break;
1563
1564         case 'w':
1565           {
1566             unsigned long int tmp_ulong;
1567             if (xstrtoul (optarg, NULL, 0, &tmp_ulong, NULL) != LONGINT_OK
1568                 || ! (0 < tmp_ulong && tmp_ulong <= SIZE_MAX))
1569               error (LS_FAILURE, 0, _("invalid line width: %s"),
1570                      quotearg (optarg));
1571             line_length = tmp_ulong;
1572             break;
1573           }
1574
1575         case 'x':
1576           format = horizontal;
1577           break;
1578
1579         case 'A':
1580           if (ignore_mode == IGNORE_DEFAULT)
1581             ignore_mode = IGNORE_DOT_AND_DOTDOT;
1582           break;
1583
1584         case 'B':
1585           add_ignore_pattern ("*~");
1586           add_ignore_pattern (".*~");
1587           break;
1588
1589         case 'C':
1590           format = many_per_line;
1591           break;
1592
1593         case 'D':
1594           dired = true;
1595           break;
1596
1597         case 'F':
1598           indicator_style = classify;
1599           break;
1600
1601         case 'G':               /* inhibit display of group info */
1602           print_group = false;
1603           break;
1604
1605         case 'H':
1606           dereference = DEREF_COMMAND_LINE_ARGUMENTS;
1607           break;
1608
1609         case DEREFERENCE_COMMAND_LINE_SYMLINK_TO_DIR_OPTION:
1610           dereference = DEREF_COMMAND_LINE_SYMLINK_TO_DIR;
1611           break;
1612
1613         case 'I':
1614           add_ignore_pattern (optarg);
1615           break;
1616
1617         case 'L':
1618           dereference = DEREF_ALWAYS;
1619           break;
1620
1621         case 'N':
1622           set_quoting_style (NULL, literal_quoting_style);
1623           break;
1624
1625         case 'Q':
1626           set_quoting_style (NULL, c_quoting_style);
1627           break;
1628
1629         case 'R':
1630           recursive = true;
1631           break;
1632
1633         case 'S':
1634           sort_type = sort_size;
1635           sort_type_specified = true;
1636           break;
1637
1638         case 'T':
1639           {
1640             unsigned long int tmp_ulong;
1641             if (xstrtoul (optarg, NULL, 0, &tmp_ulong, NULL) != LONGINT_OK
1642                 || SIZE_MAX < tmp_ulong)
1643               error (LS_FAILURE, 0, _("invalid tab size: %s"),
1644                      quotearg (optarg));
1645             tabsize = tmp_ulong;
1646             break;
1647           }
1648
1649         case 'U':
1650           sort_type = sort_none;
1651           sort_type_specified = true;
1652           break;
1653
1654         case 'X':
1655           sort_type = sort_extension;
1656           sort_type_specified = true;
1657           break;
1658
1659         case '1':
1660           /* -1 has no effect after -l.  */
1661           if (format != long_format)
1662             format = one_per_line;
1663           break;
1664
1665         case AUTHOR_OPTION:
1666           print_author = true;
1667           break;
1668
1669         case HIDE_OPTION:
1670           {
1671             struct ignore_pattern *hide = xmalloc (sizeof *hide);
1672             hide->pattern = optarg;
1673             hide->next = hide_patterns;
1674             hide_patterns = hide;
1675           }
1676           break;
1677
1678         case SORT_OPTION:
1679           sort_type = XARGMATCH ("--sort", optarg, sort_args, sort_types);
1680           sort_type_specified = true;
1681           break;
1682
1683         case TIME_OPTION:
1684           time_type = XARGMATCH ("--time", optarg, time_args, time_types);
1685           break;
1686
1687         case FORMAT_OPTION:
1688           format = XARGMATCH ("--format", optarg, format_args, format_types);
1689           break;
1690
1691         case FULL_TIME_OPTION:
1692           format = long_format;
1693           time_style_option = "full-iso";
1694           break;
1695
1696         case COLOR_OPTION:
1697           {
1698             int i;
1699             if (optarg)
1700               i = XARGMATCH ("--color", optarg, color_args, color_types);
1701             else
1702               /* Using --color with no argument is equivalent to using
1703                  --color=always.  */
1704               i = color_always;
1705
1706             print_with_color = (i == color_always
1707                                 || (i == color_if_tty
1708                                     && isatty (STDOUT_FILENO)));
1709
1710             if (print_with_color)
1711               {
1712                 /* Don't use TAB characters in output.  Some terminal
1713                    emulators can't handle the combination of tabs and
1714                    color codes on the same line.  */
1715                 tabsize = 0;
1716               }
1717             break;
1718           }
1719
1720         case INDICATOR_STYLE_OPTION:
1721           indicator_style = XARGMATCH ("--indicator-style", optarg,
1722                                        indicator_style_args,
1723                                        indicator_style_types);
1724           break;
1725
1726         case QUOTING_STYLE_OPTION:
1727           set_quoting_style (NULL,
1728                              XARGMATCH ("--quoting-style", optarg,
1729                                         quoting_style_args,
1730                                         quoting_style_vals));
1731           break;
1732
1733         case TIME_STYLE_OPTION:
1734           time_style_option = optarg;
1735           break;
1736
1737         case SHOW_CONTROL_CHARS_OPTION:
1738           qmark_funny_chars = false;
1739           break;
1740
1741         case BLOCK_SIZE_OPTION:
1742           human_output_opts = human_options (optarg, true, &output_block_size);
1743           file_output_block_size = output_block_size;
1744           break;
1745
1746         case SI_OPTION:
1747           human_output_opts = human_autoscale | human_SI;
1748           file_output_block_size = output_block_size = 1;
1749           break;
1750
1751         case_GETOPT_HELP_CHAR;
1752
1753         case_GETOPT_VERSION_CHAR (PROGRAM_NAME, AUTHORS);
1754
1755         default:
1756           usage (LS_FAILURE);
1757         }
1758     }
1759
1760   max_idx = MAX (1, line_length / MIN_COLUMN_WIDTH);
1761
1762   filename_quoting_options = clone_quoting_options (NULL);
1763   if (get_quoting_style (filename_quoting_options) == escape_quoting_style)
1764     set_char_quoting (filename_quoting_options, ' ', 1);
1765   if (indicator_style != none)
1766     {
1767       char const *p;
1768       for (p = "*=@|" + indicator_style - 1;  *p;  p++)
1769         set_char_quoting (filename_quoting_options, *p, 1);
1770     }
1771
1772   dirname_quoting_options = clone_quoting_options (NULL);
1773   set_char_quoting (dirname_quoting_options, ':', 1);
1774
1775   /* --dired is meaningful only with --format=long (-l).
1776      Otherwise, ignore it.  FIXME: warn about this?
1777      Alternatively, make --dired imply --format=long?  */
1778   if (dired && format != long_format)
1779     dired = false;
1780
1781   /* If -c or -u is specified and not -l (or any other option that implies -l),
1782      and no sort-type was specified, then sort by the ctime (-c) or atime (-u).
1783      The behavior of ls when using either -c or -u but with neither -l nor -t
1784      appears to be unspecified by POSIX.  So, with GNU ls, `-u' alone means
1785      sort by atime (this is the one that's not specified by the POSIX spec),
1786      -lu means show atime and sort by name, -lut means show atime and sort
1787      by atime.  */
1788
1789   if ((time_type == time_ctime || time_type == time_atime)
1790       && !sort_type_specified && format != long_format)
1791     {
1792       sort_type = sort_time;
1793     }
1794
1795   if (format == long_format)
1796     {
1797       char *style = time_style_option;
1798       static char const posix_prefix[] = "posix-";
1799
1800       if (! style)
1801         if (! (style = getenv ("TIME_STYLE")))
1802           style = "posix-long-iso";
1803
1804       while (strncmp (style, posix_prefix, sizeof posix_prefix - 1) == 0)
1805         {
1806           if (! hard_locale (LC_TIME))
1807             return optind;
1808           style += sizeof posix_prefix - 1;
1809         }
1810
1811       if (*style == '+')
1812         {
1813           char *p0 = style + 1;
1814           char *p1 = strchr (p0, '\n');
1815           if (! p1)
1816             p1 = p0;
1817           else
1818             {
1819               if (strchr (p1 + 1, '\n'))
1820                 error (LS_FAILURE, 0, _("invalid time style format %s"),
1821                        quote (p0));
1822               *p1++ = '\0';
1823             }
1824           long_time_format[0] = p0;
1825           long_time_format[1] = p1;
1826         }
1827       else
1828         switch (XARGMATCH ("time style", style,
1829                            time_style_args,
1830                            time_style_types))
1831           {
1832           case full_iso_time_style:
1833             long_time_format[0] = long_time_format[1] =
1834               "%Y-%m-%d %H:%M:%S.%N %z";
1835             break;
1836
1837           case long_iso_time_style:
1838             long_time_format[0] = long_time_format[1] = "%Y-%m-%d %H:%M";
1839             break;
1840
1841           case iso_time_style:
1842             long_time_format[0] = "%Y-%m-%d ";
1843             long_time_format[1] = "%m-%d %H:%M";
1844             break;
1845
1846           case locale_time_style:
1847             if (hard_locale (LC_TIME))
1848               {
1849                 int i;
1850                 for (i = 0; i < 2; i++)
1851                   long_time_format[i] =
1852                     dcgettext (NULL, long_time_format[i], LC_TIME);
1853               }
1854           }
1855     }
1856
1857   return optind;
1858 }
1859
1860 /* Parse a string as part of the LS_COLORS variable; this may involve
1861    decoding all kinds of escape characters.  If equals_end is set an
1862    unescaped equal sign ends the string, otherwise only a : or \0
1863    does.  Set *OUTPUT_COUNT to the number of bytes output.  Return
1864    true if successful.
1865
1866    The resulting string is *not* null-terminated, but may contain
1867    embedded nulls.
1868
1869    Note that both dest and src are char **; on return they point to
1870    the first free byte after the array and the character that ended
1871    the input string, respectively.  */
1872
1873 static bool
1874 get_funky_string (char **dest, const char **src, bool equals_end,
1875                   size_t *output_count)
1876 {
1877   char num;                     /* For numerical codes */
1878   size_t count;                 /* Something to count with */
1879   enum {
1880     ST_GND, ST_BACKSLASH, ST_OCTAL, ST_HEX, ST_CARET, ST_END, ST_ERROR
1881   } state;
1882   const char *p;
1883   char *q;
1884
1885   p = *src;                     /* We don't want to double-indirect */
1886   q = *dest;                    /* the whole darn time.  */
1887
1888   count = 0;                    /* No characters counted in yet.  */
1889   num = 0;
1890
1891   state = ST_GND;               /* Start in ground state.  */
1892   while (state < ST_END)
1893     {
1894       switch (state)
1895         {
1896         case ST_GND:            /* Ground state (no escapes) */
1897           switch (*p)
1898             {
1899             case ':':
1900             case '\0':
1901               state = ST_END;   /* End of string */
1902               break;
1903             case '\\':
1904               state = ST_BACKSLASH; /* Backslash scape sequence */
1905               ++p;
1906               break;
1907             case '^':
1908               state = ST_CARET; /* Caret escape */
1909               ++p;
1910               break;
1911             case '=':
1912               if (equals_end)
1913                 {
1914                   state = ST_END; /* End */
1915                   break;
1916                 }
1917               /* else fall through */
1918             default:
1919               *(q++) = *(p++);
1920               ++count;
1921               break;
1922             }
1923           break;
1924
1925         case ST_BACKSLASH:      /* Backslash escaped character */
1926           switch (*p)
1927             {
1928             case '0':
1929             case '1':
1930             case '2':
1931             case '3':
1932             case '4':
1933             case '5':
1934             case '6':
1935             case '7':
1936               state = ST_OCTAL; /* Octal sequence */
1937               num = *p - '0';
1938               break;
1939             case 'x':
1940             case 'X':
1941               state = ST_HEX;   /* Hex sequence */
1942               num = 0;
1943               break;
1944             case 'a':           /* Bell */
1945               num = 7;          /* Not all C compilers know what \a means */
1946               break;
1947             case 'b':           /* Backspace */
1948               num = '\b';
1949               break;
1950             case 'e':           /* Escape */
1951               num = 27;
1952               break;
1953             case 'f':           /* Form feed */
1954               num = '\f';
1955               break;
1956             case 'n':           /* Newline */
1957               num = '\n';
1958               break;
1959             case 'r':           /* Carriage return */
1960               num = '\r';
1961               break;
1962             case 't':           /* Tab */
1963               num = '\t';
1964               break;
1965             case 'v':           /* Vtab */
1966               num = '\v';
1967               break;
1968             case '?':           /* Delete */
1969               num = 127;
1970               break;
1971             case '_':           /* Space */
1972               num = ' ';
1973               break;
1974             case '\0':          /* End of string */
1975               state = ST_ERROR; /* Error! */
1976               break;
1977             default:            /* Escaped character like \ ^ : = */
1978               num = *p;
1979               break;
1980             }
1981           if (state == ST_BACKSLASH)
1982             {
1983               *(q++) = num;
1984               ++count;
1985               state = ST_GND;
1986             }
1987           ++p;
1988           break;
1989
1990         case ST_OCTAL:          /* Octal sequence */
1991           if (*p < '0' || *p > '7')
1992             {
1993               *(q++) = num;
1994               ++count;
1995               state = ST_GND;
1996             }
1997           else
1998             num = (num << 3) + (*(p++) - '0');
1999           break;
2000
2001         case ST_HEX:            /* Hex sequence */
2002           switch (*p)
2003             {
2004             case '0':
2005             case '1':
2006             case '2':
2007             case '3':
2008             case '4':
2009             case '5':
2010             case '6':
2011             case '7':
2012             case '8':
2013             case '9':
2014               num = (num << 4) + (*(p++) - '0');
2015               break;
2016             case 'a':
2017             case 'b':
2018             case 'c':
2019             case 'd':
2020             case 'e':
2021             case 'f':
2022               num = (num << 4) + (*(p++) - 'a') + 10;
2023               break;
2024             case 'A':
2025             case 'B':
2026             case 'C':
2027             case 'D':
2028             case 'E':
2029             case 'F':
2030               num = (num << 4) + (*(p++) - 'A') + 10;
2031               break;
2032             default:
2033               *(q++) = num;
2034               ++count;
2035               state = ST_GND;
2036               break;
2037             }
2038           break;
2039
2040         case ST_CARET:          /* Caret escape */
2041           state = ST_GND;       /* Should be the next state... */
2042           if (*p >= '@' && *p <= '~')
2043             {
2044               *(q++) = *(p++) & 037;
2045               ++count;
2046             }
2047           else if (*p == '?')
2048             {
2049               *(q++) = 127;
2050               ++count;
2051             }
2052           else
2053             state = ST_ERROR;
2054           break;
2055
2056         default:
2057           abort ();
2058         }
2059     }
2060
2061   *dest = q;
2062   *src = p;
2063   *output_count = count;
2064
2065   return state != ST_ERROR;
2066 }
2067
2068 static void
2069 parse_ls_color (void)
2070 {
2071   const char *p;                /* Pointer to character being parsed */
2072   char *buf;                    /* color_buf buffer pointer */
2073   int state;                    /* State of parser */
2074   int ind_no;                   /* Indicator number */
2075   char label[3];                /* Indicator label */
2076   struct color_ext_type *ext;   /* Extension we are working on */
2077
2078   if ((p = getenv ("LS_COLORS")) == NULL || *p == '\0')
2079     return;
2080
2081   ext = NULL;
2082   strcpy (label, "??");
2083
2084   /* This is an overly conservative estimate, but any possible
2085      LS_COLORS string will *not* generate a color_buf longer than
2086      itself, so it is a safe way of allocating a buffer in
2087      advance.  */
2088   buf = color_buf = xstrdup (p);
2089
2090   state = 1;
2091   while (state > 0)
2092     {
2093       switch (state)
2094         {
2095         case 1:         /* First label character */
2096           switch (*p)
2097             {
2098             case ':':
2099               ++p;
2100               break;
2101
2102             case '*':
2103               /* Allocate new extension block and add to head of
2104                  linked list (this way a later definition will
2105                  override an earlier one, which can be useful for
2106                  having terminal-specific defs override global).  */
2107
2108               ext = xmalloc (sizeof *ext);
2109               ext->next = color_ext_list;
2110               color_ext_list = ext;
2111
2112               ++p;
2113               ext->ext.string = buf;
2114
2115               state = (get_funky_string (&buf, &p, true, &ext->ext.len)
2116                        ? 4 : -1);
2117               break;
2118
2119             case '\0':
2120               state = 0;        /* Done! */
2121               break;
2122
2123             default:    /* Assume it is file type label */
2124               label[0] = *(p++);
2125               state = 2;
2126               break;
2127             }
2128           break;
2129
2130         case 2:         /* Second label character */
2131           if (*p)
2132             {
2133               label[1] = *(p++);
2134               state = 3;
2135             }
2136           else
2137             state = -1; /* Error */
2138           break;
2139
2140         case 3:         /* Equal sign after indicator label */
2141           state = -1;   /* Assume failure...  */
2142           if (*(p++) == '=')/* It *should* be...  */
2143             {
2144               for (ind_no = 0; indicator_name[ind_no] != NULL; ++ind_no)
2145                 {
2146                   if (STREQ (label, indicator_name[ind_no]))
2147                     {
2148                       color_indicator[ind_no].string = buf;
2149                       state = (get_funky_string (&buf, &p, false,
2150                                                  &color_indicator[ind_no].len)
2151                                ? 1 : -1);
2152                       break;
2153                     }
2154                 }
2155               if (state == -1)
2156                 error (0, 0, _("unrecognized prefix: %s"), quotearg (label));
2157             }
2158          break;
2159
2160         case 4:         /* Equal sign after *.ext */
2161           if (*(p++) == '=')
2162             {
2163               ext->seq.string = buf;
2164               state = (get_funky_string (&buf, &p, false, &ext->seq.len)
2165                        ? 1 : -1);
2166             }
2167           else
2168             state = -1;
2169           break;
2170         }
2171     }
2172
2173   if (state < 0)
2174     {
2175       struct color_ext_type *e;
2176       struct color_ext_type *e2;
2177
2178       error (0, 0,
2179              _("unparsable value for LS_COLORS environment variable"));
2180       free (color_buf);
2181       for (e = color_ext_list; e != NULL; /* empty */)
2182         {
2183           e2 = e;
2184           e = e->next;
2185           free (e2);
2186         }
2187       print_with_color = false;
2188     }
2189
2190   if (color_indicator[C_LINK].len == 6
2191       && !strncmp (color_indicator[C_LINK].string, "target", 6))
2192     color_symlink_as_referent = true;
2193 }
2194
2195 /* Set the exit status to report a failure.  If SERIOUS, it is a
2196    serious failure; otherwise, it is merely a minor problem.  */
2197
2198 static void
2199 set_exit_status (bool serious)
2200 {
2201   if (serious)
2202     exit_status = LS_FAILURE;
2203   else if (exit_status == EXIT_SUCCESS)
2204     exit_status = LS_MINOR_PROBLEM;
2205 }
2206
2207 /* Assuming a failure is serious if SERIOUS, use the printf-style
2208    MESSAGE to report the failure to access a file named FILE.  Assume
2209    errno is set appropriately for the failure.  */
2210
2211 static void
2212 file_failure (bool serious, char const *message, char const *file)
2213 {
2214   error (0, errno, message, quotearg_colon (file));
2215   set_exit_status (serious);
2216 }
2217
2218 /* Request that the directory named NAME have its contents listed later.
2219    If REALNAME is nonzero, it will be used instead of NAME when the
2220    directory name is printed.  This allows symbolic links to directories
2221    to be treated as regular directories but still be listed under their
2222    real names.  NAME == NULL is used to insert a marker entry for the
2223    directory named in REALNAME.
2224    If NAME is non-NULL, we use its dev/ino information to save
2225    a call to stat -- when doing a recursive (-R) traversal.
2226    COMMAND_LINE_ARG means this directory was mentioned on the command line.  */
2227
2228 static void
2229 queue_directory (char const *name, char const *realname, bool command_line_arg)
2230 {
2231   struct pending *new = xmalloc (sizeof *new);
2232   new->realname = realname ? xstrdup (realname) : NULL;
2233   new->name = name ? xstrdup (name) : NULL;
2234   new->command_line_arg = command_line_arg;
2235   new->next = pending_dirs;
2236   pending_dirs = new;
2237 }
2238
2239 /* Read directory NAME, and list the files in it.
2240    If REALNAME is nonzero, print its name instead of NAME;
2241    this is used for symbolic links to directories.
2242    COMMAND_LINE_ARG means this directory was mentioned on the command line.  */
2243
2244 static void
2245 print_dir (char const *name, char const *realname, bool command_line_arg)
2246 {
2247   DIR *dirp;
2248   struct dirent *next;
2249   uintmax_t total_blocks = 0;
2250   static bool first = true;
2251
2252   errno = 0;
2253   dirp = opendir (name);
2254   if (!dirp)
2255     {
2256       file_failure (command_line_arg, "%s", name);
2257       return;
2258     }
2259
2260   if (LOOP_DETECT)
2261     {
2262       struct stat dir_stat;
2263       int fd = dirfd (dirp);
2264
2265       /* If dirfd failed, endure the overhead of using stat.  */
2266       if ((0 <= fd
2267            ? fstat (fd, &dir_stat)
2268            : stat (name, &dir_stat)) < 0)
2269         {
2270           file_failure (command_line_arg,
2271                         _("cannot determine device and inode of %s"), name);
2272           return;
2273         }
2274
2275       /* If we've already visited this dev/inode pair, warn that
2276          we've found a loop, and do not process this directory.  */
2277       if (visit_dir (dir_stat.st_dev, dir_stat.st_ino))
2278         {
2279           error (0, 0, _("%s: not listing already-listed directory"),
2280                  quotearg_colon (name));
2281           return;
2282         }
2283
2284       DEV_INO_PUSH (dir_stat.st_dev, dir_stat.st_ino);
2285     }
2286
2287   /* Read the directory entries, and insert the subfiles into the `files'
2288      table.  */
2289
2290   clear_files ();
2291
2292   while (1)
2293     {
2294       /* Set errno to zero so we can distinguish between a readdir failure
2295          and when readdir simply finds that there are no more entries.  */
2296       errno = 0;
2297       next = readdir (dirp);
2298       if (next)
2299         {
2300           if (! file_ignored (next->d_name))
2301             {
2302               enum filetype type = unknown;
2303
2304 #if HAVE_STRUCT_DIRENT_D_TYPE
2305               if (next->d_type == DT_BLK
2306                   || next->d_type == DT_CHR
2307                   || next->d_type == DT_DIR
2308                   || next->d_type == DT_FIFO
2309                   || next->d_type == DT_LNK
2310                   || next->d_type == DT_REG
2311                   || next->d_type == DT_SOCK)
2312                 type = next->d_type;
2313 #endif
2314               total_blocks += gobble_file (next->d_name, type, false, name);
2315             }
2316         }
2317       else if (errno != 0)
2318         {
2319           file_failure (command_line_arg, _("reading directory %s"), name);
2320           if (errno != EOVERFLOW)
2321             break;
2322         }
2323       else
2324         break;
2325     }
2326
2327   if (CLOSEDIR (dirp) != 0)
2328     {
2329       file_failure (command_line_arg, _("closing directory %s"), name);
2330       /* Don't return; print whatever we got.  */
2331     }
2332
2333   /* Sort the directory contents.  */
2334   sort_files ();
2335
2336   /* If any member files are subdirectories, perhaps they should have their
2337      contents listed rather than being mentioned here as files.  */
2338
2339   if (recursive)
2340     extract_dirs_from_files (name, command_line_arg);
2341
2342   if (recursive | print_dir_name)
2343     {
2344       if (!first)
2345         DIRED_PUTCHAR ('\n');
2346       first = false;
2347       DIRED_INDENT ();
2348       PUSH_CURRENT_DIRED_POS (&subdired_obstack);
2349       dired_pos += quote_name (stdout, realname ? realname : name,
2350                                dirname_quoting_options, NULL);
2351       PUSH_CURRENT_DIRED_POS (&subdired_obstack);
2352       DIRED_FPUTS_LITERAL (":\n", stdout);
2353     }
2354
2355   if (format == long_format || print_block_size)
2356     {
2357       const char *p;
2358       char buf[LONGEST_HUMAN_READABLE + 1];
2359
2360       DIRED_INDENT ();
2361       p = _("total");
2362       DIRED_FPUTS (p, stdout, strlen (p));
2363       DIRED_PUTCHAR (' ');
2364       p = human_readable (total_blocks, buf, human_output_opts,
2365                           ST_NBLOCKSIZE, output_block_size);
2366       DIRED_FPUTS (p, stdout, strlen (p));
2367       DIRED_PUTCHAR ('\n');
2368     }
2369
2370   if (files_index)
2371     print_current_files ();
2372 }
2373
2374 /* Add `pattern' to the list of patterns for which files that match are
2375    not listed.  */
2376
2377 static void
2378 add_ignore_pattern (const char *pattern)
2379 {
2380   struct ignore_pattern *ignore;
2381
2382   ignore = xmalloc (sizeof *ignore);
2383   ignore->pattern = pattern;
2384   /* Add it to the head of the linked list.  */
2385   ignore->next = ignore_patterns;
2386   ignore_patterns = ignore;
2387 }
2388
2389 /* Return true if one of the PATTERNS matches FILE.  */
2390
2391 static bool
2392 patterns_match (struct ignore_pattern const *patterns, char const *file)
2393 {
2394   struct ignore_pattern const *p;
2395   for (p = patterns; p; p = p->next)
2396     if (fnmatch (p->pattern, file, FNM_PERIOD) == 0)
2397       return true;
2398   return false;
2399 }
2400
2401 /* Return true if FILE should be ignored.  */
2402
2403 static bool
2404 file_ignored (char const *name)
2405 {
2406   return ((ignore_mode != IGNORE_MINIMAL
2407            && name[0] == '.'
2408            && (ignore_mode == IGNORE_DEFAULT || ! name[1 + (name[1] == '.')]))
2409           || (ignore_mode == IGNORE_DEFAULT
2410               && patterns_match (hide_patterns, name))
2411           || patterns_match (ignore_patterns, name));
2412 }
2413
2414 /* POSIX requires that a file size be printed without a sign, even
2415    when negative.  Assume the typical case where negative sizes are
2416    actually positive values that have wrapped around.  */
2417
2418 static uintmax_t
2419 unsigned_file_size (off_t size)
2420 {
2421   return size + (size < 0) * ((uintmax_t) OFF_T_MAX - OFF_T_MIN + 1);
2422 }
2423
2424 /* Enter and remove entries in the table `files'.  */
2425
2426 /* Empty the table of files.  */
2427
2428 static void
2429 clear_files (void)
2430 {
2431   size_t i;
2432
2433   for (i = 0; i < files_index; i++)
2434     {
2435       free (files[i].name);
2436       if (files[i].linkname)
2437         free (files[i].linkname);
2438     }
2439
2440   files_index = 0;
2441   inode_number_width = 0;
2442   block_size_width = 0;
2443   nlink_width = 0;
2444   owner_width = 0;
2445   group_width = 0;
2446   author_width = 0;
2447   major_device_number_width = 0;
2448   minor_device_number_width = 0;
2449   file_size_width = 0;
2450 }
2451
2452 /* Add a file to the current table of files.
2453    Verify that the file exists, and print an error message if it does not.
2454    Return the number of blocks that the file occupies.  */
2455
2456 static uintmax_t
2457 gobble_file (char const *name, enum filetype type, bool command_line_arg,
2458              char const *dirname)
2459 {
2460   uintmax_t blocks;
2461   char *path;
2462   struct fileinfo *f;
2463
2464   if (files_index == nfiles)
2465     {
2466       files = xnrealloc (files, nfiles, 2 * sizeof *files);
2467       nfiles *= 2;
2468     }
2469
2470   f = &files[files_index];
2471   f->linkname = 0;
2472   f->linkmode = 0;
2473   f->linkok = false;
2474
2475   if (command_line_arg
2476       || format_needs_stat
2477       || (format_needs_type
2478           && (type == unknown
2479
2480               /* FIXME: remove this disjunct.
2481                  I don't think we care about symlinks here, but for now
2482                  this won't make a big performance difference.  */
2483               || type == symbolic_link
2484
2485               /* --indicator-style=classify (aka -F)
2486                  requires that we stat each regular file
2487                  to see if it's executable.  */
2488               || (type == normal && (indicator_style == classify
2489                                      /* This is so that --color ends up
2490                                         highlighting files with the executable
2491                                         bit set even when options like -F are
2492                                         not specified.  */
2493                                      || (print_with_color
2494                                          && is_colored (C_EXEC))
2495                                      )))))
2496
2497     {
2498       /* `path' is the absolute pathname of this file.  */
2499       int err;
2500
2501       if (name[0] == '/' || dirname[0] == 0)
2502         path = (char *) name;
2503       else
2504         {
2505           path = alloca (strlen (name) + strlen (dirname) + 2);
2506           attach (path, dirname, name);
2507         }
2508
2509       switch (dereference)
2510         {
2511         case DEREF_ALWAYS:
2512           err = stat (path, &f->stat);
2513           break;
2514
2515         case DEREF_COMMAND_LINE_ARGUMENTS:
2516         case DEREF_COMMAND_LINE_SYMLINK_TO_DIR:
2517           if (command_line_arg)
2518             {
2519               bool need_lstat;
2520               err = stat (path, &f->stat);
2521
2522               if (dereference == DEREF_COMMAND_LINE_ARGUMENTS)
2523                 break;
2524
2525               need_lstat = (err < 0
2526                             ? errno == ENOENT
2527                             : ! S_ISDIR (f->stat.st_mode));
2528               if (!need_lstat)
2529                 break;
2530
2531               /* stat failed because of ENOENT, maybe indicating a dangling
2532                  symlink.  Or stat succeeded, PATH does not refer to a
2533                  directory, and --dereference-command-line-symlink-to-dir is
2534                  in effect.  Fall through so that we call lstat instead.  */
2535             }
2536
2537         default: /* DEREF_NEVER */
2538           err = lstat (path, &f->stat);
2539           break;
2540         }
2541
2542       if (err < 0)
2543         {
2544           file_failure (command_line_arg, "%s", path);
2545           return 0;
2546         }
2547
2548 #if HAVE_ACL
2549       if (format == long_format)
2550         {
2551           int n = file_has_acl (path, &f->stat);
2552           f->have_acl = (0 < n);
2553           if (n < 0)
2554             error (0, errno, "%s", quotearg_colon (path));
2555         }
2556 #endif
2557
2558       if (S_ISLNK (f->stat.st_mode)
2559           && (format == long_format || check_symlink_color))
2560         {
2561           char *linkpath;
2562           struct stat linkstats;
2563
2564           get_link_name (path, f, command_line_arg);
2565           linkpath = make_link_path (path, f->linkname);
2566
2567           /* Avoid following symbolic links when possible, ie, when
2568              they won't be traced and when no indicator is needed.  */
2569           if (linkpath
2570               && (indicator_style != none || check_symlink_color)
2571               && stat (linkpath, &linkstats) == 0)
2572             {
2573               f->linkok = true;
2574
2575               /* Symbolic links to directories that are mentioned on the
2576                  command line are automatically traced if not being
2577                  listed as files.  */
2578               if (!command_line_arg || format == long_format
2579                   || !S_ISDIR (linkstats.st_mode))
2580                 {
2581                   /* Get the linked-to file's mode for the filetype indicator
2582                      in long listings.  */
2583                   f->linkmode = linkstats.st_mode;
2584                   f->linkok = true;
2585                 }
2586             }
2587           if (linkpath)
2588             free (linkpath);
2589         }
2590
2591       if (S_ISLNK (f->stat.st_mode))
2592         f->filetype = symbolic_link;
2593       else if (S_ISDIR (f->stat.st_mode))
2594         {
2595           if (command_line_arg & !immediate_dirs)
2596             f->filetype = arg_directory;
2597           else
2598             f->filetype = directory;
2599         }
2600       else
2601         f->filetype = normal;
2602
2603       {
2604         char buf[INT_BUFSIZE_BOUND (uintmax_t)];
2605         int len = strlen (umaxtostr (f->stat.st_ino, buf));
2606         if (inode_number_width < len)
2607           inode_number_width = len;
2608       }
2609
2610       blocks = ST_NBLOCKS (f->stat);
2611       {
2612         char buf[LONGEST_HUMAN_READABLE + 1];
2613         int len = mbswidth (human_readable (blocks, buf, human_output_opts,
2614                                             ST_NBLOCKSIZE, output_block_size),
2615                             0);
2616         if (block_size_width < len)
2617           block_size_width = len;
2618       }
2619
2620       if (print_owner)
2621         {
2622           int len = format_user_width (f->stat.st_uid);
2623           if (owner_width < len)
2624             owner_width = len;
2625         }
2626
2627       if (print_group)
2628         {
2629           int len = format_group_width (f->stat.st_gid);
2630           if (group_width < len)
2631             group_width = len;
2632         }
2633
2634       if (print_author)
2635         {
2636           int len = format_user_width (f->stat.st_uid);
2637           if (author_width < len)
2638             author_width = len;
2639         }
2640
2641       {
2642         char buf[INT_BUFSIZE_BOUND (uintmax_t)];
2643         int len = strlen (umaxtostr (f->stat.st_nlink, buf));
2644         if (nlink_width < len)
2645           nlink_width = len;
2646       }
2647
2648       if (S_ISCHR (f->stat.st_mode) || S_ISBLK (f->stat.st_mode))
2649         {
2650           char buf[INT_BUFSIZE_BOUND (uintmax_t)];
2651           int len = strlen (umaxtostr (major (f->stat.st_rdev), buf));
2652           if (major_device_number_width < len)
2653             major_device_number_width = len;
2654           len = strlen (umaxtostr (minor (f->stat.st_rdev), buf));
2655           if (minor_device_number_width < len)
2656             minor_device_number_width = len;
2657           len = major_device_number_width + 2 + minor_device_number_width;
2658           if (file_size_width < len)
2659             file_size_width = len;
2660         }
2661       else
2662         {
2663           char buf[LONGEST_HUMAN_READABLE + 1];
2664           uintmax_t size = unsigned_file_size (f->stat.st_size);
2665           int len = mbswidth (human_readable (size, buf, human_output_opts,
2666                                               1, file_output_block_size),
2667                               0);
2668           if (file_size_width < len)
2669             file_size_width = len;
2670         }
2671     }
2672   else
2673     {
2674       f->filetype = type;
2675 #if HAVE_STRUCT_DIRENT_D_TYPE
2676       f->stat.st_mode = DTTOIF (type);
2677 #endif
2678       blocks = 0;
2679     }
2680
2681   f->name = xstrdup (name);
2682   files_index++;
2683
2684   return blocks;
2685 }
2686
2687 #ifdef S_ISLNK
2688
2689 /* Put the name of the file that FILENAME is a symbolic link to
2690    into the LINKNAME field of `f'.  COMMAND_LINE_ARG indicates whether
2691    FILENAME is a command-line argument.  */
2692
2693 static void
2694 get_link_name (char const *filename, struct fileinfo *f, bool command_line_arg)
2695 {
2696   f->linkname = xreadlink (filename, f->stat.st_size);
2697   if (f->linkname == NULL)
2698     file_failure (command_line_arg, _("cannot read symbolic link %s"),
2699                   filename);
2700 }
2701
2702 /* If `linkname' is a relative path and `path' contains one or more
2703    leading directories, return `linkname' with those directories
2704    prepended; otherwise, return a copy of `linkname'.
2705    If `linkname' is zero, return zero.  */
2706
2707 static char *
2708 make_link_path (const char *path, const char *linkname)
2709 {
2710   char *linkbuf;
2711   size_t bufsiz;
2712
2713   if (!linkname)
2714     return NULL;
2715
2716   if (*linkname == '/')
2717     return xstrdup (linkname);
2718
2719   /* The link is to a relative path.  Prepend any leading path
2720      in `path' to the link name.  */
2721   linkbuf = strrchr (path, '/');
2722   if (linkbuf == 0)
2723     return xstrdup (linkname);
2724
2725   bufsiz = linkbuf - path + 1;
2726   linkbuf = xmalloc (bufsiz + strlen (linkname) + 1);
2727   strncpy (linkbuf, path, bufsiz);
2728   strcpy (linkbuf + bufsiz, linkname);
2729   return linkbuf;
2730 }
2731 #endif
2732
2733 /* Return true if base_name (NAME) ends in `.' or `..'
2734    This is so we don't try to recurse on `././././. ...' */
2735
2736 static bool
2737 basename_is_dot_or_dotdot (const char *name)
2738 {
2739   char const *base = base_name (name);
2740   return DOT_OR_DOTDOT (base);
2741 }
2742
2743 /* Remove any entries from FILES that are for directories,
2744    and queue them to be listed as directories instead.
2745    DIRNAME is the prefix to prepend to each dirname
2746    to make it correct relative to ls's working dir;
2747    if it is null, no prefix is needed and "." and ".." should not be ignored.
2748    If COMMAND_LINE_ARG is true, this directory was mentioned at the top level,
2749    This is desirable when processing directories recursively.  */
2750
2751 static void
2752 extract_dirs_from_files (char const *dirname, bool command_line_arg)
2753 {
2754   size_t i;
2755   size_t j;
2756   bool ignore_dot_and_dot_dot = (dirname != NULL);
2757
2758   if (dirname && LOOP_DETECT)
2759     {
2760       /* Insert a marker entry first.  When we dequeue this marker entry,
2761          we'll know that DIRNAME has been processed and may be removed
2762          from the set of active directories.  */
2763       queue_directory (NULL, dirname, false);
2764     }
2765
2766   /* Queue the directories last one first, because queueing reverses the
2767      order.  */
2768   for (i = files_index; i-- != 0; )
2769     if ((files[i].filetype == directory || files[i].filetype == arg_directory)
2770         && (!ignore_dot_and_dot_dot
2771             || !basename_is_dot_or_dotdot (files[i].name)))
2772       {
2773         if (!dirname || files[i].name[0] == '/')
2774           {
2775             queue_directory (files[i].name, files[i].linkname,
2776                              command_line_arg);
2777           }
2778         else
2779           {
2780             char *path = path_concat (dirname, files[i].name, NULL);
2781             queue_directory (path, files[i].linkname, command_line_arg);
2782             free (path);
2783           }
2784         if (files[i].filetype == arg_directory)
2785           free (files[i].name);
2786       }
2787
2788   /* Now delete the directories from the table, compacting all the remaining
2789      entries.  */
2790
2791   for (i = 0, j = 0; i < files_index; i++)
2792     {
2793       if (files[i].filetype != arg_directory)
2794         {
2795           if (j < i)
2796             files[j] = files[i];
2797           ++j;
2798         }
2799     }
2800   files_index = j;
2801 }
2802
2803 /* Use strcoll to compare strings in this locale.  If an error occurs,
2804    report an error and longjmp to failed_strcoll.  */
2805
2806 static jmp_buf failed_strcoll;
2807
2808 static int
2809 xstrcoll (char const *a, char const *b)
2810 {
2811   int diff;
2812   errno = 0;
2813   diff = strcoll (a, b);
2814   if (errno)
2815     {
2816       error (0, errno, _("cannot compare file names %s and %s"),
2817              quote_n (0, a), quote_n (1, b));
2818       set_exit_status (false);
2819       longjmp (failed_strcoll, 1);
2820     }
2821   return diff;
2822 }
2823
2824 /* Comparison routines for sorting the files.  */
2825
2826 typedef void const *V;
2827
2828 static inline int
2829 cmp_ctime (struct fileinfo const *a, struct fileinfo const *b,
2830            int (*cmp) (char const *, char const *))
2831 {
2832   int diff = CTIME_CMP (b->stat, a->stat);
2833   return diff ? diff : cmp (a->name, b->name);
2834 }
2835 static int compare_ctime (V a, V b) { return cmp_ctime (a, b, xstrcoll); }
2836 static int compstr_ctime (V a, V b) { return cmp_ctime (a, b, strcmp); }
2837 static int rev_cmp_ctime (V a, V b) { return compare_ctime (b, a); }
2838 static int rev_str_ctime (V a, V b) { return compstr_ctime (b, a); }
2839
2840 static inline int
2841 cmp_mtime (struct fileinfo const *a, struct fileinfo const *b,
2842            int (*cmp) (char const *, char const *))
2843 {
2844   int diff = MTIME_CMP (b->stat, a->stat);
2845   return diff ? diff : cmp (a->name, b->name);
2846 }
2847 static int compare_mtime (V a, V b) { return cmp_mtime (a, b, xstrcoll); }
2848 static int compstr_mtime (V a, V b) { return cmp_mtime (a, b, strcmp); }
2849 static int rev_cmp_mtime (V a, V b) { return compare_mtime (b, a); }
2850 static int rev_str_mtime (V a, V b) { return compstr_mtime (b, a); }
2851
2852 static inline int
2853 cmp_atime (struct fileinfo const *a, struct fileinfo const *b,
2854            int (*cmp) (char const *, char const *))
2855 {
2856   int diff = ATIME_CMP (b->stat, a->stat);
2857   return diff ? diff : cmp (a->name, b->name);
2858 }
2859 static int compare_atime (V a, V b) { return cmp_atime (a, b, xstrcoll); }
2860 static int compstr_atime (V a, V b) { return cmp_atime (a, b, strcmp); }
2861 static int rev_cmp_atime (V a, V b) { return compare_atime (b, a); }
2862 static int rev_str_atime (V a, V b) { return compstr_atime (b, a); }
2863
2864 static inline int
2865 cmp_size (struct fileinfo const *a, struct fileinfo const *b,
2866           int (*cmp) (char const *, char const *))
2867 {
2868   int diff = longdiff (b->stat.st_size, a->stat.st_size);
2869   return diff ? diff : cmp (a->name, b->name);
2870 }
2871 static int compare_size (V a, V b) { return cmp_size (a, b, xstrcoll); }
2872 static int compstr_size (V a, V b) { return cmp_size (a, b, strcmp); }
2873 static int rev_cmp_size (V a, V b) { return compare_size (b, a); }
2874 static int rev_str_size (V a, V b) { return compstr_size (b, a); }
2875
2876 static inline int
2877 cmp_version (struct fileinfo const *a, struct fileinfo const *b)
2878 {
2879   return strverscmp (a->name, b->name);
2880 }
2881 static int compare_version (V a, V b) { return cmp_version (a, b); }
2882 static int rev_cmp_version (V a, V b) { return compare_version (b, a); }
2883
2884 static inline int
2885 cmp_name (struct fileinfo const *a, struct fileinfo const *b,
2886           int (*cmp) (char const *, char const *))
2887 {
2888   return cmp (a->name, b->name);
2889 }
2890 static int compare_name (V a, V b) { return cmp_name (a, b, xstrcoll); }
2891 static int compstr_name (V a, V b) { return cmp_name (a, b, strcmp); }
2892 static int rev_cmp_name (V a, V b) { return compare_name (b, a); }
2893 static int rev_str_name (V a, V b) { return compstr_name (b, a); }
2894
2895 /* Compare file extensions.  Files with no extension are `smallest'.
2896    If extensions are the same, compare by filenames instead.  */
2897
2898 static inline int
2899 cmp_extension (struct fileinfo const *a, struct fileinfo const *b,
2900                int (*cmp) (char const *, char const *))
2901 {
2902   char const *base1 = strrchr (a->name, '.');
2903   char const *base2 = strrchr (b->name, '.');
2904   int diff = cmp (base1 ? base1 : "", base2 ? base2 : "");
2905   return diff ? diff : cmp (a->name, b->name);
2906 }
2907 static int compare_extension (V a, V b) { return cmp_extension (a, b, xstrcoll); }
2908 static int compstr_extension (V a, V b) { return cmp_extension (a, b, strcmp); }
2909 static int rev_cmp_extension (V a, V b) { return compare_extension (b, a); }
2910 static int rev_str_extension (V a, V b) { return compstr_extension (b, a); }
2911
2912 /* Sort the files now in the table.  */
2913
2914 static void
2915 sort_files (void)
2916 {
2917   int (*func) (V, V);
2918
2919   /* Try strcoll.  If it fails, fall back on strcmp.  We can't safely
2920      ignore strcoll failures, as a failing strcoll might be a
2921      comparison function that is not a total order, and if we ignored
2922      the failure this might cause qsort to dump core.  */
2923
2924   if (! setjmp (failed_strcoll))
2925     {
2926       switch (sort_type)
2927         {
2928         case sort_none:
2929           return;
2930         case sort_time:
2931           switch (time_type)
2932             {
2933             case time_ctime:
2934               func = sort_reverse ? rev_cmp_ctime : compare_ctime;
2935               break;
2936             case time_mtime:
2937               func = sort_reverse ? rev_cmp_mtime : compare_mtime;
2938               break;
2939             case time_atime:
2940               func = sort_reverse ? rev_cmp_atime : compare_atime;
2941               break;
2942             default:
2943               abort ();
2944             }
2945           break;
2946         case sort_name:
2947           func = sort_reverse ? rev_cmp_name : compare_name;
2948           break;
2949         case sort_extension:
2950           func = sort_reverse ? rev_cmp_extension : compare_extension;
2951           break;
2952         case sort_size:
2953           func = sort_reverse ? rev_cmp_size : compare_size;
2954           break;
2955         case sort_version:
2956           func = sort_reverse ? rev_cmp_version : compare_version;
2957           break;
2958         default:
2959           abort ();
2960         }
2961     }
2962   else
2963     {
2964       switch (sort_type)
2965         {
2966         case sort_time:
2967           switch (time_type)
2968             {
2969             case time_ctime:
2970               func = sort_reverse ? rev_str_ctime : compstr_ctime;
2971               break;
2972             case time_mtime:
2973               func = sort_reverse ? rev_str_mtime : compstr_mtime;
2974               break;
2975             case time_atime:
2976               func = sort_reverse ? rev_str_atime : compstr_atime;
2977               break;
2978             default:
2979               abort ();
2980             }
2981           break;
2982         case sort_name:
2983           func = sort_reverse ? rev_str_name : compstr_name;
2984           break;
2985         case sort_extension:
2986           func = sort_reverse ? rev_str_extension : compstr_extension;
2987           break;
2988         case sort_size:
2989           func = sort_reverse ? rev_str_size : compstr_size;
2990           break;
2991         default:
2992           abort ();
2993         }
2994     }
2995
2996   qsort (files, files_index, sizeof (struct fileinfo), func);
2997 }
2998
2999 /* List all the files now in the table.  */
3000
3001 static void
3002 print_current_files (void)
3003 {
3004   size_t i;
3005
3006   switch (format)
3007     {
3008     case one_per_line:
3009       for (i = 0; i < files_index; i++)
3010         {
3011           print_file_name_and_frills (files + i);
3012           putchar ('\n');
3013         }
3014       break;
3015
3016     case many_per_line:
3017       print_many_per_line ();
3018       break;
3019
3020     case horizontal:
3021       print_horizontal ();
3022       break;
3023
3024     case with_commas:
3025       print_with_commas ();
3026       break;
3027
3028     case long_format:
3029       for (i = 0; i < files_index; i++)
3030         {
3031           print_long_format (files + i);
3032           DIRED_PUTCHAR ('\n');
3033         }
3034       break;
3035     }
3036 }
3037
3038 /* Return the expected number of columns in a long-format time stamp,
3039    or zero if it cannot be calculated.  */
3040
3041 static int
3042 long_time_expected_width (void)
3043 {
3044   static int width = -1;
3045
3046   if (width < 0)
3047     {
3048       time_t epoch = 0;
3049       struct tm const *tm = localtime (&epoch);
3050       char const *fmt = long_time_format[0];
3051       char initbuf[100];
3052       char *buf = initbuf;
3053       size_t bufsize = sizeof initbuf;
3054       size_t len;
3055
3056       for (;;)
3057         {
3058           *buf = '\1';
3059           len = nstrftime (buf, bufsize, fmt, tm, 0, 0);
3060           if (len || ! *buf)
3061             break;
3062           buf = alloca (bufsize *= 2);
3063         }
3064
3065       width = mbsnwidth (buf, len, 0);
3066       if (width < 0)
3067         width = 0;
3068     }
3069
3070   return width;
3071 }
3072
3073 /* Get the current time.  */
3074
3075 static void
3076 get_current_time (void)
3077 {
3078 #if HAVE_CLOCK_GETTIME && defined CLOCK_REALTIME
3079   {
3080     struct timespec timespec;
3081     if (clock_gettime (CLOCK_REALTIME, &timespec) == 0)
3082       {
3083         current_time = timespec.tv_sec;
3084         current_time_ns = timespec.tv_nsec;
3085         return;
3086       }
3087   }
3088 #endif
3089
3090   /* The clock does not have nanosecond resolution, so get the maximum
3091      possible value for the current time that is consistent with the
3092      reported clock.  That way, files are not considered to be in the
3093      future merely because their time stamps have higher resolution
3094      than the clock resolution.  */
3095
3096 #if HAVE_GETTIMEOFDAY
3097   {
3098     struct timeval timeval;
3099     gettimeofday (&timeval, NULL);
3100     current_time = timeval.tv_sec;
3101     current_time_ns = timeval.tv_usec * 1000 + 999;
3102   }
3103 #else
3104   current_time = time (NULL);
3105   current_time_ns = 999999999;
3106 #endif
3107 }
3108
3109 /* Print the user or group name NAME, with numeric id ID, using a
3110    print width of WIDTH columns.  */
3111
3112 static void
3113 format_user_or_group (char const *name, unsigned long int id, int width)
3114 {
3115   size_t len;
3116
3117   if (name)
3118     {
3119       int width_gap = width - mbswidth (name, 0);
3120       int pad = MAX (0, width_gap);
3121       fputs (name, stdout);
3122       len = strlen (name) + pad;
3123
3124       do
3125         putchar (' ');
3126       while (pad--);
3127     }
3128   else
3129     {
3130       printf ("%*lu ", width, id);
3131       len = width;
3132     }
3133
3134   dired_pos += len + 1;
3135 }
3136
3137 /* Print the name or id of the user with id U, using a print width of
3138    WIDTH.  */
3139
3140 static void
3141 format_user (uid_t u, int width)
3142 {
3143   format_user_or_group (numeric_ids ? NULL : getuser (u), u, width);
3144 }
3145
3146 /* Likewise, for groups.  */
3147
3148 static void
3149 format_group (gid_t g, int width)
3150 {
3151   format_user_or_group (numeric_ids ? NULL : getgroup (g), g, width);
3152 }
3153
3154 /* Return the number of columns that format_user_or_group will print.  */
3155
3156 static int
3157 format_user_or_group_width (char const *name, unsigned long int id)
3158 {
3159   if (name)
3160     {
3161       int len = mbswidth (name, 0);
3162       return MAX (0, len);
3163     }
3164   else
3165     {
3166       char buf[INT_BUFSIZE_BOUND (unsigned long int)];
3167       sprintf (buf, "%lu", id);
3168       return strlen (buf);
3169     }
3170 }
3171
3172 /* Return the number of columns that format_user will print.  */
3173
3174 static int
3175 format_user_width (uid_t u)
3176 {
3177   return format_user_or_group_width (numeric_ids ? NULL : getuser (u), u);
3178 }
3179
3180 /* Likewise, for groups.  */
3181
3182 static int
3183 format_group_width (gid_t g)
3184 {
3185   return format_user_or_group_width (numeric_ids ? NULL : getgroup (g), g);
3186 }
3187
3188
3189 /* Print information about F in long format.  */
3190
3191 static void
3192 print_long_format (const struct fileinfo *f)
3193 {
3194   char modebuf[12];
3195   char init_bigbuf
3196     [LONGEST_HUMAN_READABLE + 1         /* inode */
3197      + LONGEST_HUMAN_READABLE + 1       /* size in blocks */
3198      + sizeof (modebuf) - 1 + 1         /* mode string */
3199      + INT_BUFSIZE_BOUND (uintmax_t)    /* st_nlink */
3200      + LONGEST_HUMAN_READABLE + 2       /* major device number */
3201      + LONGEST_HUMAN_READABLE + 1       /* minor device number */
3202      + 35 + 1   /* usual length of time/date -- may be longer; see below */
3203      ];
3204   char *buf = init_bigbuf;
3205   size_t bufsize = sizeof (init_bigbuf);
3206   size_t s;
3207   char *p;
3208   time_t when;
3209   int when_ns IF_LINT (= 0);
3210   struct tm *when_local;
3211
3212   /* Compute mode string.  On most systems, it's based on st_mode.
3213      On systems with migration (via the stat.st_dm_mode field), use
3214      the file's migrated status.  */
3215   mode_string (ST_DM_MODE (f->stat), modebuf);
3216
3217   modebuf[10] = (FILE_HAS_ACL (f) ? '+' : ' ');
3218   modebuf[11] = '\0';
3219
3220   switch (time_type)
3221     {
3222     case time_ctime:
3223       when = f->stat.st_ctime;
3224       when_ns = TIMESPEC_NS (f->stat.st_ctim);
3225       break;
3226     case time_mtime:
3227       when = f->stat.st_mtime;
3228       when_ns = TIMESPEC_NS (f->stat.st_mtim);
3229       break;
3230     case time_atime:
3231       when = f->stat.st_atime;
3232       when_ns = TIMESPEC_NS (f->stat.st_atim);
3233       break;
3234     }
3235
3236   p = buf;
3237
3238   if (print_inode)
3239     {
3240       char hbuf[INT_BUFSIZE_BOUND (uintmax_t)];
3241       sprintf (p, "%*s ", inode_number_width,
3242                umaxtostr (f->stat.st_ino, hbuf));
3243       p += inode_number_width + 1;
3244     }
3245
3246   if (print_block_size)
3247     {
3248       char hbuf[LONGEST_HUMAN_READABLE + 1];
3249       char const *blocks =
3250         human_readable (ST_NBLOCKS (f->stat), hbuf, human_output_opts,
3251                         ST_NBLOCKSIZE, output_block_size);
3252       int pad;
3253       for (pad = block_size_width - mbswidth (blocks, 0); 0 < pad; pad--)
3254         *p++ = ' ';
3255       while ((*p++ = *blocks++))
3256         continue;
3257       p[-1] = ' ';
3258     }
3259
3260   /* The last byte of the mode string is the POSIX
3261      "optional alternate access method flag".  */
3262   {
3263     char hbuf[INT_BUFSIZE_BOUND (uintmax_t)];
3264     sprintf (p, "%s %*s ", modebuf, nlink_width,
3265              umaxtostr (f->stat.st_nlink, hbuf));
3266   }
3267   p += sizeof modebuf + nlink_width + 1;
3268
3269   DIRED_INDENT ();
3270
3271   if (print_owner | print_group | print_author)
3272     {
3273       DIRED_FPUTS (buf, stdout, p - buf);
3274
3275       if (print_owner)
3276         format_user (f->stat.st_uid, owner_width);
3277
3278       if (print_group)
3279         format_group (f->stat.st_gid, group_width);
3280
3281       if (print_author)
3282         format_user (f->stat.st_author, author_width);
3283
3284       p = buf;
3285     }
3286
3287   if (S_ISCHR (f->stat.st_mode) || S_ISBLK (f->stat.st_mode))
3288     {
3289       char majorbuf[INT_BUFSIZE_BOUND (uintmax_t)];
3290       char minorbuf[INT_BUFSIZE_BOUND (uintmax_t)];
3291       int blanks_width = (file_size_width
3292                           - (major_device_number_width + 2
3293                              + minor_device_number_width));
3294       sprintf (p, "%*s, %*s ",
3295                major_device_number_width + MAX (0, blanks_width),
3296                umaxtostr (major (f->stat.st_rdev), majorbuf),
3297                minor_device_number_width,
3298                umaxtostr (minor (f->stat.st_rdev), minorbuf));
3299       p += file_size_width + 1;
3300     }
3301   else
3302     {
3303       char hbuf[LONGEST_HUMAN_READABLE + 1];
3304       char const *size =
3305         human_readable (unsigned_file_size (f->stat.st_size),
3306                         hbuf, human_output_opts, 1, file_output_block_size);
3307       int pad;
3308       for (pad = file_size_width - mbswidth (size, 0); 0 < pad; pad--)
3309         *p++ = ' ';
3310       while ((*p++ = *size++))
3311         continue;
3312       p[-1] = ' ';
3313     }
3314
3315   if ((when_local = localtime (&when)))
3316     {
3317       time_t six_months_ago;
3318       bool recent;
3319       char const *fmt;
3320
3321       /* If the file appears to be in the future, update the current
3322          time, in case the file happens to have been modified since
3323          the last time we checked the clock.  */
3324       if (current_time < when
3325           || (current_time == when && current_time_ns < when_ns))
3326         {
3327           /* Note that get_current_time calls gettimeofday which, on some non-
3328              compliant systems, clobbers the buffer used for localtime's result.
3329              But it's ok here, because we use a gettimeofday wrapper that
3330              saves and restores the buffer around the gettimeofday call.  */
3331           get_current_time ();
3332         }
3333
3334       /* Consider a time to be recent if it is within the past six
3335          months.  A Gregorian year has 365.2425 * 24 * 60 * 60 ==
3336          31556952 seconds on the average.  Write this value as an
3337          integer constant to avoid floating point hassles.  */
3338       six_months_ago = current_time - 31556952 / 2;
3339       recent = (six_months_ago <= when
3340                 && (when < current_time
3341                     || (when == current_time && when_ns <= current_time_ns)));
3342       fmt = long_time_format[recent];
3343
3344       for (;;)
3345         {
3346           char *newbuf;
3347           *p = '\1';
3348           s = nstrftime (p, buf + bufsize - p - 1, fmt,
3349                          when_local, 0, when_ns);
3350           if (s || ! *p)
3351             break;
3352           newbuf = alloca (bufsize *= 2);
3353           memcpy (newbuf, buf, p - buf);
3354           p = newbuf + (p - buf);
3355           buf = newbuf;
3356         }
3357
3358       p += s;
3359       *p++ = ' ';
3360
3361       /* NUL-terminate the string -- fputs (via DIRED_FPUTS) requires it.  */
3362       *p = '\0';
3363     }
3364   else
3365     {
3366       /* The time cannot be represented as a local time;
3367          print it as a huge integer number of seconds.  */
3368       char hbuf[INT_BUFSIZE_BOUND (intmax_t)];
3369       sprintf (p, "%*s ", long_time_expected_width (),
3370                (TYPE_SIGNED (time_t)
3371                 ? imaxtostr (when, hbuf)
3372                 : umaxtostr (when, hbuf)));
3373       p += strlen (p);
3374     }
3375
3376   DIRED_FPUTS (buf, stdout, p - buf);
3377   print_name_with_quoting (f->name, FILE_OR_LINK_MODE (f), f->linkok,
3378                            &dired_obstack);
3379
3380   if (f->filetype == symbolic_link)
3381     {
3382       if (f->linkname)
3383         {
3384           DIRED_FPUTS_LITERAL (" -> ", stdout);
3385           print_name_with_quoting (f->linkname, f->linkmode, f->linkok - 1,
3386                                    NULL);
3387           if (indicator_style != none)
3388             print_type_indicator (f->linkmode);
3389         }
3390     }
3391   else if (indicator_style != none)
3392     print_type_indicator (f->stat.st_mode);
3393 }
3394
3395 /* Output to OUT a quoted representation of the file name NAME,
3396    using OPTIONS to control quoting.  Produce no output if OUT is NULL.
3397    Store the number of screen columns occupied by NAME's quoted
3398    representation into WIDTH, if non-NULL.  Return the number of bytes
3399    produced.  */
3400
3401 static size_t
3402 quote_name (FILE *out, const char *name, struct quoting_options const *options,
3403             size_t *width)
3404 {
3405   char smallbuf[BUFSIZ];
3406   size_t len = quotearg_buffer (smallbuf, sizeof smallbuf, name, -1, options);
3407   char *buf;
3408   size_t displayed_width IF_LINT (= 0);
3409
3410   if (len < sizeof smallbuf)
3411     buf = smallbuf;
3412   else
3413     {
3414       buf = alloca (len + 1);
3415       quotearg_buffer (buf, len + 1, name, -1, options);
3416     }
3417
3418   if (qmark_funny_chars)
3419     {
3420 #if HAVE_MBRTOWC
3421       if (MB_CUR_MAX > 1)
3422         {
3423           char const *p = buf;
3424           char const *plimit = buf + len;
3425           char *q = buf;
3426           displayed_width = 0;
3427
3428           while (p < plimit)
3429             switch (*p)
3430               {
3431                 case ' ': case '!': case '"': case '#': case '%':
3432                 case '&': case '\'': case '(': case ')': case '*':
3433                 case '+': case ',': case '-': case '.': case '/':
3434                 case '0': case '1': case '2': case '3': case '4':
3435                 case '5': case '6': case '7': case '8': case '9':
3436                 case ':': case ';': case '<': case '=': case '>':
3437                 case '?':
3438                 case 'A': case 'B': case 'C': case 'D': case 'E':
3439                 case 'F': case 'G': case 'H': case 'I': case 'J':
3440                 case 'K': case 'L': case 'M': case 'N': case 'O':
3441                 case 'P': case 'Q': case 'R': case 'S': case 'T':
3442                 case 'U': case 'V': case 'W': case 'X': case 'Y':
3443                 case 'Z':
3444                 case '[': case '\\': case ']': case '^': case '_':
3445                 case 'a': case 'b': case 'c': case 'd': case 'e':
3446                 case 'f': case 'g': case 'h': case 'i': case 'j':
3447                 case 'k': case 'l': case 'm': case 'n': case 'o':
3448                 case 'p': case 'q': case 'r': case 's': case 't':
3449                 case 'u': case 'v': case 'w': case 'x': case 'y':
3450                 case 'z': case '{': case '|': case '}': case '~':
3451                   /* These characters are printable ASCII characters.  */
3452                   *q++ = *p++;
3453                   displayed_width += 1;
3454                   break;
3455                 default:
3456                   /* If we have a multibyte sequence, copy it until we
3457                      reach its end, replacing each non-printable multibyte
3458                      character with a single question mark.  */
3459                   {
3460                     mbstate_t mbstate;
3461                     memset (&mbstate, 0, sizeof mbstate);
3462                     do
3463                       {
3464                         wchar_t wc;
3465                         size_t bytes;
3466                         int w;
3467
3468                         bytes = mbrtowc (&wc, p, plimit - p, &mbstate);
3469
3470                         if (bytes == (size_t) -1)
3471                           {
3472                             /* An invalid multibyte sequence was
3473                                encountered.  Skip one input byte, and
3474                                put a question mark.  */
3475                             p++;
3476                             *q++ = '?';
3477                             displayed_width += 1;
3478                             break;
3479                           }
3480
3481                         if (bytes == (size_t) -2)
3482                           {
3483                             /* An incomplete multibyte character
3484                                at the end.  Replace it entirely with
3485                                a question mark.  */
3486                             p = plimit;
3487                             *q++ = '?';
3488                             displayed_width += 1;
3489                             break;
3490                           }
3491
3492                         if (bytes == 0)
3493                           /* A null wide character was encountered.  */
3494                           bytes = 1;
3495
3496                         w = wcwidth (wc);
3497                         if (w >= 0)
3498                           {
3499                             /* A printable multibyte character.
3500                                Keep it.  */
3501                             for (; bytes > 0; --bytes)
3502                               *q++ = *p++;
3503                             displayed_width += w;
3504                           }
3505                         else
3506                           {
3507                             /* An unprintable multibyte character.
3508                                Replace it entirely with a question
3509                                mark.  */
3510                             p += bytes;
3511                             *q++ = '?';
3512                             displayed_width += 1;
3513                           }
3514                       }
3515                     while (! mbsinit (&mbstate));
3516                   }
3517                   break;
3518               }
3519
3520           /* The buffer may have shrunk.  */
3521           len = q - buf;
3522         }
3523       else
3524 #endif
3525         {
3526           char *p = buf;
3527           char const *plimit = buf + len;
3528
3529           while (p < plimit)
3530             {
3531               if (! ISPRINT (to_uchar (*p)))
3532                 *p = '?';
3533               p++;
3534             }
3535           displayed_width = len;
3536         }
3537     }
3538   else if (width != NULL)
3539     {
3540 #if HAVE_MBRTOWC
3541       if (MB_CUR_MAX > 1)
3542         displayed_width = mbsnwidth (buf, len, 0);
3543       else
3544 #endif
3545         {
3546           char const *p = buf;
3547           char const *plimit = buf + len;
3548
3549           displayed_width = 0;
3550           while (p < plimit)
3551             {
3552               if (ISPRINT (to_uchar (*p)))
3553                 displayed_width++;
3554               p++;
3555             }
3556         }
3557     }
3558
3559   if (out != NULL)
3560     fwrite (buf, 1, len, out);
3561   if (width != NULL)
3562     *width = displayed_width;
3563   return len;
3564 }
3565
3566 static void
3567 print_name_with_quoting (const char *p, mode_t mode, int linkok,
3568                          struct obstack *stack)
3569 {
3570   if (print_with_color)
3571     print_color_indicator (p, mode, linkok);
3572
3573   if (stack)
3574     PUSH_CURRENT_DIRED_POS (stack);
3575
3576   dired_pos += quote_name (stdout, p, filename_quoting_options, NULL);
3577
3578   if (stack)
3579     PUSH_CURRENT_DIRED_POS (stack);
3580
3581   if (print_with_color)
3582     {
3583       process_signals ();
3584       prep_non_filename_text ();
3585     }
3586 }
3587
3588 static void
3589 prep_non_filename_text (void)
3590 {
3591   if (color_indicator[C_END].string != NULL)
3592     put_indicator (&color_indicator[C_END]);
3593   else
3594     {
3595       put_indicator (&color_indicator[C_LEFT]);
3596       put_indicator (&color_indicator[C_NORM]);
3597       put_indicator (&color_indicator[C_RIGHT]);
3598     }
3599 }
3600
3601 /* Print the file name of `f' with appropriate quoting.
3602    Also print file size, inode number, and filetype indicator character,
3603    as requested by switches.  */
3604
3605 static void
3606 print_file_name_and_frills (const struct fileinfo *f)
3607 {
3608   char buf[MAX (LONGEST_HUMAN_READABLE + 1, INT_BUFSIZE_BOUND (uintmax_t))];
3609
3610   if (print_inode)
3611     printf ("%*s ", format == with_commas ? 0 : inode_number_width,
3612             umaxtostr (f->stat.st_ino, buf));
3613
3614   if (print_block_size)
3615     printf ("%*s ", format == with_commas ? 0 : block_size_width,
3616             human_readable (ST_NBLOCKS (f->stat), buf, human_output_opts,
3617                             ST_NBLOCKSIZE, output_block_size));
3618
3619   print_name_with_quoting (f->name, FILE_OR_LINK_MODE (f), f->linkok, NULL);
3620
3621   if (indicator_style != none)
3622     print_type_indicator (f->stat.st_mode);
3623 }
3624
3625 static void
3626 print_type_indicator (mode_t mode)
3627 {
3628   char c;
3629
3630   if (S_ISREG (mode))
3631     {
3632       if (indicator_style == classify && (mode & S_IXUGO))
3633         c ='*';
3634       else
3635         c = 0;
3636     }
3637   else
3638     {
3639       if (S_ISDIR (mode))
3640         c = '/';
3641       else if (S_ISLNK (mode))
3642         c = '@';
3643       else if (S_ISFIFO (mode))
3644         c = '|';
3645       else if (S_ISSOCK (mode))
3646         c = '=';
3647       else if (S_ISDOOR (mode))
3648         c = '>';
3649       else
3650         c = 0;
3651     }
3652
3653   if (c)
3654     DIRED_PUTCHAR (c);
3655 }
3656
3657 static void
3658 print_color_indicator (const char *name, mode_t mode, int linkok)
3659 {
3660   int type = C_FILE;
3661   struct color_ext_type *ext;   /* Color extension */
3662   size_t len;                   /* Length of name */
3663
3664   /* Is this a nonexistent file?  If so, linkok == -1.  */
3665
3666   if (linkok == -1 && color_indicator[C_MISSING].string != NULL)
3667     {
3668       ext = NULL;
3669       type = C_MISSING;
3670     }
3671   else
3672     {
3673       if (S_ISDIR (mode))
3674         type = C_DIR;
3675       else if (S_ISLNK (mode))
3676         type = ((!linkok && color_indicator[C_ORPHAN].string)
3677                 ? C_ORPHAN : C_LINK);
3678       else if (S_ISFIFO (mode))
3679         type = C_FIFO;
3680       else if (S_ISSOCK (mode))
3681         type = C_SOCK;
3682       else if (S_ISBLK (mode))
3683         type = C_BLK;
3684       else if (S_ISCHR (mode))
3685         type = C_CHR;
3686       else if (S_ISDOOR (mode))
3687         type = C_DOOR;
3688
3689       if (type == C_FILE && (mode & S_IXUGO) != 0)
3690         type = C_EXEC;
3691
3692       /* Check the file's suffix only if still classified as C_FILE.  */
3693       ext = NULL;
3694       if (type == C_FILE)
3695         {
3696           /* Test if NAME has a recognized suffix.  */
3697
3698           len = strlen (name);
3699           name += len;          /* Pointer to final \0.  */
3700           for (ext = color_ext_list; ext != NULL; ext = ext->next)
3701             {
3702               if (ext->ext.len <= len
3703                   && strncmp (name - ext->ext.len, ext->ext.string,
3704                               ext->ext.len) == 0)
3705                 break;
3706             }
3707         }
3708     }
3709
3710   put_indicator (&color_indicator[C_LEFT]);
3711   put_indicator (ext ? &(ext->seq) : &color_indicator[type]);
3712   put_indicator (&color_indicator[C_RIGHT]);
3713 }
3714
3715 /* Output a color indicator (which may contain nulls).  */
3716 static void
3717 put_indicator (const struct bin_str *ind)
3718 {
3719   size_t i;
3720   const char *p;
3721
3722   p = ind->string;
3723
3724   for (i = ind->len; i != 0; --i)
3725     putchar (*(p++));
3726 }
3727
3728 static size_t
3729 length_of_file_name_and_frills (const struct fileinfo *f)
3730 {
3731   size_t len = 0;
3732   size_t name_width;
3733   char buf[MAX (LONGEST_HUMAN_READABLE + 1, INT_BUFSIZE_BOUND (uintmax_t))];
3734
3735   if (print_inode)
3736     len += 1 + (format == with_commas
3737                 ? strlen (umaxtostr (f->stat.st_ino, buf))
3738                 : inode_number_width);
3739
3740   if (print_block_size)
3741     len += 1 + (format == with_commas
3742                 ? strlen (human_readable (ST_NBLOCKS (f->stat), buf,
3743                                           human_output_opts, ST_NBLOCKSIZE,
3744                                           output_block_size))
3745                 : block_size_width);
3746
3747   quote_name (NULL, f->name, filename_quoting_options, &name_width);
3748   len += name_width;
3749
3750   if (indicator_style != none)
3751     {
3752       mode_t filetype = f->stat.st_mode;
3753
3754       if (S_ISREG (filetype))
3755         {
3756           if (indicator_style == classify
3757               && (f->stat.st_mode & S_IXUGO))
3758             len += 1;
3759         }
3760       else if (S_ISDIR (filetype)
3761                || S_ISLNK (filetype)
3762                || S_ISFIFO (filetype)
3763                || S_ISSOCK (filetype)
3764                || S_ISDOOR (filetype)
3765                )
3766         len += 1;
3767     }
3768
3769   return len;
3770 }
3771
3772 static void
3773 print_many_per_line (void)
3774 {
3775   size_t row;                   /* Current row.  */
3776   size_t cols = calculate_columns (true);
3777   struct column_info const *line_fmt = &column_info[cols - 1];
3778
3779   /* Calculate the number of rows that will be in each column except possibly
3780      for a short column on the right.  */
3781   size_t rows = files_index / cols + (files_index % cols != 0);
3782
3783   for (row = 0; row < rows; row++)
3784     {
3785       size_t col = 0;
3786       size_t filesno = row;
3787       size_t pos = 0;
3788
3789       /* Print the next row.  */
3790       while (1)
3791         {
3792           size_t name_length = length_of_file_name_and_frills (files + filesno);
3793           size_t max_name_length = line_fmt->col_arr[col++];
3794           print_file_name_and_frills (files + filesno);
3795
3796           filesno += rows;
3797           if (filesno >= files_index)
3798             break;
3799
3800           indent (pos + name_length, pos + max_name_length);
3801           pos += max_name_length;
3802         }
3803       putchar ('\n');
3804     }
3805 }
3806
3807 static void
3808 print_horizontal (void)
3809 {
3810   size_t filesno;
3811   size_t pos = 0;
3812   size_t cols = calculate_columns (false);
3813   struct column_info const *line_fmt = &column_info[cols - 1];
3814   size_t name_length = length_of_file_name_and_frills (files);
3815   size_t max_name_length = line_fmt->col_arr[0];
3816
3817   /* Print first entry.  */
3818   print_file_name_and_frills (files);
3819
3820   /* Now the rest.  */
3821   for (filesno = 1; filesno < files_index; ++filesno)
3822     {
3823       size_t col = filesno % cols;
3824
3825       if (col == 0)
3826         {
3827           putchar ('\n');
3828           pos = 0;
3829         }
3830       else
3831         {
3832           indent (pos + name_length, pos + max_name_length);
3833           pos += max_name_length;
3834         }
3835
3836       print_file_name_and_frills (files + filesno);
3837
3838       name_length = length_of_file_name_and_frills (files + filesno);
3839       max_name_length = line_fmt->col_arr[col];
3840     }
3841   putchar ('\n');
3842 }
3843
3844 static void
3845 print_with_commas (void)
3846 {
3847   size_t filesno;
3848   size_t pos = 0;
3849
3850   for (filesno = 0; filesno < files_index; filesno++)
3851     {
3852       size_t len = length_of_file_name_and_frills (files + filesno);
3853
3854       if (filesno != 0)
3855         {
3856           char separator;
3857
3858           if (pos + len + 2 < line_length)
3859             {
3860               pos += 2;
3861               separator = ' ';
3862             }
3863           else
3864             {
3865               pos = 0;
3866               separator = '\n';
3867             }
3868
3869           putchar (',');
3870           putchar (separator);
3871         }
3872
3873       print_file_name_and_frills (files + filesno);
3874       pos += len;
3875     }
3876   putchar ('\n');
3877 }
3878
3879 /* Assuming cursor is at position FROM, indent up to position TO.
3880    Use a TAB character instead of two or more spaces whenever possible.  */
3881
3882 static void
3883 indent (size_t from, size_t to)
3884 {
3885   while (from < to)
3886     {
3887       if (tabsize != 0 && to / tabsize > (from + 1) / tabsize)
3888         {
3889           putchar ('\t');
3890           from += tabsize - from % tabsize;
3891         }
3892       else
3893         {
3894           putchar (' ');
3895           from++;
3896         }
3897     }
3898 }
3899
3900 /* Put DIRNAME/NAME into DEST, handling `.' and `/' properly.  */
3901 /* FIXME: maybe remove this function someday.  See about using a
3902    non-malloc'ing version of path_concat.  */
3903
3904 static void
3905 attach (char *dest, const char *dirname, const char *name)
3906 {
3907   const char *dirnamep = dirname;
3908
3909   /* Copy dirname if it is not ".".  */
3910   if (dirname[0] != '.' || dirname[1] != 0)
3911     {
3912       while (*dirnamep)
3913         *dest++ = *dirnamep++;
3914       /* Add '/' if `dirname' doesn't already end with it.  */
3915       if (dirnamep > dirname && dirnamep[-1] != '/')
3916         *dest++ = '/';
3917     }
3918   while (*name)
3919     *dest++ = *name++;
3920   *dest = 0;
3921 }
3922
3923 /* Allocate enough column info suitable for the current number of
3924    files and display columns, and initialize the info to represent the
3925    narrowest possible columns.  */
3926
3927 static void
3928 init_column_info (void)
3929 {
3930   size_t i;
3931   size_t max_cols = MIN (max_idx, files_index);
3932
3933   /* Currently allocated columns in column_info.  */
3934   static size_t column_info_alloc;
3935
3936   if (column_info_alloc < max_cols)
3937     {
3938       size_t new_column_info_alloc;
3939       size_t *p;
3940
3941       if (max_cols < max_idx / 2)
3942         {
3943           /* The number of columns is far less than the display width
3944              allows.  Grow the allocation, but only so that it's
3945              double the current requirements.  If the display is
3946              extremely wide, this avoids allocating a lot of memory
3947              that is never needed.  */
3948           column_info = xnrealloc (column_info, max_cols,
3949                                    2 * sizeof *column_info);
3950           new_column_info_alloc = 2 * max_cols;
3951         }
3952       else
3953         {
3954           column_info = xnrealloc (column_info, max_idx, sizeof *column_info);
3955           new_column_info_alloc = max_idx;
3956         }
3957
3958       /* Allocate the new size_t objects by computing the triangle
3959          formula n * (n + 1) / 2, except that we don't need to
3960          allocate the part of the triangle that we've already
3961          allocated.  Check for address arithmetic overflow.  */
3962       {
3963         size_t column_info_growth = new_column_info_alloc - column_info_alloc;
3964         size_t s = column_info_alloc + 1 + new_column_info_alloc;
3965         size_t t = s * column_info_growth;
3966         if (s < new_column_info_alloc || t / column_info_growth != s)
3967           xalloc_die ();
3968         p = xnmalloc (t / 2, sizeof *p);
3969       }
3970
3971       /* Grow the triangle by parceling out the cells just allocated.  */
3972       for (i = column_info_alloc; i < new_column_info_alloc; i++)
3973         {
3974           column_info[i].col_arr = p;
3975           p += i + 1;
3976         }
3977
3978       column_info_alloc = new_column_info_alloc;
3979     }
3980
3981   for (i = 0; i < max_cols; ++i)
3982     {
3983       size_t j;
3984
3985       column_info[i].valid_len = true;
3986       column_info[i].line_len = (i + 1) * MIN_COLUMN_WIDTH;
3987       for (j = 0; j <= i; ++j)
3988         column_info[i].col_arr[j] = MIN_COLUMN_WIDTH;
3989     }
3990 }
3991
3992 /* Calculate the number of columns needed to represent the current set
3993    of files in the current display width.  */
3994
3995 static size_t
3996 calculate_columns (bool by_columns)
3997 {
3998   size_t filesno;               /* Index into files.  */
3999   size_t cols;                  /* Number of files across.  */
4000
4001   /* Normally the maximum number of columns is determined by the
4002      screen width.  But if few files are available this might limit it
4003      as well.  */
4004   size_t max_cols = MIN (max_idx, files_index);
4005
4006   init_column_info ();
4007
4008   /* Compute the maximum number of possible columns.  */
4009   for (filesno = 0; filesno < files_index; ++filesno)
4010     {
4011       size_t name_length = length_of_file_name_and_frills (files + filesno);
4012       size_t i;
4013
4014       for (i = 0; i < max_cols; ++i)
4015         {
4016           if (column_info[i].valid_len)
4017             {
4018               size_t idx = (by_columns
4019                             ? filesno / ((files_index + i) / (i + 1))
4020                             : filesno % (i + 1));
4021               size_t real_length = name_length + (idx == i ? 0 : 2);
4022
4023               if (column_info[i].col_arr[idx] < real_length)
4024                 {
4025                   column_info[i].line_len += (real_length
4026                                               - column_info[i].col_arr[idx]);
4027                   column_info[i].col_arr[idx] = real_length;
4028                   column_info[i].valid_len = (column_info[i].line_len
4029                                               < line_length);
4030                 }
4031             }
4032         }
4033     }
4034
4035   /* Find maximum allowed columns.  */
4036   for (cols = max_cols; 1 < cols; --cols)
4037     {
4038       if (column_info[cols - 1].valid_len)
4039         break;
4040     }
4041
4042   return cols;
4043 }
4044
4045 void
4046 usage (int status)
4047 {
4048   if (status != EXIT_SUCCESS)
4049     fprintf (stderr, _("Try `%s --help' for more information.\n"),
4050              program_name);
4051   else
4052     {
4053       printf (_("Usage: %s [OPTION]... [FILE]...\n"), program_name);
4054       fputs (_("\
4055 List information about the FILEs (the current directory by default).\n\
4056 Sort entries alphabetically if none of -cftuSUX nor --sort.\n\
4057 \n\
4058 "), stdout);
4059       fputs (_("\
4060 Mandatory arguments to long options are mandatory for short options too.\n\
4061 "), stdout);
4062       fputs (_("\
4063   -a, --all                  do not ignore entries starting with .\n\
4064   -A, --almost-all           do not list implied . and ..\n\
4065       --author               with -l, print the author of each file\n\
4066   -b, --escape               print octal escapes for nongraphic characters\n\
4067 "), stdout);
4068       fputs (_("\
4069       --block-size=SIZE      use SIZE-byte blocks\n\
4070   -B, --ignore-backups       do not list implied entries ending with ~\n\
4071   -c                         with -lt: sort by, and show, ctime (time of last\n\
4072                                modification of file status information)\n\
4073                                with -l: show ctime and sort by name\n\
4074                                otherwise: sort by ctime\n\
4075 "), stdout);
4076       fputs (_("\
4077   -C                         list entries by columns\n\
4078       --color[=WHEN]         control whether color is used to distinguish file\n\
4079                                types.  WHEN may be `never', `always', or `auto'\n\
4080   -d, --directory            list directory entries instead of contents,\n\
4081                                and do not dereference symbolic links\n\
4082   -D, --dired                generate output designed for Emacs' dired mode\n\
4083 "), stdout);
4084       fputs (_("\
4085   -f                         do not sort, enable -aU, disable -lst\n\
4086   -F, --classify             append indicator (one of */=@|) to entries\n\
4087       --format=WORD          across -x, commas -m, horizontal -x, long -l,\n\
4088                                single-column -1, verbose -l, vertical -C\n\
4089       --full-time            like -l --time-style=full-iso\n\
4090 "), stdout);
4091       fputs (_("\
4092   -g                         like -l, but do not list owner\n\
4093   -G, --no-group             like -l, but do not list group\n\
4094   -h, --human-readable       with -l, print sizes in human readable format\n\
4095                                (e.g., 1K 234M 2G)\n\
4096       --si                   likewise, but use powers of 1000 not 1024\n\
4097   -H, --dereference-command-line\n\
4098                              follow symbolic links listed on the command line\n\
4099       --dereference-command-line-symlink-to-dir\n\
4100                              follow each command line symbolic link\n\
4101                              that points to a directory\n\
4102       --hide=PATTERN         do not list implied entries matching shell PATTERN\n\
4103                                (overridden by -a or -A)\n\
4104 "), stdout);
4105       fputs (_("\
4106       --indicator-style=WORD append indicator with style WORD to entry names:\n\
4107                                none (default), classify (-F), file-type (-p)\n\
4108   -i, --inode                with -l, print the index number of each file\n\
4109   -I, --ignore=PATTERN       do not list implied entries matching shell PATTERN\n\
4110   -k                         like --block-size=1K\n\
4111 "), stdout);
4112       fputs (_("\
4113   -l                         use a long listing format\n\
4114   -L, --dereference          when showing file information for a symbolic\n\
4115                                link, show information for the file the link\n\
4116                                references rather than for the link itself\n\
4117   -m                         fill width with a comma separated list of entries\n\
4118 "), stdout);
4119       fputs (_("\
4120   -n, --numeric-uid-gid      like -l, but list numeric UIDs and GIDs\n\
4121   -N, --literal              print raw entry names (don't treat e.g. control\n\
4122                                characters specially)\n\
4123   -o                         like -l, but do not list group information\n\
4124   -p, --file-type            append indicator (one of /=@|) to entries\n\
4125 "), stdout);
4126       fputs (_("\
4127   -q, --hide-control-chars   print ? instead of non graphic characters\n\
4128       --show-control-chars   show non graphic characters as-is (default\n\
4129                              unless program is `ls' and output is a terminal)\n\
4130   -Q, --quote-name           enclose entry names in double quotes\n\
4131       --quoting-style=WORD   use quoting style WORD for entry names:\n\
4132                                literal, locale, shell, shell-always, c, escape\n\
4133 "), stdout);
4134       fputs (_("\
4135   -r, --reverse              reverse order while sorting\n\
4136   -R, --recursive            list subdirectories recursively\n\
4137   -s, --size                 with -l, print size of each file, in blocks\n\
4138 "), stdout);
4139       fputs (_("\
4140   -S                         sort by file size\n\
4141       --sort=WORD            extension -X, none -U, size -S, time -t,\n\
4142                              version -v, status -c, time -t, atime -u,\n\
4143                              access -u, use -u\n\
4144       --time=WORD            with -l, show time as WORD instead of modification\n\
4145                              time: atime, access, use, ctime or status; use\n\
4146                              specified time as sort key if --sort=time\n\
4147 "), stdout);
4148       fputs (_("\
4149       --time-style=STYLE     with -l, show times using style STYLE:\n\
4150                              full-iso, long-iso, iso, locale, +FORMAT.\n\
4151                              FORMAT is interpreted like `date'; if FORMAT is\n\
4152                              FORMAT1<newline>FORMAT2, FORMAT1 applies to\n\
4153                              non-recent files and FORMAT2 to recent files;\n\
4154                              if STYLE is prefixed with `posix-', STYLE\n\
4155                              takes effect only outside the POSIX locale\n\
4156   -t                         sort by modification time\n\
4157   -T, --tabsize=COLS         assume tab stops at each COLS instead of 8\n\
4158 "), stdout);
4159       fputs (_("\
4160   -u                         with -lt: sort by, and show, access time\n\
4161                                with -l: show access time and sort by name\n\
4162                                otherwise: sort by access time\n\
4163   -U                         do not sort; list entries in directory order\n\
4164   -v                         sort by version\n\
4165 "), stdout);
4166       fputs (_("\
4167   -w, --width=COLS           assume screen width instead of current value\n\
4168   -x                         list entries by lines instead of by columns\n\
4169   -X                         sort alphabetically by entry extension\n\
4170   -1                         list one file per line\n\
4171 "), stdout);
4172       fputs (HELP_OPTION_DESCRIPTION, stdout);
4173       fputs (VERSION_OPTION_DESCRIPTION, stdout);
4174       fputs (_("\n\
4175 SIZE may be (or may be an integer optionally followed by) one of following:\n\
4176 kB 1000, K 1024, MB 1000*1000, M 1024*1024, and so on for G, T, P, E, Z, Y.\n\
4177 "), stdout);
4178       fputs (_("\
4179 \n\
4180 By default, color is not used to distinguish types of files.  That is\n\
4181 equivalent to using --color=none.  Using the --color option without the\n\
4182 optional WHEN argument is equivalent to using --color=always.  With\n\
4183 --color=auto, color codes are output only if standard output is connected\n\
4184 to a terminal (tty).\n\
4185 "), stdout);
4186       fputs (_("\
4187 \n\
4188 Exit status is 0 if OK, 1 if minor problems, 2 if serious trouble.\n\
4189 "), stdout);
4190       printf (_("\nReport bugs to <%s>.\n"), PACKAGE_BUGREPORT);
4191     }
4192   exit (status);
4193 }