changeset 5689:9a16df2b1916

[project @ 2006-03-17 05:00:57 by jwe]
author jwe
date Fri, 17 Mar 2006 05:00:57 +0000
parents 6274256266d9
children 161ebd1f3410
files scripts/ChangeLog scripts/miscellaneous/dir.m
diffstat 2 files changed, 74 insertions(+), 93 deletions(-) [+]
line wrap: on
line diff
--- a/scripts/ChangeLog	Thu Mar 16 20:36:29 2006 +0000
+++ b/scripts/ChangeLog	Fri Mar 17 05:00:57 2006 +0000
@@ -1,3 +1,7 @@
+2006-03-16  Bill Denney  <bill@givebillmoney.com>
+
+	* miscellaneous/dir.m: Improve compatibility.
+
 2006-03-15  William Poetra Yoga Hadisoeseno  <williampoetra@gmail.com>
 
 	* time/calendar.m, time/datestr.m, time/datevec.m, time/eomday.m,
--- a/scripts/miscellaneous/dir.m	Thu Mar 16 20:36:29 2006 +0000
+++ b/scripts/miscellaneous/dir.m	Fri Mar 17 05:00:57 2006 +0000
@@ -37,8 +37,9 @@
 ## in which @code{statinfo} is the structure returned from @code{stat}.
 ##
 ## If @var{directory} is not a directory, return information about the
-## named file.
-## @var{filename}.
+## named @var{filename}.  @var{directory} may be a list of directories
+## specified either by name or with wildcard characters (like * and ?)
+## which will be expanded with glob.
 ## @seealso{ls, stat, readdir, glob, filesep}
 ## @end deftypefn
 
@@ -49,98 +50,74 @@
 
 function retval = dir (file)
 
-  if (nargin == 1)
-    if (isstr (file))
-      flst = glob (file);
-      nf = length (flst);
-      if (nf == 0)
-	if (nargout > 0)
-	  ## XXX FIXME XXX -- need a way to create an empty (0x1)
-	  ## structure array.
-	  retval = [];
-	else
-	  warning ("dir: nonexistent file \"%s\"", file);
-	endif
-      else
-	nt = 0;
-	len = zeros (nf, 1);
-	finfo = cell (nf, 1);
-	## Collect results.
-	for i = nf:-1:1
-	  fn = flst{i};
-	  if (isstr (fn))
-	    [st, err, msg] = lstat (fn);
-	    if (err < 0)
-	      warning ("dir: nonexistent file \"%s\"", fn);
-	    else
-	      if (st.modestr(1) == "d")
-		lst = readdir (fn);
-		n = length (lst);
-		for j = n:-1:1
-		  tfn = lst{j};
-		  ## The lstat call seems to be the bottleneck for large
-		  ## directories.
-		  [st, err, msg] = lstat (strcat (fn, filesep, tfn));
-		  if (err < 0)
-		    warning ("dir: stat failed for %s (%s)", tfn, msg);
-		  else
-		    info(j).name = tfn;
-		    ## Generating the pretty time string also takes a
-		    ## significant amount of time for large directories.
-		    info(j).date = strftime ("%d-%b-%Y %T",
-					     localtime (st.mtime));
-		    info(j).bytes = st.size;
-		    info(j).isdir = st.modestr(1) == "d";
-		    info(j).statinfo = st;
-		  endif
-		endfor
-	      else
-		[dummy, fn, ext] = fileparts (fn);
-		fn = strcat (fn, ext);
-		info.name = fn;
-		info.date = strftime ("%d-%b-%Y %T", localtime (st.mtime));
-		info.bytes = st.size;
-		info.isdir = st.modestr(1) == "d";
-		info.statinfo = st;
-	      endif
-	      nt += (len(i) = length (info));
-	      finfo{i} = info;
-	    endif
-	  else
-	    error ("dir: expecting filename argument to be a string");
-	  endif
-	endfor
-	## Condense results to a single struct array.
-	## XXX FIXME XXX -- need a way to create an empty (0x) struct
-	## array in case the file is nonexistent.
-	if (nt == 0)
-	  file_list = [];
-	else
-	  off = 1;
-	  for i = 1:nf
-	    tlen = len(i);
-	    file_list(off:off+tlen-1,1) = finfo{i}.';
-	    off += tlen;
-	  endfor
-	endif
-	if (nargout > 0)
-	  if (length (file_list) > 0)
-	    retval = file_list;
-	  else
-	    retval = [];
-	  endif
-	else
-	  ## XXX FIXME XXX -- need a way to neatly list these in columns.
-	  for i = 1:nt
-	    printf ("  %s\n", file_list(i).name);
-	  endfor
-	endif
-      endif
-    else
-      error ("dir: expecting directory or filename to be a string");
-    endif
-  else
+  if (nargin == 0)
+    file = '.';
+  elseif (nargin > 1)
     usage ("dir (file)");
   endif
 
+  ## prep the retval
+  info = struct(zeros(0,1));
+
+  if (ischar (file))
+    if (strcmp(file, '*'))
+      file = '.';
+    endif
+    flst = glob (file);
+    nf = length (flst);
+
+    ## determine the file list for the case where a directory is
+    ## specified and that directory should be recursed into.
+    if ((nf == 1) && strcmp(file, flist{1}))
+      [st, err, msg] = lstat(flst{1});
+      if (err < 0)
+	warning("dir: nonexistent file \"%s\"", flst{i});
+	nf = 0;
+      elseif (st.modestr(1) == "d")
+	flst = glob ([flst{1} filesep '*']);
+	nf = length(flst);
+      endif
+    endif
+
+    if (length(flst) > 0)
+      len = zeros (nf, 1);
+      finfo = cell (nf, 1);
+      ## Collect results.
+      for i = nf:-1:1
+	fn = flst{i};
+	[st, err, msg] = lstat (fn);
+	if (err < 0)
+	  warning ("dir: nonexistent file \"%s\"", fn);
+	else
+	  [dummy, fn, ext] = fileparts (fn);
+	  fn = strcat (fn, ext);
+	  info(i).name = fn;
+	  info(i).date = strftime ("%d-%b-%Y %T", localtime (st.mtime));
+	  info(i).bytes = st.size;
+	  info(i).isdir = st.modestr(1) == "d";
+	  info(i).statinfo = st;
+	endif
+      endfor
+
+    endif
+  else
+    error ("dir: expecting directory or filename to be a char array");
+  endif
+
+  ## return the output arguements
+  if (nargout > 0)
+    ## Return the requested structure
+    retval = info;
+  else
+    if (length(info) > 0)
+      ## Print the structure to the screen
+      ## XXX FIXME XXX -- need a way to neatly list these in columns.
+      for i = 1:length(info)
+	printf ("  %s\n", info(i).name);
+      endfor
+    else
+      warning("dir: nonexistent file \"%s\"", file);
+    endif
+  endif
+
 endfunction