
///////////////////////////////////////////////////////////////////////////////
//                                                                           //
//                           Double Integer - test                           //
//                                                                           //
///////////////////////////////////////////////////////////////////////////////
// Compile as Release x64 !

// fast division flags (LOW part in 3 bits = mode, 1 bit neg flag, HIGH part = number of shifts):
#ifndef FASTDIV_BIT
enum { // mode in LOW part (max. 8 modes!)
	FASTDIV_0 = 0,	// divide by zero
	FASTDIV_1,		// divide by 1
	FASTDIV_2,		// divide by 2
	FASTDIV_SHIFT,	// divide by shift, HIGH = number of shifts 0...
	FASTDIV_HIGH,	// divide by number with highest bit set, mul=divider, result 0 or 1
	FASTDIV_MUL,	// divide, simple multiplier, HIGH = number of shifts 0...
	FASTDIV_FULL,	// divide, multiplier in full range with hidden highest bit "1"
					//   HIGH = number of shifts 0...
};

#define FASTDIV_NEG B3	// flag - divisor is negative

#define FASTDIV_BIT 4	// number of bits of mode (=LOW part), 3 bits mode + 1 bit negative flag
#define FASTDIV_BASE (1 << FASTDIV_BIT) // base of number of shifts (=HIGH part)
#define FASTDIV_MASK (FASTDIV_BASE - 1) // mask of flags (=LOW part)
#define FASTDIV_MASK2 (FASTDIV_MASK & ~FASTDIV_NEG) // mask of flags without negative flag
#endif // FASTDIV_BIT

// --- double integer uint128, sint128

// uint32, sint32 (only for test)
#define DBLUINT uint32	// double integer class unsigned
#define BASEUINT u16	// base integer unsigned
#define HALFUINT u8		// half integer unsigned
#define DBLSINT sint32	// double integer class signed
#define BASESINT s16	// base integer signed
#define HALFSINT s8		// half integer signed
#define DBLFIX fix32	// double fixed point class
#include "dblint_h.h"

// uint64, sint64 (only for test)
#define DBLUINT uint64	// double integer class unsigned
#define BASEUINT u32	// base integer unsigned
#define HALFUINT u16	// half integer unsigned
#define DBLSINT sint64	// double integer class signed
#define BASESINT s32	// base integer signed
#define HALFSINT s16		// half integer signed
#define DBLFIX fix64	// double fixed point class
#include "dblint_h.h"

// uint128, sint128 (with assembler)
#define DBLUINT uint128	// double integer class unsigned
#define BASEUINT u64	// base integer unsigned
#define HALFUINT u32	// half integer unsigned
#define DBLSINT sint128	// double integer class signed
#define BASESINT s64	// base integer signed
#define HALFSINT s32	// half integer signed
#define DBLFIX fix128	// double fixed point class
#define USEASM			// can use assembler
#include "dblint_h.h"

// uint128ref, sint128ref (without assembler - only for test as reference)
#define DBLUINT uint128ref // double integer class unsigned
#define BASEUINT u64	// base integer unsigned
#define HALFUINT u32	// half integer unsigned
#define DBLSINT sint128ref	// double integer class signed
#define BASESINT s64	// base integer signed
#define HALFSINT s32	// half integer signed
#define DBLFIX fix128ref // double fixed point class
#include "dblint_h.h"

// --- quadruple integer uint256

// uint64B, sint64B (only for test)
#define QUADUINT uint64B // quadruple integer class
#define DBLUINT uint32	// double integer class unsigned
#define BASEUINT u16	// base integer unsigned
#define HALFUINT u8		// half integer unsigned
#define QUADSINT sint64B // double integer class signed
#define DBLSINT sint32	// double integer class signed
#define BASESINT s16	// base integer signed
#define HALFSINT s8		// half integer signed
#define DBLFIX fix32	// double fixed point class
#define QUADFIX fix64B	// quadruple fixed point class
#include "quadint_h.h"

// uint128B, sint128B (only for test)
#define QUADUINT uint128B // quadruple integer class
#define DBLUINT uint64	// double integer class unsigned
#define BASEUINT u32	// base integer unsigned
#define HALFUINT u16	// half integer unsigned
#define QUADSINT sint128B // double integer class signed
#define DBLSINT sint64	// double integer class signed
#define BASESINT s32	// base integer signed
#define HALFSINT s16	// half integer signed
#define DBLFIX fix64	// double fixed point class
#define QUADFIX fix128B	// quadruple fixed point class
#include "quadint_h.h"

// uint256, sint256 (with assembler)
#define QUADUINT uint256 // quadruple integer class
#define DBLUINT uint128	// double integer class unsigned
#define BASEUINT u64	// base integer unsigned
#define HALFUINT u32	// half integer unsigned
#define QUADSINT sint256 // double integer class signed
#define DBLSINT sint128	// double integer class signed
#define BASESINT s64	// base integer signed
#define HALFSINT s32	// half integer signed
#define DBLFIX fix128	// double fixed point class
#define QUADFIX fix256	// quadruple fixed point class
#define USEASM			// can use assembler
#include "quadint_h.h"

// uint256ref, sint256ref (without assembler - only for test as reference)
#define QUADUINT uint256ref // quadruple integer class unsigned
#define DBLUINT uint128	// double integer class unsigned
#define BASEUINT u64	// base integer unsigned
#define HALFUINT u32	// half integer unsigned
#define QUADSINT sint256ref // double integer class signed
#define DBLSINT sint128	// double integer class signed
#define BASESINT s64	// base integer signed
#define HALFSINT s32	// half integer signed
#define DBLFIX fix128ref // double fixed point class
#define QUADFIX fix256ref // quadruple fixed point class
#include "quadint_h.h"

// check double integer + u64
void Check_dbluint(int max);

// check double integer + s64
void Check_dblsint(int max);

// check double fix + double
void Check_dblfix(int max);

// check quadruple integer + u64
void Check_quaduint(int max);

// check quadruple integer + s64
void Check_quadsint(int max);

// check quadruple fix + double
void Check_quadfix(int max);

// check quadruple integer + double integer unsigned
void Check_quadudbl(int max);

// check quadruple integer + double integer signed
void Check_quadsdbl(int max);

// check double integer assembler unsigned
void Check_dbluint_asm(int max);

// check double integer assembler signed
void Check_dblsint_asm(int max);

// check quadruple integer assembler unsigned
void Check_quaduint_asm(int max);

// check quadruple integer assembler signed
void Check_quadsint_asm(int max);

// test dblint timming
void TestDblIntTime();

// test quadint timming
void TestQuadIntTime();
