Add dtach -N.

dtach -N is similar to dtach -n, except dtach will not daemonize.

Based on patches by Ciprian Dorin Craciun and Frank Hunleth.
This commit is contained in:
Ned T. Crigler 2014-08-03 22:24:47 -07:00
parent 8527d8e876
commit c7b68ae3fa
4 changed files with 39 additions and 8 deletions

10
dtach.1
View File

@ -13,6 +13,9 @@ dtach \- simple program that emulates the detach feature of screen.
.br
.B dtach \-n
.I <socket> <options> <command...>
.br
.B dtach \-N
.I <socket> <options> <command...>
.SH DESCRIPTION
.B dtach
@ -93,6 +96,13 @@ which the specified program is executed.
.B dtach
does not try to attach to the newly created session, however, and exits
instead.
.TP
.B \-N
Creates a new session, without attaching to it or daemonizing. A new session is
created in which the specified program is executed.
.B dtach
does not try to attach to the newly created session, however, and will stay
in the foreground until the program exits.
.PP
.SS OPTIONS

View File

@ -128,7 +128,7 @@ struct packet
#define EOS "\033[999H"
int attach_main(int noerror);
int master_main(char **argv, int waitattach);
int master_main(char **argv, int waitattach, int dontfork);
#ifdef sun
#define BROKEN_MASTER

16
main.c
View File

@ -55,6 +55,7 @@ usage()
" dtach -A <socket> <options> <command...>\n"
" dtach -c <socket> <options> <command...>\n"
" dtach -n <socket> <options> <command...>\n"
" dtach -N <socket> <options> <command...>\n"
"Modes:\n"
" -a\t\tAttach to the specified socket.\n"
" -A\t\tAttach to the specified socket, or create it if it\n"
@ -62,6 +63,9 @@ usage()
" -c\t\tCreate a new socket and run the specified command.\n"
" -n\t\tCreate a new socket and run the specified command "
"detached.\n"
" -N\t\tCreate a new socket and run the specified command "
"detached,\n"
"\t\t and have dtach run in the foreground.\n"
"Options:\n"
" -e <char>\tSet the detach character to <char>, defaults "
"to ^\\.\n"
@ -102,7 +106,7 @@ main(int argc, char **argv)
if (mode == '?')
usage();
else if (mode != 'a' && mode != 'c' && mode != 'n' &&
mode != 'A')
mode != 'A' && mode != 'N')
{
printf("%s: Invalid mode '-%c'\n", progname, mode);
printf("Try '%s --help' for more information.\n",
@ -215,7 +219,7 @@ main(int argc, char **argv)
dont_have_tty = 1;
}
if (dont_have_tty && mode != 'n')
if (dont_have_tty && mode != 'n' && mode != 'N')
{
printf("%s: Attaching to a session requires a terminal.\n",
progname);
@ -235,10 +239,12 @@ main(int argc, char **argv)
return attach_main(0);
}
else if (mode == 'n')
return master_main(argv, 0);
return master_main(argv, 0, 0);
else if (mode == 'N')
return master_main(argv, 0, 1);
else if (mode == 'c')
{
if (master_main(argv, 1) != 0)
if (master_main(argv, 1, 0) != 0)
return 1;
return attach_main(0);
}
@ -252,7 +258,7 @@ main(int argc, char **argv)
{
if (errno == ECONNREFUSED)
unlink(sockname);
if (master_main(argv, 1) != 0)
if (master_main(argv, 1, 0) != 0)
return 1;
}
return attach_main(0);

View File

@ -543,7 +543,7 @@ master_process(int s, char **argv, int waitattach, int statusfd)
}
int
master_main(char **argv, int waitattach)
master_main(char **argv, int waitattach, int dontfork)
{
int fd[2] = {-1, -1};
int s;
@ -566,7 +566,16 @@ master_main(char **argv, int waitattach)
/* If FD_CLOEXEC works, create a pipe and use it to report any errors
** that occur while trying to execute the program. */
if (pipe(fd) >= 0)
if (dontfork)
{
fd[1] = dup(2);
if (fcntl(fd[1], F_SETFD, FD_CLOEXEC) < 0)
{
close(fd[1]);
fd[1] = -1;
}
}
else if (pipe(fd) >= 0)
{
if (fcntl(fd[0], F_SETFD, FD_CLOEXEC) < 0 ||
fcntl(fd[1], F_SETFD, FD_CLOEXEC) < 0)
@ -578,6 +587,12 @@ master_main(char **argv, int waitattach)
}
#endif
if (dontfork)
{
master_process(s, argv, waitattach, fd[1]);
return 0;
}
/* Fork off so we can daemonize and such */
pid = fork();
if (pid < 0)