Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- /*
- Simplistic Genetic Programming ISA.
- * Based around 3R instructions.
- * Each instruction word is 64 bits.
- * There are 16 or 32 registers (R0..R31).
- ** Each register is 64 bits.
- ** R0: ZR (Zero Register)
- ** R1: LR (Link Register) / IMM (Immediate)
- Instruction encoding (Basic 3R):
- * (63:48): Opcode (8 or 10 logical bits)
- * (47:24): Ignore / Imm24
- * (23:16): Rd / Ld
- * (15: 8): Rs
- * ( 7: 0): Rt
- Instruction encoding (Basic 2R):
- * (63:48): Opcode (8 or 10 logical bits)
- * (47:24): Ignore / Imm24
- * (23:16): Rd
- * (15: 8): Rs
- * ( 7: 0): Opcode 2
- Instruction encoding (Imm48):
- * (63:56): Opcode (4 or 5 logical bits)
- * (55:48): Rd
- * (47: 0): Imm48
- Multiple encodings may map to the same logical register, and using ECC bits makes the register ID more resistant to random bit-flips (caused by the mutator).
- The 8 bit register field will consist of 4 or 5 data bits and 4 or 3 parity bits.
- * The data bits will encode the register number using Gray-Coding
- * The parity bits will each XOR a group of 3 bits.
- * 4-bit: abcd: a^b^c, b^c^d, c^d^a
- * 5-bit: abcde: a^b^c, b^c^d, c^d^e
- Encodings which fall into the "unrecoverable" or "disallowed" parts of the encoding space are interpreted as NOPs.
- Opcodes will be encoded as either a single 4 or 5 bit value, or as a pair of 4 or 5 bit values. Opcodes will use either the 4 or 5 bit Gray Coding scheme.
- Using a smaller encoding space may allow for faster convergence.
- Vector immediate values will be encoded as 48-bits, such as four 12-bit floating-point values (S.E5.M6), which may also be stored in gray-coded form. There might also be 2x 24-bit bit (truncated gray-coded single), or 1x 48-bit (truncated gray-coded double).
- Opcode-Space:
- * 00: End Program
- * 01: 3R ALU
- ** 01-00: ADD
- ** 01-01: SUB
- ** 01-02: SHAD
- ** 01-03: SHLD
- ** 01-04: MUL
- ** 01-05: AND
- ** 01-06: OR
- ** 01-07: XOR
- ** 01-08: MIN
- ** 01-09: MAX
- ** 01-0A: DIV
- ** 01-0B: MOD
- ** 01-0C-00: MOV
- * 02: Compare Branch
- ** 02-00: JCMPEQ
- ** 02-01: JCMPGT
- ** 02-02: JCMPGE
- ** 02-03: BSR (PC+Ld)
- ** 02-04: JCMPNE
- ** 02-05: JCMPLE
- ** 02-06: JCMPLT
- ** 02-07: JMP (Rs)
- ** 02-08: JCMPFEQ
- ** 02-09: JCMPFGT
- ** 02-0A: JCMPFGE
- ** 02-0B: -
- ** 02-0C: JCMPFNE
- ** 02-0D: JCMPFLE
- ** 02-0E: JCMPFLT
- ** 02-0F: -
- * 03: 3R FPU
- ** 03-00: FADD
- ** 03-01: FSUB
- ** 03-02: FMUL
- ** 03-03: FDIV
- ** 03-04: FMAC
- ** 03-05: FMASC
- ** 03-06: FMIN
- ** 03-07: FMAX
- ** 03-0C-00: RCP
- ** 03-0C-01: SQRT
- ** 03-0C-02: ATAN
- ** 03-0C-04: I2F
- ** 03-0C-05: F2I
- * 04: 3R VEC2F
- ** 04-00: PADD.F
- ** 04-01: PSUB.F
- ** 04-02: PMUL.F
- ** 04-03: PDIV.F
- * 05: 3R VEC4H
- ** 05-00: PADD.H
- ** 05-01: PSUB.H
- ** 05-02: PMUL.H
- ** 05-03: PDIV.H
- * 0C: IMM Int48 (Load 48-bit Integer, Sign Extend)
- * 0D: IMM Float (Load 48-bit Truncated Double)
- * 0E: IMM VEC2F (Load 2x Float24, Truncated Single)
- * 0F: IMM VEC4H (Load 4x Float12, Truncated Half)
- */
- #include <stdio.h>
- #include <stdlib.h>
- #include <string.h>
- #include <stdint.h>
- #include <math.h>
- #define GPI_ROMSZ 256
- #define GPI_GENSZ 256
- #define GPI_GENSEL 32
- typedef int8_t sbyte;
- typedef uint8_t byte;
- typedef int16_t s16;
- typedef uint16_t u16;
- typedef int32_t s32;
- typedef uint32_t u32;
- typedef int64_t s64;
- typedef uint64_t u64;
- typedef struct GPI_VMProg_s GPI_VMProg;
- typedef struct GPI_VMState_s GPI_VMState;
- typedef struct GPI_Context_s GPI_Context;
- struct GPI_VMProg_s {
- u64 rom[GPI_ROMSZ];
- };
- struct GPI_VMState_s {
- u64 reg[32];
- u64 u_reg[8];
- short nnop;
- byte pc;
- GPI_VMProg *prog;
- };
- struct GPI_Context_s {
- GPI_VMProg *prog[GPI_GENSZ];
- double prgw[GPI_GENSZ];
- GPI_VMProg prg_arr[GPI_GENSZ];
- void *userdata;
- void (*SetupState)(GPI_Context *ctx, GPI_VMState *vm);
- double (*RankState)(GPI_Context *ctx, GPI_VMState *vm);
- };
- byte gpi_gray4enc[16];
- byte gpi_gray4dec[16];
- byte gpi_gray5enc[32];
- byte gpi_gray5dec[32];
- byte gpi_gray8enc[256];
- byte gpi_gray8dec[256];
- byte gpi_base4encp[16];
- byte gpi_base5encp[32];
- byte gpi_base4decp[256];
- byte gpi_base5decp[256];
- byte gpi_gray4encp[16];
- byte gpi_gray5encp[32];
- byte gpi_gray4decp[256];
- byte gpi_gray5decp[256];
- byte gpi_gray4decpr[256];
- byte gpi_gray5decpr[256];
- byte gpi_graydecr[256];
- byte gpi_graydeco[256];
- u32 gpi_halfdechi[64];
- u16 gpi_halfenchi[512];
- void GPI_InitTables(void)
- {
- int p0, p1, p2, p3;
- int i, j, k;
- for(i=0; i<16; i++)
- {
- j=i^(i>>1);
- gpi_gray4enc[i]=j;
- gpi_gray4dec[j]=i;
- }
- for(i=0; i<32; i++)
- {
- j=i^(i>>1);
- gpi_gray5enc[i]=j;
- gpi_gray5dec[j]=i;
- }
- for(i=0; i<256; i++)
- {
- j=i^(i>>1);
- gpi_gray8enc[i]=j;
- gpi_gray8dec[j]=i;
- }
- memset(gpi_base4decp, 0xFF, 256);
- memset(gpi_base5decp, 0xFF, 256);
- for(i=0; i<16; i++)
- {
- p0=((i>>3)^(i>>2)^(i>>1))&1;
- p1=((i>>2)^(i>>1)^(i>>0))&1;
- p2=((i>>1)^(i>>0)^(i>>3))&1;
- p3=((i>>3)^(i>>2)^(i>>1)^(i>>0))&1;
- j=i|(p0<<7)|(p1<<6)|(p2<<5)|(p3<<4);
- gpi_base4encp[i]=j;
- gpi_base4decp[j]=i;
- }
- for(i=0; i<32; i++)
- {
- p0=((i>>4)^(i>>3)^(i>>2))&1;
- p1=((i>>3)^(i>>2)^(i>>1))&1;
- p2=((i>>2)^(i>>1)^(i>>0))&1;
- j=i|(p0<<7)|(p1<<6)|(p2<<5);
- gpi_base5encp[i]=j;
- gpi_base5decp[j]=i;
- }
- for(i=0; i<256; i++)
- {
- j=gpi_base4decp[i];
- if(j!=255)continue;
- for(j=0; j<8; j++)
- {
- p0=i^(1<<j);
- p1=gpi_base4decp[p0];
- p2=gpi_base4encp[p1];
- if((p1!=255) && (p2==p0))
- {
- gpi_base4decp[i]=p1;
- break;
- }
- }
- }
- #if 0
- for(i=0; i<256; i++)
- {
- j=gpi_base4decp[i];
- if(j!=255)continue;
- for(j=0; j<8; j++)
- for(k=0; k<8; k++)
- {
- p0=i^(1<<j)^(1<<k);
- p1=gpi_base4decp[p0];
- p2=gpi_base4encp[p1];
- if((p1!=255) && (p2==p0))
- {
- gpi_base4decp[i]=p1;
- break;
- }
- }
- }
- #endif
- for(i=0; i<256; i++)
- {
- j=gpi_base5decp[i];
- if(j!=255)continue;
- for(j=0; j<8; j++)
- {
- p0=i^(1<<j);
- p1=gpi_base5decp[p0];
- p2=gpi_base5encp[p1];
- if((p1!=255) && (p2==p0))
- {
- gpi_base5decp[i]=p1;
- break;
- }
- }
- }
- for(i=0; i<16; i++)
- { gpi_gray4encp[i]=gpi_base4encp[gpi_gray4enc[i]]; }
- for(i=0; i<32; i++)
- { gpi_gray5encp[i]=gpi_base5encp[gpi_gray5enc[i]]; }
- for(i=0; i<256; i++)
- {
- j=gpi_base4decp[i];
- k=(j>32)?255:gpi_gray4dec[j];
- gpi_gray4decp[i]=k;
- if(k==255) k=0;
- gpi_gray4decpr[i]=k;
- j=gpi_base5decp[i];
- k=(j>32)?255:gpi_gray5dec[j];
- gpi_gray5decp[i]=k;
- if(k==255) k=0;
- gpi_gray5decpr[i]=k;
- }
- for(i=0; i<16; i++)
- {
- j=gpi_gray4encp[i];
- k=gpi_gray4decp[j];
- if(k!=i)
- { printf("Gray4: Round Trip Fail\n"); }
- }
- for(i=0; i<32; i++)
- {
- j=gpi_gray5encp[i];
- k=gpi_gray5decp[j];
- if(k!=i)
- { printf("Gray5: Round Trip Fail\n"); }
- }
- for(i=0; i<32; i++)
- {
- j=((i-15)+127)<<23;
- if(i== 0) j= 0U<<23;
- if(i==31) j=255U<<23;
- gpi_halfdechi[0x00|i]=j;
- gpi_halfdechi[0x20|i]=j|0x80000000U;
- }
- for(i=0; i<256; i++)
- {
- j=(i-127)+15;
- if(j<=0)j=0;
- if(j>=15)j=15;
- k=j<<10;
- gpi_halfenchi[0x000|i]=0x0000|k;
- gpi_halfenchi[0x100|i]=0x8000|k;
- }
- for(i=0; i<256; i++)
- {
- gpi_graydecr[i]=gpi_gray4decpr[i];
- // gpi_graydecr[i]=gpi_gray5decpr[i];
- gpi_graydeco[i]=gpi_gray4decpr[i];
- }
- }
- void GPI_DumpTables(void)
- {
- int stat[64];
- int i, j, k;
- printf("Gray4 Enc:\n");
- for(i=0; i<16; i++)
- { printf("%02X ", gpi_gray4enc[i]); }
- printf("\n");
- printf("Gray4 EncP:\n");
- for(i=0; i<16; i++)
- { printf("%02X ", gpi_gray4encp[i]); }
- printf("\n");
- printf("Gray5 Enc:\n");
- for(i=0; i<32; i++)
- { printf("%02X ", gpi_gray5enc[i]); }
- printf("\n");
- printf("Gray5 EncP:\n");
- for(i=0; i<32; i++)
- { printf("%02X ", gpi_gray5encp[i]); }
- printf("\n");
- printf("Gray4 DecP:\n");
- for(i=0; i<64; i++)
- stat[i]=0;
- for(i=0; i<16; i++)
- {
- for(j=0; j<16; j++)
- {
- k=gpi_gray4decp[i*16+j];
- printf("%02X ", k);
- stat[k&63]++;
- }
- printf("\n");
- }
- for(i=0; i<16; i++)
- {
- printf("%d ", stat[i]);
- }
- printf("%d\n", stat[63]);
- printf("Gray5 DecP:\n");
- for(i=0; i<64; i++)
- stat[i]=0;
- for(i=0; i<16; i++)
- {
- for(j=0; j<16; j++)
- {
- k=gpi_gray5decp[i*16+j];
- printf("%02X ", k);
- stat[k&63]++;
- }
- printf("\n");
- }
- for(i=0; i<32; i++)
- {
- printf("%d ", stat[i]);
- }
- printf("%d\n", stat[63]);
- }
- int GPI_InterpAdd2F(GPI_VMState *ctx, int rs, int rt, int rd)
- {
- float *fvs, *fvt, *fvd;
- u64 vs, vt, vd;
- vs=ctx->reg[rs]; vt=ctx->reg[rt];
- fvs=(float *)(&vs);
- fvt=(float *)(&vt);
- fvd=(float *)(&vd);
- fvd[0]=fvs[0]+fvt[0];
- fvd[1]=fvs[1]+fvt[1];
- ctx->reg[rd]=vd;
- return(0);
- }
- int GPI_InterpSub2F(GPI_VMState *ctx, int rs, int rt, int rd)
- {
- float *fvs, *fvt, *fvd;
- u64 vs, vt, vd;
- vs=ctx->reg[rs]; vt=ctx->reg[rt];
- fvs=(float *)(&vs);
- fvt=(float *)(&vt);
- fvd=(float *)(&vd);
- fvd[0]=fvs[0]-fvt[0];
- fvd[1]=fvs[1]-fvt[1];
- ctx->reg[rd]=vd;
- return(0);
- }
- int GPI_InterpMul2F(GPI_VMState *ctx, int rs, int rt, int rd)
- {
- float *fvs, *fvt, *fvd;
- u64 vs, vt, vd;
- vs=ctx->reg[rs]; vt=ctx->reg[rt];
- fvs=(float *)(&vs);
- fvt=(float *)(&vt);
- fvd=(float *)(&vd);
- fvd[0]=fvs[0]*fvt[0];
- fvd[1]=fvs[1]*fvt[1];
- ctx->reg[rd]=vd;
- return(0);
- }
- int GPI_InterpDiv2F(GPI_VMState *ctx, int rs, int rt, int rd)
- {
- float *fvs, *fvt, *fvd;
- u64 vs, vt, vd;
- vs=ctx->reg[rs]; vt=ctx->reg[rt];
- fvs=(float *)(&vs);
- fvt=(float *)(&vt);
- fvd=(float *)(&vd);
- fvd[0]=fvs[0]/fvt[0];
- fvd[1]=fvs[1]/fvt[1];
- ctx->reg[rd]=vd;
- return(0);
- }
- float GPU_VecUnpackHalf(int val)
- {
- float f;
- u32 hf;
- hf=gpi_halfdechi[(val>>10)&63]|((val&1023)<<13);
- *(u32 *)(&f)=hf;
- return(f);
- }
- int GPU_VecPackHalf(float val)
- {
- u32 tv;
- u16 hf;
- tv=*(u32 *)(&val);
- hf=gpi_halfenchi[(tv>>23)&511]|((tv>>13)&1023);
- return(hf);
- }
- void GPU_VecUnpack4H(u64 vec, float *rfv)
- {
- rfv[0]=GPU_VecUnpackHalf(vec>> 0);
- rfv[1]=GPU_VecUnpackHalf(vec>>16);
- rfv[2]=GPU_VecUnpackHalf(vec>>32);
- rfv[3]=GPU_VecUnpackHalf(vec>>48);
- }
- u64 GPU_VecPack4H(float *rfv)
- {
- u64 tv;
- u32 i0, i1, i2, i3;
- i0=GPU_VecPackHalf(rfv[0]);
- i1=GPU_VecPackHalf(rfv[1]);
- i2=GPU_VecPackHalf(rfv[2]);
- i3=GPU_VecPackHalf(rfv[3]);
- i1=(i1<<16)|i0;
- i3=(i3<<16)|i2;
- tv=(((u64)i3)<<32)|i1;
- return(tv);
- }
- int GPI_InterpAdd4H(GPI_VMState *ctx, int rs, int rt, int rd)
- {
- float fvs[4], fvt[4], fvd[4];
- u64 vs, vt, vd;
- vs=ctx->reg[rs]; vt=ctx->reg[rt];
- GPU_VecUnpack4H(vs, fvs);
- GPU_VecUnpack4H(vt, fvt);
- fvd[0]=fvs[0]+fvt[0];
- fvd[1]=fvs[1]+fvt[1];
- fvd[2]=fvs[2]+fvt[2];
- fvd[3]=fvs[3]+fvt[3];
- vd=GPU_VecPack4H(fvd);
- ctx->reg[rd]=vd;
- return(0);
- }
- int GPI_InterpSub4H(GPI_VMState *ctx, int rs, int rt, int rd)
- {
- float fvs[4], fvt[4], fvd[4];
- u64 vs, vt, vd;
- vs=ctx->reg[rs]; vt=ctx->reg[rt];
- GPU_VecUnpack4H(vs, fvs);
- GPU_VecUnpack4H(vt, fvt);
- fvd[0]=fvs[0]-fvt[0];
- fvd[1]=fvs[1]-fvt[1];
- fvd[2]=fvs[2]-fvt[2];
- fvd[3]=fvs[3]-fvt[3];
- vd=GPU_VecPack4H(fvd);
- ctx->reg[rd]=vd;
- return(0);
- }
- int GPI_InterpMul4H(GPI_VMState *ctx, int rs, int rt, int rd)
- {
- float fvs[4], fvt[4], fvd[4];
- u64 vs, vt, vd;
- vs=ctx->reg[rs]; vt=ctx->reg[rt];
- GPU_VecUnpack4H(vs, fvs);
- GPU_VecUnpack4H(vt, fvt);
- fvd[0]=fvs[0]*fvt[0];
- fvd[1]=fvs[1]*fvt[1];
- fvd[2]=fvs[2]*fvt[2];
- fvd[3]=fvs[3]*fvt[3];
- vd=GPU_VecPack4H(fvd);
- ctx->reg[rd]=vd;
- return(0);
- }
- int GPI_InterpDiv4H(GPI_VMState *ctx, int rs, int rt, int rd)
- {
- float fvs[4], fvt[4], fvd[4];
- u64 vs, vt, vd;
- vs=ctx->reg[rs]; vt=ctx->reg[rt];
- GPU_VecUnpack4H(vs, fvs);
- GPU_VecUnpack4H(vt, fvt);
- fvd[0]=fvs[0]/fvt[0];
- fvd[1]=fvs[1]/fvt[1];
- fvd[2]=fvs[2]/fvt[2];
- fvd[3]=fvs[3]/fvt[3];
- vd=GPU_VecPack4H(fvd);
- ctx->reg[rd]=vd;
- return(0);
- }
- int GPI_InterpStep(GPI_VMState *ctx)
- {
- double f, g, e, h;
- s64 li, la, lb, lc;
- u64 opw;
- int pc, rd, rs, rt;
- int i0, i1, i2;
- int i, j, opn, opy, ret;
- ctx->reg[0]=0;
- ret=0;
- pc=ctx->pc;
- ctx->pc=pc+1;
- opw=ctx->prog->rom[pc];
- // opn=gpi_gray5decp[(opw>>56)&255];
- opn=gpi_graydeco[(opw>>56)&255];
- switch(opn)
- {
- case 0x00:
- // ret=1;
- break;
- case 0x01:
- rd=gpi_graydecr[(opw>>16)&255];
- rs=gpi_graydecr[(opw>> 8)&255];
- rt=gpi_graydecr[(opw>> 0)&255];
- i0= gpi_gray8dec[(opw>>40)&255];
- i0=(i0<<8) | gpi_gray8dec[(opw>>32)&255];
- i0=(i0<<8) | gpi_gray8dec[(opw>>24)&255];
- i0=((s32)(i0<<8))>>8;
- ctx->nnop++;
- // switch(gpi_gray5decp[(opw>>48)&255])
- switch(gpi_graydeco[(opw>>48)&255])
- {
- case 0x00:
- la=ctx->reg[rs];
- lb=ctx->reg[rt];
- if(rs==1)la=i0;
- if(rt==1)lb=i0;
- lc=la+lb;
- ctx->reg[rd]=lc;
- break;
- case 0x01:
- la=ctx->reg[rs];
- lb=ctx->reg[rt];
- if(rs==1)la=i0;
- if(rt==1)lb=i0;
- lc=la-lb;
- ctx->reg[rd]=lc;
- break;
- case 0x02:
- j=(sbyte)ctx->reg[rt];
- if(rt==1) j=i0;
- if(j>=0)
- ctx->reg[rd]=((s64)ctx->reg[rs])<<(( j)&63);
- else
- ctx->reg[rd]=((s64)ctx->reg[rs])>>((-j)&63);
- break;
- case 0x03:
- j=(sbyte)ctx->reg[rt];
- if(rt==1) j=i0;
- if(j>=0)
- ctx->reg[rd]=((u64)ctx->reg[rs])<<(( j)&63);
- else
- ctx->reg[rd]=((u64)ctx->reg[rs])>>((-j)&63);
- break;
- case 0x04:
- la=ctx->reg[rs];
- lb=ctx->reg[rt];
- if(rs==1)la=i0;
- if(rt==1)lb=i0;
- lc=la*lb;
- ctx->reg[rd]=lc;
- break;
- case 0x05:
- la=ctx->reg[rs];
- lb=ctx->reg[rt];
- if(rs==1)la=i0;
- if(rt==1)lb=i0;
- lc=la&lb;
- ctx->reg[rd]=lc;
- break;
- case 0x06:
- la=ctx->reg[rs];
- lb=ctx->reg[rt];
- if(rs==1)la=i0;
- if(rt==1)lb=i0;
- lc=la|lb;
- ctx->reg[rd]=lc;
- break;
- case 0x07:
- la=ctx->reg[rs];
- lb=ctx->reg[rt];
- if(rs==1)la=i0;
- if(rt==1)lb=i0;
- lc=la^lb;
- ctx->reg[rd]=lc;
- break;
- case 0x08:
- la=ctx->reg[rs];
- lb=ctx->reg[rt];
- if(rs==1)la=i0;
- if(rt==1)lb=i0;
- lc=(la<lb)?la:lb;
- ctx->reg[rd]=lc;
- break;
- case 0x09:
- la=ctx->reg[rs];
- lb=ctx->reg[rt];
- if(rs==1)la=i0;
- if(rt==1)lb=i0;
- lc=(la>lb)?la:lb;
- ctx->reg[rd]=lc;
- break;
- case 0x0A:
- la=ctx->reg[rs];
- lb=ctx->reg[rt];
- if(rs==1)la=i0;
- if(rt==1)lb=i0;
- lc=(lb!=0)?(la/lb):0;
- ctx->reg[rd]=lc;
- break;
- case 0x0B:
- la=ctx->reg[rs];
- lb=ctx->reg[rt];
- if(rs==1)la=i0;
- if(rt==1)lb=i0;
- lc=(lb!=0)?(la%lb):0;
- ctx->reg[rd]=lc;
- break;
- case 0x0D:
- rs=rd;
- case 0x0C:
- switch(rt)
- {
- case 0x00:
- ctx->reg[rd]=ctx->reg[rs];
- break;
- }
- break;
- default:
- break;
- }
- break;
- case 0x02:
- rd=gpi_graydecr[(opw>>16)&255];
- rs=gpi_graydecr[(opw>> 8)&255];
- rt=gpi_graydecr[(opw>> 0)&255];
- ctx->nnop++;
- opy=gpi_graydeco[(opw>>48)&255];
- // switch(gpi_gray5decp[(opw>>48)&255])
- switch(opy)
- {
- case 0x00:
- case 0x04:
- la=ctx->reg[rs];
- lb=ctx->reg[rt];
- j=(rd>>1)^((rd&1)?-1:0);
- if((la==lb) ^ ((opy&4)!=0))
- {
- // ctx->reg[1]=op->pc;
- ctx->pc=(pc+1+j)&(GPI_ROMSZ-1);
- if(ctx->pc==pc)
- ret=1;
- }
- break;
- case 0x01:
- case 0x05:
- la=ctx->reg[rs];
- lb=ctx->reg[rt];
- j=(rd>>1)^((rd&1)?-1:0);
- if((la>lb) ^ ((opy&4)!=0))
- {
- // ctx->reg[1]=op->pc;
- ctx->pc=(pc+1+j)&(GPI_ROMSZ-1);
- if(ctx->pc==pc)
- ret=1;
- }
- break;
- case 0x02:
- case 0x06:
- la=ctx->reg[rs];
- lb=ctx->reg[rt];
- j=(rd>>1)^((rd&1)?-1:0);
- if((la>=lb) ^ ((opy&4)!=0))
- {
- // ctx->reg[1]=op->pc;
- ctx->pc=(pc+1+j)&(GPI_ROMSZ-1);
- if(ctx->pc==pc)
- ret=1;
- }
- break;
- case 0x03:
- j=(rd>>1)^((rd&1)?-1:0);
- ctx->pc=pc+1+j;
- if(ctx->pc==pc)
- ret=1;
- break;
- case 0x07:
- la=ctx->reg[rs];
- ctx->pc=la&(GPI_ROMSZ-1);
- if(ctx->pc==pc)
- ret=1;
- break;
- case 0x08:
- case 0x0C:
- f=*(double *)(ctx->reg+rs);
- g=*(double *)(ctx->reg+rt);
- j=(rd>>1)^((rd&1)?-1:0);
- if((f==g) ^ ((opy&4)!=0))
- {
- // ctx->reg[1]=op->pc;
- ctx->pc=(pc+1+j)&(GPI_ROMSZ-1);
- if(ctx->pc==pc)
- ret=1;
- }
- break;
- case 0x09:
- case 0x0D:
- f=*(double *)(ctx->reg+rs);
- g=*(double *)(ctx->reg+rt);
- j=(rd>>1)^((rd&1)?-1:0);
- if((f>g) ^ ((opy&4)!=0))
- {
- // ctx->reg[1]=op->pc;
- ctx->pc=(pc+1+j)&(GPI_ROMSZ-1);
- if(ctx->pc==pc)
- ret=1;
- }
- break;
- case 0x0A:
- case 0x0E:
- f=*(double *)(ctx->reg+rs);
- g=*(double *)(ctx->reg+rt);
- j=(rd>>1)^((rd&1)?-1:0);
- if((f>=g) ^ ((opy&4)!=0))
- {
- // ctx->reg[1]=op->pc;
- ctx->pc=(pc+1+j)&(GPI_ROMSZ-1);
- if(ctx->pc==pc)
- ret=1;
- }
- break;
- default:
- break;
- }
- break;
- case 0x03:
- rd=gpi_graydecr[(opw>>16)&255];
- rs=gpi_graydecr[(opw>> 8)&255];
- rt=gpi_graydecr[(opw>> 0)&255];
- i0= gpi_gray8dec[(opw>>40)&255];
- i0=(i0<<8) | gpi_gray8dec[(opw>>32)&255];
- i0=(i0<<8) | gpi_gray8dec[(opw>>24)&255];
- i0=(i0<<8);
- e=*(float *)(&i0);
- ctx->nnop++;
- // switch(gpi_gray5decp[(opw>>48)&255])
- switch(gpi_graydeco[(opw>>48)&255])
- {
- case 0x00:
- f=*(double *)(ctx->reg+rs);
- g=*(double *)(ctx->reg+rt);
- if(rs==1)f=e;
- if(rt==1)g=e;
- h=f+g;
- *(double *)(ctx->reg+rd)=h;
- break;
- case 0x01:
- f=*(double *)(ctx->reg+rs);
- g=*(double *)(ctx->reg+rt);
- if(rs==1)f=e;
- if(rt==1)g=e;
- h=f-g;
- *(double *)(ctx->reg+rd)=h;
- break;
- case 0x02:
- f=*(double *)(ctx->reg+rs);
- g=*(double *)(ctx->reg+rt);
- if(rs==1)f=e;
- if(rt==1)g=e;
- h=f*g;
- *(double *)(ctx->reg+rd)=h;
- break;
- case 0x03:
- f=*(double *)(ctx->reg+rs);
- g=*(double *)(ctx->reg+rt);
- if(rs==1)f=e;
- if(rt==1)g=e;
- h = (g!=0) ? (f/g) : 0;
- *(double *)(ctx->reg+rd)=h;
- break;
- case 0x04:
- f=*(double *)(ctx->reg+rs);
- g=*(double *)(ctx->reg+rt);
- if(rs==1)f=e;
- if(rt==1)g=e;
- h=*(double *)(ctx->reg+rd);
- h=h+f*g;
- *(double *)(ctx->reg+rd)=h;
- break;
- case 0x05:
- f=*(double *)(ctx->reg+rs);
- g=*(double *)(ctx->reg+rt);
- h=f+g*e;
- *(double *)(ctx->reg+rd)=h;
- break;
- case 0x06:
- f=*(double *)(ctx->reg+rs);
- g=*(double *)(ctx->reg+rt);
- if(rs==1)f=e;
- if(rt==1)g=e;
- // h=*(double *)(ctx->reg+rd);
- h=(f<g)?f:g;
- *(double *)(ctx->reg+rd)=h;
- break;
- case 0x07:
- f=*(double *)(ctx->reg+rs);
- g=*(double *)(ctx->reg+rt);
- if(rs==1)f=e;
- if(rt==1)g=e;
- // h=*(double *)(ctx->reg+rd);
- h=(f>g)?f:g;
- *(double *)(ctx->reg+rd)=h;
- break;
- case 0x0D:
- rs=rd;
- case 0x0C:
- switch(rt)
- {
- case 0x00:
- f=*(double *)(ctx->reg+rs);
- h = (f!=0) ? (1.0/f) : 0;
- *(double *)(ctx->reg+rd)=h;
- break;
- case 0x01:
- f=*(double *)(ctx->reg+rs);
- h = (f>=0) ? sqrt(f) : -sqrt(-f);
- *(double *)(ctx->reg+rd)=h;
- break;
- case 0x02:
- f=*(double *)(ctx->reg+rs);
- h = atan(f);
- *(double *)(ctx->reg+rd)=h;
- break;
- case 0x04:
- f=ctx->reg[rs];
- *(double *)(ctx->reg+rd)=f;
- break;
- case 0x05:
- f=*(double *)(ctx->reg+rs);
- ctx->reg[rd]=f;
- break;
- }
- break;
- default:
- break;
- }
- break;
- case 0x04:
- rd=gpi_graydecr[(opw>>16)&255];
- rs=gpi_graydecr[(opw>> 8)&255];
- rt=gpi_graydecr[(opw>> 0)&255];
- ctx->nnop++;
- // switch(gpi_gray5decp[(opw>>48)&255])
- switch(gpi_graydeco[(opw>>48)&255])
- {
- case 0x00:
- GPI_InterpAdd2F(ctx, rs, rt, rd);
- break;
- case 0x01:
- GPI_InterpSub2F(ctx, rs, rt, rd);
- break;
- case 0x02:
- GPI_InterpMul2F(ctx, rs, rt, rd);
- break;
- case 0x03:
- GPI_InterpDiv2F(ctx, rs, rt, rd);
- break;
- default:
- break;
- }
- break;
- case 0x05:
- rd=gpi_graydecr[(opw>>16)&255];
- rs=gpi_graydecr[(opw>> 8)&255];
- rt=gpi_graydecr[(opw>> 0)&255];
- ctx->nnop++;
- // switch(gpi_gray5decp[(opw>>48)&255])
- switch(gpi_graydeco[(opw>>48)&255])
- {
- case 0x00:
- GPI_InterpAdd4H(ctx, rs, rt, rd);
- break;
- case 0x01:
- GPI_InterpSub4H(ctx, rs, rt, rd);
- break;
- case 0x02:
- GPI_InterpMul4H(ctx, rs, rt, rd);
- break;
- case 0x03:
- GPI_InterpDiv4H(ctx, rs, rt, rd);
- break;
- default:
- break;
- }
- break;
- case 0x0C:
- rd=gpi_graydecr[(opw>>48)&255];
- li= gpi_gray8dec[(opw>>40)&255];
- li=(li<<8) | gpi_gray8dec[(opw>>32)&255];
- li=(li<<8) | gpi_gray8dec[(opw>>24)&255];
- li=(li<<8) | gpi_gray8dec[(opw>>16)&255];
- li=(li<<8) | gpi_gray8dec[(opw>> 8)&255];
- li=(li<<8) | gpi_gray8dec[(opw>> 0)&255];
- li=(li<<16)>>16;
- ctx->reg[rd]=li;
- ctx->nnop++;
- break;
- case 0x0D:
- rd=gpi_graydecr[(opw>>48)&255];
- li= gpi_gray8dec[(opw>>40)&255];
- li=(li<<8) | gpi_gray8dec[(opw>>32)&255];
- li=(li<<8) | gpi_gray8dec[(opw>>24)&255];
- li=(li<<8) | gpi_gray8dec[(opw>>16)&255];
- li=(li<<8) | gpi_gray8dec[(opw>> 8)&255];
- li=(li<<8) | gpi_gray8dec[(opw>> 0)&255];
- li=(li<<16);
- ctx->reg[rd]=li;
- ctx->nnop++;
- break;
- case 0x0E:
- rd=gpi_graydecr[(opw>>48)&255];
- li= gpi_gray8dec[(opw>>40)&255];
- li=(li<<8) | gpi_gray8dec[(opw>>32)&255];
- li=(li<<8) | gpi_gray8dec[(opw>>24)&255];
- li=(li<<8);
- li=(li<<8) | gpi_gray8dec[(opw>>16)&255];
- li=(li<<8) | gpi_gray8dec[(opw>> 8)&255];
- li=(li<<8) | gpi_gray8dec[(opw>> 0)&255];
- li=(li<<8);
- ctx->reg[rd]=li;
- ctx->nnop++;
- break;
- case 0x0F:
- rd=gpi_graydecr[(opw>>48)&255];
- if(!rd)
- {
- ret=1;
- break;
- }
- i0= gpi_gray8dec[(opw>>40)&255];
- i0=(i0<<8) | gpi_gray8dec[(opw>>32)&255];
- i0=(i0<<8) | gpi_gray8dec[(opw>>24)&255];
- i1= gpi_gray8dec[(opw>>16)&255];
- i1=(i1<<8) | gpi_gray8dec[(opw>> 8)&255];
- i1=(i1<<8) | gpi_gray8dec[(opw>> 0)&255];
- li= (((i0>>12)&4095)<<4);
- li=(li<<16) | (((i0>> 0)&4095)<<4);
- li=(li<<16) | (((i1>>12)&4095)<<4);
- li=(li<<16) | (((i1>> 0)&4095)<<4);
- ctx->reg[rd]=li;
- ctx->nnop++;
- break;
- default:
- /* NOP */
- break;
- }
- return(ret);
- }
- int GPI_RunSteps(GPI_VMState *ctx)
- {
- int pc, cnt, rt;
- ctx->pc=0;
- ctx->nnop=0;
- cnt=512;
- while((cnt--)>0)
- {
- rt=GPI_InterpStep(ctx);
- if(rt>0)
- break;
- }
- return(cnt);
- }
- int GPI_ProgDumpOp(GPI_VMProg *prog, int pc)
- {
- double f, g, h;
- char *sn;
- s64 li;
- u64 opw;
- int rd, rs, rt;
- int i0, i1, i2;
- int i, j, opn, opy, ret;
- ret=0;
- sn=0;
- opw=prog->rom[pc];
- opn=gpi_graydeco[(opw>>56)&255];
- switch(opn)
- {
- case 0x00:
- // ret=1;
- break;
- case 0x01:
- rd=gpi_graydecr[(opw>>16)&255];
- rs=gpi_graydecr[(opw>> 8)&255];
- rt=gpi_graydecr[(opw>> 0)&255];
- opy=gpi_graydeco[(opw>>48)&255];
- switch(opy)
- {
- case 0x00: sn="ADD"; break;
- case 0x01: sn="SUB"; break;
- case 0x02: sn="SHAD"; break;
- case 0x03: sn="SHLD"; break;
- case 0x04: sn="MUL"; break;
- case 0x05: sn="AND"; break;
- case 0x06: sn="OR"; break;
- case 0x07: sn="XOR"; break;
- case 0x08: sn="MIN"; break;
- case 0x09: sn="MAX"; break;
- case 0x0A: sn="DIV"; break;
- case 0x0B: sn="MOD"; break;
- case 0x0D:
- rs=rd;
- case 0x0C:
- switch(rt)
- {
- case 0x00: sn="MOV"; break;
- }
- break;
- default:
- break;
- }
- if(sn)
- {
- if(opy>=0x0C)
- printf(" %s R%d, R%d\n", sn, rs, rd);
- else
- printf(" %s R%d, R%d, R%d\n", sn, rs, rt, rd);
- }
- break;
- case 0x02:
- rd=gpi_graydecr[(opw>>16)&255];
- rs=gpi_graydecr[(opw>> 8)&255];
- rt=gpi_graydecr[(opw>> 0)&255];
- opy=gpi_graydeco[(opw>>48)&255];
- switch(opy)
- {
- case 0x00: sn="JCMPEQ"; break;
- case 0x01: sn="JCMPGT"; break;
- case 0x02: sn="JCMPGE"; break;
- case 0x03: sn="BSR"; break;
- case 0x04: sn="JCMPNE"; break;
- case 0x05: sn="JCMPLE"; break;
- case 0x06: sn="JCMPLT"; break;
- case 0x07: sn="JMP"; break;
- case 0x08: sn="JCMPFEQ"; break;
- case 0x09: sn="JCMPFGT"; break;
- case 0x0A: sn="JCMPFGE"; break;
- case 0x0C: sn="JCMPFNE"; break;
- case 0x0D: sn="JCMPFLE"; break;
- case 0x0E: sn="JCMPFLT"; break;
- }
- if(sn)
- {
- printf(" %s R%d, R%d, L%d\n", sn, rs, rt, rd);
- }
- break;
- case 0x03:
- rd=gpi_graydecr[(opw>>16)&255];
- rs=gpi_graydecr[(opw>> 8)&255];
- rt=gpi_graydecr[(opw>> 0)&255];
- i0=0;
- opy=gpi_graydeco[(opw>>48)&255];
- switch(opy)
- {
- case 0x00: sn="FADD"; break;
- case 0x01: sn="FSUB"; break;
- case 0x02: sn="FMUL"; break;
- case 0x03: sn="FDIV"; break;
- case 0x04: sn="FMAC"; break;
- case 0x05:
- i0= gpi_gray8dec[(opw>>40)&255];
- i0=(i0<<8) | gpi_gray8dec[(opw>>32)&255];
- i0=(i0<<8) | gpi_gray8dec[(opw>>24)&255];
- sn="FMASC";
- break;
- case 0x06: sn="FMIN"; break;
- case 0x07: sn="FMAX"; break;
- case 0x0D:
- rs=rd;
- case 0x0C:
- switch(rt)
- {
- case 0x00: sn="RCP"; break;
- case 0x01: sn="SQRT"; break;
- case 0x02: sn="ATAN"; break;
- case 0x04: sn="I2F"; break;
- case 0x05: sn="F2I"; break;
- }
- break;
- default:
- break;
- }
- if(sn)
- {
- if(opy>=0x0C)
- printf(" %s R%d, R%d\n", sn, rs, rd);
- else if(i0)
- printf(" %s R%d, R%d, %X, R%d\n", sn, rs, rt, i0, rd);
- else
- printf(" %s R%d, R%d, R%d\n", sn, rs, rt, rd);
- }
- break;
- case 0x04:
- rd=gpi_graydecr[(opw>>16)&255];
- rs=gpi_graydecr[(opw>> 8)&255];
- rt=gpi_graydecr[(opw>> 0)&255];
- opy=gpi_graydeco[(opw>>48)&255];
- switch(opy)
- {
- case 0x00: sn="PADD.F"; break;
- case 0x01: sn="PSUB.F"; break;
- case 0x02: sn="PMUL.F"; break;
- case 0x03: sn="PDIV.F"; break;
- default:
- break;
- }
- if(sn)
- { printf(" %s R%d, R%d, R%d\n", sn, rs, rt, rd); }
- break;
- case 0x05:
- rd=gpi_graydecr[(opw>>16)&255];
- rs=gpi_graydecr[(opw>> 8)&255];
- rt=gpi_graydecr[(opw>> 0)&255];
- opy=gpi_graydeco[(opw>>48)&255];
- switch(opy)
- {
- case 0x00: sn="PADD.H"; break;
- case 0x01: sn="PSUB.H"; break;
- case 0x02: sn="PMUL.H"; break;
- case 0x03: sn="PDIV.H"; break;
- default:
- break;
- }
- if(sn)
- { printf(" %s R%d, R%d, R%d\n", sn, rs, rt, rd); }
- break;
- case 0x0C:
- rd=gpi_graydecr[(opw>>48)&255];
- li= gpi_gray8dec[(opw>>40)&255];
- li=(li<<8) | gpi_gray8dec[(opw>>32)&255];
- li=(li<<8) | gpi_gray8dec[(opw>>24)&255];
- li=(li<<8) | gpi_gray8dec[(opw>>16)&255];
- li=(li<<8) | gpi_gray8dec[(opw>> 8)&255];
- li=(li<<8) | gpi_gray8dec[(opw>> 0)&255];
- li=(li<<16)>>16;
- printf(" MOV %llX, R%d\n", li, rd);
- break;
- case 0x0D:
- rd=gpi_graydecr[(opw>>48)&255];
- li= gpi_gray8dec[(opw>>40)&255];
- li=(li<<8) | gpi_gray8dec[(opw>>32)&255];
- li=(li<<8) | gpi_gray8dec[(opw>>24)&255];
- li=(li<<8) | gpi_gray8dec[(opw>>16)&255];
- li=(li<<8) | gpi_gray8dec[(opw>> 8)&255];
- li=(li<<8) | gpi_gray8dec[(opw>> 0)&255];
- li=(li<<16);
- printf(" MOV %llX, R%d\n", li, rd);
- break;
- case 0x0E:
- rd=gpi_graydecr[(opw>>48)&255];
- li= gpi_gray8dec[(opw>>40)&255];
- li=(li<<8) | gpi_gray8dec[(opw>>32)&255];
- li=(li<<8) | gpi_gray8dec[(opw>>24)&255];
- li=(li<<8);
- li=(li<<8) | gpi_gray8dec[(opw>>16)&255];
- li=(li<<8) | gpi_gray8dec[(opw>> 8)&255];
- li=(li<<8) | gpi_gray8dec[(opw>> 0)&255];
- li=(li<<8);
- printf(" MOV %llX, R%d\n", li, rd);
- break;
- case 0x0F:
- rd=gpi_graydecr[(opw>>48)&255];
- if(!rd)
- {
- ret=1;
- break;
- }
- i0= gpi_gray8dec[(opw>>40)&255];
- i0=(i0<<8) | gpi_gray8dec[(opw>>32)&255];
- i0=(i0<<8) | gpi_gray8dec[(opw>>24)&255];
- i1= gpi_gray8dec[(opw>>16)&255];
- i1=(i1<<8) | gpi_gray8dec[(opw>> 8)&255];
- i1=(i1<<8) | gpi_gray8dec[(opw>> 0)&255];
- li= (((i0>>12)&4095)<<4);
- li=(li<<16) | (((i0>> 0)&4095)<<4);
- li=(li<<16) | (((i1>>12)&4095)<<4);
- li=(li<<16) | (((i1>> 0)&4095)<<4);
- printf(" MOV %llX, R%d\n", li, rd);
- break;
- default:
- /* NOP */
- break;
- }
- return(ret);
- }
- int GPI_ProgDump(GPI_VMProg *prog)
- {
- int i, j, k;
- for(i=0; i<GPI_ROMSZ; i++)
- {
- k=GPI_ProgDumpOp(prog, i);
- if(k>0)
- break;
- }
- return(0);
- }
- u64 gpi_rngseed1;
- u64 gpi_rngseed2;
- u64 gpi_rngseed3;
- u64 gpi_rngseed4;
- int gpi_rand16()
- {
- u64 s1, s2, s3, s4;
- s1=gpi_rngseed1*2147483647ULL*65521ULL;
- s2=gpi_rngseed2*2147483647ULL*65521ULL;
- s3=gpi_rngseed3*2147483647ULL*65521ULL;
- s4=gpi_rngseed4*2147483647ULL*65521ULL;
- gpi_rngseed1=s1+(gpi_rngseed4>>48)+1;
- gpi_rngseed2=s2+(gpi_rngseed1>>48)+1;
- gpi_rngseed3=s3+(gpi_rngseed2>>48)+1;
- gpi_rngseed4=s4+(gpi_rngseed3>>48)+1;
- return((u16)(s1>>48));
- }
- u64 gpi_randbits64()
- {
- u64 li;
- li= gpi_rand16();
- li=(li<<16) | gpi_rand16();
- li=(li<<16) | gpi_rand16();
- li=(li<<16) | gpi_rand16();
- return(li);
- }
- int GPI_PrgBreedPair(GPI_VMProg *prga, GPI_VMProg *prgb, GPI_VMProg *prgc)
- {
- byte ofstab[16]={0, 1, 1, 2, 1, 2, 2, 3, 1, 2, 2, 3, 2, 3, 3, 4};
- u64 m;
- int i, j, k, ofs;
- ofs=0;
- k=gpi_rand16();
- // if((k&0xFF00)==0x0F00)
- if(0)
- {
- // ofs=(k&7);
- ofs=ofstab[k&15];
- // ofs=1;
- if(k&128)
- ofs=-ofs;
- for(i=0; i<GPI_ROMSZ; i++)
- {
- m=gpi_randbits64();
- j=i+ofs;
- if((j<0) || (j>=GPI_ROMSZ))
- {
- prgc->rom[i]=m;
- continue;
- }
- prgc->rom[i]=(prga->rom[j]&m)|(prgb->rom[j]&(~m));
- }
- }else
- {
- for(i=0; i<GPI_ROMSZ; i++)
- {
- m=gpi_randbits64();
- prgc->rom[i]=(prga->rom[i]&m)|(prgb->rom[i]&(~m));
- }
- }
- // for(i=0; i<64; i++)
- for(i=0; i<256; i++)
- // for(i=0; i<1024; i++)
- {
- j=gpi_rand16();
- prgc->rom[(j>>8)&255]^=(1ULL<<(j&63));
- }
- return(0);
- }
- int GPI_PrgBreedInit(GPI_VMProg *prg)
- {
- u64 m;
- int i, j, k, ofs;
- for(i=0; i<GPI_ROMSZ; i++)
- {
- m=gpi_randbits64();
- for(j=0; j<256; j++)
- {
- // k=gpi_gray5decp[(m>>56)&255];
- k=gpi_graydeco[(m>>56)&255];
- // if(k==0xFF)
- if(k==0x00)
- break;
- m^=((u64)gpi_rand16())<<48;
- }
- prg->rom[i]=m;
- }
- return(0);
- }
- int GPI_SetupContextInit(GPI_Context *ctx)
- {
- int i, j, k;
- for(i=0; i<GPI_GENSZ; i++)
- {
- ctx->prog[i]=(ctx->prg_arr)+i;
- GPI_PrgBreedInit(ctx->prog[i]);
- }
- return(0);
- }
- int GPI_StepContext(GPI_Context *ctx)
- {
- GPI_VMState tvm;
- GPI_VMProg *prg;
- GPI_VMState *vm;
- double f;
- int i0, i1;
- int i, j, k;
- vm=&tvm;
- for(i=0; i<GPI_GENSZ; i++)
- {
- vm->prog=ctx->prog[i];
- if(!(vm->prog))
- {
- ctx->prgw[i]=999999999;
- continue;
- }
- for(j=0; j<32; j++)
- {
- // vm->reg[j]=gpi_randbits64()|0x4000400040004000ULL;
- vm->reg[j]=gpi_randbits64()|0x7F0070007F007000ULL;
- }
- if(ctx->SetupState)
- ctx->SetupState(ctx, vm);
- GPI_RunSteps(vm);
- if(ctx->RankState)
- ctx->prgw[i]=ctx->RankState(ctx, vm);
- }
- for(i=0; i<GPI_GENSZ; i++)
- {
- for(j=i+1; j<GPI_GENSZ; j++)
- {
- if(ctx->prgw[j]<ctx->prgw[i])
- {
- f=ctx->prgw[i];
- ctx->prgw[i]=ctx->prgw[j];
- ctx->prgw[j]=f;
- prg=ctx->prog[i];
- ctx->prog[i]=ctx->prog[j];
- ctx->prog[j]=prg;
- }
- }
- }
- for(i=GPI_GENSEL; i<GPI_GENSZ; i++)
- {
- // j=gpi_rand16();
- // i0=(j>>0)&(GPI_GENSEL-1);
- // i1=(j>>8)&(GPI_GENSEL-1);
- for(j=0; j<64; j++)
- {
- i0=gpi_rand16()&4095;
- i1=gpi_rand16()&4095;
- i0=(i0*i0)>>12;
- i1=(i1*i1)>>12;
- i0=i0/(4096/GPI_GENSEL);
- i1=i1/(4096/GPI_GENSEL);
- if(i0!=i1)
- break;
- }
- GPI_PrgBreedPair(
- ctx->prog[i0],
- ctx->prog[i1],
- ctx->prog[i]);
- }
- }
- void atan2_SetupState(GPI_Context *ctx, GPI_VMState *vm)
- {
- double xa[8];
- double x, y, th;
- int i, j, k;
- j=gpi_rand16();
- // x=(((j>>8)&255)-127)*(1.0/32);
- // y=(((j>>0)&255)-127)*(1.0/32);
- y=0;
- for(i=0; i<4; i++)
- {
- x=(gpi_rand16()/16.0)-j;
- xa[i]=x;
- y=y+x;
- }
- // th=y/8;
- th=y;
- // th=atan2(y, x);
- // *(double *)(vm->u_reg+0)=x;
- // *(double *)(vm->u_reg+1)=y;
- *(double *)(vm->u_reg+2)=th;
- // *(double *)(vm->reg+4)=x;
- // *(double *)(vm->reg+5)=y;
- for(i=0; i<8; i++)
- *(double *)(vm->reg+4+i)=xa[i];
- }
- double atan2_RankState(GPI_Context *ctx, GPI_VMState *vm)
- {
- double th0, th1, d;
- int i;
- th0=*(double *)(vm->u_reg+2);
- th1=*(double *)(vm->reg+2);
- d=(th0-th1);
- // d=(d*d)*1000000;
- // d=(d*d)*0.001;
- d=(d*d)*0.01;
- if((d>9999999) || isinf(d) || isnan(d))
- d=9999999;
- d+=0.00001*vm->nnop;
- return(d);
- // i=d;
- // if(i<0)
- // i=99999999;
- // i+=vm->nnop;
- // return(i);
- }
- char *gpi_print_ffixed(char *tb, double val)
- {
- int hi, lo;
- hi=val;
- lo=(val-hi)*10000;
- sprintf(tb, "%6d.%04d", hi, lo);
- return(tb);
- }
- int main()
- {
- char tb1[64];
- char tb2[64];
- GPI_Context *ctx;
- double e, le;
- int i, j, k;
- GPI_InitTables();
- // GPI_DumpTables();
- ctx=malloc(sizeof(GPI_Context));
- memset(ctx, 0, sizeof(GPI_Context));
- GPI_SetupContextInit(ctx);
- ctx->SetupState=atan2_SetupState;
- ctx->RankState=atan2_RankState;
- le=999999999.0;
- // for(i=0; i<4096; i++)
- // for(i=0; i<65536; i++)
- for(i=0; i<262144; i++)
- {
- e=0;
- for(j=0; j<16; j++)
- e+=ctx->prgw[j];
- le=(le*0.999)+(e*0.001);
- if((i>1024) && (le<0.001))
- {
- printf("\n");
- printf("Convergence Detected\n");
- break;
- }
- // printf("Gen %d, best=%d\n", i, ctx->prgw[0]);
- // printf("Gen %d, best=%-05.4f %-06.4f \r", i, ctx->prgw[0], e);
- printf("Gen %d, best=%s %s \r", i,
- gpi_print_ffixed(tb1, ctx->prgw[0]),
- gpi_print_ffixed(tb2, e));
- GPI_StepContext(ctx);
- // printf("Best w=%d\n", ctx->prgw[0]);
- }
- printf("\n");
- GPI_ProgDump(ctx->prog[0]);
- }
Advertisement
Add Comment
Please, Sign In to add comment