/* du -- summarize disk usage                                                   This is the du utility
   Copyright (C) 1988-2018 Free Software Foundation, Inc.                       
                                                                                
   This program is free software: you can redistribute it and/or modify         
   it under the terms of the GNU General Public License as published by         
   the Free Software Foundation, either version 3 of the License, or            
   (at your option) any later version.                                          
                                                                                
   This program is distributed in the hope that it will be useful,              
   but WITHOUT ANY WARRANTY; without even the implied warranty of               
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the                
   GNU General Public License for more details.                                 
                                                                                
   You should have received a copy of the GNU General Public License            
   along with this program.  If not, see <https://www.gnu.org/licenses/>.  */   The GNUv3 license
                                                                                
/* Differences from the Unix du:                                                
   * Doesn't simply ignore the names of regular files given as arguments        
     when -a is given.                                                          
                                                                                
   By tege@sics.se, Torbjorn Granlund,                                          
   and djm@ai.mit.edu, David MacKenzie.                                         
   Variable blocks added by lm@sgi.com and eggert@twinsun.com.                  
   Rewritten to use nftw, then to use fts by Jim Meyering.  */                  
                                                                                
#include <config.h>                                                             Provides system specific information
#include <getopt.h>                                                             ...!includes auto-comment...
#include <sys/types.h>                                                          Provides system data types
#include <assert.h>                                                             ...!includes auto-comment...
#include "system.h"                                                             ...!includes auto-comment...
#include "argmatch.h"                                                           ...!includes auto-comment...
#include "argv-iter.h"                                                          ...!includes auto-comment...
#include "di-set.h"                                                             ...!includes auto-comment...
#include "die.h"                                                                ...!includes auto-comment...
#include "error.h"                                                              ...!includes auto-comment...
#include "exclude.h"                                                            ...!includes auto-comment...
#include "fprintftime.h"                                                        ...!includes auto-comment...
#include "human.h"                                                              ...!includes auto-comment...
#include "mountlist.h"                                                          ...!includes auto-comment...
#include "quote.h"                                                              ...!includes auto-comment...
#include "stat-size.h"                                                          ...!includes auto-comment...
#include "stat-time.h"                                                          ...!includes auto-comment...
#include "stdio--.h"                                                            ...!includes auto-comment...
#include "xfts.h"                                                               ...!includes auto-comment...
#include "xstrtol.h"                                                            ...!includes auto-comment...
                                                                                
extern bool fts_debug;                                                          Line 47
                                                                                
/* The official name of this program (e.g., no 'g' prefix).  */                 
#define PROGRAM_NAME "du"                                                       Line 50
                                                                                
#define AUTHORS \                                                               Line 52
  proper_name ("Torbjorn Granlund"), \                                          Line 53
  proper_name ("David MacKenzie"), \                                            Line 54
  proper_name ("Paul Eggert"), \                                                Line 55
  proper_name ("Jim Meyering")                                                  Line 56
                                                                                
#if DU_DEBUG                                                                    Line 58
# define FTS_CROSS_CHECK(Fts) fts_cross_check (Fts)                             Line 59
#else                                                                           Line 60
# define FTS_CROSS_CHECK(Fts)                                                   Line 61
#endif                                                                          Line 62
                                                                                
/* A set of dev/ino pairs to help identify files and directories                
   whose sizes have already been counted.  */                                   
static struct di_set *di_files;                                                 Line 66
                                                                                
/* A set containing a dev/ino pair for each local mount point directory.  */    
static struct di_set *di_mnt;                                                   Line 69
                                                                                
/* Keep track of the preceding "level" (depth in hierarchy)                     
   from one call of process_file to the next.  */                               
static size_t prev_level;                                                       Line 73
                                                                                
/* Define a class for collecting directory information. */                      
struct duinfo                                                                   Line 76
{                                                                               
  /* Size of files in directory.  */                                            
  uintmax_t size;                                                               Line 79
                                                                                
  /* Number of inodes in directory.  */                                         
  uintmax_t inodes;                                                             Line 82
                                                                                
  /* Latest timestamp found.  If tmax.tv_sec == TYPE_MINIMUM (time_t)           
     && tmax.tv_nsec < 0, no timestamp has been found.  */                      
  struct timespec tmax;                                                         Line 86
};                                                                              
                                                                                
/* Initialize directory data.  */                                               
static inline void                                                              Line 90
duinfo_init (struct duinfo *a)                                                  Line 91
{                                                                               
  a->size = 0;                                                                  Line 93
  a->inodes = 0;                                                                Line 94
  a->tmax.tv_sec = TYPE_MINIMUM (time_t);                                       Line 95
  a->tmax.tv_nsec = -1;                                                         Line 96
}                                                                               Block 2
                                                                                
/* Set directory data.  */                                                      
static inline void                                                              Line 100
duinfo_set (struct duinfo *a, uintmax_t size, struct timespec tmax)             Line 101
{                                                                               
  a->size = size;                                                               Line 103
  a->inodes = 1;                                                                Line 104
  a->tmax = tmax;                                                               Line 105
}                                                                               Block 3
                                                                                
/* Accumulate directory data.  */                                               
static inline void                                                              Line 109
duinfo_add (struct duinfo *a, struct duinfo const *b)                           Line 110
{                                                                               
  uintmax_t sum = a->size + b->size;                                            Line 112
  a->size = a->size <= sum ? sum : UINTMAX_MAX;                                 Line 113
  a->inodes = a->inodes + b->inodes;                                            Line 114
  if (timespec_cmp (a->tmax, b->tmax) < 0)                                      Line 115
    a->tmax = b->tmax;                                                          Line 116
}                                                                               Block 4
                                                                                
/* A structure for per-directory level information.  */                         
struct dulevel                                                                  Line 120
{                                                                               
  /* Entries in this directory.  */                                             
  struct duinfo ent;                                                            Line 123
                                                                                
  /* Total for subdirectories.  */                                              
  struct duinfo subdir;                                                         Line 126
};                                                                              
                                                                                
/* If true, display counts for all files, not just directories.  */             
static bool opt_all = false;                                                    Line 130
                                                                                
/* If true, rather than using the disk usage of each file,                      
   use the apparent size (a la stat.st_size).  */                               
static bool apparent_size = false;                                              Line 134
                                                                                
/* If true, count each hard link of files with multiple links.  */              
static bool opt_count_all = false;                                              Line 137
                                                                                
/* If true, hash all files to look for hard links.  */                          
static bool hash_all;                                                           Line 140
                                                                                
/* If true, output the NUL byte instead of a newline at the end of each line. */
static bool opt_nul_terminate_output = false;                                   Line 143
                                                                                
/* If true, print a grand total at the end.  */                                 
static bool print_grand_total = false;                                          Line 146
                                                                                
/* If nonzero, do not add sizes of subdirectories.  */                          
static bool opt_separate_dirs = false;                                          Line 149
                                                                                
/* Show the total for each directory (and file if --all) that is at             
   most MAX_DEPTH levels down from the root of the hierarchy.  The root         
   is at level 0, so 'du --max-depth=0' is equivalent to 'du -s'.  */           
static size_t max_depth = SIZE_MAX;                                             Line 154
                                                                                
/* Only output entries with at least this SIZE if positive,                     
   or at most if negative.  See --threshold option.  */                         
static intmax_t opt_threshold = 0;                                              Line 158
                                                                                
/* Human-readable options for output.  */                                       
static int human_output_opts;                                                   Line 161
                                                                                
/* Output inodes count instead of blocks used.  */                              
static bool opt_inodes = false;                                                 Line 164
                                                                                
/* If true, print most recently modified date, using the specified format.  */  
static bool opt_time = false;                                                   Line 167
                                                                                
/* Type of time to display. controlled by --time.  */                           
                                                                                
enum time_type                                                                  Line 171
  {                                                                             
    time_mtime,   /* default */                                                 Line 173
    time_ctime,                                                                 Line 174
    time_atime                                                                  Line 175
  };                                                                            Block 6
                                                                                
static enum time_type time_type = time_mtime;                                   Line 178
                                                                                
/* User specified date / time style */                                          
static char const *time_style = NULL;                                           Line 181
                                                                                
/* Format used to display date / time. Controlled by --time-style */            
static char const *time_format = NULL;                                          Line 184
                                                                                
/* The local time zone rules, as per the TZ environment variable.  */           
static timezone_t localtz;                                                      Line 187
                                                                                
/* The units to use when printing sizes.  */                                    
static uintmax_t output_block_size;                                             Line 190
                                                                                
/* File name patterns to exclude.  */                                           
static struct exclude *exclude;                                                 Line 193
                                                                                
/* Grand total size of all args, in bytes. Also latest modified date. */        
static struct duinfo tot_dui;                                                   Line 196
                                                                                
#define IS_DIR_TYPE(Type) \                                                     Line 198
  ((Type) == FTS_DP  \                                                          Line 199
   || (Type) == FTS_DNR)                                                        Line 200
                                                                                
/* For long options that have no equivalent short option, use a                 
   non-character as a pseudo short option, starting with CHAR_MAX + 1.  */      
enum                                                                            Line 204
{                                                                               
  APPARENT_SIZE_OPTION = CHAR_MAX + 1,                                          Line 206
  EXCLUDE_OPTION,                                                               Line 207
  FILES0_FROM_OPTION,                                                           Line 208
  HUMAN_SI_OPTION,                                                              Line 209
  FTS_DEBUG,                                                                    Line 210
  TIME_OPTION,                                                                  Line 211
  TIME_STYLE_OPTION,                                                            Line 212
  INODES_OPTION                                                                 Line 213
};                                                                              Block 7
                                                                                
static struct option const long_options[] =                                     Line 216
{                                                                               
  {"all", no_argument, NULL, 'a'},                                              Line 218
  {"apparent-size", no_argument, NULL, APPARENT_SIZE_OPTION},                   Line 219
  {"block-size", required_argument, NULL, 'B'},                                 Line 220
  {"bytes", no_argument, NULL, 'b'},                                            Line 221
  {"count-links", no_argument, NULL, 'l'},                                      Line 222
  /* {"-debug", no_argument, NULL, FTS_DEBUG}, */                               
  {"dereference", no_argument, NULL, 'L'},                                      Line 224
  {"dereference-args", no_argument, NULL, 'D'},                                 Line 225
  {"exclude", required_argument, NULL, EXCLUDE_OPTION},                         Line 226
  {"exclude-from", required_argument, NULL, 'X'},                               Line 227
  {"files0-from", required_argument, NULL, FILES0_FROM_OPTION},                 Line 228
  {"human-readable", no_argument, NULL, 'h'},                                   Line 229
  {"inodes", no_argument, NULL, INODES_OPTION},                                 Line 230
  {"si", no_argument, NULL, HUMAN_SI_OPTION},                                   Line 231
  {"max-depth", required_argument, NULL, 'd'},                                  Line 232
  {"null", no_argument, NULL, '0'},                                             Line 233
  {"no-dereference", no_argument, NULL, 'P'},                                   Line 234
  {"one-file-system", no_argument, NULL, 'x'},                                  Line 235
  {"separate-dirs", no_argument, NULL, 'S'},                                    Line 236
  {"summarize", no_argument, NULL, 's'},                                        Line 237
  {"total", no_argument, NULL, 'c'},                                            Line 238
  {"threshold", required_argument, NULL, 't'},                                  Line 239
  {"time", optional_argument, NULL, TIME_OPTION},                               Line 240
  {"time-style", required_argument, NULL, TIME_STYLE_OPTION},                   Line 241
  {GETOPT_HELP_OPTION_DECL},                                                    Line 242
  {GETOPT_VERSION_OPTION_DECL},                                                 Line 243
  {NULL, 0, NULL, 0}                                                            Line 244
};                                                                              Block 8
                                                                                
static char const *const time_args[] =                                          Line 247
{                                                                               
  "atime", "access", "use", "ctime", "status", NULL                             Line 249
};                                                                              Block 9
static enum time_type const time_types[] =                                      Line 251
{                                                                               
  time_atime, time_atime, time_atime, time_ctime, time_ctime                    Line 253
};                                                                              Block 10
ARGMATCH_VERIFY (time_args, time_types);                                        Line 255
                                                                                
/* 'full-iso' uses full ISO-style dates and times.  'long-iso' uses longer      
   ISO-style timestamps, though shorter than 'full-iso'.  'iso' uses shorter    
   ISO-style timestamps.  */                                                    
enum time_style                                                                 Line 260
  {                                                                             
    full_iso_time_style,       /* --time-style=full-iso */                      Line 262
    long_iso_time_style,       /* --time-style=long-iso */                      Line 263
    iso_time_style        /* --time-style=iso */                                Line 264
  };                                                                            Block 11
                                                                                
static char const *const time_style_args[] =                                    Line 267
{                                                                               
  "full-iso", "long-iso", "iso", NULL                                           Line 269
};                                                                              Block 12
static enum time_style const time_style_types[] =                               Line 271
{                                                                               
  full_iso_time_style, long_iso_time_style, iso_time_style                      Line 273
};                                                                              Block 13
ARGMATCH_VERIFY (time_style_args, time_style_types);                            Line 275
                                                                                
void                                                                            Line 277
usage (int status)                                                              Line 278
{                                                                               
  if (status != EXIT_SUCCESS)                                                   Line 280
    emit_try_help ();                                                           ...!common auto-comment...
  else                                                                          Line 282
    {                                                                           
      printf (_("\                                                              Line 284
Usage: %s [OPTION]... [FILE]...\n\                                              Line 285
  or:  %s [OPTION]... --files0-from=F\n\                                        Line 286
"), program_name, program_name);                                                Line 287
      fputs (_("\                                                               Line 288
Summarize disk usage of the set of FILEs, recursively for directories.\n\       Line 289
"), stdout);                                                                    Line 290
                                                                                
      emit_mandatory_arg_note ();                                               ...!common auto-comment...
                                                                                
      fputs (_("\                                                               Line 294
  -0, --null            end each output line with NUL, not newline\n\           Line 295
  -a, --all             write counts for all files, not just directories\n\     Line 296
      --apparent-size   print apparent sizes, rather than disk usage; although\ Line 297
\n\                                                                             
                          the apparent size is usually smaller, it may be\n\    Line 299
                          larger due to holes in ('sparse') files, internal\n\  Line 300
                          fragmentation, indirect blocks, and the like\n\       Line 301
"), stdout);                                                                    Line 302
      fputs (_("\                                                               Line 303
  -B, --block-size=SIZE  scale sizes by SIZE before printing them; e.g.,\n\     Line 304
                           '-BM' prints sizes in units of 1,048,576 bytes;\n\   Line 305
                           see SIZE format below\n\                             Line 306
  -b, --bytes           equivalent to '--apparent-size --block-size=1'\n\       Line 307
  -c, --total           produce a grand total\n\                                Line 308
  -D, --dereference-args  dereference only symlinks that are listed on the\n\   Line 309
                          command line\n\                                       Line 310
  -d, --max-depth=N     print the total for a directory (or file, with --all)\n\Line 311
                          only if it is N or fewer levels below the command\n\  Line 312
                          line argument;  --max-depth=0 is the same as\n\       Line 313
                          --summarize\n\                                        Line 314
"), stdout);                                                                    Line 315
      fputs (_("\                                                               Line 316
      --files0-from=F   summarize disk usage of the\n\                          Line 317
                          NUL-terminated file names specified in file F;\n\     Line 318
                          if F is -, then read names from standard input\n\     Line 319
  -H                    equivalent to --dereference-args (-D)\n\                Line 320
  -h, --human-readable  print sizes in human readable format (e.g., 1K 234M 2G)\Line 321
\n\                                                                             
      --inodes          list inode usage information instead of block usage\n\  Line 323
"), stdout);                                                                    Line 324
      fputs (_("\                                                               Line 325
  -k                    like --block-size=1K\n\                                 Line 326
  -L, --dereference     dereference all symbolic links\n\                       Line 327
  -l, --count-links     count sizes many times if hard linked\n\                Line 328
  -m                    like --block-size=1M\n\                                 Line 329
"), stdout);                                                                    Line 330
      fputs (_("\                                                               Line 331
  -P, --no-dereference  don't follow any symbolic links (this is the default)\n\Line 332
  -S, --separate-dirs   for directories do not include size of subdirectories\n\Line 333
      --si              like -h, but use powers of 1000 not 1024\n\             Line 334
  -s, --summarize       display only a total for each argument\n\               Line 335
"), stdout);                                                                    Line 336
      fputs (_("\                                                               Line 337
  -t, --threshold=SIZE  exclude entries smaller than SIZE if positive,\n\       Line 338
                          or entries greater than SIZE if negative\n\           Line 339
      --time            show time of the last modification of any file in the\n\Line 340
                          directory, or any of its subdirectories\n\            Line 341
      --time=WORD       show time as WORD instead of modification time:\n\      Line 342
                          atime, access, use, ctime or status\n\                Line 343
      --time-style=STYLE  show times using STYLE, which can be:\n\              Line 344
                            full-iso, long-iso, iso, or +FORMAT;\n\             Line 345
                            FORMAT is interpreted like in 'date'\n\             Line 346
"), stdout);                                                                    Line 347
      fputs (_("\                                                               Line 348
  -X, --exclude-from=FILE  exclude files that match any pattern in FILE\n\      Line 349
      --exclude=PATTERN    exclude files that match PATTERN\n\                  Line 350
  -x, --one-file-system    skip directories on different file systems\n\        Line 351
"), stdout);                                                                    Line 352
      fputs (HELP_OPTION_DESCRIPTION, stdout);                                  Line 353
      fputs (VERSION_OPTION_DESCRIPTION, stdout);                               Line 354
      emit_blocksize_note ("DU");                                               Line 355
      emit_size_note ();                                                        Line 356
      emit_ancillary_info (PROGRAM_NAME);                                       Line 357
    }                                                                           
  exit (status);                                                                Line 359
}                                                                               Block 14
                                                                                
/* Try to insert the INO/DEV pair into DI_SET.                                  
   Return true if the pair is successfully inserted,                            
   false if the pair was already there.  */                                     
static bool                                                                     Line 365
hash_ins (struct di_set *di_set, ino_t ino, dev_t dev)                          Line 366
{                                                                               
  int inserted = di_set_insert (di_set, dev, ino);                              Line 368
  if (inserted < 0)                                                             Line 369
    xalloc_die ();                                                              ...!common auto-comment...
  return inserted;                                                              Line 371
}                                                                               Block 15
                                                                                
/* FIXME: this code is nearly identical to code in date.c  */                   
/* Display the date and time in WHEN according to the format specified          
   in FORMAT.  */                                                               
                                                                                
static void                                                                     Line 378
show_date (const char *format, struct timespec when, timezone_t tz)             Line 379
{                                                                               
  struct tm tm;                                                                 Line 381
  if (localtime_rz (tz, &when.tv_sec, &tm))                                     Line 382
    fprintftime (stdout, format, &tm, tz, when.tv_nsec);                        Line 383
  else                                                                          Line 384
    {                                                                           
      char buf[INT_BUFSIZE_BOUND (intmax_t)];                                   Line 386
      char *when_str = timetostr (when.tv_sec, buf);                            Line 387
      error (0, 0, _("time %s is out of range"), quote (when_str));             Line 388
      fputs (when_str, stdout);                                                 Line 389
    }                                                                           
}                                                                               Block 16
                                                                                
/* Print N_BYTES.  Convert it to a readable value before printing.  */          
                                                                                
static void                                                                     Line 395
print_only_size (uintmax_t n_bytes)                                             Line 396
{                                                                               
  char buf[LONGEST_HUMAN_READABLE + 1];                                         Line 398
  fputs ((n_bytes == UINTMAX_MAX                                                Line 399
          ? _("Infinity")                                                       Line 400
          : human_readable (n_bytes, buf, human_output_opts,                    Line 401
                            1, output_block_size)),                             Line 402
         stdout);                                                               Line 403
}                                                                               Block 17
                                                                                
/* Print size (and optionally time) indicated by *PDUI, followed by STRING.  */ 
                                                                                
static void                                                                     Line 408
print_size (const struct duinfo *pdui, const char *string)                      Line 409
{                                                                               
  print_only_size (opt_inodes                                                   Line 411
                   ? pdui->inodes                                               Line 412
                   : pdui->size);                                               Line 413
                                                                                
  if (opt_time)                                                                 Line 415
    {                                                                           
      putchar ('\t');                                                           Line 417
      show_date (time_format, pdui->tmax, localtz);                             Line 418
    }                                                                           
  printf ("\t%s%c", string, opt_nul_terminate_output ? '\0' : '\n');            Line 420
  fflush (stdout);                                                              Line 421
}                                                                               Block 18
                                                                                
/* Fill the di_mnt set with local mount point dev/ino pairs.  */                
                                                                                
static void                                                                     Line 426
fill_mount_table (void)                                                         Line 427
{                                                                               
  struct mount_entry *mnt_ent = read_file_system_list (false);                  Line 429
  while (mnt_ent)                                                               Line 430
    {                                                                           
      struct mount_entry *mnt_free;                                             Line 432
      if (!mnt_ent->me_remote && !mnt_ent->me_dummy)                            Line 433
        {                                                                       
          struct stat buf;                                                      Line 435
          if (!stat (mnt_ent->me_mountdir, &buf))                               Line 436...!syscalls auto-comment...
            hash_ins (di_mnt, buf.st_ino, buf.st_dev);                          Line 437
          else                                                                  Line 438
            {                                                                   
              /* Ignore stat failure.  False positives are too common.          
                 E.g., "Permission denied" on /run/user/<name>/gvfs.  */        
            }                                                                   
        }                                                                       
                                                                                
      mnt_free = mnt_ent;                                                       Line 445
      mnt_ent = mnt_ent->me_next;                                               Line 446
      free_mount_entry (mnt_free);                                              Line 447
    }                                                                           
}                                                                               Block 19
                                                                                
/* This function checks whether any of the directories in the cycle that        
   fts detected is a mount point.  */                                           
                                                                                
static bool                                                                     Line 454
mount_point_in_fts_cycle (FTSENT const *ent)                                    Line 455
{                                                                               
  FTSENT const *cycle_ent = ent->fts_cycle;                                     Line 457
                                                                                
  if (!di_mnt)                                                                  Line 459
    {                                                                           
      /* Initialize the set of dev,inode pairs.  */                             
      di_mnt = di_set_alloc ();                                                 Line 462
      if (!di_mnt)                                                              Line 463
        xalloc_die ();                                                          ...!common auto-comment...
                                                                                
      fill_mount_table ();                                                      Line 466
    }                                                                           
                                                                                
  while (ent && ent != cycle_ent)                                               Line 469
    {                                                                           
      if (di_set_lookup (di_mnt, ent->fts_statp->st_dev,                        Line 471
                         ent->fts_statp->st_ino) > 0)                           Line 472
        {                                                                       
          return true;                                                          Line 474
        }                                                                       
      ent = ent->fts_parent;                                                    Line 476
    }                                                                           
                                                                                
  return false;                                                                 Line 479
}                                                                               Block 20
                                                                                
/* This function is called once for every file system object that fts           
   encounters.  fts does a depth-first traversal.  This function knows          
   that and accumulates per-directory totals based on changes in                
   the depth of the current entry.  It returns true on success.  */             
                                                                                
static bool                                                                     Line 487
process_file (FTS *fts, FTSENT *ent)                                            Line 488
{                                                                               
  bool ok = true;                                                               Line 490
  struct duinfo dui;                                                            Line 491
  struct duinfo dui_to_print;                                                   Line 492
  size_t level;                                                                 Line 493
  static size_t n_alloc;                                                        Line 494
  /* First element of the structure contains:                                   
     The sum of the st_size values of all entries in the single directory       
     at the corresponding level.  Although this does include the st_size        
     corresponding to each subdirectory, it does not include the size of        
     any file in a subdirectory. Also corresponding last modified date.         
     Second element of the structure contains:                                  
     The sum of the sizes of all entries in the hierarchy at or below the       
     directory at the specified level.  */                                      
  static struct dulevel *dulvl;                                                 Line 503
                                                                                
  const char *file = ent->fts_path;                                             Line 505
  const struct stat *sb = ent->fts_statp;                                       Line 506
  int info = ent->fts_info;                                                     Line 507
                                                                                
  if (info == FTS_DNR)                                                          Line 509
    {                                                                           
      /* An error occurred, but the size is known, so count it.  */             
      error (0, ent->fts_errno, _("cannot read directory %s"), quoteaf (file)); Line 512
      ok = false;                                                               Line 513
    }                                                                           
  else if (info != FTS_DP)                                                      Line 515
    {                                                                           
      bool excluded = excluded_file_name (exclude, file);                       Line 517
      if (! excluded)                                                           Line 518
        {                                                                       
          /* Make the stat buffer *SB valid, or fail noisily.  */               
                                                                                
          if (info == FTS_NSOK)                                                 Line 522
            {                                                                   
              fts_set (fts, ent, FTS_AGAIN);                                    Line 524
              FTSENT const *e = fts_read (fts);                                 Line 525...!syscalls auto-comment...
              assert (e == ent);                                                Line 526
              info = ent->fts_info;                                             Line 527
            }                                                                   
                                                                                
          if (info == FTS_NS || info == FTS_SLNONE)                             Line 530
            {                                                                   
              error (0, ent->fts_errno, _("cannot access %s"), quoteaf (file)); Line 532
              return false;                                                     Line 533
            }                                                                   
                                                                                
          /* The --one-file-system (-x) option cannot exclude anything          
             specified on the command-line.  By definition, it can exclude      
             a file or directory only when its device number is different       
             from that of its just-processed parent directory, and du does      
             not process the parent of a command-line argument.  */             
          if (fts->fts_options & FTS_XDEV                                       Line 541
              && FTS_ROOTLEVEL < ent->fts_level                                 Line 542
              && fts->fts_dev != sb->st_dev)                                    Line 543
            excluded = true;                                                    Line 544
        }                                                                       
                                                                                
      if (excluded                                                              Line 547
          || (! opt_count_all                                                   Line 548
              && (hash_all || (! S_ISDIR (sb->st_mode) && 1 < sb->st_nlink))    Line 549
              && ! hash_ins (di_files, sb->st_ino, sb->st_dev)))                Line 550
        {                                                                       
          /* If ignoring a directory in preorder, skip its children.            
             Ignore the next fts_read output too, as it's a postorder           
             visit to the same directory.  */                                   
          if (info == FTS_D)                                                    Line 555
            {                                                                   
              fts_set (fts, ent, FTS_SKIP);                                     Line 557
              FTSENT const *e = fts_read (fts);                                 Line 558...!syscalls auto-comment...
              assert (e == ent);                                                Line 559
            }                                                                   
                                                                                
          return true;                                                          Line 562
        }                                                                       
                                                                                
      switch (info)                                                             Line 565
        {                                                                       
        case FTS_D:                                                             Line 567
          return true;                                                          Line 568
                                                                                
        case FTS_ERR:                                                           Line 570
          /* An error occurred, but the size is known, so count it.  */         
          error (0, ent->fts_errno, "%s", quotef (file));                       Line 572
          ok = false;                                                           Line 573
          break;                                                                Line 574
                                                                                
        case FTS_DC:                                                            Line 576
          /* If not following symlinks and not a (bind) mount point.  */        
          if (cycle_warning_required (fts, ent)                                 Line 578
              && ! mount_point_in_fts_cycle (ent))                              Line 579
            {                                                                   
              emit_cycle_warning (file);                                        Line 581
              return false;                                                     Line 582
            }                                                                   
          return true;                                                          Line 584
        }                                                                       
    }                                                                           
                                                                                
  duinfo_set (&dui,                                                             Line 588
              (apparent_size                                                    Line 589
               ? MAX (0, sb->st_size)                                           Line 590
               : (uintmax_t) ST_NBLOCKS (*sb) * ST_NBLOCKSIZE),                 Line 591
              (time_type == time_mtime ? get_stat_mtime (sb)                    Line 592
               : time_type == time_atime ? get_stat_atime (sb)                  Line 593
               : get_stat_ctime (sb)));                                         Line 594
                                                                                
  level = ent->fts_level;                                                       Line 596
  dui_to_print = dui;                                                           Line 597
                                                                                
  if (n_alloc == 0)                                                             Line 599
    {                                                                           
      n_alloc = level + 10;                                                     Line 601
      dulvl = xcalloc (n_alloc, sizeof *dulvl);                                 Line 602
    }                                                                           
  else                                                                          Line 604
    {                                                                           
      if (level == prev_level)                                                  Line 606
        {                                                                       
          /* This is usually the most common case.  Do nothing.  */             
        }                                                                       
      else if (level > prev_level)                                              Line 610
        {                                                                       
          /* Descending the hierarchy.                                          
             Clear the accumulators for *all* levels between prev_level         
             and the current one.  The depth may change dramatically,           
             e.g., from 1 to 10.  */                                            
                                                                                
          if (n_alloc <= level)                                                 Line 617
            {                                                                   
              dulvl = xnrealloc (dulvl, level, 2 * sizeof *dulvl);              Line 619
              n_alloc = level * 2;                                              Line 620
            }                                                                   
                                                                                
          for (size_t i = prev_level + 1; i <= level; i++)                      Line 623
            {                                                                   
              duinfo_init (&dulvl[i].ent);                                      Line 625
              duinfo_init (&dulvl[i].subdir);                                   Line 626
            }                                                                   
        }                                                                       
      else /* level < prev_level */                                             Line 629
        {                                                                       
          /* Ascending the hierarchy.                                           
             Process a directory only after all entries in that                 
             directory have been processed.  When the depth decreases,          
             propagate sums from the children (prev_level) to the parent.       
             Here, the current level is always one smaller than the             
             previous one.  */                                                  
          assert (level == prev_level - 1);                                     Line 637
          duinfo_add (&dui_to_print, &dulvl[prev_level].ent);                   Line 638
          if (!opt_separate_dirs)                                               Line 639
            duinfo_add (&dui_to_print, &dulvl[prev_level].subdir);              Line 640
          duinfo_add (&dulvl[level].subdir, &dulvl[prev_level].ent);            Line 641
          duinfo_add (&dulvl[level].subdir, &dulvl[prev_level].subdir);         Line 642
        }                                                                       
    }                                                                           
                                                                                
  prev_level = level;                                                           Line 646
                                                                                
  /* Let the size of a directory entry contribute to the total for the          
     containing directory, unless --separate-dirs (-S) is specified.  */        
  if (! (opt_separate_dirs && IS_DIR_TYPE (info)))                              Line 650
    duinfo_add (&dulvl[level].ent, &dui);                                       Line 651
                                                                                
  /* Even if this directory is unreadable or we can't chdir into it,            
     do let its size contribute to the total. */                                
  duinfo_add (&tot_dui, &dui);                                                  Line 655
                                                                                
  if ((IS_DIR_TYPE (info) && level <= max_depth)                                Line 657
      || (opt_all && level <= max_depth)                                        Line 658
      || level == 0)                                                            Line 659
    {                                                                           
      /* Print or elide this entry according to the --threshold option.  */     
      uintmax_t v = opt_inodes ? dui_to_print.inodes : dui_to_print.size;       Line 662
      if (opt_threshold < 0                                                     Line 663
          ? v <= -opt_threshold                                                 Line 664
          : v >= opt_threshold)                                                 Line 665
        print_size (&dui_to_print, file);                                       Line 666
    }                                                                           
                                                                                
  return ok;                                                                    Line 669
}                                                                               Block 21
                                                                                
/* Recursively print the sizes of the directories (and, if selected, files)     
   named in FILES, the last entry of which is NULL.                             
   BIT_FLAGS controls how fts works.                                            
   Return true if successful.  */                                               
                                                                                
static bool                                                                     Line 677
du_files (char **files, int bit_flags)                                          Line 678
{                                                                               
  bool ok = true;                                                               Line 680
                                                                                
  if (*files)                                                                   Line 682
    {                                                                           
      FTS *fts = xfts_open (files, bit_flags, NULL);                            Line 684...!syscalls auto-comment...
                                                                                
      while (1)                                                                 Line 686
        {                                                                       
          FTSENT *ent;                                                          Line 688
                                                                                
          ent = fts_read (fts);                                                 Line 690...!syscalls auto-comment...
          if (ent == NULL)                                                      Line 691
            {                                                                   
              if (errno != 0)                                                   Line 693
                {                                                               
                  error (0, errno, _("fts_read failed: %s"),                    Line 695
                         quotef (fts->fts_path));                               Line 696
                  ok = false;                                                   Line 697
                }                                                               
                                                                                
              /* When exiting this loop early, be careful to reset the          
                 global, prev_level, used in process_file.  Otherwise, its      
                 (level == prev_level - 1) assertion could fail.  */            
              prev_level = 0;                                                   Line 703
              break;                                                            Line 704
            }                                                                   
          FTS_CROSS_CHECK (fts);                                                Line 706
                                                                                
          ok &= process_file (fts, ent);                                        Line 708
        }                                                                       
                                                                                
      if (fts_close (fts) != 0)                                                 Line 711...!syscalls auto-comment...
        {                                                                       
          error (0, errno, _("fts_close failed"));                              Line 713
          ok = false;                                                           Line 714
        }                                                                       
    }                                                                           
                                                                                
  return ok;                                                                    Line 718
}                                                                               Block 22
                                                                                
int                                                                             
main (int argc, char **argv)                                                    Line 722
{                                                                               
  char *cwd_only[2];                                                            Line 724
  bool max_depth_specified = false;                                             Line 725
  bool ok = true;                                                               Line 726
  char *files_from = NULL;                                                      Line 727
                                                                                
  /* Bit flags that control how fts works.  */                                  
  int bit_flags = FTS_NOSTAT;                                                   Line 730
                                                                                
  /* Select one of the three FTS_ options that control if/when                  
     to follow a symlink.  */                                                   
  int symlink_deref_bits = FTS_PHYSICAL;                                        Line 734
                                                                                
  /* If true, display only a total for each argument. */                        
  bool opt_summarize_only = false;                                              Line 737
                                                                                
  cwd_only[0] = bad_cast (".");                                                 Line 739
  cwd_only[1] = NULL;                                                           Line 740
                                                                                
  initialize_main (&argc, &argv);                                               VMS-specific entry point handling wildcard expansion
  set_program_name (argv[0]);                                                   Retains program name and discards path
  setlocale (LC_ALL, "");                                                       Sets up internationalization (i18n)
  bindtextdomain (PACKAGE, LOCALEDIR);                                          Assigns i18n directorySets text domain for _() [gettext()] function
  textdomain (PACKAGE);                                                         Sets text domain for _() [gettext()] function
                                                                                
  atexit (close_stdout);                                                        Close stdout on exit (see gnulib)
                                                                                
  exclude = new_exclude ();                                                     Line 750
                                                                                
  human_options (getenv ("DU_BLOCK_SIZE"),                                      Line 752
                 &human_output_opts, &output_block_size);                       Line 753
                                                                                
  while (true)                                                                  Line 755
    {                                                                           
      int oi = -1;                                                              Line 757
      int c = getopt_long (argc, argv, "0abd:chHklmst:xB:DLPSX:",               Line 758
                           long_options, &oi);                                  Line 759
      if (c == -1)                                                              Line 760
        break;                                                                  Line 761
                                                                                
      switch (c)                                                                Line 763
        {                                                                       
#if DU_DEBUG                                                                    Line 765
        case FTS_DEBUG:                                                         Line 766
          fts_debug = true;                                                     Line 767
          break;                                                                Line 768
#endif                                                                          Line 769
                                                                                
        case '0':                                                               Line 771
          opt_nul_terminate_output = true;                                      Line 772
          break;                                                                Line 773
                                                                                
        case 'a':                                                               Line 775
          opt_all = true;                                                       Line 776
          break;                                                                Line 777
                                                                                
        case APPARENT_SIZE_OPTION:                                              Line 779
          apparent_size = true;                                                 Line 780
          break;                                                                Line 781
                                                                                
        case 'b':                                                               Line 783
          apparent_size = true;                                                 Line 784
          human_output_opts = 0;                                                Line 785
          output_block_size = 1;                                                Line 786
          break;                                                                Line 787
                                                                                
        case 'c':                                                               Line 789
          print_grand_total = true;                                             Line 790
          break;                                                                Line 791
                                                                                
        case 'h':                                                               Line 793
          human_output_opts = human_autoscale | human_SI | human_base_1024;     Line 794
          output_block_size = 1;                                                Line 795
          break;                                                                Line 796
                                                                                
        case HUMAN_SI_OPTION:                                                   Line 798
          human_output_opts = human_autoscale | human_SI;                       Line 799
          output_block_size = 1;                                                Line 800
          break;                                                                Line 801
                                                                                
        case 'k':                                                               Line 803
          human_output_opts = 0;                                                Line 804
          output_block_size = 1024;                                             Line 805
          break;                                                                Line 806
                                                                                
        case 'd':  /* --max-depth=N */                                          Line 808
          {                                                                     
            unsigned long int tmp_ulong;                                        Line 810
            if (xstrtoul (optarg, NULL, 0, &tmp_ulong, NULL) == LONGINT_OK      Line 811
                && tmp_ulong <= SIZE_MAX)                                       Line 812
              {                                                                 
                max_depth_specified = true;                                     Line 814
                max_depth = tmp_ulong;                                          Line 815
              }                                                                 
            else                                                                Line 817
              {                                                                 
                error (0, 0, _("invalid maximum depth %s"),                     Line 819
                       quote (optarg));                                         Line 820
                ok = false;                                                     Line 821
              }                                                                 
          }                                                                     
          break;                                                                Line 824
                                                                                
        case 'm':                                                               Line 826
          human_output_opts = 0;                                                Line 827
          output_block_size = 1024 * 1024;                                      Line 828
          break;                                                                Line 829
                                                                                
        case 'l':                                                               Line 831
          opt_count_all = true;                                                 Line 832
          break;                                                                Line 833
                                                                                
        case 's':                                                               Line 835
          opt_summarize_only = true;                                            Line 836
          break;                                                                Line 837
                                                                                
        case 't':                                                               Line 839
          {                                                                     
            enum strtol_error e;                                                Line 841
            e = xstrtoimax (optarg, NULL, 0, &opt_threshold, "kKmMGTPEZY0");    Line 842
            if (e != LONGINT_OK)                                                Line 843
              xstrtol_fatal (e, oi, c, long_options, optarg);                   Line 844
            if (opt_threshold == 0 && *optarg == '-')                           Line 845
              {                                                                 
                /* Do not allow -0, as this wouldn't make sense anyway.  */     
                die (EXIT_FAILURE, 0, _("invalid --threshold argument '-0'"));  Line 848
              }                                                                 
          }                                                                     
          break;                                                                Line 851
                                                                                
        case 'x':                                                               Line 853
          bit_flags |= FTS_XDEV;                                                Line 854
          break;                                                                Line 855
                                                                                
        case 'B':                                                               Line 857
          {                                                                     
            enum strtol_error e = human_options (optarg, &human_output_opts,    Line 859
                                                 &output_block_size);           Line 860
            if (e != LONGINT_OK)                                                Line 861
              xstrtol_fatal (e, oi, c, long_options, optarg);                   Line 862
          }                                                                     
          break;                                                                Line 864
                                                                                
        case 'H':  /* NOTE: before 2008-12, -H was equivalent to --si.  */      Line 866
        case 'D':                                                               Line 867
          symlink_deref_bits = FTS_COMFOLLOW | FTS_PHYSICAL;                    Line 868
          break;                                                                Line 869
                                                                                
        case 'L': /* --dereference */                                           Line 871
          symlink_deref_bits = FTS_LOGICAL;                                     Line 872
          break;                                                                Line 873
                                                                                
        case 'P': /* --no-dereference */                                        Line 875
          symlink_deref_bits = FTS_PHYSICAL;                                    Line 876
          break;                                                                Line 877
                                                                                
        case 'S':                                                               Line 879
          opt_separate_dirs = true;                                             Line 880
          break;                                                                Line 881
                                                                                
        case 'X':                                                               Line 883
          if (add_exclude_file (add_exclude, exclude, optarg,                   Line 884
                                EXCLUDE_WILDCARDS, '\n'))                       Line 885
            {                                                                   
              error (0, errno, "%s", quotef (optarg));                          Line 887
              ok = false;                                                       Line 888
            }                                                                   
          break;                                                                Line 890
                                                                                
        case FILES0_FROM_OPTION:                                                Line 892
          files_from = optarg;                                                  Line 893
          break;                                                                Line 894
                                                                                
        case EXCLUDE_OPTION:                                                    Line 896
          add_exclude (exclude, optarg, EXCLUDE_WILDCARDS);                     Line 897
          break;                                                                Line 898
                                                                                
        case INODES_OPTION:                                                     Line 900
          opt_inodes = true;                                                    Line 901
          break;                                                                Line 902
                                                                                
        case TIME_OPTION:                                                       Line 904
          opt_time = true;                                                      Line 905
          time_type =                                                           Line 906
            (optarg                                                             Line 907
             ? XARGMATCH ("--time", optarg, time_args, time_types)              Line 908
             : time_mtime);                                                     Line 909
          localtz = tzalloc (getenv ("TZ"));                                    Line 910
          break;                                                                Line 911
                                                                                
        case TIME_STYLE_OPTION:                                                 Line 913
          time_style = optarg;                                                  Line 914
          break;                                                                Line 915
                                                                                
        case_GETOPT_HELP_CHAR;                                                  Line 917
                                                                                
        case_GETOPT_VERSION_CHAR (PROGRAM_NAME, AUTHORS);                       Line 919
                                                                                
        default:                                                                Line 921
          ok = false;                                                           Line 922
        }                                                                       
    }                                                                           
                                                                                
  if (!ok)                                                                      Line 926
    usage (EXIT_FAILURE);                                                       Line 927
                                                                                
  if (opt_all && opt_summarize_only)                                            Line 929
    {                                                                           
      error (0, 0, _("cannot both summarize and show all entries"));            Line 931
      usage (EXIT_FAILURE);                                                     Line 932
    }                                                                           
                                                                                
  if (opt_summarize_only && max_depth_specified && max_depth == 0)              Line 935
    {                                                                           
      error (0, 0,                                                              Line 937
             _("warning: summarizing is the same as using --max-depth=0"));     Line 938
    }                                                                           
                                                                                
  if (opt_summarize_only && max_depth_specified && max_depth != 0)              Line 941
    {                                                                           
      unsigned long int d = max_depth;                                          Line 943
      error (0, 0, _("warning: summarizing conflicts with --max-depth=%lu"), d);Line 944
      usage (EXIT_FAILURE);                                                     Line 945
    }                                                                           
                                                                                
  if (opt_summarize_only)                                                       Line 948
    max_depth = 0;                                                              Line 949
                                                                                
  if (opt_inodes)                                                               Line 951
    {                                                                           
      if (apparent_size)                                                        Line 953
        {                                                                       
          error (0, 0, _("warning: options --apparent-size and -b are "         Line 955
                         "ineffective with --inodes"));                         Line 956
        }                                                                       
      output_block_size = 1;                                                    Line 958
    }                                                                           
                                                                                
  /* Process time style if printing last times.  */                             
  if (opt_time)                                                                 Line 962
    {                                                                           
      if (! time_style)                                                         Line 964
        {                                                                       
          time_style = getenv ("TIME_STYLE");                                   Line 966
                                                                                
          /* Ignore TIMESTYLE="locale", for compatibility with ls.  */          
          if (! time_style || STREQ (time_style, "locale"))                     Line 969
            time_style = "long-iso";                                            Line 970
          else if (*time_style == '+')                                          Line 971
            {                                                                   
              /* Ignore anything after a newline, for compatibility             
                 with ls.  */                                                   
              char *p = strchr (time_style, '\n');                              Line 975
              if (p)                                                            Line 976
                *p = '\0';                                                      Line 977
            }                                                                   
          else                                                                  Line 979
            {                                                                   
              /* Ignore "posix-" prefix, for compatibility with ls.  */         
              static char const posix_prefix[] = "posix-";                      Line 982
              static const size_t prefix_len = sizeof posix_prefix - 1;         Line 983
              while (STREQ_LEN (time_style, posix_prefix, prefix_len))          Line 984
                time_style += prefix_len;                                       Line 985
            }                                                                   
        }                                                                       
                                                                                
      if (*time_style == '+')                                                   Line 989
        time_format = time_style + 1;                                           Line 990
      else                                                                      Line 991
        {                                                                       
          switch (XARGMATCH ("time style", time_style,                          Line 993
                             time_style_args, time_style_types))                Line 994
            {                                                                   
            case full_iso_time_style:                                           Line 996
              time_format = "%Y-%m-%d %H:%M:%S.%N %z";                          Line 997
              break;                                                            Line 998
                                                                                
            case long_iso_time_style:                                           Line 1000
              time_format = "%Y-%m-%d %H:%M";                                   Line 1001
              break;                                                            Line 1002
                                                                                
            case iso_time_style:                                                Line 1004
              time_format = "%Y-%m-%d";                                         Line 1005
              break;                                                            Line 1006
            }                                                                   
        }                                                                       
    }                                                                           
                                                                                
  struct argv_iterator *ai;                                                     Line 1011
  if (files_from)                                                               Line 1012
    {                                                                           
      /* When using --files0-from=F, you may not specify any files              
         on the command-line.  */                                               
      if (optind < argc)                                                        Line 1016
        {                                                                       
          error (0, 0, _("extra operand %s"), quote (argv[optind]));            Line 1018
          fprintf (stderr, "%s\n",                                              Line 1019
                   _("file operands cannot be combined with --files0-from"));   Line 1020
          usage (EXIT_FAILURE);                                                 Line 1021
        }                                                                       
                                                                                
      if (! (STREQ (files_from, "-") || freopen (files_from, "r", stdin)))      Line 1024...!syscalls auto-comment...
        die (EXIT_FAILURE, errno, _("cannot open %s for reading"),              Line 1025
             quoteaf (files_from));                                             Line 1026
                                                                                
      ai = argv_iter_init_stream (stdin);                                       Line 1028
                                                                                
      /* It's not easy here to count the arguments, so assume the               
         worst.  */                                                             
      hash_all = true;                                                          Line 1032
    }                                                                           
  else                                                                          Line 1034
    {                                                                           
      char **files = (optind < argc ? argv + optind : cwd_only);                Line 1036
      ai = argv_iter_init_argv (files);                                         Line 1037
                                                                                
      /* Hash all dev,ino pairs if there are multiple arguments, or if          
         following non-command-line symlinks, because in either case a          
         file with just one hard link might be seen more than once.  */         
      hash_all = (optind + 1 < argc || symlink_deref_bits == FTS_LOGICAL);      Line 1042
    }                                                                           
                                                                                
  if (!ai)                                                                      Line 1045
    xalloc_die ();                                                              ...!common auto-comment...
                                                                                
  /* Initialize the set of dev,inode pairs.  */                                 
  di_files = di_set_alloc ();                                                   Line 1049
  if (!di_files)                                                                Line 1050
    xalloc_die ();                                                              ...!common auto-comment...
                                                                                
  /* If not hashing everything, process_file won't find cycles on its           
     own, so ask fts_read to check for them accurately.  */                     
  if (opt_count_all || ! hash_all)                                              Line 1055
    bit_flags |= FTS_TIGHT_CYCLE_CHECK;                                         Line 1056
                                                                                
  bit_flags |= symlink_deref_bits;                                              Line 1058
  static char *temp_argv[] = { NULL, NULL };                                    Line 1059
                                                                                
  while (true)                                                                  Line 1061
    {                                                                           
      bool skip_file = false;                                                   Line 1063
      enum argv_iter_err ai_err;                                                Line 1064
      char *file_name = argv_iter (ai, &ai_err);                                Line 1065
      if (!file_name)                                                           Line 1066
        {                                                                       
          switch (ai_err)                                                       Line 1068
            {                                                                   
            case AI_ERR_EOF:                                                    Line 1070
              goto argv_iter_done;                                              Line 1071
            case AI_ERR_READ:                                                   Line 1072
              error (0, errno, _("%s: read error"),                             Line 1073
                     quotef (files_from));                                      Line 1074
              ok = false;                                                       Line 1075
              goto argv_iter_done;                                              Line 1076
            case AI_ERR_MEM:                                                    Line 1077
              xalloc_die ();                                                    ...!common auto-comment...
            default:                                                            Line 1079
              assert (!"unexpected error code from argv_iter");                 Line 1080
            }                                                                   
        }                                                                       
      if (files_from && STREQ (files_from, "-") && STREQ (file_name, "-"))      Line 1083
        {                                                                       
          /* Give a better diagnostic in an unusual case:                       
             printf - | du --files0-from=- */                                   
          error (0, 0, _("when reading file names from stdin, "                 Line 1087
                         "no file name of %s allowed"),                         Line 1088
                 quoteaf (file_name));                                          Line 1089
          skip_file = true;                                                     Line 1090
        }                                                                       
                                                                                
      /* Report and skip any empty file names before invoking fts.              
         This works around a glitch in fts, which fails immediately             
         (without looking at the other file names) when given an empty          
         file name.  */                                                         
      if (!file_name[0])                                                        Line 1097
        {                                                                       
          /* Diagnose a zero-length file name.  When it's one                   
             among many, knowing the record number may help.                    
             FIXME: currently print the record number only with                 
             --files0-from=FILE.  Maybe do it for argv, too?  */                
          if (files_from == NULL)                                               Line 1103
            error (0, 0, "%s", _("invalid zero-length file name"));             Line 1104
          else                                                                  Line 1105
            {                                                                   
              /* Using the standard 'filename:line-number:' prefix here is      
                 not totally appropriate, since NUL is the separator, not NL,   
                 but it might be better than nothing.  */                       
              unsigned long int file_number = argv_iter_n_args (ai);            Line 1110
              error (0, 0, "%s:%lu: %s", quotef (files_from),                   Line 1111
                     file_number, _("invalid zero-length file name"));          Line 1112
            }                                                                   
          skip_file = true;                                                     Line 1114
        }                                                                       
                                                                                
      if (skip_file)                                                            Line 1117
        ok = false;                                                             Line 1118
      else                                                                      Line 1119
        {                                                                       
          temp_argv[0] = file_name;                                             Line 1121
          ok &= du_files (temp_argv, bit_flags);                                Line 1122
        }                                                                       
    }                                                                           
 argv_iter_done:                                                                Line 1125
                                                                                
  argv_iter_free (ai);                                                          Line 1127
  di_set_free (di_files);                                                       Line 1128
  if (di_mnt)                                                                   Line 1129
    di_set_free (di_mnt);                                                       Line 1130
                                                                                
  if (files_from && (ferror (stdin) || fclose (stdin) != 0) && ok)              Line 1132...!syscalls auto-comment...
    die (EXIT_FAILURE, 0, _("error reading %s"), quoteaf (files_from));         Line 1133
                                                                                
  if (print_grand_total)                                                        Line 1135
    print_size (&tot_dui, _("total"));                                          Line 1136
                                                                                
  return ok ? EXIT_SUCCESS : EXIT_FAILURE;                                      Line 1138
}                                                                               Block 23