@ -8,40 +8,49 @@
# include "cgit.h"
static int write_tar_gzip _archive ( struct archiver_args * args )
static int write_compressed_ tar_archive ( struct archiver_args * args , const char * filter )
{
int rw [ 2 ] ;
pid_t gzpid ;
int stdout2 ;
int status ;
int rv ;
int rw [ 2 ] ;
pid_t gzpid ;
int stdout2 ;
int status ;
int rv ;
stdout2 = chk_non_negative ( dup ( STDIN_FILENO ) , " Preserving STDOUT before compressing " ) ;
chk_zero ( pipe ( rw ) , " Opening pipe from compressor subprocess " ) ;
gzpid = chk_non_negative ( fork ( ) , " Forking compressor subprocess " ) ;
if ( gzpid = = 0 ) {
/* child */
chk_zero ( close ( rw [ 1 ] ) , " Closing write end of pipe in child " ) ;
chk_zero ( close ( STDIN_FILENO ) , " Closing STDIN " ) ;
chk_non_negative ( dup2 ( rw [ 0 ] , STDIN_FILENO ) , " Redirecting compressor input to stdin " ) ;
execlp ( filter , filter , NULL ) ;
_exit ( - 1 ) ;
}
/* parent */
chk_zero ( close ( rw [ 0 ] ) , " Closing read end of pipe " ) ;
chk_non_negative ( dup2 ( rw [ 1 ] , STDOUT_FILENO ) , " Redirecting output to compressor " ) ;
rv = write_tar_archive ( args ) ;
stdout2 = chk_non_negative ( dup ( STDIN_FILENO ) , " Preserving STDOUT before compressing " ) ;
chk_zero ( pipe ( rw ) , " Opening pipe from compressor subprocess " ) ;
gzpid = chk_non_negative ( fork ( ) , " Forking compressor subprocess " ) ;
if ( gzpid = = 0 ) {
/* child */
chk_zero ( close ( rw [ 1 ] ) , " Closing write end of pipe in child " ) ;
chk_zero ( close ( STDIN_FILENO ) , " Closing STDIN " ) ;
chk_non_negative ( dup2 ( rw [ 0 ] , STDIN_FILENO ) , " Redirecting compressor input to stdin " ) ;
execlp ( " gzip " , " gzip " , NULL ) ;
_exit ( - 1 ) ;
}
/* parent */
chk_zero ( close ( rw [ 0 ] ) , " Closing read end of pipe " ) ;
chk_non_negative ( dup2 ( rw [ 1 ] , STDOUT_FILENO ) , " Redirecting output to compressor " ) ;
rv = write_tar_archive ( args ) ;
chk_zero ( close ( STDOUT_FILENO ) , " Closing STDOUT redirected to compressor " ) ;
chk_non_negative ( dup2 ( stdout2 , STDOUT_FILENO ) , " Restoring uncompressed STDOUT " ) ;
chk_zero ( close ( stdout2 ) , " Closing uncompressed STDOUT " ) ;
chk_zero ( close ( rw [ 1 ] ) , " Closing write end of pipe in parent " ) ;
chk_positive ( waitpid ( gzpid , & status , 0 ) , " Waiting on compressor process " ) ;
if ( ! ( WIFEXITED ( status ) & & WEXITSTATUS ( status ) = = 0 ) )
cgit_print_error ( " Failed to compress archive " ) ;
chk_zero ( close ( STDOUT_FILENO ) , " Closing STDOUT redirected to compressor " ) ;
chk_non_negative ( dup2 ( stdout2 , STDOUT_FILENO ) , " Restoring uncompressed STDOUT " ) ;
chk_zero ( close ( stdout2 ) , " Closing uncompressed STDOUT " ) ;
chk_zero ( close ( rw [ 1 ] ) , " Closing write end of pipe in parent " ) ;
chk_positive ( waitpid ( gzpid , & status , 0 ) , " Waiting on compressor process " ) ;
if ( ! ( WIFEXITED ( status ) & & WEXITSTATUS ( status ) = = 0 ) )
cgit_print_error ( " Failed to compress archive " ) ;
return rv ;
}
return rv ;
static int write_tar_gzip_archive ( struct archiver_args * args )
{
return write_compressed_tar_archive ( args , " gzip " ) ;
}
static int write_tar_bzip2_archive ( struct archiver_args * args )
{
return write_compressed_tar_archive ( args , " bzip2 " ) ;
}
static const struct snapshot_archive_t {
@ -50,7 +59,8 @@ static const struct snapshot_archive_t {
write_archive_fn_t write_func ;
} snapshot_archives [ ] = {
{ " .zip " , " application/x-zip " , write_zip_archive } ,
{ " .tar.gz " , " application/x-gzip " , write_tar_gzip_archive }
{ " .tar.gz " , " application/x-tar " , write_tar_gzip_archive } ,
{ " .tar.bz2 " , " application/x-tar " , write_tar_bzip2_archive }
} ;
void cgit_print_snapshot ( struct cacheitem * item , const char * hex ,
@ -102,3 +112,4 @@ void cgit_print_snapshot_links(const char *repo,const char *hex)
fmt ( " id=%s&name=%s " , hex , filename ) ) , filename ) ;
}
}
/* vim:set sw=8: */