GCC-Builtins
view release on metacpan or search on metacpan
lib/GCC/Builtins.pm view on Meta::CPAN
/* clobbers: we are messing with these registers: */
: "eax"
);
// return an arrayref of the two outputs
AV* ret = newAV();
sv_2mortal((SV*)ret);
av_push(ret, newSViv(num_leading_zeros));
av_push(ret, newSViv(mssb));
return ret;
}
You can also inline assembly in your Perl code with L<Inline::ASM>
Be advised that GCC builtins are also calling assembly code.
In fact the above assembly code is how GCC implements C<clz()>.
So, inline assembly and L<GCC::Builtins> should yield, more-or-less,
the same performance gain.
=head1 TESTING
For each exported sub there is a corresponding auto-generated
test file. The test goes as far as loading the library and
calling the function from Perl.
However, there may be errors in the expected results
because that was done without verifying with a C test program.
=head1 BENCHMARKS
Counting leading zeros (clz) will be used to
benchmark the GCC builtin C<__builtin_clz()>
and a pure Perl implementation as suggested
by Perl Monk L<coldr3ality|https://perlmonks.org/?node_id=1232041>
in this L<discussion|https://perlmonks.org/?node_id=11158279>
C<clz()> operating on the binary representation of a number
counts the zeros starting from the most significant end until
it finds the first bit set (to 1). Which essentially gives the
zero-based index of the MSB set to 1.
The benchmarks favour the GCC builtin C<__builtin_clz()>
which is about twice as fast as the pure Perl implementation.
The benchmarks can be run with C<make benchmarks>
An easy way to let Perl fetch and unpack the distribution
for you is to use C<cpanm> to open a shell
cpanm --look GCC::Builtins
and then
perl Makefile.PL && make all && make test && make benchmarks
The following benchamrk results indicate that the use
of L<GCC::Builtins> (C<clz()> in this case)
yields more than 100% performance gain
over equivalent pure perl code:
Benchmark: timing 50000000 iterations of clz/xs, clz/pp-ugly...
clz/xs: 3.92331 wallclock secs ( 3.92 usr + 0.00 sys = 3.92 CPU) @ 12755102.04/s (n=50000000)
clz/pp-ugly: 8.24574 wallclock secs ( 8.23 usr + 0.00 sys = 8.23 CPU) @ 6075334.14/s (n=50000000)
Rate clz/pp-ugly clz/xs
clz/pp-ugly 6075334/s -- -52%
clz/xs 12755102/s 110% --
KEY:
clz/xs : calling GCC builtin clz() via XS from Perl
clz/pp-ugly : as suggested by coldr3ality (see https://perlmonks.org/?node_id=11158279)
Benchmark: timing 50000000 iterations of clzl/xs, clzl/pp-ugly...
clzl/xs: 3.84597 wallclock secs ( 3.84 usr + 0.00 sys = 3.84 CPU) @ 13020833.33/s (n=50000000)
clzl/pp-ugly: 8.44006 wallclock secs ( 8.43 usr + 0.00 sys = 8.43 CPU) @ 5931198.10/s (n=50000000)
Rate clzl/pp-ugly clzl/xs
clzl/pp-ugly 5931198/s -- -54%
clzl/xs 13020833/s 120% --
KEY:
clzl/xs : calling GCC builtin clzl() via XS from Perl
clzl/pp-ugly : as suggested by coldr3ality (see https://perlmonks.org/?node_id=11158279)
So, it pays to use this module if performance is an issue.
=head1 CAVEATS
If you observe weird return results or core-dumps it is very likely that
the fault is mine while compiling the C<XS typemap>. The file in the distribution
C<typemap> was compiled by me to translate C's data types into Perls.
And for some of this I am not sure what the right type is. For example,
is C's C<uint_fast16_t> equivalent to Perl's C<T_UV>? How about
C's C<long double> mapping to Perl's C<T_DOUBLE> and C<unsigned long long>
to C<T_U_LONG>?
Please L<report|https://rt.cpan.org/NoAuth/ReportBug.html?Queue=GCC-Builtins> any corrections.
Note that C<lib/GCC/Builtins.pm>, C<lib/GCC/Builtins.xs>
and C<typemap> are auto-generated by above scripts. Do not
edit them. Edit C<sbin/build-gcc-builtins-package.pl>
instead.
=head1 AUTHOR
Andreas Hadjiprocopis, C<< <bliako ta cpan.org / andreashad2 ta gmail.com> >>
=head1 BUGS
Please report any bugs or feature requests to C<bug-gcc-builtins at rt.cpan.org>, or through
the web interface at L<https://rt.cpan.org/NoAuth/ReportBug.html?Queue=GCC-Builtins>. I will be notified, and then you'll
automatically be notified of progress on your bug as I make changes.
=head1 SUPPORT
You can find documentation for this module with the perldoc command.
perldoc GCC::Builtins
You can also look for information at:
=over 4
=item * RT: CPAN's request tracker (report bugs here)
L<https://rt.cpan.org/NoAuth/Bugs.html?Dist=GCC-Builtins>
=item * Review this module at PerlMonks
L<https://www.perlmonks.org/?node_id=21144>
=item * Search CPAN
( run in 0.420 second using v1.01-cache-2.11-cpan-71847e10f99 )