using
std::cout;
using
std::cerr;
using
std::endl;
#ifndef __CPP__INCLUDED__RPerl__DataType__GMPInteger_cpp
#define __CPP__INCLUDED__RPerl__DataType__GMPInteger_cpp 0.005_000
#include <RPerl/HelperFunctions.cpp> // -> HelperFunctions.h
#include <RPerl/DataType/GMPInteger.h> // -> NULL (relies on native C type)
#include <RPerl/Operation/Expression/Operator/GMPFunctions.cpp> // -> GMPFunctions.h
#include <RPerl/DataType/Boolean.cpp> // -> Boolean.h
#include <RPerl/DataType/UnsignedInteger.cpp> // -> UnsignedInteger.h
#include <RPerl/DataType/Integer.cpp> // -> Integer.h
#include <RPerl/DataType/Number.cpp> // -> Number.h
#include <RPerl/DataType/Character.cpp> // -> Character.h
#include <RPerl/DataType/String.cpp> // -> String.h
void
gmp_integer_CHECK(SV* possible_gmp_integer) {
if
(not (SvOK(possible_gmp_integer))) { croak(
"\nERROR EMPV00, TYPE-CHECKING MISMATCH, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer external wrapper value expected but undefined/null value found,\ncroaking"
); }
if
(not (SvHROKp(possible_gmp_integer))) { croak(
"\nERROR EMPV01, TYPE-CHECKING MISMATCH, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer external wrapper value expected but non-hashref value found,\ncroaking"
); }
if
(not (sv_isobject(possible_gmp_integer))) { croak(
"\nERROR EMPV02, TYPE-CHECKING MISMATCH, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer external wrapper value expected but non-object (blessed hashref) value found,\ncroaking"
); }
if
(not (sv_derived_from(possible_gmp_integer,
"Math::BigInt"
))) { croak(
"\nERROR EMPV03, TYPE-CHECKING MISMATCH, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer external wrapper value expected but non-Math::BigInt-derived object value found,\ncroaking"
); }
if
(not (sv_isa(possible_gmp_integer,
"gmp_integer"
))) { croak(
"\nERROR EMPV04, TYPE-CHECKING MISMATCH, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer external wrapper value expected but non-gmp_integer object value found,\ncroaking"
); }
HV* possible_gmp_integer_deref = (HV*) SvRV(possible_gmp_integer);
if
(not hv_exists(possible_gmp_integer_deref, (
const
char
*)
"value"
, (U32) 5)) { croak(
"\nERROR EMPV05, MISSING HASH ENTRY, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer internal wrapped object in hash entry expected at key 'value' but no hash entry exists,\ncroaking"
); }
SV** possible_gmp_integer_value_ptr = hv_fetch(possible_gmp_integer_deref, (
const
char
*)
"value"
, (U32) 5, (I32) 0);
if
(possible_gmp_integer_value_ptr == NULL) { croak(
"\nERROR EMPV06, MISSING HASH ENTRY, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer internal wrapped hash entry expected at key 'value' but no hash entry defined,\ncroaking"
); }
if
(not (SvOK(*possible_gmp_integer_value_ptr))) { croak(
"\nERROR EMPV07, TYPE-CHECKING MISMATCH, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer internal wrapped value expected but undefined/null value found,\ncroaking"
); }
if
(not (sv_isobject(*possible_gmp_integer_value_ptr))) { croak(
"\nERROR EMPV08, TYPE-CHECKING MISMATCH, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer internal wrapped value expected but non-object (blessed hashref) value found,\ncroaking"
); }
if
(not (sv_derived_from(*possible_gmp_integer_value_ptr,
"Math::BigInt::GMP"
))) { croak(
"\nERROR EMPV09, TYPE-CHECKING MISMATCH, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer internal wrapped value expected but non-Math::BigInt::GMP object value found,\ncroaking"
); }
}
void
gmp_integer_CHECKTRACE(SV* possible_gmp_integer,
const
char
* variable_name,
const
char
* subroutine_name) {
if
(not (SvOK(possible_gmp_integer))) { croak(
"\nERROR EMPV00, TYPE-CHECKING MISMATCH, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer external wrapper value expected but undefined/null value found,\nin variable %s from subroutine %s,\ncroaking"
, variable_name, subroutine_name); }
if
(not (SvHROKp(possible_gmp_integer))) { croak(
"\nERROR EMPV01, TYPE-CHECKING MISMATCH, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer external wrapper value expected but non-hashref value found,\nin variable %s from subroutine %s,\ncroaking"
, variable_name, subroutine_name); }
if
(not (sv_isobject(possible_gmp_integer))) { croak(
"\nERROR EMPV02, TYPE-CHECKING MISMATCH, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer external wrapper value expected but non-object (blessed hashref) value found,\nin variable %s from subroutine %s,\ncroaking"
, variable_name, subroutine_name); }
if
(not (sv_derived_from(possible_gmp_integer,
"Math::BigInt"
))) { croak(
"\nERROR EMPV03, TYPE-CHECKING MISMATCH, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer external wrapper value expected but non-Math::BigInt-derived object value found,\nin variable %s from subroutine %s,\ncroaking"
, variable_name, subroutine_name); }
if
(not (sv_isa(possible_gmp_integer,
"gmp_integer"
))) { croak(
"\nERROR EMPV04, TYPE-CHECKING MISMATCH, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer external wrapper value expected but non-gmp_integer object value found,\nin variable %s from subroutine %s,\ncroaking"
, variable_name, subroutine_name); }
HV* possible_gmp_integer_deref = (HV*) SvRV(possible_gmp_integer);
if
(not hv_exists(possible_gmp_integer_deref, (
const
char
*)
"value"
, (U32) 5)) { croak(
"\nERROR EMPV05, MISSING HASH ENTRY, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer internal wrapped object in hash entry expected at key 'value' but no hash entry exists,\nin variable %s from subroutine %s,\ncroaking"
, variable_name, subroutine_name); }
SV** possible_gmp_integer_value_ptr = hv_fetch(possible_gmp_integer_deref, (
const
char
*)
"value"
, (U32) 5, (I32) 0);
if
(possible_gmp_integer_value_ptr == NULL) { croak(
"\nERROR EMPV06, MISSING HASH ENTRY, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer internal wrapped hash entry expected at key 'value' but no hash entry defined,\nin variable %s from subroutine %s,\ncroaking"
, variable_name, subroutine_name); }
if
(not (SvOK(*possible_gmp_integer_value_ptr))) { croak(
"\nERROR EMPV07, TYPE-CHECKING MISMATCH, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer internal wrapped value expected but undefined/null value found,\nin variable %s from subroutine %s,\ncroaking"
, variable_name, subroutine_name); }
if
(not (sv_isobject(*possible_gmp_integer_value_ptr))) { croak(
"\nERROR EMPV08, TYPE-CHECKING MISMATCH, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer internal wrapped value expected but non-object (blessed hashref) value found,\nin variable %s from subroutine %s,\ncroaking"
, variable_name, subroutine_name); }
if
(not (sv_derived_from(*possible_gmp_integer_value_ptr,
"Math::BigInt::GMP"
))) { croak(
"\nERROR EMPV09, TYPE-CHECKING MISMATCH, CPPOPS_PERLTYPES & CPPOPS_CPPTYPES:\ngmp_integer internal wrapped value expected but non-Math::BigInt::GMP object value found,\nin variable %s from subroutine %s,\ncroaking"
, variable_name, subroutine_name); }
}
# ifdef __CPP__TYPES
gmp_integer_retval XS_unpack_gmp_integer_retval(SV* input_hvref) {
gmp_integer_CHECKTRACE(input_hvref,
"input_hvref"
,
"XS_unpack_gmp_integer_retval()"
);
return
(gmp_integer_retval) *((gmp_integer_rawptr) SvMAGIC(SvRV(*(hv_fetch((HV*)SvRV(input_hvref), (
const
char
*)
"value"
, (U32) 5, (I32) 0))))->mg_ptr)
*
pow
(-1, (SvPV_nolen(*hv_fetch((HV*)SvRV(input_hvref), (
const
char
*)
"sign"
, (U32) 4, (I32) 0))[0] ==
'-'
));
}
void
XS_pack_gmp_integer_retval(SV* output_hvref, gmp_integer_retval input_gmp_integer_retval) {
dSP;
ENTER;
SAVETMPS;
PUSHMARK(SP);
XPUSHs(sv_2mortal(newSVpv(
"gmp_integer"
, 0)));
PUTBACK;
integer callback_retval_count = call_method(
"new"
, G_SCALAR);
SPAGAIN;
if
(callback_retval_count != 1) {
croak(
"\nERROR EMPV10, CONSTRUCTOR RETURN VALUE MISMATCH, CPPOPS_CPPTYPES:\nexactly 1 return value expected but %"
INTEGER
" return value(s) found,\ncroaking"
, callback_retval_count);
}
SV* gmp_integer_hvref = POPs;
gmp_integer_CHECKTRACE(gmp_integer_hvref,
"gmp_integer_hvref"
,
"XS_pack_gmp_integer_retval()"
);
PUTBACK;
SV* temp_sv_pointer;
temp_sv_pointer = newSVrv(output_hvref, NULL);
SvREFCNT_dec(temp_sv_pointer);
SvRV(output_hvref) = SvRV(gmp_integer_hvref);
SvREFCNT_inc(SvRV(output_hvref));
SV* gmp_integer_hvref_value_value = *hv_fetch((HV*)SvRV(gmp_integer_hvref), (
const
char
*)
"value"
, (U32) 5, (I32) 0);
MAGIC* gmp_integer_hvref_value_value_magic = SvMAGIC(SvRV(gmp_integer_hvref_value_value));
gmp_integer_rawptr gmp_integer_tmp = (gmp_integer_rawptr) gmp_integer_hvref_value_value_magic->mg_ptr;
gmp_set(*gmp_integer_tmp, input_gmp_integer_retval.gmp_integer_unretval());
FREETMPS;
LEAVE;
}
# endif
# ifdef __PERL__TYPES
SV* gmp_integer_to_boolean(SV* input_gmp_integer) {
gmp_integer_CHECKTRACE(input_gmp_integer,
"input_gmp_integer"
,
"gmp_integer_to_boolean()"
);
}
# elif defined __CPP__TYPES
boolean gmp_integer_to_boolean(gmp_integer_retval input_gmp_integer_retval) {
if
(gmp_get_signed_integer(input_gmp_integer_retval.gmp_integer_unretval()) == 0) {
return
0; }
else
{
return
1; }
}
# endif
# ifdef __PERL__TYPES
SV* gmp_integer_to_unsigned_integer(SV* input_gmp_integer) {
gmp_integer_CHECKTRACE(input_gmp_integer,
"input_gmp_integer"
,
"gmp_integer_to_unsigned_integer()"
);
}
# elif defined __CPP__TYPES
unsigned_integer gmp_integer_to_unsigned_integer(gmp_integer_retval input_gmp_integer_retval) {
return
gmp_get_signed_integer(input_gmp_integer_retval.gmp_integer_unretval());
}
# endif
# ifdef __PERL__TYPES
SV* gmp_integer_to_integer(SV* input_gmp_integer) {
gmp_integer_CHECKTRACE(input_gmp_integer,
"input_gmp_integer"
,
"gmp_integer_to_integer()"
);
}
# elif defined __CPP__TYPES
integer gmp_integer_to_integer(gmp_integer_retval input_gmp_integer_retval) {
return
gmp_get_signed_integer(input_gmp_integer_retval.gmp_integer_unretval());
}
# endif
# ifdef __PERL__TYPES
SV* gmp_integer_to_number(SV* input_gmp_integer) {
gmp_integer_CHECKTRACE(input_gmp_integer,
"input_gmp_integer"
,
"gmp_integer_to_number()"
);
}
# elif defined __CPP__TYPES
number gmp_integer_to_number(gmp_integer_retval input_gmp_integer_retval) {
return
(
double
) gmp_get_signed_integer(input_gmp_integer_retval.gmp_integer_unretval());
}
# endif
# ifdef __PERL__TYPES
SV* gmp_integer_to_character(SV* input_gmp_integer) {
gmp_integer_CHECKTRACE(input_gmp_integer,
"input_gmp_integer"
,
"gmp_integer_to_character()"
);
}
# elif defined __CPP__TYPES
character gmp_integer_to_character(gmp_integer_retval input_gmp_integer_retval) {
return
(character) gmp_integer_to_string_CPPTYPES(input_gmp_integer_retval).at(0);
}
# endif
# ifdef __PERL__TYPES
SV* gmp_integer_to_string(SV* input_gmp_integer) {
gmp_integer_CHECKTRACE(input_gmp_integer,
"input_gmp_integer"
,
"gmp_integer_to_string()"
);
}
# elif defined __CPP__TYPES
string gmp_integer_to_string(gmp_integer_retval input_gmp_integer_retval) {
return
gmp_integer_to_string_CPPTYPES(input_gmp_integer_retval);
}
# endif
string gmp_integer_to_string_CPPTYPES(gmp_integer_retval input_gmp_integer_retval)
{
std::ostringstream output_stream;
output_stream.precision(std::numeric_limits<
double
>::digits10);
output_stream << gmp_get_signed_integer(input_gmp_integer_retval.gmp_integer_unretval());
string output_string = output_stream.str();
boolean is_negative = 0;
if
(gmp_get_signed_integer(input_gmp_integer_retval.gmp_integer_unretval()) < 0) { is_negative = 1; }
std::reverse(output_string.begin(), output_string.end());
if
(is_negative) { output_string.pop_back(); }
string output_string_underscores =
""
;
for
(std::string::size_type i = 0; i < output_string.size(); ++i) {
output_string_underscores += output_string[i];
if
(((i % 3) == 2) && (i > 0) && (i != (output_string.size() - 1))) {
output_string_underscores +=
'_'
;
}
}
std::reverse(output_string_underscores.begin(), output_string_underscores.end());
if
(output_string_underscores ==
""
) {
output_string_underscores =
"0"
;
}
if
(is_negative) { output_string_underscores =
'-'
+ output_string_underscores; }
return
output_string_underscores;
}
# ifdef __PERL__TYPES
SV* boolean_to_gmp_integer(SV* input_boolean) {
boolean_CHECKTRACE(input_boolean,
"input_boolean"
,
"boolean_to_gmp_integer()"
);
}
SV* unsigned_integer_to_gmp_integer(SV* input_unsigned_integer) {
unsigned_integer_CHECKTRACE(input_unsigned_integer,
"input_unsigned_integer"
,
"unsigned_integer_to_gmp_integer()"
);
}
SV* integer_to_gmp_integer(SV* input_integer) {
integer_CHECKTRACE(input_integer,
"input_integer"
,
"integer_to_gmp_integer()"
);
}
SV* number_to_gmp_integer(SV* input_number) {
number_CHECKTRACE(input_number,
"input_number"
,
"number_to_gmp_integer()"
);
}
SV* character_to_gmp_integer(SV* input_character) {
character_CHECKTRACE(input_character,
"input_character"
,
"character_to_gmp_integer()"
);
}
SV* string_to_gmp_integer(SV* input_string) {
string_CHECKTRACE(input_string,
"input_string"
,
"string_to_gmp_integer()"
);
string_substitute_global(input_string,
"_"
,
""
);
}
# elif defined __CPP__TYPES
gmp_integer_retval boolean_to_gmp_integer(boolean input_boolean) {
return
(gmp_integer_retval) input_boolean;
}
gmp_integer_retval unsigned_integer_to_gmp_integer(unsigned_integer input_unsigned_integer) {
return
(gmp_integer_retval) input_unsigned_integer;
}
gmp_integer_retval integer_to_gmp_integer(integer input_integer) {
return
(gmp_integer_retval) input_integer;
}
gmp_integer_retval number_to_gmp_integer(number input_number) {
return
(gmp_integer_retval) ((integer)
floor
(input_number));
}
gmp_integer_retval character_to_gmp_integer(character input_character) {
return
(gmp_integer_retval)
atoi
(&input_character);
}
gmp_integer_retval string_to_gmp_integer(string input_string) {
string_substitute_global(input_string,
"_"
,
""
);
return
(gmp_integer_retval)
atoi
(input_string.c_str());
}
# endif
# ifdef __PERL__TYPES
SV* gmp_integer_typetest0() {
}
SV* gmp_integer_typetest1(SV* lucky_gmp_integer) {
gmp_integer_CHECKTRACE(lucky_gmp_integer,
"lucky_gmp_integer"
,
"gmp_integer_typetest1()"
);
}
# elif defined __CPP__TYPES
gmp_integer_retval gmp_integer_typetest0() {
RPerl_object_property_init(newSViv(0));
return
(gmp_integer_retval) ((21 / 7) + RPerl__DataType__GMPInteger__MODE_ID());
}
gmp_integer_retval gmp_integer_typetest1(gmp_integer_retval lucky_gmp_integer_retval) {
return
(gmp_integer_retval) ((gmp_get_signed_integer(lucky_gmp_integer_retval.gmp_integer_unretval()) * 2) + RPerl__DataType__GMPInteger__MODE_ID());
}
# endif
#endif