File Coverage

blib/lib/FFI/Platypus/Function.pm
Criterion Covered Total %
statement 74 74 100.0
branch 6 6 100.0
condition n/a
subroutine 19 19 100.0
pod n/a
total 99 99 100.0


line stmt bran cond sub pod time code
1             package FFI::Platypus::Function;
2              
3 56     56   373075 use strict;
  56         98  
  56         1274  
4 56     56   227 use warnings;
  56         98  
  56         975  
5 56     56   700 use 5.008004;
  56         159  
6 56     56   1355 use FFI::Platypus;
  56         100  
  56         5876  
7              
8             # ABSTRACT: An FFI function object
9             our $VERSION = '2.07'; # VERSION
10              
11              
12             use overload '&{}' => sub {
13 98     98   21273 my $ffi = shift;
14 98     98   364 sub { $ffi->call(@_) };
  98         841  
15             }, 'bool' => sub {
16 9     9   303 my $ffi = shift;
17 9         44 return $ffi;
18 56     56   348 }, fallback => 1;
  56         98  
  56         634  
19              
20             package FFI::Platypus::Function::Function;
21              
22 56     56   24022 use parent qw( FFI::Platypus::Function );
  56         13039  
  56         290  
23              
24             sub attach
25             {
26 867     867   2858 my($self, $perl_name, $proto) = @_;
27              
28 867         1076 my $frame = -1;
29 867         1124 my($caller, $filename, $line);
30              
31 867         1000 do {
32 1735         11521 ($caller, $filename, $line) = caller(++$frame);
33             } while( $caller =~ /^FFI::Platypus(|::Function|::Function::Wrapper|::Declare)$/ );
34              
35 867 100       2658 $perl_name = join '::', $caller, $perl_name
36             unless $perl_name =~ /::/;
37              
38 867         7765 $self->_attach($perl_name, "$filename:$line", $proto);
39 867         4989 $self;
40             }
41              
42             sub sub_ref
43             {
44 24     24   54 my($self) = @_;
45              
46 24         41 my $frame = -1;
47 24         38 my($caller, $filename, $line);
48              
49 24         41 do {
50 65         453 ($caller, $filename, $line) = caller(++$frame);
51             } while( $caller =~ /^FFI::Platypus(|::Function|::Function::Wrapper|::Declare)$/ );
52              
53 24         237 $self->_sub_ref("$filename:$line");
54             }
55              
56             package FFI::Platypus::Function::Wrapper;
57              
58 56     56   15629 use parent qw( FFI::Platypus::Function );
  56         120  
  56         207  
59              
60             sub new
61             {
62 32     32   112 my($class, $function, $wrapper) = @_;
63 32         130 bless [ $function, $wrapper ], $class;
64             }
65              
66             sub call
67             {
68 19     19   2267 my($function, $wrapper) = @{ shift() };
  19         117  
69 19         43 @_ = ($function, @_);
70 19         61 goto &$wrapper;
71             }
72              
73             sub attach
74             {
75 21     21   91 my($self, $perl_name, $proto) = @_;
76 21         40 my($function, $wrapper) = @{ $self };
  21         411  
77              
78 21 100       95 unless($perl_name =~ /::/)
79             {
80 20         39 my $caller;
81 20         42 my $frame = -1;
82 20         38 do { $caller = caller(++$frame) } while( $caller =~ /^FFI::Platypus(|::Declare)$/ );
  37         170  
83 20         79 $perl_name = join '::', $caller, $perl_name
84             }
85              
86 21         67 my $xsub = $function->sub_ref;
87              
88             {
89 21         45 my $code = sub {
90 46     46   17654 unshift @_, $xsub;
91 46         193 goto &$wrapper;
92 21         125 };
93 21 100       70 if(defined $proto)
94             {
95 4         14 _set_prototype($proto, $code);
96             }
97 56     56   14635 no strict 'refs';
  56         147  
  56         7905  
98 21         40 *{$perl_name} = $code;
  21         111  
99             }
100              
101 21         60 $self;
102             }
103              
104             sub sub_ref
105             {
106 1     1   3 my($self) = @_;
107 1         1 my($function, $wrapper) = @{ $self };
  1         3  
108 1         3 my $xsub = $function->sub_ref;
109              
110             return sub {
111 1     1   6 unshift @_, $xsub;
112 1         3 goto &$wrapper;
113 1         5 };
114             }
115              
116             1;
117              
118             __END__