Win32-File-Summary
view release on metacpan or search on metacpan
Archive/Tar.pm view on Meta::CPAN
package Archive::Tar;
use strict;
use Carp;
use Cwd;
use File::Basename;
BEGIN {
# This bit is straight from the manpages
use Exporter ();
use vars qw($VERSION @ISA @EXPORT @EXPORT_OK %EXPORT_TAGS $symlinks $compression $has_getpwuid $has_getgrgid);
$VERSION = 0.072;
@ISA = qw(Exporter);
@EXPORT = qw ();
%EXPORT_TAGS = ();
@EXPORT_OK = ();
# The following bit is not straight from the manpages
# Check if symbolic links are available
$symlinks = 1;
eval { $_ = readlink $0; }; # Pointless assigment to make -w shut up
if ($@) {
warn "Symbolic links not available.\n";
$symlinks = undef;
}
# Check if Compress::Zlib is available
$compression = 1;
eval {require Compress::Zlib;};
if ($@) {
warn "Compression not available.\n";
$compression = undef;
}
# Check for get* (they don't exist on WinNT)
eval {$_=getpwuid(0)}; # Pointless assigment to make -w shut up
$has_getpwuid = !$@;
eval {$_=getgrgid(0)}; # Pointless assigment to make -w shut up
$has_getgrgid = !$@;
}
use vars qw(@EXPORT_OK $tar_unpack_header $tar_header_length $error);
$tar_unpack_header
='A100 A8 A8 A8 A12 A12 A8 A1 A100 A6 A2 A32 A32 A8 A8 A155';
$tar_header_length = 512;
sub format_tar_entry;
sub format_tar_file;
###
### Non-method functions
###
sub drat {$error=$!;return undef}
sub read_tar {
my ($filename, $compressed) = @_;
my @tarfile = ();
my $i = 0;
my $head;
if ($compressed) {
if ($compression) {
$compressed = Compress::Zlib::gzopen($filename,"rb") or drat; # Open compressed
$compressed->gzread($head,$tar_header_length);
}
else {
$error = "Compression not available (install Compress::Zlib).\n";
return undef;
}
}
else {
open(TAR, $filename) or drat;
binmode TAR;
read(TAR,$head,$tar_header_length);
}
READLOOP:
while (length($head)==$tar_header_length) {
my ($name, # string
$mode, # octal number
$uid, # octal number
$gid, # octal number
$size, # octal number
$mtime, # octal number
$chksum, # octal number
$typeflag, # character
$linkname, # string
$magic, # string
$version, # two bytes
$uname, # string
$gname, # string
$devmajor, # octal number
$devminor, # octal number
$prefix) = unpack($tar_unpack_header,$head);
my ($data, $diff, $dummy);
Archive/Tar.pm view on Meta::CPAN
sub add_files {
my ($self) = shift;
my (@files) = @_;
my $file;
my ($mode,$uid,$gid,$rdev,$size,$mtime,$data,$typeflag,$linkname);
my $counter = 0;
local ($/);
undef $/;
foreach $file (@files) {
if ((undef,undef,$mode,undef,$uid,$gid,$rdev,$size,
undef,$mtime,undef,undef,undef) = stat($file)) {
$data = "";
$linkname = "";
if (-f $file) { # Plain file
$typeflag = 0;
unless (open(FILE,$file)) {
next; # Can't open file, for some reason. Try next one.
}
binmode FILE;
$data = <FILE>;
$data = "" unless defined $data;
close FILE;
}
elsif (-l $file) { # Symlink
$typeflag = 1;
$linkname = readlink $file if $symlinks;
}
elsif (-d $file) { # Directory
$typeflag = 5;
}
elsif (-p $file) { # Named pipe
$typeflag = 6;
}
elsif (-S $file) { # Socket
$typeflag = 8; # Bogus value, POSIX doesn't believe in sockets
}
elsif (-b $file) { # Block special
$typeflag = 4;
}
elsif (-c $file) { # Character special
$typeflag = 3;
}
else { # Something else (like what?)
$typeflag = 9; # Also bogus value.
}
push(@{$self->{'_data'}},{
name => $file,
mode => $mode,
uid => $uid,
gid => $gid,
size => length $data,
mtime => $mtime,
chksum => " ",
typeflag => $typeflag,
linkname => $linkname,
magic => "ustar\0",
version => "00",
# WinNT protection
uname =>
$has_getpwuid?(getpwuid($uid))[0]:"unknown",
gname =>
$has_getgrgid?(getgrgid($gid))[0]:"unknown",
devmajor => 0, # We don't handle this yet
devminor => 0, # We don't handle this yet
prefix => "",
'data' => $data,
});
$counter++; # Successfully added file
}
else {
next; # stat failed
}
}
return $counter;
}
sub remove {
my ($self) = shift;
my (@files) = @_;
my $file;
foreach $file (@files) {
@{$self->{'_data'}} = grep {$_->{name} ne $file} @{$self->{'_data'}};
}
return $self;
}
# Get the content of a file
sub get_content {
my ($self) = shift;
my ($file) = @_;
my $entry;
($entry) = grep {$_->{name} eq $file} @{$self->{'_data'}};
return $entry->{'data'};
}
# Replace the content of a file
sub replace_content {
my ($self) = shift;
my ($file,$content) = @_;
my $entry;
($entry) = grep {$_->{name} eq $file} @{$self->{'_data'}};
if ($entry) {
$entry->{'data'} = $content;
return 1;
}
else {
return undef;
}
}
# Add data as a file
sub add_data {
my ($self, $file, $data, $opt) = @_;
my $ref = {};
my ($key);
$ref->{'data'}=$data;
$ref->{name}=$file;
$ref->{mode}=0666&(0777-umask);
$ref->{uid}=$>;
$ref->{gid}=(split(/ /,$)))[0]; # Yuck
$ref->{size}=length $data;
$ref->{mtime}=time;
$ref->{chksum}=" "; # Utterly pointless
$ref->{typeflag}=0; # Ordinary file
$ref->{linkname}="";
$ref->{magic}="ustar\0";
$ref->{version}="00";
# WinNT protection
$ref->{uname}=$has_getpwuid?(getpwuid($>))[0]:"unknown";
$ref->{gname}=$has_getgrgid?(getgrgid($ref->{gid}))[0]:"unknown";
$ref->{devmajor}=0;
$ref->{devminor}=0;
$ref->{prefix}="";
if ($opt) {
foreach $key (keys %$opt) {
$ref->{$key} = $opt->{$key}
}
}
push(@{$self->{'_data'}},$ref);
return 1;
}
# Write a single (probably) file from the in-memory archive to disk
sub extract {
my $self = shift;
my (@files) = @_;
my ($file, $current, @path);
foreach $file (@files) {
foreach (@{$self->{'_data'}}) {
if ($_->{name} eq $file) {
# For the moment, we assume that all paths in tarfiles
# are given according to Unix standards.
# Which they *are*, according to the tar format spec!
(@path) = split(/\//,$file);
$file = pop @path;
$current = cwd;
foreach (@path) {
if (-e $_ && ! -d $_) {
warn "$_ exists but is not a directory!\n";
next;
}
mkdir $_,0777 unless -d $_;
chdir $_;
}
if (not $_->{typeflag}) { # Ordinary file
open(FILE,">".$file);
binmode FILE;
print FILE $_->{'data'};
close FILE;
}
elsif ($_->{typeflag}==5) { # Directory
if (-e $file && ! -d $file) {
drat;
}
mkdir $file,0777 unless -d $file;
}
elsif ($_->{typeflag}==1 || $_->{typeflag}==2) {
symlink $_->{linkname},$file if $symlinks;
}
elsif ($_->{typeflag}==6) {
warn "Doesn't handle named pipes (yet).\n";
return 1;
}
elsif ($_->{typeflag}==4) {
warn "Doesn't handle device files (yet).\n";
return 1;
( run in 0.857 second using v1.01-cache-2.11-cpan-39bf76dae61 )