- rewrote the code that searches the for a free pty/tty - it is much cleaner now, as we talked about on the mailing list some time ago. \n- started to apply our styling guide \n- some changes not worth mentioning here and there ;)
git-svn-id: file:///srv/svn/repos/haiku/trunk/current@9534 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
+300
-313
@@ -1,5 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright (c) 2003-4 Kian Duffy <[email protected]>
|
* Copyright (c) 2003-4 Kian Duffy <[email protected]>
|
||||||
|
* Copyright (c) 2004 Daniel Furrer <[email protected]>
|
||||||
* Parts Copyright (C) 1998,99 Kazuho Okui and Takashi Murai.
|
* Parts Copyright (C) 1998,99 Kazuho Okui and Takashi Murai.
|
||||||
*
|
*
|
||||||
* Permission is hereby granted, free of charge, to any person obtaining
|
* Permission is hereby granted, free of charge, to any person obtaining
|
||||||
@@ -28,6 +29,7 @@
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include <dirent.h>
|
||||||
#include <sys/param.h>
|
#include <sys/param.h>
|
||||||
#include <sys/file.h>
|
#include <sys/file.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
@@ -56,7 +58,7 @@ extern char **environ;
|
|||||||
|
|
||||||
char spawn_alert_msg [] = \
|
char spawn_alert_msg [] = \
|
||||||
"alert --stop " \
|
"alert --stop " \
|
||||||
"'MuTerminal Error!!\n\
|
"'Haiku Terminal Error!!\n\
|
||||||
Cannot execute shell [%s].\n\
|
Cannot execute shell [%s].\n\
|
||||||
Check \"Shell\" in preferance panel.' "\
|
Check \"Shell\" in preferance panel.' "\
|
||||||
"'Exec /bin/sh' 'Abort'";
|
"'Exec /bin/sh' 'Abort'";
|
||||||
@@ -68,23 +70,23 @@ Check \"Shell\" in preferance panel.' "\
|
|||||||
void
|
void
|
||||||
Setenv (const char *var, const char *value)
|
Setenv (const char *var, const char *value)
|
||||||
{
|
{
|
||||||
int envindex = 0;
|
int envindex = 0;
|
||||||
const int len = strlen(var);
|
const int len = strlen(var);
|
||||||
const int val_len = strlen (value);
|
const int val_len = strlen (value);
|
||||||
|
|
||||||
while (environ [envindex] != NULL) {
|
while (environ [envindex] != NULL) {
|
||||||
if (strncmp (environ [envindex], var, len) == 0) {
|
if (strncmp (environ [envindex], var, len) == 0) {
|
||||||
/* found it */
|
/* found it */
|
||||||
environ[envindex] = (char *)malloc ((unsigned)len + val_len + 1);
|
environ[envindex] = (char *)malloc ((unsigned)len + val_len + 1);
|
||||||
sprintf (environ [envindex], "%s%s", var, value);
|
sprintf (environ [envindex], "%s%s", var, value);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
envindex ++;
|
envindex ++;
|
||||||
}
|
}
|
||||||
|
|
||||||
environ [envindex] = (char *) malloc ((unsigned)len + val_len + 1);
|
environ [envindex] = (char *) malloc ((unsigned)len + val_len + 1);
|
||||||
sprintf (environ [envindex], "%s%s", var, value);
|
sprintf (environ [envindex], "%s%s", var, value);
|
||||||
environ [++envindex] = NULL;
|
environ [++envindex] = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -104,10 +106,10 @@ int cp_pipe[2]; /* this pipe is used for child to parent transfer */
|
|||||||
/* handshake interface */
|
/* handshake interface */
|
||||||
typedef struct
|
typedef struct
|
||||||
{
|
{
|
||||||
int status; /* status of child */
|
int status; /* status of child */
|
||||||
char msg[256]; /* error message */
|
char msg[256]; /* error message */
|
||||||
int row; /* terminal rows */
|
int row; /* terminal rows */
|
||||||
int col; /* Terminal columns */
|
int col; /* Terminal columns */
|
||||||
} handshake_t;
|
} handshake_t;
|
||||||
|
|
||||||
/* status of handshake */
|
/* status of handshake */
|
||||||
@@ -118,356 +120,341 @@ typedef struct
|
|||||||
/* global varriables */
|
/* global varriables */
|
||||||
|
|
||||||
pid_t sh_pid;
|
pid_t sh_pid;
|
||||||
char tty_name[16];
|
char tty_name[B_PATH_NAME_LENGTH];
|
||||||
int pfd_num = 0;
|
|
||||||
|
|
||||||
int
|
int
|
||||||
spawn_shell (int row, int col, const char *command, const char *coding)
|
spawn_shell (int row, int col, const char *command, const char *coding)
|
||||||
{
|
{
|
||||||
int done = 0;
|
int done = 0;
|
||||||
char *s;
|
pid_t pgrp;
|
||||||
char *t = 0;
|
|
||||||
pid_t pgrp;
|
|
||||||
|
|
||||||
int master = 0;
|
int master = 0;
|
||||||
int slave;
|
int slave;
|
||||||
struct termios tio;
|
struct termios tio;
|
||||||
struct winsize ws;
|
struct winsize ws;
|
||||||
|
|
||||||
handshake_t handshake;
|
handshake_t handshake;
|
||||||
|
|
||||||
char pty_name[16];
|
int i = 0;
|
||||||
|
time_t now_time_t;
|
||||||
int i = 0;
|
struct tm *now_time;
|
||||||
time_t now_time_t;
|
int now_hour;
|
||||||
struct tm *now_time;
|
|
||||||
int now_hour;
|
|
||||||
|
|
||||||
char *args[16];
|
char *args[16];
|
||||||
char com_line[256];
|
char com_line[256];
|
||||||
char *ptr;
|
char *ptr;
|
||||||
|
|
||||||
char err_msg[256];
|
char err_msg[256];
|
||||||
|
|
||||||
signal (SIGTTOU, SIG_IGN);
|
signal(SIGTTOU, SIG_IGN);
|
||||||
|
|
||||||
/*
|
|
||||||
* Get a psuedo-tty. We do this by cycling through all the possible
|
|
||||||
* names. The oparationg system will not allow us to open a master
|
|
||||||
* which is already in use, so we simply go until the open successed.
|
|
||||||
*/
|
|
||||||
|
|
||||||
for (s = PTYCHAR1; *s != 0; s++) {
|
|
||||||
for (t = PTYCHAR2; *t != 0; t++) {
|
|
||||||
sprintf (pty_name, PTYDEV, *s, *t);
|
|
||||||
if ((master = open (pty_name, O_RDWR)) >= 0)
|
|
||||||
goto out;
|
|
||||||
pfd_num++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
out:
|
|
||||||
/*
|
|
||||||
* If s and t are NULL, we ran out of pseudo ttys before we found
|
|
||||||
* one we can use
|
|
||||||
*/
|
|
||||||
if ((*s == 0) && (*t == 0)) {
|
|
||||||
printf ("don't found pesudo ttys.");
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Change "/dev/pt/XX (master) to "/dev/tt/XX" (slave). */
|
|
||||||
|
|
||||||
sprintf (pty_name,"%c%c", *s, *t);
|
|
||||||
sprintf (tty_name, TTYDEV, *s, *t);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Get the modes of the current terminal. We will duplicates these
|
|
||||||
* on the pseudo terminal.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* Create pipe that be use to handshake */
|
|
||||||
if ( pipe (pc_pipe) || pipe (cp_pipe)) {
|
|
||||||
printf ("Could not create handshake pipe.");
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* If set prosess group ID is MuTerminal process ID, MuTerminal
|
|
||||||
* ignore SIGINT for exec Terminal.
|
|
||||||
*
|
|
||||||
* pgrp = getpid ();
|
|
||||||
* setpgid (0, pgrp);
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* Fork a child process. */
|
|
||||||
if ((sh_pid=fork()) < 0) {
|
|
||||||
close (master);
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (sh_pid == 0) {
|
|
||||||
/*
|
|
||||||
* Now in child process.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* close master pty and control tty. */
|
|
||||||
// close (tty);
|
|
||||||
// for (i = 0; i <= 2; i++)
|
|
||||||
// close (i);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Make our controlling tty the pseudo tty. This hapens because
|
|
||||||
* we cleared our original controlling terminal above.
|
|
||||||
*/
|
|
||||||
|
|
||||||
close (cp_pipe[0]);
|
|
||||||
close (pc_pipe[1]);
|
|
||||||
|
|
||||||
/* Set process session leader */
|
|
||||||
if ((pgrp = setsid()) < 0) {
|
|
||||||
handshake.status = PTY_NG;
|
|
||||||
sprintf (handshake.msg, "could not set session leader.");
|
|
||||||
write (cp_pipe[1], (char *)&handshake, sizeof (handshake));
|
|
||||||
exit (1);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* change pty owner and asscess mode. */
|
|
||||||
chown (tty_name, getuid(), getgid());
|
|
||||||
chmod (tty_name, S_IRUSR | S_IWUSR);
|
|
||||||
|
|
||||||
/* open slave pty */
|
|
||||||
if ((slave = open (tty_name, O_RDWR)) < 0) {
|
|
||||||
handshake.status = PTY_NG;
|
|
||||||
sprintf (handshake.msg, "can't open tty (%s).", tty_name);
|
|
||||||
write (cp_pipe[1], (char *)&handshake, sizeof (handshake));
|
|
||||||
exit (1);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* get tty termios (don't necessary). */
|
|
||||||
tcgetattr (slave, &tio);
|
|
||||||
|
|
||||||
/* set signal default */
|
|
||||||
signal (SIGCHLD, SIG_DFL);
|
|
||||||
signal (SIGHUP, SIG_DFL);
|
|
||||||
signal (SIGQUIT, SIG_DFL);
|
|
||||||
signal (SIGTERM, SIG_DFL);
|
|
||||||
signal (SIGINT, SIG_DFL);
|
|
||||||
signal (SIGTTOU, SIG_DFL);
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Set Terminal interface.
|
* Get a psuedo-tty. We do this by cycling through files in the
|
||||||
*/
|
* directory. The oparationg system will not allow us to open a master
|
||||||
|
* which is already in use, so we simply go until the open succeeds.
|
||||||
|
*/
|
||||||
|
|
||||||
tio.c_line = 0;
|
DIR *dir;
|
||||||
|
dir = opendir("/dev/pt/");
|
||||||
|
|
||||||
|
struct dirent *dir_entry;
|
||||||
|
char pty_name[B_PATH_NAME_LENGTH];
|
||||||
|
while(NULL != (dir_entry = readdir(dir)))
|
||||||
|
{
|
||||||
|
if (dir_entry->d_name[0] == '.') // skip . and ..
|
||||||
|
continue;
|
||||||
|
sprintf(pty_name, "/dev/pt/%s", dir_entry->d_name);
|
||||||
|
printf("%s\n", pty_name);
|
||||||
|
master = open(pty_name, O_RDWR);
|
||||||
|
if (master >= 0)
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
// If master is still < 0 then we haven't found a tty we can use
|
||||||
|
if (master < 0)
|
||||||
|
{
|
||||||
|
printf("didn't find any available pesudo ttys.");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Set the tty that corresponds to the pty we found
|
||||||
|
sprintf (tty_name, "/dev/tt/%s", dir_entry->d_name);
|
||||||
|
|
||||||
tio.c_lflag |= ECHOE;
|
/*
|
||||||
|
* Get the modes of the current terminal. We will duplicates these
|
||||||
|
* on the pseudo terminal.
|
||||||
|
*/
|
||||||
|
|
||||||
/* input: nl->nl, cr->nl */
|
/* Create pipe that be use to handshake */
|
||||||
tio.c_iflag &= ~(INLCR|IGNCR);
|
if ( pipe (pc_pipe) || pipe (cp_pipe)) {
|
||||||
tio.c_iflag |= ICRNL;
|
printf ("Could not create handshake pipe.");
|
||||||
tio.c_iflag &= ~ISTRIP;
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Fork a child process. */
|
||||||
|
if ((sh_pid = fork()) < 0) {
|
||||||
|
close(master);
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (sh_pid == 0) {
|
||||||
|
/*
|
||||||
|
* Now in child process.
|
||||||
|
*/
|
||||||
|
|
||||||
/* output: cr->cr, nl in not retrun, no delays, ln->cr/ln */
|
/*
|
||||||
tio.c_oflag &= ~(OCRNL|ONLRET|NLDLY|CRDLY|TABDLY|BSDLY|VTDLY|FFDLY);
|
* Make our controlling tty the pseudo tty. This hapens because
|
||||||
tio.c_oflag |= ONLCR;
|
* we cleared our original controlling terminal above.
|
||||||
tio.c_oflag |= OPOST;
|
*/
|
||||||
|
|
||||||
|
close(cp_pipe[0]);
|
||||||
|
close(pc_pipe[1]);
|
||||||
|
|
||||||
|
/* Set process session leader */
|
||||||
|
if ((pgrp = setsid()) < 0) {
|
||||||
|
handshake.status = PTY_NG;
|
||||||
|
sprintf(handshake.msg, "could not set session leader.");
|
||||||
|
write(cp_pipe[1], (char *)&handshake, sizeof (handshake));
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* change pty owner and asscess mode. */
|
||||||
|
chown (tty_name, getuid(), getgid());
|
||||||
|
chmod (tty_name, S_IRUSR | S_IWUSR);
|
||||||
|
|
||||||
|
/* open slave pty */
|
||||||
|
if ((slave = open (tty_name, O_RDWR)) < 0) {
|
||||||
|
handshake.status = PTY_NG;
|
||||||
|
sprintf (handshake.msg, "can't open tty (%s).", tty_name);
|
||||||
|
write (cp_pipe[1], (char *)&handshake, sizeof (handshake));
|
||||||
|
exit (1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* get tty termios (don't necessary). */
|
||||||
|
tcgetattr (slave, &tio);
|
||||||
|
|
||||||
|
/* set signal default */
|
||||||
|
signal (SIGCHLD, SIG_DFL);
|
||||||
|
signal (SIGHUP, SIG_DFL);
|
||||||
|
signal (SIGQUIT, SIG_DFL);
|
||||||
|
signal (SIGTERM, SIG_DFL);
|
||||||
|
signal (SIGINT, SIG_DFL);
|
||||||
|
signal (SIGTTOU, SIG_DFL);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Set Terminal interface.
|
||||||
|
*/
|
||||||
|
|
||||||
|
tio.c_line = 0;
|
||||||
|
|
||||||
|
tio.c_lflag |= ECHOE;
|
||||||
|
|
||||||
|
/* input: nl->nl, cr->nl */
|
||||||
|
tio.c_iflag &= ~(INLCR|IGNCR);
|
||||||
|
tio.c_iflag |= ICRNL;
|
||||||
|
tio.c_iflag &= ~ISTRIP;
|
||||||
|
|
||||||
|
/* output: cr->cr, nl in not retrun, no delays, ln->cr/ln */
|
||||||
|
tio.c_oflag &= ~(OCRNL|ONLRET|NLDLY|CRDLY|TABDLY|BSDLY|VTDLY|FFDLY);
|
||||||
|
tio.c_oflag |= ONLCR;
|
||||||
|
tio.c_oflag |= OPOST;
|
||||||
|
|
||||||
|
|
||||||
/* baud rate is 19200 (equal beterm) */
|
/* baud rate is 19200 (equal beterm) */
|
||||||
tio.c_cflag &= ~(CBAUD);
|
tio.c_cflag &= ~(CBAUD);
|
||||||
tio.c_cflag |= B19200;
|
tio.c_cflag |= B19200;
|
||||||
|
|
||||||
tio.c_cflag &= ~CSIZE;
|
tio.c_cflag &= ~CSIZE;
|
||||||
tio.c_cflag |= CS8;
|
tio.c_cflag |= CS8;
|
||||||
tio.c_cflag |= CREAD;
|
tio.c_cflag |= CREAD;
|
||||||
|
|
||||||
tio.c_cflag |= HUPCL;
|
tio.c_cflag |= HUPCL;
|
||||||
tio.c_iflag &= ~(IGNBRK|BRKINT);
|
tio.c_iflag &= ~(IGNBRK|BRKINT);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* enable signals, canonical processing (erase, kill, etc), echo.
|
* enable signals, canonical processing (erase, kill, etc), echo.
|
||||||
*/
|
*/
|
||||||
tio.c_lflag |= ISIG|ICANON|ECHO|ECHOE|ECHONL;
|
tio.c_lflag |= ISIG|ICANON|ECHO|ECHOE|ECHONL;
|
||||||
tio.c_lflag &= ~ECHOK;
|
tio.c_lflag &= ~ECHOK;
|
||||||
|
|
||||||
tio.c_lflag &= ~IEXTEN;
|
tio.c_lflag &= ~IEXTEN;
|
||||||
|
|
||||||
|
|
||||||
/* set control charactors. */
|
/* set control charactors. */
|
||||||
tio.c_cc[VINTR] = 'C' & 0x1f; /* '^C' */
|
tio.c_cc[VINTR] = 'C' & 0x1f; /* '^C' */
|
||||||
tio.c_cc[VQUIT] = CQUIT; /* '^\' */
|
tio.c_cc[VQUIT] = CQUIT; /* '^\' */
|
||||||
tio.c_cc[VERASE] = 0x08; /* '^H' */
|
tio.c_cc[VERASE] = 0x08; /* '^H' */
|
||||||
tio.c_cc[VKILL] = 'U' & 0x1f; /* '^U' */
|
tio.c_cc[VKILL] = 'U' & 0x1f; /* '^U' */
|
||||||
tio.c_cc[VEOF] = CEOF; /* '^D' */
|
tio.c_cc[VEOF] = CEOF; /* '^D' */
|
||||||
tio.c_cc[VEOL] = CEOL; /* '^@' */
|
tio.c_cc[VEOL] = CEOL; /* '^@' */
|
||||||
tio.c_cc[VMIN] = 4;
|
tio.c_cc[VMIN] = 4;
|
||||||
tio.c_cc[VTIME] = 0;
|
tio.c_cc[VTIME] = 0;
|
||||||
tio.c_cc[VEOL2] = CEOL; /* '^@' */
|
tio.c_cc[VEOL2] = CEOL; /* '^@' */
|
||||||
tio.c_cc[VSWTCH] = CSWTCH; /* '^@' */
|
tio.c_cc[VSWTCH] = CSWTCH; /* '^@' */
|
||||||
tio.c_cc[VSTART] = CSTART; /* '^S' */
|
tio.c_cc[VSTART] = CSTART; /* '^S' */
|
||||||
tio.c_cc[VSTOP] = CSTOP; /* '^Q' */
|
tio.c_cc[VSTOP] = CSTOP; /* '^Q' */
|
||||||
tio.c_cc[VSUSP] = CSUSP; /* '^@' */
|
tio.c_cc[VSUSP] = CSUSP; /* '^@' */
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* change control tty.
|
* change control tty.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
dup2 (slave, 0);
|
dup2 (slave, 0);
|
||||||
dup2 (slave, 1);
|
dup2 (slave, 1);
|
||||||
dup2 (slave, 2);
|
dup2 (slave, 2);
|
||||||
|
|
||||||
/* close old slave fd. */
|
/* close old slave fd. */
|
||||||
if (slave > 2)
|
if (slave > 2)
|
||||||
close (slave);
|
close (slave);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* set terminal interface.
|
* set terminal interface.
|
||||||
*/
|
*/
|
||||||
if (tcsetattr (0, TCSANOW, &tio) == -1) {
|
if (tcsetattr (0, TCSANOW, &tio) == -1) {
|
||||||
handshake.status = PTY_NG;
|
handshake.status = PTY_NG;
|
||||||
sprintf (handshake.msg, "failed set terminal interface (TERMIOS).");
|
sprintf (handshake.msg, "failed set terminal interface (TERMIOS).");
|
||||||
write (cp_pipe[1], (char *)&handshake, sizeof (handshake));
|
write (cp_pipe[1], (char *)&handshake, sizeof (handshake));
|
||||||
exit (1);
|
exit (1);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* set window size.
|
* set window size.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
handshake.status = PTY_WS;
|
handshake.status = PTY_WS;
|
||||||
write (cp_pipe[1], (char *)&handshake, sizeof (handshake));
|
write (cp_pipe[1], (char *)&handshake, sizeof (handshake));
|
||||||
read (pc_pipe[0], (char *)&handshake, sizeof (handshake));
|
read (pc_pipe[0], (char *)&handshake, sizeof (handshake));
|
||||||
|
|
||||||
if (handshake.status != PTY_WS) {
|
if (handshake.status != PTY_WS) {
|
||||||
handshake.status = PTY_NG;
|
handshake.status = PTY_NG;
|
||||||
sprintf (handshake.msg, "missmatch handshake.");
|
sprintf (handshake.msg, "missmatch handshake.");
|
||||||
write (cp_pipe[1], (char *)&handshake, sizeof (handshake));
|
write (cp_pipe[1], (char *)&handshake, sizeof (handshake));
|
||||||
exit (1);
|
exit (1);
|
||||||
}
|
}
|
||||||
|
|
||||||
ws.ws_row = handshake.row;
|
ws.ws_row = handshake.row;
|
||||||
ws.ws_col = handshake.col;
|
ws.ws_col = handshake.col;
|
||||||
|
|
||||||
ioctl (0, TIOCSWINSZ, &ws);
|
ioctl (0, TIOCSWINSZ, &ws);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Set process group ID to process, and Terminal Process group ID
|
* Set process group ID to process, and Terminal Process group ID
|
||||||
* to this process group ID (equal process ID).
|
* to this process group ID (equal process ID).
|
||||||
*/
|
*/
|
||||||
|
|
||||||
pgrp = getpid ();
|
pgrp = getpid();
|
||||||
setpgid (pgrp, pgrp);
|
setpgid(pgrp, pgrp);
|
||||||
tcsetpgrp (0, pgrp);
|
tcsetpgrp(0, pgrp);
|
||||||
|
|
||||||
/* mark the pipes as close on exec */
|
/* mark the pipes as close on exec */
|
||||||
fcntl( cp_pipe[1], F_SETFD, 1);
|
fcntl( cp_pipe[1], F_SETFD, 1);
|
||||||
fcntl( pc_pipe[0], F_SETFD, 1);
|
fcntl( pc_pipe[0], F_SETFD, 1);
|
||||||
|
|
||||||
/* pty open and set termios successful. */
|
/* pty open and set termios successful. */
|
||||||
handshake.status = PTY_OK;
|
handshake.status = PTY_OK;
|
||||||
write (cp_pipe[1], (char *)&handshake, sizeof (handshake));
|
write (cp_pipe[1], (char *)&handshake, sizeof (handshake));
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* setenv TERM and TTY.
|
* setenv TERM and TTY.
|
||||||
*/
|
*/
|
||||||
Setenv ("TERM=", "xterm");
|
Setenv ("TERM=", "xterm");
|
||||||
Setenv ("TTY=",tty_name);
|
Setenv ("TTY=",tty_name);
|
||||||
Setenv ("TTYPE=", coding);
|
Setenv ("TTYPE=", coding);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* If don't set command args, exec SHELL_COMMAND.
|
* If don't set command args, exec SHELL_COMMAND.
|
||||||
*/
|
*/
|
||||||
if (command == NULL) {
|
if (command == NULL) {
|
||||||
command = SHELL_COMMAND;
|
command = SHELL_COMMAND;
|
||||||
}
|
}
|
||||||
|
|
||||||
memcpy (com_line, command, 256);
|
memcpy (com_line, command, 256);
|
||||||
ptr = com_line;
|
ptr = com_line;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* split up the arguments in the command into an artv-like structure.
|
* split up the arguments in the command into an artv-like structure.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
while (*ptr) {
|
while (*ptr) {
|
||||||
/* Skip white space */
|
/* Skip white space */
|
||||||
while ((*ptr == ' ') || (*ptr == '\t'))
|
while ((*ptr == ' ') || (*ptr == '\t'))
|
||||||
*ptr++ = 0;
|
*ptr++ = 0;
|
||||||
args[i++] = ptr;
|
args[i++] = ptr;
|
||||||
|
|
||||||
/* Skip over this word to next white space. */
|
/* Skip over this word to next white space. */
|
||||||
while ((*ptr != 0) && (*ptr != ' ') && (*ptr != '\t'))
|
while ((*ptr != 0) && (*ptr != ' ') && (*ptr != '\t'))
|
||||||
ptr++;
|
ptr++;
|
||||||
}
|
}
|
||||||
|
|
||||||
args[i] = NULL;
|
args[i] = NULL;
|
||||||
|
|
||||||
Setenv ("SHELL=", *args);
|
Setenv ("SHELL=", *args);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Print Welcome MuTerm World! Message.
|
* Print Welcome Message.
|
||||||
* (But, Only print message when MuTerminal coding is UTF8.)
|
* (But, Only print message when MuTerminal coding is UTF8.)
|
||||||
*/
|
*/
|
||||||
now_time_t = time(NULL);
|
now_time_t = time(NULL);
|
||||||
now_time = localtime (&now_time_t);
|
now_time = localtime (&now_time_t);
|
||||||
|
|
||||||
if (now_time->tm_hour >= 5 && now_time->tm_hour < 11) {
|
if (now_time->tm_hour >= 5 && now_time->tm_hour < 11) {
|
||||||
now_hour = 0;
|
now_hour = 0;
|
||||||
} else if (now_time->tm_hour >= 11 && now_time->tm_hour <= 18 ) {
|
} else if (now_time->tm_hour >= 11 && now_time->tm_hour <= 18 ) {
|
||||||
now_hour = 1;
|
now_hour = 1;
|
||||||
} else {
|
} else {
|
||||||
now_hour = 2;
|
now_hour = 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
execve (*args, args, environ);
|
execve (*args, args, environ);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Exec failed.
|
* Exec failed.
|
||||||
*/
|
*/
|
||||||
sleep (1);
|
sleep (1);
|
||||||
sprintf (err_msg, spawn_alert_msg, com_line);
|
sprintf (err_msg, spawn_alert_msg, com_line);
|
||||||
|
|
||||||
if (system (err_msg) == 0)
|
if (system (err_msg) == 0)
|
||||||
execl ("/bin/sh", "/bin/sh", "-login", NULL);
|
execl ("/bin/sh", "/bin/sh", "-login", NULL);
|
||||||
|
|
||||||
exit (1);
|
exit(1);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* In parent Process, Set up the input and output file pointers so
|
* In parent Process, Set up the input and output file pointers so
|
||||||
* that they can write and read the pseudo terminal.
|
* that they can write and read the pseudo terminal.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/* close childs's side of the pipe */
|
/* close childs's side of the pipe */
|
||||||
close (cp_pipe[1]);
|
close(cp_pipe[1]);
|
||||||
close (pc_pipe[0]);
|
close(pc_pipe[0]);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* close parent control tty.
|
* close parent control tty.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
while (!done) {
|
while (!done) {
|
||||||
read (cp_pipe[0], (char *)&handshake, sizeof (handshake));
|
read (cp_pipe[0], (char *)&handshake, sizeof (handshake));
|
||||||
|
|
||||||
switch (handshake.status) {
|
switch (handshake.status) {
|
||||||
case PTY_OK:
|
case PTY_OK:
|
||||||
done = 1;
|
done = 1;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case PTY_NG:
|
case PTY_NG:
|
||||||
printf ("%s\n", handshake.msg);
|
printf("%s\n", handshake.msg);
|
||||||
done = -1;
|
done = -1;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case PTY_WS:
|
case PTY_WS:
|
||||||
handshake.row = row;
|
handshake.row = row;
|
||||||
handshake.col = col;
|
handshake.col = col;
|
||||||
handshake.status = PTY_WS;
|
handshake.status = PTY_WS;
|
||||||
write (pc_pipe[1], (char *)&handshake, sizeof (handshake));
|
write(pc_pipe[1], (char *)&handshake, sizeof (handshake));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return (done > 0) ? master : -1;
|
return (done > 0) ? master : -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright (c) 2003-4 Kian Duffy <[email protected]>
|
* Copyright (c) 2003-4 Kian Duffy <[email protected]>
|
||||||
|
* Copyright (c) 2004 Daniel Furrer <[email protected]>
|
||||||
* Parts Copyright (C) 1998,99 Kazuho Okui and Takashi Murai.
|
* Parts Copyright (C) 1998,99 Kazuho Okui and Takashi Murai.
|
||||||
*
|
*
|
||||||
* Permission is hereby granted, free of charge, to any person obtaining
|
* Permission is hereby granted, free of charge, to any person obtaining
|
||||||
@@ -31,19 +32,6 @@
|
|||||||
#ifndef SPAWN_H
|
#ifndef SPAWN_H
|
||||||
#define SPAWN_H
|
#define SPAWN_H
|
||||||
|
|
||||||
/*
|
|
||||||
* allow for mobility of the pty master/slave directories
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define PTYDEV "/dev/pt/%c%c"
|
|
||||||
#define TTYDEV "/dev/tt/%c%c"
|
|
||||||
|
|
||||||
#define PTYCHAR1 "pqrs"
|
|
||||||
#define PTYCHAR2 "0123456789abcdef"
|
|
||||||
|
|
||||||
#define TTYFORMAT "/dev/tt/%d"
|
|
||||||
#define PTYFORMAT "/dev/pt/%d"
|
|
||||||
|
|
||||||
#define MAXPTTYS 16 * 4
|
#define MAXPTTYS 16 * 4
|
||||||
|
|
||||||
#ifndef CEOF
|
#ifndef CEOF
|
||||||
|
|||||||
Reference in New Issue
Block a user