#include "modInv.h"
#include "RessourceHandler.cpp"

void ModInvModule::exe(){
	while(true){
		while(en->read()==false){
			// std::cout << "[" << sc_time_stamp() << "]:" << "[mod_mul]:" << "en.read()==false" << std::endl;
			wait();
		}

		// 1.Clock Cycle: Initialize Registers

		sc_biguint<160> P = m->read();

		// Initialize Registers
		sc_biguint<160> quot_reg = 0;

		// Können negativ werden, daher zusätzliches Bit reservieren
		sc_bigint<161> t_reg = 0;
		sc_bigint<161> tempt_reg = 0;
		sc_bigint<161> newt_reg = 1;

		// Bleiben immer >0 
		sc_biguint<160> r_reg = m->read();
		sc_biguint<160> tempr_reg = 0;
		sc_biguint<160> newr_reg = y->read();

		sc_biguint<160> erg_reg = 0;


		// n-th Clock Cycle: Implementierung des erweiterten Euklidischen-Algorithmus	
		while(newr_reg!=0){

			// Ggf. durch echte Hardware-Division ersetzen
			quot_reg = r_reg / newr_reg;
			wait();

			// t
			tempt_reg = t_reg;
			t_reg = newt_reg;
			newt_reg = tempt_reg - quot_reg * newt_reg;

			// r
			tempr_reg = r_reg;
			r_reg = newr_reg;
			newr_reg = tempr_reg - quot_reg * newr_reg;

			wait();
		}
		if(t_reg<0){
			t_reg = t_reg + P;
		}

		wait();
		erg_reg = t_reg;

		wait();

		out->write(erg_reg);
		done->write(true);

		wait();

		// en-Signal muss mindestens einmal vorher resetted werden 
		while(en->read()==true){
			wait();
		}
		done->write(false);
		wait();

	}
}