File Coverage

blib/lib/Algorithm/IRCSRP2/Utils.pm
Criterion Covered Total %
statement 13 13 100.0
branch n/a
condition n/a
subroutine 5 5 100.0
pod n/a
total 18 18 100.0


line stmt bran cond sub pod time code
1             package Algorithm::IRCSRP2::Utils;
2              
3             BEGIN {
4 1     1   1476 $Algorithm::IRCSRP2::Utils::VERSION = '0.501';
5             }
6              
7             # ABSTRACT: Algorithm utility functions
8              
9 1     1   11 use strict;
  1         2  
  1         36  
10 1     1   4 use warnings;
  1         3  
  1         30  
11              
12             # core
13 1     1   510743 use Digest::SHA;
  1         10388  
  1         110  
14 1     1   22004 use Math::BigInt only => 'GMP,Pari';
  1         95432  
  1         6  
15              
16             # CPAN
17             use Crypt::URandom qw();
18             use Sub::Exporter;
19              
20             Sub::Exporter::setup_exporter(
21             {'exports' => [qw(urandom randint gen_a int2bytes bytes2int xorstring padto hmac_sha256_128 N g H)]});
22              
23             # -------- constants --------
24             sub H { return Digest::SHA::sha256(@_) }
25              
26             sub g { return 2 }
27              
28             sub N {
29             my @modp14 = qw(
30             FFFFFFFF FFFFFFFF C90FDAA2 2168C234 C4C6628B 80DC1CD1
31             29024E08 8A67CC74 020BBEA6 3B139B22 514A0879 8E3404DD
32             EF9519B3 CD3A431B 302B0A6D F25F1437 4FE1356D 6D51C245
33             E485B576 625E7EC6 F44C42E9 A637ED6B 0BFF5CB6 F406B7ED
34             EE386BFB 5A899FA5 AE9F2411 7C4B1FE6 49286651 ECE45B3D
35             C2007CB8 A163BF05 98DA4836 1C55D39A 69163FA8 FD24CF5F
36             83655D23 DCA3AD96 1C62F356 208552BB 9ED52907 7096966D
37             670C354E 4ABC9804 F1746C08 CA18217C 32905E46 2E36CE3B
38             E39E772C 180E8603 9B2783A2 EC07A28F B5C55DF0 6F4C52C9
39             DE2BCBF6 95581718 3995497C EA956AE5 15D22618 98FA0510
40             15728E5A 8AACAA68 FFFFFFFF FFFFFFFF);
41              
42             my $s = join('', @modp14);
43              
44             $s =~ s/\s*//g;
45             $s =~ s/\n//g;
46              
47             return Math::BigInt->new('0x' . $s)->bstr;
48             }
49              
50             sub urandom {
51             my ($amount) = @_;
52              
53             return Crypt::URandom::urandom($amount);
54             }
55              
56             sub randint {
57             my ($a, $b) = @_;
58             my $c = $b->copy;
59             my $bits = (int($c->blog(2)) + 1) / 8;
60              
61             my $candidate = 0;
62              
63             while (1) {
64             $candidate = bytes2int(urandom($bits));
65             if ($a <= $candidate && $candidate <= $b) {
66             last;
67             }
68             }
69             die 'a <= candidate <= b' unless ($a <= $candidate && $candidate <= $b);
70              
71             return $candidate->bstr;
72             }
73              
74             sub gen_a {
75             my $n = Math::BigInt::->new(N());
76             $n->bsub(1);
77             return randint(2, $n);
78             }
79              
80             sub int2bytes {
81             my ($n) = @_;
82              
83             $n = $n->copy;
84              
85             if ($n == 0) { return 0x00 }
86              
87             my $x = '';
88              
89             while ($n) {
90             $x = chr($n->copy->bmod(256)->bstr) . $x;
91             $n->bdiv(256);
92             }
93              
94             return $x;
95             }
96              
97             sub bytes2int {
98             my ($bytes) = @_;
99              
100             my @bs = split('', $bytes);
101              
102             my $n = Math::BigInt->new(0);
103              
104             foreach my $b (@bs) {
105             $n->bmul(256);
106             $n->badd(ord($b));
107             }
108              
109             return $n;
110             }
111              
112             sub xorstring {
113             my ($a, $b, $blocksize) = @_;
114              
115             my $xored = '';
116              
117             my @as = split('', $a);
118             my @bs = split('', $b);
119              
120             foreach my $i (@{[ 0 .. $blocksize - 1 ]}) {
121             $xored .= chr(ord($as[$i]) ^ ord($bs[$i]));
122             }
123              
124             return $xored;
125             }
126              
127             sub padto {
128             my ($msg, $length) = @_;
129              
130             my $L = length($msg);
131              
132             if ($L % $length) {
133             $msg .= (chr(0) x ($length - $L % $length));
134             }
135              
136             die('lenth($msg) % $length != 0') unless ((length($msg) % $length) == 0);
137              
138             return $msg;
139             }
140              
141             sub hmac_sha256_128 {
142             my ($key, $data) = @_;
143              
144             my $str = Digest::SHA::hmac_sha256($data, $key);
145             $str = substr($str, 0, 16);
146              
147             return $str;
148             }
149              
150             1;
151              
152             __END__
153              
154             =pod
155              
156             =head1 NAME
157              
158             Algorithm::IRCSRP2::Utils - Algorithm utility functions
159              
160             =head1 VERSION
161              
162             version 0.501
163              
164             =head1 AUTHOR
165              
166             Adam Flott <adam@npjh.com>
167              
168             =head1 COPYRIGHT AND LICENSE
169              
170             This software is copyright (c) 2011 by Adam Flott.
171              
172             This is free software; you can redistribute it and/or modify it under
173             the same terms as the Perl 5 programming language system itself.
174              
175             =cut