しらいです。

 file & directory 管理ツール FDclone 2.08b の patch その 4
です。

Submitted-by: shirai@chandra2
Archive-name: FD-2.08b.patch/part04

---- Cut Here and feed the following to sh ----
#!/bin/sh
# This is `FD-2.08b.shar.04' (part 4 of FD-2.08b.patch).
# Do not concatenate these parts, unpack them in order with `/bin/sh'.
# File `FD-2.08b.patch' is being continued...
#
echo=echo
touch -am 1231235999 $$.touch >/dev/null 2>&1
if test ! -f 1231235999 && test -f $$.touch; then
  shar_touch=touch
else
  shar_touch=:
  echo
  $echo 'WARNING: not restoring timestamps.  Consider getting and'
  $echo "installing GNU \`touch', distributed in GNU File Utilities..."
  echo
fi
rm -f 1231235999 $$.touch
#
if test ! -r _sh03503/seq; then
  $echo 'Please unpack part 1 first!'
  exit 1
fi
shar_sequence=`cat _sh03503/seq`
if test "$shar_sequence" != 4; then
  $echo 'Please unpack part' "$shar_sequence" 'next!'
  exit 1
fi
if test ! -f _sh03503/new; then
  $echo 'x -' 'STILL SKIPPING' 'FD-2.08b.patch'
else
  $echo 'x -' 'continuing file' 'FD-2.08b.patch'
  sed 's/^X//' << 'SHAR_EOF' >> FD-2.08b.patch &&
X extern char *getbasename __P_((char *));
X extern char *getshellname __P_((char *, int *, int *));
X extern reg_t *regexp_init __P_((char *, int));
@@ -278,6 +286,10 @@
X extern char *_evalpath __P_((char *, char *, int));
X extern char *evalpath __P_((char *, int));
X 
+extern char nullstr[];
+extern char rootpath[];
+extern char curpath[];
+extern char parentpath[];
X extern char **argvar;
X #ifndef       _NOUSEHASH
X extern hashlist **hashtable;
diff -urNP ../FD-2.08a/posixsh.c ./posixsh.c
--- ../FD-2.08a/posixsh.c       Tue Feb  7 00:00:00 2006
+++ ./posixsh.c Thu Mar 30 00:00:00 2006
@@ -96,11 +96,12 @@
X #define       ER_NOTFOUND     2
X #define       ER_NOTIDENT     4
X #define       ER_BADOPTIONS   13
-#define        ER_MISSARG      15
-#define        ER_NOTALIAS     19
-#define        ER_NOSUCHJOB    20
-#define        ER_NUMOUTRANGE  21
-#define        ER_UNKNOWNSIG   22
+#define        ER_NUMOUTRANGE  18
+#define        ER_NOTALIAS     20
+#define        ER_MISSARG      21
+#define        ER_NOSUCHJOB    22
+#define        ER_TERMINATED   23
+#define        ER_UNKNOWNSIG   26
X 
X #if   !MSDOS
X typedef struct _mailpath_t {
@@ -118,7 +119,7 @@
X int stackjob __P_((p_id_t, int, syntaxtree *));
X int stoppedjob __P_((p_id_t));
X VOID killjob __P_((VOID_A));
-VOID checkjob __P_((int));
+VOID checkjob __P_((FILE *));
X #endif        /* !NOJOB */
X char *evalposixsubst __P_((char *, int *));
X #if   !MSDOS
@@ -300,7 +301,7 @@
X       if (i < 0 || i >= maxjobs || !joblist || !(joblist[i].pids))
X               return(-1);
X       j = joblist[i].npipe;
-       if (joblist[i].stats[j] < 0 || joblist[i].stats[j] >= 128) return(-1);
+       if (joblist[i].stats[j] < 0 || joblist[i].stats[j] >= 128) return(-2);
X 
X       return(i);
X }
@@ -408,13 +409,13 @@
X       return(-1);
X }
X 
-VOID checkjob(verbose)
-int verbose;
+VOID checkjob(fp)
+FILE *fp;
X {
X       int i, j;
X 
X       while (waitjob(-1, NULL, WNOHANG | WUNTRACED) > 0);
-       if (verbose) for (i = 0; i < maxjobs; i++) {
+       if (fp) for (i = 0; i < maxjobs; i++) {
X               if (!(joblist[i].pids)) continue;
X               j = joblist[i].npipe;
X               if (joblist[i].stats[j] >= 0 && joblist[i].stats[j] < 128)
@@ -423,7 +424,7 @@
X               if (joblist[i].trp
X               && (isopbg(joblist[i].trp) || isopnown(joblist[i].trp)))
X                       joblist[i].trp -> type = OP_NONE;
-               if (jobok && interactive && !nottyout) dispjob(i, stderr);
+               if (jobok && interactive && !nottyout) dispjob(i, fp);
X               free(joblist[i].pids);
X               free(joblist[i].stats);
X               if (joblist[i].trp) {
@@ -828,10 +829,10 @@
X               redirectlist red;
X 
X               red.fd = red.type = red.new = 0;
-               red.filename = "";
+               red.filename = nullstr;
X               i = len = 0;
X               stree = newstree(NULL);
-               trp = startvar(stree, &red, "", &i, &len, 0);
+               trp = startvar(stree, &red, nullstr, &i, &len, 0);
X               trp -> cont = CN_COMM;
X               trp = analyze(s, trp, -1);
X               if (trp && (trp -> cont & CN_SBST) != CN_CASE) trp = NULL;
@@ -945,7 +946,7 @@
X                       free(mailpathlist[i].path);
X                       if (mailpathlist[i].msg) free(mailpathlist[i].msg);
X               }
-               free(mailpathlist);
+               if (mailpathlist) free(mailpathlist);
X               mailpathlist = NULL;
X               maxmailpath = 0;
X               return;
@@ -971,7 +972,7 @@
X       int i, j;
X 
X       if (mypid != orgpgrp) return(RET_SUCCESS);
-       checkjob(0);
+       checkjob(NULL);
X       for (i = 0; i < maxjobs; i++) {
X               if (!(joblist[i].pids)) continue;
X               j = joblist[i].npipe;
@@ -1004,9 +1005,10 @@
X       int i, j, n, ret;
X 
X       s = ((trp -> comm) -> argc > 1) ? (trp -> comm) -> argv[1] : NULL;
-       checkjob(0);
+       checkjob(NULL);
X       if ((i = getjob(s)) < 0) {
-               execerror((trp -> comm) -> argv[1], ER_NOSUCHJOB, 0);
+               execerror((trp -> comm) -> argv[1],
+                       (i < -1) ? ER_TERMINATED : ER_NOSUCHJOB, 0);
X               return(RET_FAIL);
X       }
X       n = joblist[i].npipe;
@@ -1047,9 +1049,10 @@
X       int i, j, n;
X 
X       s = ((trp -> comm) -> argc > 1) ? (trp -> comm) -> argv[1] : NULL;
-       checkjob(0);
+       checkjob(NULL);
X       if ((i = getjob(s)) < 0) {
-               execerror((trp -> comm) -> argv[1], ER_NOSUCHJOB, 0);
+               execerror((trp -> comm) -> argv[1],
+                       (i < -1) ? ER_TERMINATED : ER_NOSUCHJOB, 0);
X               return(RET_FAIL);
X       }
X       n = joblist[i].npipe;
@@ -1193,14 +1196,15 @@
X       }
X 
X #ifndef       NOJOB
-       checkjob(0);
+       checkjob(NULL);
X #endif
X       for (; i < (trp -> comm) -> argc; i++) {
X               s = (trp -> comm) -> argv[i];
X #ifndef       NOJOB
X               if (*s == '%') {
X                       if ((n = getjob(s)) < 0) {
-                               execerror(s, ER_NOSUCHJOB, 0);
+                               execerror(s, (n < -1)
+                                       ? ER_TERMINATED : ER_NOSUCHJOB, 0);
X                               return(RET_FAIL);
X                       }
X                       n = Xkillpg(joblist[n].pids[0], sig);
diff -urNP ../FD-2.08a/shell.c ./shell.c
--- ../FD-2.08a/shell.c Tue Feb  7 00:00:00 2006
+++ ./shell.c   Thu Mar 30 00:00:00 2006
@@ -266,7 +266,7 @@
X       if (!*ptrp) q = '\0';
X       pc = parsechar(&(s[*ptrp]), -1, '\0', 0, &q, NULL);
X       if (pc == PC_NORMAL) return(0);
-       if (pc == PC_WORD || pc == PC_META) {
+       if (pc == PC_WORD || pc == PC_ESCAPE) {
X               (*ptrp)++;
X               return(2);
X       }
@@ -1262,7 +1262,7 @@
X #endif        /* MACROMETA */
X 
X       if (!(wastty = isttyiomode)) Xttyiomode(1);
-       cp = inputstr("", 0, p, command, HST_COM);
+       cp = inputstr(nullstr, 0, p, command, HST_COM);
X       if (!wastty) Xstdiomode();
X       free(command);
X       if (!cp) {
@@ -1699,12 +1699,12 @@
X       return(0);
X }
X 
-int parsehist(str, ptrp)
+int parsehist(str, ptrp, quote)
X char *str;
-int *ptrp;
+int *ptrp, quote;
X {
X       char *cp;
-       int i, n, ptr, size;
+       int i, n, pc, ptr, size;
X 
X       ptr = (ptrp) ? *ptrp : 0;
X       size = (int)histsize[0];
@@ -1722,8 +1722,10 @@
X       }
X       else {
X               for (i = 0; str[ptr + i]; i++) {
-                       if (strchr(CMDLINE_DELIM, str[ptr + i])) break;
-                       if (iskanji1(str, ptr + i)) i++;
+                       pc = parsechar(&(str[ptr + i]), -1,
+                               '!', EA_FINDDELIM, &quote, NULL);
+                       if (pc == PC_WORD || pc == PC_ESCAPE) i++;
+                       else if (pc != PC_NORMAL && pc != PC_DQUOTE) break;
X               }
X               if (!i) n = ptr = -1;
X               else {
@@ -1738,7 +1740,10 @@
X 
X       if (ptrp) *ptrp = ptr;
X       if (n < 0 || n >= size) return(-1);
-       if (!ptrp) {
+       if (ptrp) {
+               if (!history[0][n]) return(-1);
+       }
+       else {
X               while (!history[0][n]) if (--n < 0) return(-1);
X       }
X 
@@ -1757,10 +1762,10 @@
X       for (i = j = 0, quote = '\0'; command[i]; i++) {
X               cp = c_realloc(cp, j + 1, &size);
X               pc = parsechar(&(command[i]), -1, '!', 0, &quote, NULL);
-               if (pc == PC_WORD || pc == PC_META) cp[j++] = command[i++];
+               if (pc == PC_WORD || pc == PC_ESCAPE) cp[j++] = command[i++];
X               else if (pc == '!'){
X                       len = i++;
-                       if ((n = parsehist(command, &i)) < 0) {
+                       if ((n = parsehist(command, &i, quote)) < 0) {
X                               if (i < 0) {
X                                       cp[j++] = '!';
X                                       i = len;
diff -urNP ../FD-2.08a/system.c ./system.c
--- ../FD-2.08a/system.c        Tue Feb  7 00:00:00 2006
+++ ./system.c  Thu Mar 30 00:00:00 2006
@@ -227,22 +227,19 @@
X extern int Xopen __P_((char *, int, int));
X # ifdef       _NODOSDRIVE
X # define      Xclose(f)       ((close(f)) ? -1 : 0)
+# define       Xdup            safe_dup
+# define       Xdup2           safe_dup2
X # define      Xfdopen         fdopen
X # define      Xfclose         fclose
X # define      Xfileno         fileno
X # else        /* !_NODOSDRIVE */
X extern int Xclose __P_((int));
+extern int Xdup __P_((int));
+extern int Xdup2 __P_((int, int));
X extern FILE *Xfdopen __P_((int, char*));
X extern int Xfclose __P_((FILE *));
X extern int Xfileno __P_((FILE *));
X # endif       /* !_NODOSDRIVE */
-# ifdef        _NODOSDRIVE
-# define       Xdup            safe_dup
-# define       Xdup2           safe_dup2
-# else
-extern int Xdup __P_((int));
-extern int Xdup2 __P_((int, int));
-# endif
X #else /* !FD */
X # if  MSDOS
X extern int _dospath __P_((char *));
@@ -263,11 +260,11 @@
X #define       Xunlink(p)      ((unlink(p)) ? -1 : 0)
X #define       Xopen           open
X #define       Xclose(f)       ((close(f)) ? -1 : 0)
+#define        Xdup            safe_dup
+#define        Xdup2           safe_dup2
X #define       Xfdopen         fdopen
X #define       Xfclose         fclose
X #define       Xfileno         fileno
-#define        Xdup            safe_dup
-#define        Xdup2           safe_dup2
X # if  MSDOS
X #  ifdef      DJGPP
X #  define     Xmkdir(p, m)    ((mkdir(p, m)) ? -1 : 0)
@@ -346,7 +343,7 @@
X extern int stackjob __P_((p_id_t, int, syntaxtree *));
X extern int stoppedjob __P_((p_id_t));
X extern VOID killjob __P_((VOID_A));
-extern VOID checkjob __P_((int));
+extern VOID checkjob __P_((FILE *));
X # endif       /* !NOJOB */
X extern char *evalposixsubst __P_((char *, int *));
X # if  !MSDOS
@@ -451,6 +448,9 @@
X # endif
X #endif        /* !FD */
X 
+#ifndef        NOJOB
+static VOID NEAR notifyjob __P_((VOID_A));
+#endif
X static VOID NEAR setsignal __P_((VOID_A));
X static VOID NEAR resetsignal __P_((int));
X static VOID NEAR exectrapcomm __P_((VOID_A));
@@ -965,7 +965,7 @@
X static int execerrno = 0;
X 
X static CONST char *syntaxerrstr[] = {
-       "",
+       NULL,
X #define       ER_UNEXPTOK     1
X       "unexpected token",
X #define       ER_UNEXPNL      2
@@ -976,7 +976,7 @@
X #define       SYNTAXERRSIZ    ((int)(sizeof(syntaxerrstr) / sizeof(char *)))
X 
X static CONST char *execerrstr[] = {
-       "",
+       NULL,
X #define       ER_COMNOFOUND   1
X       "command not found",
X #define       ER_NOTFOUND     2
@@ -1005,32 +1005,52 @@
X       "bad option(s)",
X #define       ER_PARAMNOTSET  14
X       "parameter not set",
-#define        ER_MISSARG      15
-       "Missing argument",
-#define        ER_RESTRICTED   16
+#define        ER_RESTRICTED   15
X       "restricted",
-#define        ER_BADULIMIT    17
-       "Bad ulimit",
-#define        ER_BADTRAP      18
+#define        ER_BADULIMIT    16
+       "bad ulimit",
+#define        ER_BADTRAP      17
X       "bad trap",
-#define        ER_NOTALIAS     19
-       "is not an alias",
-#define        ER_NOSUCHJOB    20
-       "No such job",
-#define        ER_NUMOUTRANGE  21
+#define        ER_NUMOUTRANGE  18
X       "number out of range",
-#define        ER_UNKNOWNSIG   22
-       "unknown signal; kill -l lists signals",
-#define        ER_NOHOMEDIR    23
+#define        ER_NOHOMEDIR    19
X       "no home directory",
-#define        ER_INVALDRIVE   24
-       "Invalid drive specification",
-#define        ER_INCORRECT    25
-       "incorrect",
-#define        ER_NOTLOGINSH   26
+#ifdef NOALIAS
+       NULL,
+#else
+#define        ER_NOTALIAS     20
+       "is not an alias",
+#endif
+#ifdef NOPOSIXUTIL
+       NULL,
+#else
+#define        ER_MISSARG      21
+       "missing argument",
+#endif
+#ifdef NOJOB
+       NULL, NULL,
+#else
+#define        ER_NOSUCHJOB    22
+       "no such job",
+#define        ER_TERMINATED   23
+       "job has terminated",
+#endif
+#ifdef MINIMUMSHELL
+       NULL, NULL, NULL,
+#else
+#define        ER_NOTLOGINSH   24
X       "not login shell",
-#define        ER_DIREMPTY     27
+#define        ER_DIREMPTY     25
X       "directory stack empty",
+#define        ER_UNKNOWNSIG   26
+       "unknown signal; kill -l lists signals",
+#endif
+#if    !MSDOS
+       NULL,
+#else
+#define        ER_INVALDRIVE   27
+       "invalid drive specification",
+#endif
X #ifdef        FD
X #define       ER_RECURSIVEFD  28
X       "recursive call for FDclone",
@@ -1760,7 +1780,7 @@
X {
X       if (chdir2(dir) < 0) return(-1);
X # ifndef      _NOUSEHASH
-       searchhash(NULL, "", "");
+       searchhash(NULL, nullstr, nullstr);
X # endif
X 
X       return(0);
@@ -1822,6 +1842,37 @@
X # endif       /* MSDOS && !BSPATHDELIM */
X #endif        /* !FD */
X 
+#ifndef        NOJOB
+static VOID NEAR notifyjob(VOID_A)
+{
+       FILE *fp;
+       int fd;
+
+       if ((fd = Xdup(STDERR_FILENO)) < 0) fp = stderr;
+       else if (!(fp = Xfdopen(fd, "a"))) {
+               Xclose(fd);
+               fp = stderr;
+       }
+# if   !MSDOS
+       else {
+#  ifdef       DEBUG
+               _mtrace_file = "setvbuf(start)";
+               setlbuf(fp);
+               if (_mtrace_file) _mtrace_file = NULL;
+               else {
+                       _mtrace_file = "setvbuf(end)";
+                       malloc(0);      /* dummy alloc */
+               }
+#  else
+               setlbuf(fp);
+#  endif
+       }
+# endif        /* !MSDOS */
+       checkjob(fp);
+       safefclose(fp);
+}
+#endif /* !NOJOB */
+
X static VOID NEAR setsignal(VOID_A)
X {
X       int i, sig;
@@ -1847,6 +1898,9 @@
X #if   !MSDOS && defined (NOJOB)
X       p_id_t tmp;
X #endif
+#if    defined (SIGCHLD) && !defined (NOJOB)
+       int n;
+#endif
X       int i, duperrno;
X 
X       duperrno = errno;
@@ -1856,7 +1910,7 @@
X               tmp = Xwait3(NULL, WNOHANG | WUNTRACED, NULL);
X       } while (tmp > (p_id_t)0 || (tmp < (p_id_t)0 && errno == EINTR));
X # else
-       checkjob(1);
+       notifyjob();
X       stopped = 0;
X # endif
X #endif        /* !MSDOS */
@@ -1871,9 +1925,17 @@
X #if   defined (FD) && defined (SIGALRM)
X                       noalrm--;
X #endif
-                       for (i = 0; i < NSIG; i++)
+                       for (i = 0; i < NSIG; i++) {
+#if    defined (SIGCHLD) && !defined (NOJOB)
+                               if (i == SIGCHLD && bgnotify) {
+                                       for (n = 0; n < maxjobs; n++)
+                                               if (joblist[n].pids) break;
+                                       if (n < maxjobs) continue;
+                               }
+#endif
X                               if (oldsigfunc[i] != SIG_ERR)
X                                       signal2(i, oldsigfunc[i]);
+                       }
X #if   !MSDOS
X                       Xsigsetmask(oldsigmask);
X #endif
@@ -2036,7 +2098,7 @@
X               case SIGCHLD:
X # ifndef      NOJOB
X                       if (bgnotify) {
-                               checkjob(1);
+                               notifyjob();
X                               break;
X                       }
X # endif
@@ -2389,6 +2451,7 @@
X                       }
X                       joblist[i].pids = NULL;
X               }
+               maxjobs = 0;
X               free(joblist);
X               joblist = NULL;
X       }
@@ -2472,7 +2535,8 @@
X       if (argvar && argvar[0]) fprintf2(stderr, "%k: ", argvar[0]);
X       if (s) fprintf2(stderr, "%a: ",
X               (*s && syntaxerrno != ER_UNEXPNL) ? s : "syntax error");
-       fputs(syntaxerrstr[syntaxerrno], stderr);
+       if (syntaxerrstr[syntaxerrno])
+               fputs(syntaxerrstr[syntaxerrno], stderr);
X       fputnl(stderr);
X       ret_status = RET_SYNTAXERR;
X       if (errorexit) Xexit2(RET_SYNTAXERR);
@@ -2496,7 +2560,7 @@
X #endif
X       if (argvar && argvar[0]) fprintf2(stderr, "%k: ", argvar[0]);
X       if (s) fprintf2(stderr, "%a: ", s);
-       fputs(execerrstr[n], stderr);
+       if (execerrstr[n]) fputs(execerrstr[n], stderr);
X       fputnl(stderr);
X       execerrno = n;
X #ifndef       BASHSTYLE
@@ -2971,7 +3035,7 @@
X                * ternary operator with NULL is const char *,
X                * not to be converted to char *.
X                */
-               if (!val) cp = (cp) ? (char *)NULL : "";
+               if (!val) cp = (cp) ? NULL : nullstr;
X 
X               if (cp) {
X                       setenv2("FD_EDITMODE", cp, 0);
@@ -4384,7 +4448,7 @@
X               if (dumbterm > 1 && (!shellmode || exit_status < 0)) {
X                       freeterment();
X                       term = getconstvar("TERM");
-                       getterment((term) ? term : "");
+                       getterment((term) ? term : nullstr);
X                       execerror(cp, ER_INVALTERMFD, 0);
X                       copykeyseq(keymap);
X                       freekeyseq(keymap);
@@ -4478,7 +4542,7 @@
X # ifdef       FD
X       else if (constequal(ident, "TERM", len)) {
X               freeterment();
-               getterment("");
+               getterment(nullstr);
X       }
X # endif
X #endif        /* !MSDOS */
@@ -5722,7 +5786,7 @@
X                       rp -> filename[j++] = s[i++];
X                       rp -> filename[j++] = s[i];
X               }
-               else if (pc == PC_META) {
+               else if (pc == PC_ESCAPE) {
X                       if (s[++i] != '\n' || rp -> new) {
X                               rp -> filename[j++] = PMETA;
X                               if (s[i]) rp -> filename[j++] = s[i];
@@ -5986,7 +6050,7 @@
X #endif
X               else {
X                       syntaxerrno = ER_UNEXPEOF;
-                       syntaxerror("");
+                       syntaxerror(nullstr);
X                       return(NULL);
X               }
X       }
@@ -7901,10 +7965,6 @@
X       ALLOC_T i, size;
X       int c;
X 
-       if ((trp -> comm) -> argc <= 1) {
-               execerror(NULL, ER_MISSARG, 0);
-               return(RET_FAIL);
-       }
X       for (i = 1; i < (trp -> comm) -> argc; i++) {
X               if (identcheck((trp -> comm) -> argv[i], '\0') <= 0) {
X                       execerror((trp -> comm) -> argv[i], ER_NOTIDENT, 0);
@@ -7956,6 +8016,10 @@
X               if (cp && setenv2((trp -> comm) -> argv[i], cp, 0) < 0)
X                       c = RET_FAIL;
X       }
+#ifdef BASHSTYLE
+       /* bash set the variable REPLY without any argument */
+       else if (setenv2("REPLY", buf, 0) < 0) c = RET_FAIL;
+#endif
X       free(buf);
X 
X       return(c);
@@ -8463,7 +8527,7 @@
X               s = (trp -> comm) -> argv[1];
X # ifndef      NOJOB
X               if (*s == '%') {
-                       checkjob(0);
+                       checkjob(NULL);
X                       if ((i = getjob(s)) < 0) pid = (p_id_t)-1;
X                       else {
X                               j = joblist[i].npipe;
@@ -8478,7 +8542,7 @@
X               }
X # ifndef      NOJOB
X               else {
-                       checkjob(0);
+                       checkjob(NULL);
X                       if (!joblist || (i = searchjob(pid, &j)) < 0) {
X                               pid = (p_id_t)-1;
X #  ifdef      FAKEUNINIT
@@ -8795,9 +8859,10 @@
X       int i;
X 
X       s = ((trp -> comm) -> argc > 1) ? (trp -> comm) -> argv[1] : NULL;
-       checkjob(0);
+       checkjob(NULL);
X       if ((i = getjob(s)) < 0) {
-               execerror((trp -> comm) -> argv[1], ER_NOSUCHJOB, 0);
+               execerror((trp -> comm) -> argv[1],
+                       (i < -1) ? ER_TERMINATED : ER_NOSUCHJOB, 0);
X               return(RET_FAIL);
X       }
X       free(joblist[i].pids);
@@ -10299,17 +10364,11 @@
X       else if (pipein) {
X #ifdef        CYGWIN
X       /* a trick for buggy terminal emulation */
-               fd_set readfds;
X               struct timeval tv;
-               int dupl;
X 
-               dupl = Xdup(fd);
X               tv.tv_sec = 0;
X               tv.tv_usec = 500000L;   /* maybe enough waiting limit */
-               FD_ZERO(&readfds);
-               FD_SET(dupl, &readfds);
-               select(dupl + 1, &readfds, NULL, NULL, &tv);
-               close(dupl);
+               VOID_C readselect(1, &fd, NULL, &tv);
X #endif        /* CYGWIN */
X               nownstree(trp);
X       }
@@ -10447,10 +10506,19 @@
X char *fname;
X int verbose;
X {
+#ifdef MINIMUMSHELL
+       char *cp, path[MAXPATHLEN];
+#endif
X       char **dupargvar;
X       int fd, ret, duprestricted;
X 
X       setsignal();
+#ifdef MINIMUMSHELL
+       if (*fname == '~' && fname[1] == _SC_ && (cp = getconstvar("HOME"))) {
+               strcatdelim2(path, cp, &(fname[2]));
+               fname = path;
+       }
+#endif
X       fname = strdup2(fname);
X #if   MSDOS && !defined (BSPATHDELIM)
X       fname = adjustpname(fname);
@@ -10568,7 +10636,7 @@
X #ifdef        FD
X       if (interactive) inittty(0);
X       term = getconstvar("TERM");
-       getterment((term) ? term : "");
+       getterment((term) ? term : nullstr);
X #endif        /* FD */
X 
X       return(0);
@@ -10584,19 +10652,19 @@
X 
X #ifdef        FD
X       execruncom(DEFRC, verbose);
-#else  /* !FD */
+#else
X       if (loginshell) {
X               execruncom(LSH_DEFRC, verbose);
X               execruncom(LSH_RCFILE, verbose);
X       }
-#endif /* !FD */
+#endif
X #ifndef       MINIMUMSHELL
X # if  !MSDOS
X       if (getuid() != geteuid() || getgid() != getegid()) /*EMPTY*/;
X       else
X # endif
X       if ((cp = getconstvar("ENV"))) execruncom(cp, verbose);
-#endif
+#endif /* !MINIMUMSHELL */
X #ifdef        FD
X       if (loginshell) execruncom(SH_RCFILE, verbose);
X       else execruncom(FD_RCFILE, verbose);
@@ -10683,11 +10751,28 @@
X 
X       setnbuf(stdin);
X #if   !MSDOS
+# ifdef        DEBUG
+       _mtrace_file = "setvbuf(start)";
+       setlbuf(stderr);
+       if (_mtrace_file) _mtrace_file = NULL;
+       else {
+               _mtrace_file = "setvbuf(end)";
+               malloc(0);      /* dummy alloc */
+       }
+       _mtrace_file = "setvbuf(start)";
+       setlbuf(stdout);
+       if (_mtrace_file) _mtrace_file = NULL;
+       else {
+               _mtrace_file = "setvbuf(end)";
+               malloc(0);      /* dummy alloc */
+       }
+# else
X       setlbuf(stderr);
X       setlbuf(stdout);
+# endif
X       Xsigemptyset(mask);
X       Xsigblock(oldsigmask, mask);
-#endif
+#endif /* !MSDOS */
X 
X       if (definput == STDIN_FILENO && isatty(STDIN_FILENO)) definput = ttyio;
X 
@@ -10767,7 +10852,7 @@
X                               cp = pwd -> pw_dir;
X                       else
X #endif
-                       cp = _SS_;
+                       cp = rootpath;
X                       setenv2("HOME", cp, 1);
X               }
X               if (!getconstvar("SHELL")) {
@@ -10892,7 +10977,14 @@
X               Xexit2(n);
X       }
X 
-       if (loginshell && chdir2(getconstvar("HOME")) < 0) {
+       n = 0;
+#ifdef BASHSTYLE
+       /* bash changes the current directory if the variable PWD is set */
+       if ((cp = getconstvar("PWD"))) n = chdir2(cp);
+       else
+#endif
+       if (loginshell && interactive) n = chdir2(getconstvar("HOME"));
+       if (n < 0) {
X #ifdef        FD
X               initfd(argv);
X #endif
@@ -10968,7 +11060,7 @@
X                               if (cont) {
X                                       exec_line(NULL);
X                                       syntaxerrno = ER_UNEXPEOF;
-                                       syntaxerror("");
+                                       syntaxerror(nullstr);
X                               }
X                               else {
X                                       fprintf2(stderr,
diff -urNP ../FD-2.08a/term.c ./term.c
--- ../FD-2.08a/term.c  Tue Feb  7 00:00:00 2006
+++ ./term.c    Thu Mar 30 00:00:00 2006
@@ -55,10 +55,6 @@
X } kstree_t;
X #endif        /* !MSDOS */
X 
-#ifdef USESELECTH
-#include <sys/select.h>
-#endif
-
X #ifndef       NOUNISTDH
X #include <unistd.h>
X #endif
@@ -77,7 +73,7 @@
X #include "termio.h"
X #include "term.h"
X 
-#define        WINTERMNAME     "iris"
+#define        WINTERMNAME             "iris"
X #ifdef        USESTRERROR
X #define       strerror2               strerror
X #else
@@ -338,16 +334,6 @@
X #endif
X #endif        /* !MSDOS */
X 
-#ifndef        FD_SET
-typedef struct fd_set {
-       u_int fds_bits[1];
-} fd_set;
-# define       FD_ZERO(p)      (((p) -> fds_bits[0]) = 0)
-# define       FD_SET(n, p)    (((p) -> fds_bits[0]) |= ((u_int)1 << (n)))
-#endif /* !FD_SET */
-
-#define        MAXFDSET        256
-
X static int NEAR err2 __P_((char *));
X #if   !MSDOS
X static char *NEAR tstrdup __P_((char *));
@@ -1580,8 +1566,18 @@
X       char *p;
X 
X       p = strbuf;
+#  ifdef       DEBUG
+       _mtrace_file = "tgetstr(start)";
X       s = tgetstr(s, &p);
-# endif
+       if (_mtrace_file) _mtrace_file = NULL;
+       else {
+               _mtrace_file = "tgetstr(end)";
+               malloc(0);      /* dummy alloc */
+       }
+#  else
+       s = tgetstr(s, &p);
+#  endif
+# endif        /* !USETERMINFO */
X       if (s) {
X               if (*term) free(*term);
X               *term = tstrdup(s);
@@ -1596,14 +1592,35 @@
X # ifdef       USETERMINFO
X       if (str1) str1 = tstrdup(str1);
X       else str1 = tparamstr(str2, 1, 1);
-# else
+# else /* !USETERMINFO */
X       char *p, strbuf[TERMCAPSIZE];
X 
X       p = strbuf;
X 
+#  ifdef       DEBUG
+       _mtrace_file = "tgetstr(start)";
+       str1 = tgetstr(str1, &p);
+       if (_mtrace_file) _mtrace_file = NULL;
+       else {
+               _mtrace_file = "tgetstr(end)";
+               malloc(0);      /* dummy alloc */
+       }
+       if (str1) str1 = tstrdup(str1);
+       else {
+               _mtrace_file = "tgetstr(start)";
+               str2 = tgetstr(str2, &p);
+               if (_mtrace_file) _mtrace_file = NULL;
+               else {
+                       _mtrace_file = "tgetstr(end)";
+                       malloc(0);      /* dummy alloc */
+               }
+               str1 = tparamstr(str2, 1, 1);
+       }
+#  else
X       if ((str1 = tgetstr(str1, &p))) str1 = tstrdup(str1);
X       else str1 = tparamstr(tgetstr(str2, &p), 1, 1);
-# endif
+#  endif
+# endif        /* !USETERMINFO */
X       if (str1) {
X               if (*term) free(*term);
X               *term = str1;
@@ -2600,13 +2617,12 @@
X {
X #if   defined (NOTUSEBIOS) || !defined (DJGPP) || (DJGPP < 2)
X       union REGS reg;
-#else
+#else  /* !NOTUSEBIOS && DJGPP && DJGPP >= 2 */
X # ifndef      PC98
-       fd_set readfds;
X       struct timeval tv;
-       int n, fd;
+       int n;
X # endif
-#endif
+#endif /* !NOTUSEBIOS && DJGPP && DJGPP >= 2 */
X 
X       if (ungetnum > 0) return(1);
X #ifdef        NOTUSEBIOS
@@ -2627,17 +2643,9 @@
X       return(reg.h.bh != 0);
X # else        /* !PC98 */
X #  if defined (DJGPP) && (DJGPP >= 2)
-       fd = (ttyio < MAXFDSET || (n = safe_dup(ttyio)) < 0) ? ttyio : n;
X       tv.tv_sec = (time_t)usec / (time_t)1000000;
X       tv.tv_usec = (time_t)usec % (time_t)1000000;
-       FD_ZERO(&readfds);
-       FD_SET(fd, &readfds);
-
-       do {
-               n = select(fd + 1, &readfds, NULL, NULL, &tv);
-       } while (n < 0 && errno == EINTR);
-       if (fd != ttyio) close(fd);
-       if (n < 0) err2("select()");
+       if ((n = readselect(1, &ttyio, NULL, &tv)) < 0) err2("select()");
X 
X       return(n);
X #  else       /* !DJGPP || DJGPP < 2 */
@@ -2760,7 +2768,7 @@
X                       raise(sig);
X               }
X # endif
-               if (keywaitfunc && (*keywaitfunc)() < 0) return(-1);
+               if (keywaitfunc && (ch = (*keywaitfunc)()) < 0) return(ch);
X       } while (!i);
X 
X #else /* !DJGPP || NOTUSEBIOS || PC98 */
@@ -2773,7 +2781,7 @@
X # endif
X                       memcpy((char *)tbuf1, (char *)tbuf2, sizeof(tbuf1));
X               }
-               if (keywaitfunc && (*keywaitfunc)() < 0) return(-1);
+               if (keywaitfunc && (ch = (*keywaitfunc)()) < 0) return(ch);
X       }
X #endif        /* !DJGPP || NOTUSEBIOS || PC98 */
X       if ((ch = getch2()) == EOF) return(K_NOKEY);
@@ -2809,7 +2817,11 @@
X {
X       if (ungetnum >= (int)sizeof(ungetbuf) / sizeof(u_char) - 1)
X               return(EOF);
-       ungetbuf[ungetnum++] = c;
+       if (ungetnum)
+               memmove(&(ungetbuf[1]), &(ungetbuf[0]),
+                       ungetnum * sizeof(u_char));
+       ungetbuf[0] = c;
+       ungetnum++;
X 
X       return(c);
X }
@@ -2907,21 +2919,12 @@
X # ifdef       NOSELECT
X       return((usec) ? 1 : 0);
X # else
-       fd_set readfds;
X       struct timeval tv;
-       int n, fd;
+       int n;
X 
-       fd = (ttyio < MAXFDSET || (n = safe_dup(ttyio)) < 0) ? ttyio : n;
X       tv.tv_sec = (time_t)usec / (time_t)1000000;
X       tv.tv_usec = (time_t)usec % (time_t)1000000;
-       FD_ZERO(&readfds);
-       FD_SET(fd, &readfds);
-
-       do {
-               n = select(fd + 1, &readfds, NULL, NULL, &tv);
-       } while (n < 0 && errno == EINTR);
-       if (fd != ttyio) close(fd);
-       if (n < 0) err2("select()");
+       if ((n = readselect(1, &ttyio, NULL, &tv)) < 0) err2("select()");
X 
X       return(n);
X # endif
@@ -2960,7 +2963,7 @@
X                       ttyiomode((isttyiomode) ? isttyiomode - 1 : 0);
X                       suspended = 0;
X               }
-               if (keywaitfunc && (*keywaitfunc)() < 0) return(-1);
+               if (keywaitfunc && (ch = (*keywaitfunc)()) < 0) return(ch);
X # ifndef      TIOCSTI
X               if (ungetnum > 0) return((int)ungetbuf[--ungetnum]);
X # endif
@@ -2991,10 +2994,12 @@
X                       return(mkmetakey(ch));
X               for (j = 0; j < p -> num; j++)
X                       if (key == keyseq[p -> next[j].key].str[0]) break;
-               if (j >= p -> num) return(key);
+               if (j >= p -> num) {
+                       ungetch2(ch);
+                       return(key);
+               }
X               p = &(p -> next[j]);
-               if (keyseq[p -> key].len == 1)
-                       return(keyseq[p -> key].code);
+               if (keyseq[p -> key].len == 1) return(keyseq[p -> key].code);
X       }
X       else {
X               for (j = 0; j < p -> num; j++)
@@ -3010,14 +3015,19 @@
X       for (i = 1; p && p -> next; i++) {
X               for (j = 0; j < p -> num; j++)
X                       if (ch == keyseq[p -> next[j].key].str[i]) break;
-               if (j >= p -> num) return(key);
+               if (j >= p -> num) break;
X               p = &(p -> next[j]);
X               if (keyseq[p -> key].len == i + 1)
X                       return(keyseq[p -> key].code);
X               if (!kbhit2(WAITKEYPAD * 1000L) || (ch = getch2()) == EOF)
-                       return(key);
+                       break;
X       }
X 
+       for (j = 1; j < i; j++) {
+               if (j >= keyseq[p -> key].len) break;
+               ungetch2(keyseq[p -> key].str[j]);
+       }
+       ungetch2(ch);
X       return(key);
X }
X 
@@ -3046,7 +3056,11 @@
X # else
X       if (ungetnum >= (int)sizeof(ungetbuf) / sizeof(u_char) - 1)
X               return(EOF);
-       ungetbuf[ungetnum++] = c;
+       if (ungetnum)
+               memmove(&(ungetbuf[1]), &(ungetbuf[0]),
+                       ungetnum * sizeof(u_char));
+       ungetbuf[0] = c;
+       ungetnum++;
X # endif
X 
X       return(c);
@@ -3122,7 +3136,8 @@
X 
X       if (dumbterm) /*EMPTY*/;
X       else if (usegetcursor || x < 0 || y < 0) {
-               VOID_C setscroll(-1, -1);
+               if (usegetcursor) VOID_C setscroll(-1, -1);
+               else VOID_C setscroll(0, 998);
X               if (maxlocate(&ty, &tx) >= 0 && (tx > x || ty > y)) {
X                       if (tx > x) x = tx;
X                       if (ty > y) y = ty;
@@ -3141,7 +3156,7 @@
X       if (n_line <= 0 || (ymax > 0 && n_line < ymax))
X               return("Line size too small");
X 
-       if (xmax > 0 && ymax > 0) VOID_C setscroll(-1, -1);
+       if (xmax > 0 && ymax > 0) VOID_C setscroll(0, n_line - 1);
X 
X       return(NULL);
X }
diff -urNP ../FD-2.08a/termemu.c ./termemu.c
--- ../FD-2.08a/termemu.c       Tue Feb  7 00:00:00 2006
+++ ./termemu.c Thu Mar 30 00:00:00 2006
@@ -13,10 +13,6 @@
X #include "kanji.h"
X #include "termemu.h"
X 
-#ifdef USESELECTH
-#include <sys/select.h>
-#endif
-
X #ifdef        _NOORIGSHELL
X #include <signal.h>
X #include "termio.h"
@@ -29,19 +25,12 @@
X # endif
X #endif
X 
-#ifndef        FD_SET
-typedef struct fd_set {
-       u_int fds_bits[1];
-} fd_set;
-# define       FD_ZERO(p)      (((p) -> fds_bits[0]) = 0)
-# define       FD_SET(n, p)    (((p) -> fds_bits[0]) |= ((u_int)1 << (n)))
-#endif /* !FD_SET */
-
-extern int internal_status;
+extern char fullpath[];
X extern int hideclock;
X extern int fdmode;
X 
X int ptymode = 0;
+int ptyinternal = 0;
X char *ptyterm = NULL;
X int ptymenukey = -1;
X ptyinfo_t ptylist[MAXWINDOWS];
@@ -132,29 +121,12 @@
X       }
X }
X 
-int selectpty(fd, fds, result, timeout)
-int fd, fds[];
+int selectpty(max, fds, result, timeout)
+int max, fds[];
X char result[];
X int timeout;
X {
-       fd_set readfds;
X       struct timeval tv, *t;
-       int i, n, max;
-
-       max = -1;
-       FD_ZERO(&readfds);
-       if (fd < 0) max = 0;
-       else {
-               max = fd;
-               FD_SET(fd, &readfds);
-       }
-       for (i = 0; i < MAXWINDOWS; i++) {
-               if (!(ptylist[i].pid)) continue;
-               if (fds[i] > max) max = fds[i];
-               FD_SET(fds[i], &readfds);
-       }
-
-       if (!max) return(0);
X 
X       if (timeout < 0) t = NULL;
X       else if (!timeout) {
@@ -168,13 +140,7 @@
X               t = &tv;
X       }
X 
-       if ((n = select(max + 1, &readfds, NULL, NULL, t)) < 0) return(-1);
-       for (i = 0; i < MAXWINDOWS; i++)
-               result[i] = (ptylist[i].pid && FD_ISSET(fds[i], &readfds))
-                       ? 1 : 0;
-       if (fd >= 0) result[i] = (FD_ISSET(fd, &readfds)) ? 1 : 0;
-
-       return(n);
+       return(readselect(max, fds, result, t));
X }
X 
X static int NEAR genbackend(VOID_A)
@@ -229,7 +195,7 @@
X       }
X 
X       safeclose(fds[0]);
-       emufd = fds[1];
+       emufd = newdup(fds[1]);
X       emupid = pid;
X       for (i = 0; i < MAXWINDOWS; i++) {
X               safeclose(ptylist[i].fd);
@@ -617,6 +583,12 @@
X                       sendbuf(fd, &val, sizeof(val));
X                       if (n >= 0 && duptty[n]) sendbuf(fd, duptty[n], val);
X                       break;
+               case TE_INTERNAL:
+                       n = va_arg(args, int);
+                       cp = va_arg(args, char *);
+                       sendbuf(fd, &n, sizeof(n));
+                       sendstring(fd, cp);
+                       break;
X               default:
X                       break;
X       }
@@ -638,6 +610,7 @@
X       sendbuf(emufd, &flags, sizeof(flags));
X       sendstring(emufd, command);
X       sendstring(emufd, arg);
+       sendstring(emufd, fullpath);
X }
X 
X #if   !defined (_NOORIGSHELL) && !defined (NOJOB)
@@ -664,7 +637,7 @@
X char **commandp, **argp;
X int *flagsp;
X {
-       char *command, *arg;
+       char *command, *arg, *cwd;
X       int flags;
X 
X       Xttyiomode(1);
@@ -675,6 +648,10 @@
X               if (command) free(command);
X               return(-1);
X       }
+       if (recvstring(ttyio, &cwd) >= 0 && cwd) {
+               VOID_C chdir2(cwd);
+               free(cwd);
+       }
X 
X       keyflush();
X       if (!(flags & F_TTYIOMODE)) Xstdiomode();
@@ -696,14 +673,14 @@
X {
X       int i, n;
X 
-       if (parentfd < 0) {
+       if (parentfd < 0 && emufd < 0) {
X               if (ptymode) {
-                       hideclock = 1;
+                       hideclock = 2;
X                       warning(0, NOPTY_K);
X               }
X               for (i = 0; i < MAXWINDOWS; i++) if (ptylist[i].pid) break;
X               if (i < MAXWINDOWS) {
-                       hideclock = 1;
+                       hideclock = 2;
X                       if (!yesno(KILL_K)) return(-1);
X                       killallpty();
X               }
@@ -734,7 +711,7 @@
X       }
X       else
X #endif
-       if (!ptymode) return(callmacro(command, arg, flags));
+       if (!ptymode || ptyinternal) return(callmacro(command, arg, flags));
X 
X       if (ptylist[win].pid && emufd >= 0) {
X               awakechild(command, arg, flags);
@@ -812,7 +789,6 @@
X                       dup2(fd, ttyio);
X                       safeclose(fd);
X               }
-               maxfile = -1;
X 
X               setdefterment();
X               setdefkeyseq();
@@ -846,7 +822,7 @@
X 
X       safeclose(fds[1]);
X       ptylist[win].pid = pid;
-       ptylist[win].pipe = fds[0];
+       ptylist[win].pipe = newdup(fds[0]);
X       ptylist[win].status = -1;
X 
X       sigvecset(n);
@@ -880,8 +856,10 @@
X 
X       for (i = 0; i < MAXWINDOWS; i++) {
X               killpty(i, NULL);
-               free(ptylist[i].path);
-               ptylist[i].path = NULL;
+               if (ptylist[i].path) {
+                       free(ptylist[i].path);
+                       ptylist[i].path = NULL;
+               }
X       }
X 
X       if (emupid) {
@@ -900,5 +878,34 @@
X 
X       safeclose(emufd);
X       emufd = -1;
+}
+
+int checkpty(n)
+int n;
+{
+       int status;
+
+       if (!(ptylist[n].pid)) return(0);
+       if (waitstatus(ptylist[n].pid, WNOHANG, &status) < 0) return(0);
+       ptylist[n].pid = (p_id_t)0;
+       ptylist[n].status = status;
+       changewin(n, (p_id_t)0);
+       killpty(n, &status);
+
+       return(-1);
+}
+
+int checkallpty(VOID_A)
+{
+       int i, n;
+
+       n = 0;
+       for (i = 0; i < MAXWINDOWS; i++) if (checkpty(i) < 0) n = -1;
+       if (n < 0) {
+               changewin(MAXWINDOWS, (p_id_t)-1);
+               return(-1);
+       }
+
+       return(0);
X }
X #endif        /* !_NOPTY */
diff -urNP ../FD-2.08a/termemu.h ./termemu.h
--- ../FD-2.08a/termemu.h       Tue Feb  7 00:00:00 2006
+++ ./termemu.h Thu Mar 30 00:00:00 2006
@@ -64,4 +64,5 @@
X #define       TE_LOCKFRONT            25
X #define       TE_UNLOCKFRONT          26
X #define       TE_SAVETTYIO            27
+#define        TE_INTERNAL             28
X #define       TE_CHANGESTATUS         99
diff -urNP ../FD-2.08a/termio.c ./termio.c
--- ../FD-2.08a/termio.c        Tue Feb  7 00:00:00 2006
+++ ./termio.c  Thu Mar 30 00:00:00 2006
@@ -10,6 +10,10 @@
X #include "machine.h"
X #include "termio.h"
X 
+#ifdef USESELECTH
+#include <sys/select.h>
+#endif
+
X #ifndef       NOUNISTDH
X #include <unistd.h>
X #endif
@@ -34,21 +38,21 @@
X 
X #if   defined (USESYSCONF) && defined (_SC_OPEN_MAX)
X #define       MAXOPENFILE     sysconf(_SC_OPEN_MAX)
-#else
+#else  /* !USESYSCONF || !_SC_OPEN_MAX */
X # ifdef       NOFILE
X # define      MAXOPENFILE     NOFILE
-# else
+# else /* !NOFILE */
X #  ifdef      OPEN_MAX
X #  define     MAXOPENFILE     OPEN_MAX
-#  else
+#  else                /* !OPEN_MAX */
X #   if        MSDOS
X #   define    MAXOPENFILE     20
X #   else
X #   define    MAXOPENFILE     64
X #   endif
-#  endif
-# endif
-#endif
+#  endif       /* !OPEN_MAX */
+# endif        /* !NOFILE */
+#endif /* !USESYSCONF || !_SC_OPEN_MAX */
X 
X #ifndef       _PATH_TTY
X # if  MSDOS
@@ -74,6 +78,20 @@
X #endif
X 
X #define       K_CTRL(c)       ((c) & 037)
+#define        MAXFDSET        256
+#define        MAXSELECT       16
+
+#ifndef        FD_SET
+#include "printf.h"
+typedef struct fd_set {
+       u_int fds_bits[1];
+} fd_set;
+# define       FD_SET(n, p)    (((p) -> fds_bits[0]) |= ((u_int)1 << (n)))
+# define       FD_ISSET(n, p)  (((p) -> fds_bits[0]) & ((u_int)1 << (n)))
+# define       FD_ZERO(p)      (((p) -> fds_bits[0]) = 0)
+# undef                MAXFDSET
+# define       MAXFDSET        (BITSPERBYTE * sizeof(u_int))
+#endif /* !FD_SET */
X 
X #if   !defined (FD) || defined (_NODOSDRIVE)
X #define       Xread           read
@@ -596,3 +614,44 @@
X       return(pid);
X }
X #endif        /* CYGWIN */
+
+#if    !MSDOS \
+|| (!defined(NOTUSEBIOS) && defined (DJGPP) && (DJGPP >= 2) && !defined(PC98))
+int readselect(nfd, fds, result, vp)
+int nfd, fds[];
+char result[];
+VOID_P vp;
+{
+       fd_set readfds;
+       int i, n, max, dupfds[MAXSELECT];
+
+       FD_ZERO(&readfds);
+       max = -1;
+       if (nfd > MAXSELECT) nfd = MAXSELECT;
+
+       for (i = 0; i < nfd; i++) {
+               dupfds[i] = fds[i];
+               if (result) result[i] = 0;
+               if (fds[i] < 0) continue;
+               if (fds[i] >= MAXFDSET && (n = safe_dup(fds[i])) >= 0)
+                       dupfds[i] = n;
+               if (dupfds[i] > max) max = dupfds[i];
+               FD_SET(dupfds[i], &readfds);
+       }
+       if (max++ < 0) return(0);
+
+       do {
+               n = select(max, &readfds, NULL, NULL, (struct timeval *)vp);
+       } while (n < 0 && errno == EINTR);
+       for (i = 0; i < nfd; i++)
+               if (dupfds[i] != fds[i]) safeclose(dupfds[i]);
+       if (n <= 0) return(n);
+
+       if (result) for (i = 0; i < nfd; i++) {
+               if (dupfds[i] < 0) continue;
+               if (FD_ISSET(dupfds[i], &readfds)) result[i] = 1;
+       }
+
+       return(n);
+}
+#endif /* !MSDOS || (!NOTUSEBIOS && DJGPP && DJGPP >= 2 && !PC98) */
diff -urNP ../FD-2.08a/termio.h ./termio.h
--- ../FD-2.08a/termio.h        Tue Feb  7 00:00:00 2006
+++ ./termio.h  Thu Mar 30 00:00:00 2006
@@ -257,5 +257,9 @@
X #else
X #define       Xfork           fork
X #endif
+#if    !MSDOS \
+|| (!defined(NOTUSEBIOS) && defined (DJGPP) && (DJGPP >= 2) && !defined(PC98))
+extern int readselect __P_((int, int [], char [], VOID_P));
+#endif
X 
X #endif        /* !__TERMIO_H_ */
diff -urNP ../FD-2.08a/tree.c ./tree.c
--- ../FD-2.08a/tree.c  Tue Feb  7 00:00:00 2006
+++ ./tree.c    Thu Mar 30 00:00:00 2006
@@ -83,9 +83,9 @@
X #if   MSDOS
X       cp = path;
X       if (_dospath(cp)) cp += 2;
-       if (strcmp(cp, _SS_)) strcatdelim(path);
+       if (!isrootpath(cp)) strcatdelim(path);
X #else
-       if (strcmp(path, _SS_)) strcatdelim(path);
+       if (!isrootpath(path)) strcatdelim(path);
X #endif
X       len = strlen(path);
X       i = x = 0;
@@ -103,7 +103,7 @@
X               }
X               else if (disp) {
X                       Xlocate(x + TREEFIELD + 4, min + y);
-                       Xcprintf2("%-*.*k", w, w, dp -> d_name);
+                       cputstr(w, dp -> d_name);
X                       i++;
X                       if (++y >= FILEPERROW) {
X                               y = 1;
@@ -114,7 +114,7 @@
X       }
X       if (disp && !i) {
X               Xlocate(x + TREEFIELD + 4, min + 1);
-               Xcprintf2("%-*.*s", w, w, "[No Files]");
+               cputstr(w, "[No Files]");
X       }
X       Xclosedir(dirp);
X 
@@ -153,7 +153,7 @@
X       if (_dospath(path)) path += 2;
X #endif
X       if (*path == _SC_) {
-               dir = strdup2(_SS_);
+               dir = strdup2(rootpath);
X               subdir = path + 1;
X               if (!*subdir) subdir = NULL;
X       }
@@ -176,7 +176,7 @@
X       *maxp = 0;
X       i = _chdir2(dir);
X       free(dir);
-       if (i < 0 || !(dirp = Xopendir("."))) return(NULL);
+       if (i < 0 || !(dirp = Xopendir(curpath))) return(NULL);
X 
X       i = 0;
X       while ((dp = Xreaddir(dirp))) {
@@ -271,7 +271,7 @@
X       {
X               if (_chdir2(fullpath) < 0) error(fullpath);
X       }
-       else if (strcmp(path, ".") && _chdir2(cwd) < 0) error("..");
+       else if (isdotdir(path) != 2 && _chdir2(cwd) < 0) error(parentpath);
X 
X       return(list);
X }
@@ -336,7 +336,7 @@
X       for (i = 1; i < FILEPERROW; i++) {
X               Xlocate(1, min + i);
X               if (min + i == tr_line) Xputterm(T_STANDOUT);
-               Xcprintf2("%-*.*k", TREEFIELD, TREEFIELD, bufptr(i));
+               cputstr(TREEFIELD, bufptr(i));
X               if (min + i == tr_line) Xputterm(END_STANDOUT);
X       }
X       evaldir(treepath, 1);
@@ -443,7 +443,7 @@
X               return(1);
X       }
X       for (cp = treepath, i = 0; (cp = strdelim(cp, 0)); cp++, i++);
-       lptmp = maketree(".", list -> sub, list, i, &(list -> max));
+       lptmp = maketree(curpath, list -> sub, list, i, &(list -> max));
X       if (_chdir2(fullpath) < 0) lostcwd(fullpath);
X       if (list -> max < 0) {
X               i = (list -> max < -1) ? 1 : 0;
@@ -745,12 +745,12 @@
X #else /* !MSDOS */
X # ifdef       _NODOSDRIVE
X       strcpy(path, fullpath);
-       tr_cur[0].name = strdup2(_SS_);
+       tr_cur[0].name = strdup2(rootpath);
X # else
-       if (dospath("", path)) tr_cur[0].name = strndup2(path, 3);
+       if (dospath(nullstr, path)) tr_cur[0].name = strndup2(path, 3);
X       else {
X               strcpy(path, fullpath);
-               tr_cur[0].name = strdup2(_SS_);
+               tr_cur[0].name = strdup2(rootpath);
X       }
X # endif
X #endif        /* !MSDOS */
@@ -776,7 +776,7 @@
X       if (_dospath(cwd)) cwd += 2;
X # endif
X #endif        /* !MSDOS */
-       if (!strcmp(cwd, _SS_)) /*EMPTY*/;
+       if (isrootpath(cwd)) /*EMPTY*/;
X       else for (cp = cwd; (cp = strdelim(cp, 0)); cp++, tr_line++)
X               if ((tr_line + 1) * DIRFIELD + 2 > TREEFIELD
X               || !(tr_cur = &(tr_cur -> sub[0])))
@@ -811,13 +811,11 @@
X               else if (oy != tr_line) {
X                       Xlocate(1, tr_line);
X                       Xputterm(T_STANDOUT);
-                       Xcprintf2("%-*.*k",
-                               TREEFIELD, TREEFIELD, bufptr(tr_line - min));
+                       cputstr(TREEFIELD, bufptr(tr_line - min));
X                       Xputterm(END_STANDOUT);
X                       Xlocate(1, oy);
X                       if (stable_standout) Xputterm(END_STANDOUT);
-                       else Xcprintf2("%-*.*k",
-                               TREEFIELD, TREEFIELD, bufptr(oy - min));
+                       else cputstr(TREEFIELD, bufptr(oy - min));
X                       evaldir(path, 1);
X               }
X       } while (ch != K_ESC && ch != K_CR);
diff -urNP ../FD-2.08a/types.h ./types.h
--- ../FD-2.08a/types.h Tue Feb  7 00:00:00 2006
+++ ./types.h   Thu Mar 30 00:00:00 2006
@@ -123,6 +123,7 @@
X #define       F_WSMRK                 0002
X #define       F_ISARG                 0004
X #define       F_STAT                  0010
+#define        F_ISCHGDIR              0020
X #define       isdir(file)             ((file) -> flags & F_ISDIR)
X #define       islink(file)            ((file) -> flags & F_ISLNK)
X #define       isdev(file)             ((file) -> flags & F_ISDEV)
@@ -134,6 +135,7 @@
X #define       wasmark(file)           ((file) -> tmpflags & F_WSMRK)
X #define       isarg(file)             ((file) -> tmpflags & F_ISARG)
X #define       havestat(file)          ((file) -> tmpflags & F_STAT)
+#define        ischgdir(file)          ((file) -> tmpflags & F_ISCHGDIR)
X #define       s_isdir(s)              ((((s) -> st_mode) & S_IFMT) == S_IFDIR)
X #define       s_isreg(s)              ((((s) -> st_mode) & S_IFMT) == S_IFREG)
X #define       s_islnk(s)              ((((s) -> st_mode) & S_IFMT) == S_IFLNK)
diff -urNP ../FD-2.08a/unixdisk.c ./unixdisk.c
--- ../FD-2.08a/unixdisk.c      Tue Feb  7 00:00:00 2006
+++ ./unixdisk.c        Thu Mar 30 00:00:00 2006
@@ -44,6 +44,7 @@
X extern char *strcatdelim __P_((char *));
X extern char *strcatdelim2 __P_((char *, char *, char *));
X extern int isdotdir __P_((char *));
+extern char curpath[];
X #else
X static int NEAR _dospath __P_((char *));
X static char *NEAR strdelim __P_((char *, int));
@@ -52,6 +53,7 @@
X static char *NEAR strcatdelim __P_((char *));
X static char *NEAR strcatdelim2 __P_((char *, char *, char *));
X static int NEAR isdotdir __P_((char *));
+static char curpath[] = ".";
X #endif
X 
X #ifdef        DJGPP
@@ -398,7 +400,7 @@
X       }
X 
X       if (!nodir) {
-               path = ".";
+               path = curpath;
X               reg.x.ax = 0x3b00;
X #ifdef        DJGPP
X               dos_putpath(path, 0);
@@ -1934,7 +1936,7 @@
X       strcpy(fbuf, to);
X       if (!(tp = strrdelim(fbuf, 1))) {
X               tp = to;
-               strcpy(fbuf, ".");
+               strcpy(fbuf, curpath);
X       }
X       else {
X               if (*tp == _SC_) tp++;
@@ -2321,8 +2323,8 @@
X #ifdef        _NOUSELFN
X       if ((i = dos_findfirst(path, SEARCHATTRS, &dbuf)) < 0) {
X               if (errno && errno != ENOENT) return(-1);
-               if (!strcmp(path, ".."))
-                       i = dos_findfirst(".", SEARCHATTRS, &dbuf);
+               if (isdotdir(path) == 1)
+                       i = dos_findfirst(curpath, SEARCHATTRS, &dbuf);
X               else i = dos_findfirst(path, DS_IFLABEL, &dbuf);
X       }
X #else /* !_NOUSELFN */
@@ -2340,16 +2342,16 @@
X               fd = (u_int)-1;
X               if ((i = dos_findfirst(path, SEARCHATTRS, &dbuf)) < 0) {
X                       if (errno && errno != ENOENT) return(-1);
-                       if (!strcmp(path, ".."))
-                               i = dos_findfirst(".", SEARCHATTRS, &dbuf);
+                       if (isdotdir(path) == 1)
+                               i = dos_findfirst(curpath, SEARCHATTRS, &dbuf);
X                       else i = dos_findfirst(path, DS_IFLABEL, &dbuf);
X               }
X       }
X       else {
X               if ((i = lfn_findfirst(&fd, path, SEARCHATTRS, &lbuf)) < 0) {
X                       if (errno && errno != ENOENT) return(-1);
-                       if (!strcmp(path, ".."))
-                               i = lfn_findfirst(&fd, ".",
+                       if (isdotdir(path) == 1)
+                               i = lfn_findfirst(&fd, curpath,
X                                       SEARCHATTRS, &lbuf);
X                       else i = dos_findfirst(path, DS_IFLABEL, &dbuf);
X               }
diff -urNP ../FD-2.08a/version.h ./version.h
--- ../FD-2.08a/version.h       Tue Feb  7 00:00:00 2006
+++ ./version.h Thu Mar 30 00:00:00 2006
@@ -5,4 +5,4 @@
X  */
X 
X char *distributor = NULL;
-static char version[] = "@(#)fd.c  2.08a 02/07/06";
+static char version[] = "@(#)fd.c  2.08b 03/30/06";
SHAR_EOF
  $echo 'File' 'FD-2.08b.patch' 'is complete' &&
  $shar_touch -am 03261918106 'FD-2.08b.patch' &&
  chmod 0644 'FD-2.08b.patch' ||
  $echo 'restore of' 'FD-2.08b.patch' 'failed'
  if ( md5sum --help 2>&1 | grep 'sage: md5sum \[' ) >/dev/null 2>&1 \
  && ( md5sum --version 2>&1 | grep -v 'textutils 1.12' ) >/dev/null; then
    md5sum -c << SHAR_EOF >/dev/null 2>&1 \
    || $echo 'FD-2.08b.patch:' 'MD5 check failed'
f4c938307c8d9e177ab5f568cc49098b  FD-2.08b.patch
SHAR_EOF
  else
    shar_count="`LC_ALL= LC_CTYPE= LANG= wc -c < 'FD-2.08b.patch'`"
    test 185215 -eq "$shar_count" ||
    $echo 'FD-2.08b.patch:' 'original size' '185215,' 'current size' "$shar_count!"
  fi
fi
$echo 'You have unpacked the last part'
rm -fr _sh03503
exit 0
-- 
                                               しらい たかし