libcryptx-perl/inc/CryptX_Cipher.xs.inc

189 lines
4.4 KiB
C++

MODULE = CryptX PACKAGE = Crypt::Cipher
Crypt::Cipher
_new(cipher_name, key, rounds=0)
char * cipher_name
SV * key
int rounds
CODE:
{
STRLEN key_len;
unsigned char *key_data=NULL;
int rv;
int id;
if (!SvPOK (key)) croak("FATAL: key must be string scalar");
key_data = (unsigned char *)SvPVbyte(key, key_len);
id = find_cipher(cipher_name);
if(id==-1) croak("FATAL: find_cipfer failed for '%s'", cipher_name);
Newz(0, RETVAL, 1, struct cipher_struct);
if (!RETVAL) croak("FATAL: Newz failed");
RETVAL->id = id;
RETVAL->desc = &cipher_descriptor[id];
rv = RETVAL->desc->setup(key_data, (int)key_len, rounds, &RETVAL->skey);
if(rv!=CRYPT_OK) croak("FATAL: cipher setup failed: %s", error_to_string(rv));
}
OUTPUT:
RETVAL
void
DESTROY(self)
Crypt::Cipher self
CODE:
Safefree(self);
int
_max_keysize(self, ...)
Crypt::Cipher self
CODE:
RETVAL = self->desc->max_key_length;
OUTPUT:
RETVAL
int
_min_keysize(self, ...)
Crypt::Cipher self
CODE:
RETVAL = self->desc->min_key_length;
OUTPUT:
RETVAL
int
_blocksize(self, ...)
Crypt::Cipher self
CODE:
RETVAL = self->desc->block_length;
OUTPUT:
RETVAL
int
_default_rounds(self, ...)
Crypt::Cipher self
CODE:
RETVAL = self->desc->default_rounds;
OUTPUT:
RETVAL
SV *
encrypt(self, data)
Crypt::Cipher self
SV * data
CODE:
{
int rv;
STRLEN len;
void *plaintext = SvPVbyte(data, len);
if (len==0)
RETVAL = newSVpvn("", 0);
else if (len % self->desc->block_length)
croak ("FATAL: sizeof(data) should be multiple of blocksize (%d)", self->desc->block_length);
else {
/* idea from Crypt::Rijndael */
RETVAL = NEWSV(0, len);
SvPOK_only(RETVAL);
SvCUR_set(RETVAL, len);
rv = self->desc->ecb_encrypt((unsigned char *)plaintext, (unsigned char *)SvPV_nolen(RETVAL), &self->skey);
if (rv!=CRYPT_OK) croak("FATAL: encrypt failed: %s", error_to_string(rv));
}
}
OUTPUT:
RETVAL
SV *
decrypt(self, data)
Crypt::Cipher self
SV * data
CODE:
{
int rv;
STRLEN len;
void *ciphertext = SvPVbyte(data, len);
if (len==0)
RETVAL = newSVpvn("", 0);
else if (len % self->desc->block_length)
croak ("FATAL: sizeof(data) should be multiple of blocksize (%d)", self->desc->block_length);
else {
/* idea from Crypt::Rijndael */
RETVAL = NEWSV(0, len);
SvPOK_only(RETVAL);
SvCUR_set(RETVAL, len);
rv = self->desc->ecb_decrypt((unsigned char *)ciphertext, (unsigned char *)SvPV_nolen(RETVAL), &self->skey);
if (rv!=CRYPT_OK) croak("FATAL: decrypt failed: %s", error_to_string(rv));
}
}
OUTPUT:
RETVAL
int
_block_length_by_name(cipher_name)
char * cipher_name
CODE:
{
int rv, id;
id = find_cipher(cipher_name);
if(id==-1) croak("FATAL: find_cipfer failed for '%s'", cipher_name);
rv = cipher_descriptor[id].block_length;
if (!rv) XSRETURN_UNDEF;
RETVAL = rv;
}
OUTPUT:
RETVAL
int
_min_key_length_by_name(cipher_name)
char * cipher_name
CODE:
{
int rv, id;
id = find_cipher(cipher_name);
if(id==-1) croak("FATAL: find_cipfer failed for '%s'", cipher_name);
rv = cipher_descriptor[id].min_key_length;
if (!rv) XSRETURN_UNDEF;
RETVAL = rv;
}
OUTPUT:
RETVAL
int
_max_key_length_by_name(cipher_name)
char * cipher_name
CODE:
{
int rv, id;
id = find_cipher(cipher_name);
if(id==-1) croak("FATAL: find_cipfer failed for '%s'", cipher_name);
rv = cipher_descriptor[id].max_key_length;
if (!rv) XSRETURN_UNDEF;
RETVAL = rv;
}
OUTPUT:
RETVAL
int
_default_rounds_by_name(cipher_name)
char * cipher_name
CODE:
{
int rv, id;
id = find_cipher(cipher_name);
if(id==-1) croak("FATAL: find_cipfer failed for '%s'", cipher_name);
rv = cipher_descriptor[id].default_rounds;
if (!rv) XSRETURN_UNDEF;
RETVAL = rv;
}
OUTPUT:
RETVAL