Subject: | File::KeePass damages database files when unknown fields are present |
Date: | Mon, 18 Apr 2011 11:22:32 +0200 |
To: | bug-File-KeePass [...] rt.cpan.org |
From: | Sebastian Schmidt <yath [...] yath.de> |
Hi,
when File::KeePass encounters unknown fields either in the group or in
the entries header they get stored inside $group->{unknown}->{$id} or
$entry->{unknown}->{$id} respectively to be written out again when
saving the database.
However, though the type field was followed by the length, the length is
not written back when generating the database file. This causes the next
field to start four bytes prematurely.
Reproducable by creating an empty database with 0.4.3 (Debian unstable,
in my case), a field with type 0x09 (though unused it is referenced as
"flags" in the source code) gets created.
Sebastian
Patch:
diff -ur File-KeePass-0.03.old/lib/File/KeePass.pm File-KeePass-0.03/lib/File/KeePass.pm
--- File-KeePass-0.03.old/lib/File/KeePass.pm 2011-04-18 11:13:52.000000000 +0200
+++ File-KeePass-0.03/lib/File/KeePass.pm 2011-04-18 11:15:18.000000000 +0200
@@ -442,7 +442,8 @@
[7, pack('LL', 4, $g->{'icon'} || 0)],
[8, pack('LS', 2, $g->{'level'} || 0)],
[0xFFFF, pack('L', 0)]);
- push @d, [$_, $g->{'unknown'}->{$_}] for keys %{ $g->{'unknown'} || {} };
+ push @d, [$_, pack('L', length($g->{'unknown'}->{$_})).$g->{'unknown'}->{$_}]
+ for keys %{ $g->{'unknown'} || {} };
$buffer .= pack('S',$_->[0]).$_->[1] for sort {$a->[0] <=> $b->[0]} @d;
foreach my $e (@{ $g->{'entries'} || [] }) {
$head->{'n_entries'}++;
@@ -462,7 +463,8 @@
[0xD, pack('L', length($e->{'bin_desc'})+1)."$e->{'bin_desc'}\0"],
[0xE, pack('L', length($e->{'binary'})).$e->{'binary'}],
[0xFFFF, pack('L', 0)]);
- push @d, [$_, $e->{'unknown'}->{$_}] for keys %{ $e->{'unknown'} || {} };
+ push @d, [$_, pack('L', length($e->{'unknown'}->{$_})).$e->{'unknown'}->{$_}]
+ for keys %{ $e->{'unknown'} || {} };
$entries .= pack('S',$_->[0]).$_->[1] for sort {$a->[0] <=> $b->[0]} @d;
}
}