Codebase list libgeo-ipfree-perl / 72fb681
Merge pull request #3 from atoomic/fast++ Remove Memoize dependency and make Faster faster ℕicolas ℝ authored 2 years ago GitHub committed 2 years ago
4 changed file(s) with 48 addition(s) and 40 deletion(s). Raw diff Collapse all Expand all
1818 ),
1919 PREREQ_PM => {
2020 'Test::More' => '0.47',
21 'Memoize' => 0,
2221 },
2322 ( eval { ExtUtils::MakeMaker->VERSION(6.46) }
2423 ? ( META_MERGE => {
00 #!perl
11
22 requires "Carp" => "0";
3 requires "Memoize" => "0";
43 requires "ExtUtils::MakeMaker" => "0";
54
65 on "test" => sub {
98
109 on "recommends" => sub {
1110 requires "Test::CPAN::Meta" => "0";
11 requires "Test::Pod::Coverage" => "0";
1212 requires "Test::NoTabs" => "0";
1313 requires "Test2::Bundle::Extended" => "0";
1414 requires "Test2::Tools::Explain" => "0";
22 use strict;
33 use warnings;
44
5 use Memoize;
65 use Carp qw();
76
87 require Exporter;
2221 split( m{}, q(.,;'"`<>{}[]=+-~*@#%$&!?) )
2322 );
2423
25 my ( %baseX, $base, $THIS, %countrys );
24 my ( %baseX, $base, $THIS, %countrys, $base0, $base1, $base2, $base3, $base4 );
2625
2726 {
2827 my $c = 0;
2928 %baseX = map { $_ => ( $c++ ) } @baseX;
3029 $base = @baseX;
30 $base0 = $base**0;
31 $base1 = $base**1;
32 $base2 = $base**2;
33 $base3 = $base**3;
34 $base4 = $base**4;
3135
3236 my @data;
3337 while ( <DATA> ) {
124128
125129 my ( $ip ) = @_;
126130
127 $ip =~ s/\.+/\./gs;
128 $ip =~ s/^\.//;
129 $ip =~ s/\.$//;
131 $ip =~ s/\.+/\./gs if index($ip,'..') > -1;
132 substr($ip,0,1,'') if substr($ip,0,1) eq '.';
133 chop $ip if substr($ip,-1) eq '.';
130134
131135 if ( $ip !~ /^\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}$/ ) {
132136 $ip = nslookup( $ip );
150154 if ( $ipnb <= $Key ) { $buf_pos = $this->{ pos }{ $Key }; last; }
151155 }
152156
153 my ( $buffer, $country, $iprange );
157 my ( $buffer, $country, $iprange, $basex2 );
154158
155159 ## Will use the DB in the memory:
156 if ( $this->{ FASTER } ) {
157 while ( $buf_pos < $this->{ DB_SIZE } ) {
158 $buffer = substr( $this->{ DB }, $buf_pos, 7 );
159 $country = substr( $buffer, 0, 2 );
160 $iprange = baseX2dec( substr( $buffer, 2, 5 ) );
160 if ( $this->{FASTER} ) {
161 my $base_cache = $this->{'baseX2dec'} ||= {};
162 while ( $buf_pos < $this->{DB_SIZE} ) {
163 if ( $ipnb >= ( $base_cache->{ ( $basex2 = substr( $this->{DB}, $buf_pos + 2, 5 ) ) } ||= baseX2dec($basex2) ) ) {
164 $country = substr( $this->{DB}, $buf_pos, 2 );
165 last;
166 }
161167 $buf_pos += 7;
162 last if $ipnb >= $iprange;
163168 }
169 $country ||= substr( $this->{DB}, $buf_pos-7, 2 );
164170 }
165171 ## Will read the DB in the disk:
166172 else {
167 seek( $this->{ handler }, 0, 0 )
168 if $] < 5.006001; ## Fix bug on Perl 5.6.0
169 seek( $this->{ handler }, $buf_pos + $this->{ start }, 0 );
170 while ( read( $this->{ handler }, $buffer, 7 ) ) {
171 $country = substr( $buffer, 0, 2 );
172 $iprange = baseX2dec( substr( $buffer, 2 ) );
173 last if $ipnb >= $iprange;
173 seek( $this->{handler}, 0, 0 )
174 if $] < 5.006001; ## Fix bug on Perl 5.6.0
175 seek( $this->{handler}, $buf_pos + $this->{start}, 0 );
176 while ( read( $this->{handler}, $buffer, 7 ) ) {
177 if ( $ipnb >= baseX2dec( substr( $buffer, 2 ) ) ) {
178 $country = substr( $buffer, 0, 2 );
179 last;
180 }
174181 }
175182 }
176183
198205
199206 $this->{ DB } = do { local $/; <$handler>; };
200207 $this->{ DB_SIZE } = length( $this->{ DB } );
201
202 memoize( 'dec2baseX' );
203 memoize( 'baseX2dec' );
204
205208 $this->{ FASTER } = 1;
206209 }
207210
209212 my $this = shift;
210213 $this->{ CACHE_COUNT } = 0;
211214 delete $this->{ CACHE };
215 delete $this->{'baseX2dec'};
212216 return 1;
213217 }
214218
261265 }
262266
263267 sub baseX2dec {
264 my ( $input ) = @_;
265
266 my @digits = reverse split( '', $input );
267 my $dec = 0;
268
269 foreach ( 0 .. @digits - 1 ) {
270 $dec += $baseX{ $digits[ $_ ] } * ( $base**$_ );
271 }
272
273 return $dec;
268 my $string = reverse $_[0];
269 my $length = length $string;
270 return #
271 (
272 0 + ( $length > 4 ? ( $baseX{ substr( $string, 4, 1 ) } * $base4 ) : 0 ) + #
273 ( $length > 3 ? ( $baseX{ substr( $string, 3, 1 ) } * $base3 ) : 0 ) + #
274 ( $length > 2 ? ( $baseX{ substr( $string, 2, 1 ) } * $base2 ) : 0 ) + #
275 ( $length > 1 ? ( $baseX{ substr( $string, 1, 1 ) } * $base1 ) : 0 ) + #
276 ( $length ? ( $baseX{ substr( $string, 0, 1 ) } * $base0 ) : 0 ) #
277 ); #
274278 }
275279
276280 1;
00 use strict;
11 use warnings;
22
3 use Test::More tests => 173;
3 use Test::More tests => 177;
44
5 use_ok( 'Geo::IPfree' );
5 use_ok('Geo::IPfree');
66
77 my @b86 = ( 0 .. 9, 'A' .. 'Z', 'a' .. 'z', split( m{}, q(.,;'"`<>{}[]=+-~*@#%$&!?) ) );
88
9 for( 0..85 ) {
10 is( Geo::IPfree::dec2baseX( $_ ), sprintf( '%05s', $b86[ $_ ] ), "dec2baseX( '$_' )" );
11 is( Geo::IPfree::baseX2dec( $b86[ $_ ] ), $_, "baseX2dec( '$b86[ $_ ]' )" );
9 for ( 0 .. 85 ) {
10 is( Geo::IPfree::dec2baseX($_), sprintf( '%05s', $b86[$_] ), "dec2baseX( '$_' )" );
11 is( Geo::IPfree::baseX2dec( $b86[$_] ), $_, "baseX2dec( '$b86[ $_ ]' )" );
1212 }
13 is( Geo::IPfree::baseX2dec('AAAAA'), 553443550, "Geo::IPfree::baseX2dec('AAAAA')" );
14 is( Geo::IPfree::baseX2dec('BBBBB'), 608787905, "Geo::IPfree::baseX2dec('BBBBB')" );
15 is( Geo::IPfree::baseX2dec('CCCCC'), 664132260, "Geo::IPfree::baseX2dec('CCCCC')" );
16 is( Geo::IPfree::baseX2dec('x4OYa'), 3230072832, "Geo::IPfree::baseX2dec('x4OYa')" );
17