my
$fs
= Filesys::POSIX->new( Filesys::POSIX::Mem->new );
$fs
->import_module(
'Filesys::POSIX::Userland::Tar'
);
$fs
->
mkdir
(
'foo'
);
$fs
->
symlink
(
'foo'
,
'bar'
);
my
$fd
=
$fs
->
open
(
'foo/baz'
,
$O_CREAT
|
$O_WRONLY
);
foreach
( 1 .. 128 ) {
$fs
->
write
(
$fd
,
'foobarbaz'
, 9 );
}
$fs
->
close
(
$fd
);
$fd
=
$fs
->
open
(
'foo/poop'
,
$O_CREAT
|
$O_WRONLY
);
$fs
->
write
(
$fd
,
'X'
x 256, 256 );
$fs
->
write
(
$fd
,
'O'
x 256, 256 );
$fs
->
close
(
$fd
);
{
my
@parts
=
qw(
asifyoucouldnottell thisissupposedtobe areallydeepdirectorystructure whichpushesthelimits ofthefilelength toa
ratherbignumber soasyoucantelliamjustmaking crapupasi go along
)
;
$fs
->mkpath(
join
(
'/'
,
@parts
) );
}
{
pipe
my
(
$out
,
$in
);
my
$pid
=
fork
;
if
(
$pid
> 0 ) {
close
(
$out
);
lives_ok {
$fs
->tar( Filesys::POSIX::IO::Handle->new(
$in
),
'.'
);
}
"Filesys::POSIX->tar() doesn't seem to vomit"
;
}
elsif
(
$pid
== 0 ) {
close
(
$in
);
while
(
my
$len
=
sysread
(
$out
,
my
$buf
, 512 ) ) {
}
exit
0;
}
elsif
( !
defined
$pid
) {
die
(
"Unable to fork(): $!"
);
}
}
{
my
$tar_pid
= open3(
my
(
$in
,
$out
,
$error
),
qw/tar tf -/
) or
die
(
"Unable to spawn tar: $!"
);
my
$pid
=
fork
;
if
(
$pid
> 0 ) {
close
(
$in
);
while
(
sysread
(
$out
,
my
$buf
, 512 ) ) {
}
waitpid
(
$pid
, 0 );
ok( $? == 0,
"Filesys::POSIX->tar() outputs archive data in a format readable by system tar(1)"
);
}
elsif
(
$pid
== 0 ) {
close
(
$out
);
$fs
->tar( Filesys::POSIX::IO::Handle->new(
$in
),
'.'
);
exit
0;
}
elsif
( !
defined
$pid
) {
die
(
"Unable to fork(): $!"
);
}
}
{
my
$fs
= Filesys::POSIX->new(
Filesys::POSIX::Mem->new,
'noatime'
=> 1
);
$fs
->
symlink
(
'foo'
,
'bar'
);
my
$inode
=
$fs
->
lstat
(
'bar'
);
$inode
->{
'size'
} = 3;
my
$header
= Filesys::POSIX::Userland::Tar::Header->from_inode(
$inode
,
'bar'
);
is(
$header
->{
'size'
}, 0,
"File size on symlink inodes listed as 0 in header objects"
);
}
{
my
@TESTS
= (
{
'path'
=>
'foo'
,
'prefix'
=>
''
,
'suffix'
=>
'foo/'
,
'mode'
=>
$S_IFDIR
| 0755
},
{
'path'
=>
'foo'
,
'prefix'
=>
''
,
'suffix'
=>
'foo'
,
'mode'
=>
$S_IFREG
| 0644
},
{
'path'
=>
'foo/'
,
'prefix'
=>
''
,
'suffix'
=>
'foo/'
,
'mode'
=>
$S_IFDIR
| 0755
},
{
'path'
=>
'foo/'
,
'prefix'
=>
''
,
'suffix'
=>
'foo'
,
'mode'
=>
$S_IFREG
| 0644
},
{
'path'
=>
'foo/bar'
,
'prefix'
=>
''
,
'suffix'
=>
'foo/bar'
,
'mode'
=>
$S_IFREG
| 0644
},
{
'path'
=>
'foo/bar'
,
'prefix'
=>
''
,
'suffix'
=>
'foo/bar/'
,
'mode'
=>
$S_IFDIR
| 0755
},
{
'path'
=>
'/'
. (
'X'
x 154 ) .
'/'
. (
'O'
x 100 ),
'prefix'
=>
'/'
. (
'X'
x 154 ),
'suffix'
=>
'O'
x 100,
'mode'
=>
$S_IFREG
| 0644
},
{
'path'
=>
'/'
. (
'X'
x 155 ) .
'/'
. (
'O'
x 101 ),
'prefix'
=>
'/'
. (
'X'
x 147 ) .
'cba2be6'
,
'suffix'
=> (
'O'
x 93 ) .
'cba2be6'
,
'mode'
=>
$S_IFREG
| 0644
},
{
'path'
=>
'X'
x 130,
'prefix'
=>
''
,
'suffix'
=> (
'X'
x 92 ) .
'da39a3e/'
,
'mode'
=>
$S_IFDIR
| 0755
}
);
foreach
my
$test
(
@TESTS
) {
my
$inode
= Filesys::POSIX::Mem::Inode->new(
'mode'
=>
$test
->{
'mode'
} );
my
$parts
= Filesys::POSIX::Path->new(
$test
->{
'path'
} );
my
$result
= Filesys::POSIX::Userland::Tar::Header::split_path_components(
$parts
,
$inode
);
is(
$result
->{
'prefix'
},
$test
->{
'prefix'
},
"Prefix of '$test->{'path'}' is '$test->{'prefix'}'"
);
is(
$result
->{
'suffix'
},
$test
->{
'suffix'
},
"Suffix of '$test->{'path'}' is '$test->{'suffix'}'"
);
}
}
{
my
$fs
= Filesys::POSIX->new(
Filesys::POSIX::Mem->new,
'noatime'
=> 1
);
$fs
->mkpath(
'foo/bar/baz'
);
{
my
$path
=
'foo/bar/baz/'
. (
'meow'
x 70 );
my
$inode
=
$fs
->mkpath(
$path
);
my
$header
= Filesys::POSIX::Userland::Tar::Header->from_inode(
$inode
,
$path
);
ok(
$header
->{
'path'
} =~ /\/$/,
"$path ends with a / in header object"
);
is(
substr
(
$header
->encode_gnu, 0, 13 ),
'././@LongLink'
,
"GNU tar header for $path contains proper path"
);
}
{
my
$path
=
'foo/bar/baz/'
. (
'bleh'
x 70 );
my
$inode
=
$fs
->touch(
$path
);
my
$header
= Filesys::POSIX::Userland::Tar::Header->from_inode(
$inode
,
$path
);
ok(
$header
->{
'path'
} !~ /\/$/,
"$path does not end with a / in header object"
);
}
}