PDOS

[uia] / trunk / uia / vx32 / ophash.cc  

View of /trunk/uia/vx32/ophash.cc

Parent Directory Parent Directory | Revision Log Revision Log


Revision 2009 - (download) (as text) (annotate)
Thu Apr 5 17:19:47 2007 UTC (2 years, 7 months ago) by baford
File size: 3884 byte(s)
Copy old working vx32 version from vxa-060115 tag.
#include <math.h>
#include <stdio.h>
#include <string.h>
#include <assert.h>
#include <inttypes.h>

#include <openssl/aes.h>
#include <openssl/sha.h>


float z = 0.0;

int iters = 1000*1;
//int iters = 1000*1000*1000;


unsigned char zkey[128/8] = "the key!!!";
AES_KEY aeskey;

union block {
	int32_t i[4];
	int64_t l[2];
	float f[4];
	double d[2];
	uint8_t b[16];
};

struct opargs {
	union block i;
	union block o;
	SHA_CTX c;
};

#define DEFOP(name,op) \
	void name(struct opargs *a) { op; }


// Single-precision operations

#define ia1	a->i.f[0]
#define ia2	a->i.f[1]
#define ib1	a->i.f[2]
#define ib2	a->i.f[3]
#define oa	a->o.f[0]
#define ob	a->o.f[1]

DEFOP(sadd, (oa = ia1 + ia2, ob = ib1 + ib2))
DEFOP(ssub, (oa = ia1 - ia2, ob = ib1 - ib2))
DEFOP(smul, (oa = ia1 * ia2, ob = ib1 * ib2))
DEFOP(sdiv, (oa = ia1 / ia2, ob = ib1 / ib2))
DEFOP(srec, (oa = 1.0 / ia1, ob = 1.0 / ib1))
DEFOP(stoi, (a->o.i[0] = (int32_t)ia1, a->o.i[1] = (int32_t)ib1))
DEFOP(sfri, (oa = a->i.i[0], ob = a->i.i[2]))
DEFOP(ssqrt, (oa = sqrtf(ia1), ob = sqrtf(ib1)))
DEFOP(ssin, (oa = sinf(ia1), ob = sinf(ib1)))
DEFOP(sexp, (oa = expf(ia1), ob = expf(ib1)))

#undef ia1
#undef ia2
#undef ib1
#undef ib2
#undef oa
#undef ob


// Double-precision operations

#define i1	a->i.d[0]
#define i2	a->i.d[1]
#define oo	a->o.d[0]

DEFOP(dadd, (oo = i1 + i2))
DEFOP(dsub, (oo = i1 - i2))
DEFOP(dmul, (oo = i1 * i2))
DEFOP(ddiv, (oo = i1 / i2))
DEFOP(drec, (oo = 1.0 / i1))
DEFOP(dtol, (a->o.l[0] = (int64_t)i1))
DEFOP(dfrl, (oo = a->i.l[0]))
DEFOP(dsqrt, (oo = sqrt(i1)))
DEFOP(dsin, (oo = sin(i1)))
DEFOP(dexp, (oo = exp(i1)))

#undef i1
#undef i2
#undef o


void stest(char *name, int dbl, void (*op)(struct opargs *a))
{
	printf("%30s: ", name);
	fflush(stdout);

	int rc = AES_set_encrypt_key(zkey, 128, &aeskey);
	assert(rc == 0);

	// initialize the loop arguments
	struct opargs a;
	memset(&a, 0, sizeof(a));
	SHA1_Init(&a.c);

	// compute the op hash
	for (int i = 0; i < iters; i++) {

		// generate another block of arguments
		AES_encrypt(a.i.b, a.i.b, &aeskey);

		// perform the appropriate operation
		op(&a);

		// Squash NANs
		if (dbl) {
			if (isnan(a.o.d[0]))
				a.o.d[0] = 0.0;
		} else {
			if (isnan(a.o.f[0]))
				a.o.f[0] = 0.0;
			if (isnan(a.o.f[1]))
				a.o.f[1] = 0.0;
		}

		// hash the results
		SHA1_Update(&a.c, a.o.b, 8);

#if 1
		uint8_t hash[20];
		SHA1_Final(hash, &a.c);
		if (dbl) {
			printf("%d: %f,%f->%f\n", i,
				a.i.d[0], a.i.d[1], a.o.d[0]);
			printf("hex: %016llx,%016llx->%016llx\n",
				a.i.l[0], a.i.l[1], a.o.l[0]);
		} else {
			printf("%d: %f,%f->%f, %f,%f->%f\n", i,
				a.i.f[0], a.i.f[1], a.o.f[0],
				a.i.f[2], a.i.f[3], a.o.f[1]);
		}
		for (int j = 0; j < 20; j++)
			printf("%02x", hash[j]);
		printf("\n");
#endif
	}

	// output the op hash
	uint8_t hash[20];
	SHA1_Final(hash, &a.c);
	for (int i = 0; i < 20; i++)
		printf("%02x", hash[i]);
	printf("\n");
}

int main()
{
#if 0
	stest("Single-precision add", 0, sadd);
	stest("Single-precision subtract", 0, ssub);
	stest("Single-precision multiply", 0, smul);
	stest("Single-precision divide", 0, sdiv);
	stest("Single-precision reciprocal", 0, srec);
	stest("Single-precision to int", 0, stoi);
	stest("Single-precision from int", 0, sfri);
	stest("Single-precision square root", 0, ssqrt);
	stest("Single-precision sine", 0, ssin);
	stest("Single-precision exponent", 0, sexp);

	stest("Double-precision add", 1, dadd);
	stest("Double-precision subtract", 1, dsub);
	stest("Double-precision multiply", 1, dmul);
	stest("Double-precision divide", 1, ddiv);
	stest("Double-precision reciprocal", 1, drec);
	stest("Double-precision to long", 1, dtol);
	stest("Double-precision from long", 1, dfrl);
	stest("Double-precision square root", 1, dsqrt);
	stest("Double-precision sine", 1, dsin);
	stest("Double-precision exponent", 1, dexp);
#endif
	stest("Double-precision multiply", 1, dmul);
}


Maintained by PDOS
ViewVC Help
Powered by ViewVC 1.0.3