File Coverage

blib/lib/XML/Generator/Pdb.pm
Criterion Covered Total %
statement 12 78 15.3
branch 0 24 0.0
condition 0 6 0.0
subroutine 4 9 44.4
pod 0 5 0.0
total 16 122 13.1


line stmt bran cond sub pod time code
1             # $Id: Pdb.pm,v 1.1.1.1 2003/04/06 21:20:57 cvsjohan Exp $
2              
3             package XML::Generator::Pdb;
4 1     1   29191 use strict;
  1         3  
  1         38  
5 1     1   5 use warnings;
  1         2  
  1         41  
6              
7             our $VERSION = '0.1';
8              
9 1     1   1124 use Palm::Raw;
  1         9852  
  1         6  
10 1     1   50 use Palm::PDB;
  1         2  
  1         1764  
11              
12             sub new {
13 0     0 0   my ($proto, %arg) = @_;
14 0   0       my $class = ref($proto) || $proto;
15 0           my $self = { %arg };
16 0           bless $self, $class;
17            
18 0 0         $self->{PDBFile} || die "Please provide a 'PDBFile'";
19 0 0         $self->{Layout} || die "I need a 'Layout'";
20            
21 0           return $self;
22             }
23              
24             sub parse {
25 0     0 0   my $self = shift;
26              
27             # Open PDB
28 0           my $pdb = Palm::PDB->new;
29 0 0         $pdb->Load( $self->{PDBFile} ) || croak( "Couldn't open PDB: $!" );
30 0           my @records = @{$pdb->{"records"}};
  0            
31              
32             # Produce header and pdb start tag
33 0           $self->{Handler}->start_document();
34 0           $self->{Handler}->start_element(
35             {
36             Name => 'pdb',
37             Attributes =>
38             {
39             type => $pdb->{"type"},
40             name => $pdb->{"name"},
41             creator => $pdb->{"creator"}
42             }
43             });
44            
45             # For each element, try to parse and generate
46 0           for my $record (@records) {
47 0           $self->{Handler}->start_element(
48             {
49             Name => 'record',
50             Attributes =>
51             {
52             category => $record->{"category"}
53             }
54             });
55              
56 0           my $data = $record->{"data"};
57 0           my $offset = 0;
58 0           for my $field (@{$self->{Layout}}) {
  0            
59 0 0 0       if ($field eq 'int') {
    0          
    0          
    0          
    0          
    0          
    0          
60 0           my $value = unpack("N", substr($data, $offset, 4));
61 0           $offset += 4;
62 0           $self->field($field, $value, undef);
63             } elsif ($field eq 'date') {
64 0           my $raw = pack("C*",reverse unpack("C*",substr($data,$offset,8)));
65 0           my $unpacked = unpack("d", $raw);
66 0           my $value = $self->convert_date_from_nsbasic( $unpacked );
67 0           $offset += 8;
68 0           $self->field($field, $value, undef);
69             } elsif ($field eq 'time') {
70 0           my $raw = pack("C*",reverse unpack("C*",substr($data,$offset,8)));
71 0           my $unpacked = unpack("d", $raw);
72 0           my $value = $self->convert_time_from_nsbasic( $unpacked );
73 0           $offset += 8;
74 0           $self->field($field, $value, undef);
75             } elsif ($field eq 'byte') {
76 0           my $value = unpack("C", substr($data, $offset, 1));
77 0           $offset += 1;
78 0           $self->field($field, $value, undef);
79             } elsif ($field eq 'float' || $field eq 'double') {
80 0           my $raw = pack("C*",reverse unpack("C*",substr($data,$offset,8)));
81 0           my $value = unpack("d", $raw);
82 0           $offset += 8;
83             } elsif ($field eq 'short') {
84 0           my $value = unpack("n", substr($data, $offset, 2));
85 0           $offset += 2;
86 0           $self->field($field, $value, undef);
87             } elsif ($field eq 'text') {
88 0           my ($content) = ( substr($data, $offset) =~ /^(.+?)\0/ );
89 0           $offset += length($content) + 1;
90 0           $self->field($field, undef, $content);
91             } else {
92 0           warn "Unsupported field type: $field";
93             }
94             }
95              
96 0           $self->{Handler}->end_element(
97             {
98             Name => 'record'
99             });
100             }
101              
102 0           $self->{Handler}->end_element(
103             {
104             Name => 'pdb'
105             });
106 0           $self->{Handler}->end_document();
107             }
108              
109             sub field {
110 0     0 0   my ($self, $field, $value, $content) = @_;
111              
112 0           my $el = {
113             Name => 'field',
114             Attributes =>
115             {
116             type => $field
117             }
118             };
119 0 0         $el->{Attributes}->{value} = $value if $value;
120 0           $self->{Handler}->start_element( $el );
121            
122 0 0         $self->{Handler}->characters({ Data => $content }) if $content;
123            
124 0           $self->{Handler}->end_element(
125             {
126             Name => 'field'
127             });
128             }
129              
130             sub convert_date_from_nsbasic {
131 0     0 0   my ($self, $raw) = @_;
132              
133 0           my $year = int($raw / 10000) + 1900;
134 0           my $month = int(($raw - ($year-1900)*10000) / 100);
135 0           my $day = $raw - ($year-1900)*10000 - $month*100;
136              
137 0           return sprintf("%04d-%02d-%02d", $year, $month, $day);
138             }
139              
140             sub convert_time_from_nsbasic {
141 0     0 0   my ($self, $raw) = @_;
142              
143 0           my $hour = int($raw / 10000);
144 0           my $minute = int(($raw - $hour*10000) / 100);
145 0           my $second = $raw - $hour*10000 - $minute*100;
146              
147 0           return sprintf("%02d:%02d:%02d", $hour, $minute, $second);
148             }
149              
150             1;
151              
152             __END__