mirror of
https://github.com/fish-shell/fish-shell.git
synced 2024-11-23 01:36:39 +08:00
Put jobs in functions and block into their own process group in interactive mode, but do not put the 'fake jobs' associated with functions in a group
darcs-hash:20060116001556-ac50b-b91d6e45fe136874237ad31538de02b5e63a8bac.gz
This commit is contained in:
parent
24ca6ceb47
commit
18bbb5ad01
14
exec.c
14
exec.c
|
@ -389,11 +389,11 @@ static int handle_child_io( io_data_t *io, int exit_on_error )
|
|||
|
||||
\return 1 on sucess, 0 on failiure
|
||||
*/
|
||||
static int setup_child_process( job_t *j, int exit_on_error )
|
||||
static int setup_child_process( job_t *j, process_t *p )
|
||||
{
|
||||
int res;
|
||||
|
||||
if( is_interactive && !is_subshell && !is_block)
|
||||
if( is_interactive && p->type==EXTERNAL )
|
||||
{
|
||||
pid_t pid;
|
||||
/*
|
||||
|
@ -418,7 +418,7 @@ static int setup_child_process( job_t *j, int exit_on_error )
|
|||
}
|
||||
}
|
||||
|
||||
res = handle_child_io( j->io, exit_on_error );
|
||||
res = handle_child_io( j->io, (p==0) );
|
||||
|
||||
/* Set the handling for job control signals back to the default. */
|
||||
if( res )
|
||||
|
@ -601,7 +601,7 @@ static void internal_exec_helper( const wchar_t *def,
|
|||
static int handle_new_child( job_t *j, process_t *p )
|
||||
{
|
||||
|
||||
if(is_interactive && !is_subshell && !is_block)
|
||||
if( is_interactive && p->type==EXTERNAL )
|
||||
{
|
||||
int new_pgid=0;
|
||||
|
||||
|
@ -1020,7 +1020,7 @@ void exec( job_t *j )
|
|||
This is the child process. Write out the contents of the pipeline.
|
||||
*/
|
||||
p->pid = getpid();
|
||||
setup_child_process( j, 1 );
|
||||
setup_child_process( j, p );
|
||||
write( io_buffer->fd,
|
||||
io_buffer->param2.out_buffer->buff,
|
||||
io_buffer->param2.out_buffer->used );
|
||||
|
@ -1108,7 +1108,7 @@ void exec( job_t *j )
|
|||
This is the child process.
|
||||
*/
|
||||
p->pid = getpid();
|
||||
setup_child_process( j, 1 );
|
||||
setup_child_process( j, p );
|
||||
if( sb_out->used )
|
||||
fwprintf( stdout, L"%ls", sb_out->buff );
|
||||
if( sb_err->used )
|
||||
|
@ -1150,7 +1150,7 @@ void exec( job_t *j )
|
|||
This is the child process.
|
||||
*/
|
||||
p->pid = getpid();
|
||||
setup_child_process( j, 1 );
|
||||
setup_child_process( j, p );
|
||||
launch_process( p );
|
||||
|
||||
/*
|
||||
|
|
57
proc.c
57
proc.c
|
@ -60,10 +60,14 @@ Some of the code in this file is based on code from the Glibc manual.
|
|||
*/
|
||||
#define BUFFER_SIZE 4096
|
||||
|
||||
/** Status of last process to exit */
|
||||
/**
|
||||
Status of last process to exit
|
||||
*/
|
||||
static int last_status=0;
|
||||
|
||||
/** Signal flag */
|
||||
/**
|
||||
Signal flag
|
||||
*/
|
||||
static sig_atomic_t got_signal=0;
|
||||
|
||||
job_t *first_job=0;
|
||||
|
@ -85,6 +89,7 @@ static event_t event;
|
|||
Stringbuffer used to create arguments when firing events
|
||||
*/
|
||||
static string_buffer_t event_pid;
|
||||
|
||||
/**
|
||||
Stringbuffer used to create arguments when firing events
|
||||
*/
|
||||
|
@ -127,8 +132,9 @@ static void free_process( process_t *p )
|
|||
free( p );
|
||||
}
|
||||
|
||||
/** Remove job from list of jobs */
|
||||
|
||||
/**
|
||||
Remove job from list of jobs
|
||||
*/
|
||||
static int job_remove( job_t *j )
|
||||
{
|
||||
job_t *prev=0, *curr=first_job;
|
||||
|
@ -258,6 +264,8 @@ job_t *job_get_from_pid( int pid )
|
|||
|
||||
/*
|
||||
Return true if all processes in the job have stopped or completed.
|
||||
|
||||
\param j the job to test
|
||||
*/
|
||||
int job_is_stopped( const job_t *j )
|
||||
{
|
||||
|
@ -276,6 +284,8 @@ int job_is_stopped( const job_t *j )
|
|||
|
||||
/*
|
||||
Return true if all processes in the job have completed.
|
||||
|
||||
\param j the job to test
|
||||
*/
|
||||
int job_is_completed( const job_t *j )
|
||||
{
|
||||
|
@ -294,6 +304,8 @@ int job_is_completed( const job_t *j )
|
|||
|
||||
/**
|
||||
Return true if all processes in the job have completed.
|
||||
|
||||
\param j the job to test
|
||||
*/
|
||||
static int job_last_is_completed( const job_t *j )
|
||||
{
|
||||
|
@ -339,7 +351,11 @@ static void mark_process_status( job_t *j,
|
|||
|
||||
/**
|
||||
Handle status update for child \c pid. This function is called by
|
||||
the signal handler, so it mustn't use malloc or any such nonsense.
|
||||
the signal handler, so it mustn't use malloc or any such hitech
|
||||
nonsense.
|
||||
|
||||
\param pid the pid of the process whose status changes
|
||||
\param status the status as returned by wait
|
||||
*/
|
||||
static void handle_child_status( pid_t pid, int status )
|
||||
{
|
||||
|
@ -475,6 +491,9 @@ void job_handle_signal ( int signal, siginfo_t *info, void *con )
|
|||
|
||||
/**
|
||||
Format information about job status for the user to look at.
|
||||
|
||||
\param j the job to test
|
||||
\param status a string description of the job exit type
|
||||
*/
|
||||
static void format_job_info( const job_t *j, const wchar_t *status )
|
||||
{
|
||||
|
@ -733,6 +752,8 @@ void proc_update_jiffies()
|
|||
Check if there are buffers associated with the job, and select on
|
||||
them for a while if available.
|
||||
|
||||
\param j the job to test
|
||||
|
||||
\return 1 if buffers were avaialble, zero otherwise
|
||||
*/
|
||||
static int select_try( job_t *j )
|
||||
|
@ -772,6 +793,8 @@ static int select_try( job_t *j )
|
|||
|
||||
/**
|
||||
Read from descriptors until they are empty.
|
||||
|
||||
\param j the job to test
|
||||
*/
|
||||
static void read_try( job_t *j )
|
||||
{
|
||||
|
@ -823,6 +846,23 @@ static void read_try( job_t *j )
|
|||
}
|
||||
}
|
||||
|
||||
/**
|
||||
Test if a specified job contains external commands
|
||||
|
||||
\param j the job to test
|
||||
*/
|
||||
static int job_is_external( job_t *j )
|
||||
{
|
||||
process_t *p;
|
||||
for( p=j->first_process; p; p=p->next )
|
||||
{
|
||||
if( p->type == EXTERNAL )
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
void job_continue (job_t *j, int cont)
|
||||
{
|
||||
/*
|
||||
|
@ -842,7 +882,7 @@ void job_continue (job_t *j, int cont)
|
|||
|
||||
if( !job_is_completed( j ) )
|
||||
{
|
||||
if( !is_subshell && is_interactive && !is_block)
|
||||
if( is_interactive && job_is_external( j ) )
|
||||
{
|
||||
|
||||
/* Put the job into the foreground. */
|
||||
|
@ -942,8 +982,7 @@ void job_continue (job_t *j, int cont)
|
|||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
if( j->fg )
|
||||
|
@ -971,7 +1010,7 @@ void job_continue (job_t *j, int cont)
|
|||
/*
|
||||
Put the shell back in the foreground.
|
||||
*/
|
||||
if( !is_subshell && is_interactive && !is_block)
|
||||
if( is_interactive && job_is_external( j ) )
|
||||
{
|
||||
signal_block();
|
||||
if( tcsetpgrp (0, getpid()) )
|
||||
|
|
Loading…
Reference in New Issue
Block a user