/* Integer Version 2.1, RD, 16.7.93 	imod.h			*/

/* Modular arithmetic with Montgomery's method. Based on the large
   integer arithmetic libI. RD, 16.7.93.			*/


#ifndef _IMOD_H
#define _IMOD_H

#include "iint.h"

typedef struct {
	DigitType *vec;
	int length;
	DigitType nprime;
	DigitType *rsquare;
	DigitType *rcube;
	void *memsingfree;
	void *memdoubfree;
	Integer ModIval;
} ModulusType;

typedef struct {
	ModulusType *mod;
	DigitType *val;
} Minteger;

EXTERN_FUNCTION(void Merror, (const char *));		/* Error message */
EXTERN_FUNCTION(void cMod, (ModulusType *, const Integer *));
	/* Creator Modulus */
EXTERN_FUNCTION(void dMod, (ModulusType *));
	/* Destructor Modulus */
EXTERN_FUNCTION(void IasMod, (Integer *, const ModulusType *));
	/* Modulus value */

EXTERN_FUNCTION(const ModulusType * Mmod, (const Minteger *));
	/* Reference Modulus */

EXTERN_FUNCTION(void cM, (Minteger *, ModulusType *));
	/* Creator Minteger */
EXTERN_FUNCTION(void cMasI, (Minteger *, const Integer *, ModulusType *));
	/* Creator Minteger, Init Integer */
EXTERN_FUNCTION(void cMasM, (Minteger *, const Minteger *));	
	/* Creator Minteger, Init Minteger */
EXTERN_FUNCTION(void dM, (Minteger *));			/* Destructor */

EXTERN_FUNCTION(void MasM, (Minteger *, const Minteger *));
EXTERN_FUNCTION(void MasI, (Minteger *, const Integer *));
EXTERN_FUNCTION(void IasM, (Integer *, const Minteger *));

EXTERN_FUNCTION(BOOLEAN Meq0, (const Minteger *));
EXTERN_FUNCTION(void MasMplM, (Minteger *, const Minteger *, const Minteger *));
EXTERN_FUNCTION(void MplasM, (Minteger *, const Minteger *));
EXTERN_FUNCTION(void MasMmiM, (Minteger *, const Minteger *, const Minteger *));
EXTERN_FUNCTION(void MmiasM, (Minteger *, const Minteger *));
EXTERN_FUNCTION(void MasMmuM, (Minteger *, const Minteger *, const Minteger *));
EXTERN_FUNCTION(void MmuasM, (Minteger *, const Minteger *));

EXTERN_FUNCTION(BOOLEAN MasinvM, (Minteger *, const Minteger *));
#define	bMasinvM MasinvM
EXTERN_FUNCTION(void MasMdiM, (Minteger *, const Minteger *, const Minteger *));
EXTERN_FUNCTION(void MdiasM, (Minteger *, const Minteger *));

EXTERN_FUNCTION(void Mrandom, (Minteger * a));


#endif
