diff --git a/NetBSD/9.0/usr/src/sys/dev/sbus/sbusfpga_curve25519engine.c b/NetBSD/9.0/usr/src/sys/dev/sbus/sbusfpga_curve25519engine.c index ebdd54b..4c647ba 100644 --- a/NetBSD/9.0/usr/src/sys/dev/sbus/sbusfpga_curve25519engine.c +++ b/NetBSD/9.0/usr/src/sys/dev/sbus/sbusfpga_curve25519engine.c @@ -118,7 +118,9 @@ int sbusfpga_curve25519engine_close(dev_t dev, int flags, int mode, struct lwp *l) { struct sbusfpga_curve25519engine_softc *sc = device_lookup_private(&sbusfpga_c29e_cd, minor(dev)); - power_off(sc); + + if (sc->active_sessions == 0) + power_off(sc); return (0); } @@ -145,8 +147,10 @@ static const uint32_t program_gcm[20] = {0x0010100d, 0x0094100d, 0x0118100d, 0x0 static const uint32_t program_aes[58] = {0x0001f003, 0x0005e012, 0x00841012, 0x01041012, 0x01841012, 0x0001d052, 0x00800052, 0x01000052, 0x01800052, 0x0005c012, 0x00841012, 0x01041012, 0x01841012, 0x0001b052, 0x00800052, 0x01000052, 0x01800052, 0x0005a012, 0x00841012, 0x01041012, 0x01841012, 0x00019052, 0x00800052, 0x01000052, 0x01800052, 0x00058012, 0x00841012, 0x01041012, 0x01841012, 0x00017052, 0x00800052, 0x01000052, 0x01800052, 0x00056012, 0x00841012, 0x01041012, 0x01841012, 0x00015052, 0x00800052, 0x01000052, 0x01800052, 0x00054012, 0x00841012, 0x01041012, 0x01841012, 0x00013052, 0x00800052, 0x01000052, 0x01800052, 0x00052012, 0x00841012, 0x01041012, 0x01841012, 0x02011052, 0x02800052, 0x03000052, 0x03800052, 0x0000000a }; -static const uint32_t* programs[4] = { program_ec25519, program_gcm, program_aes, NULL }; -static const uint32_t program_len[4] = { 134, 20, 58, 0 }; +static const uint32_t program_gcm_ad[70] = {0x00400800, 0x00080840, 0x0001f403, 0x0005e012, 0x00841012, 0x01041012, 0x01841012, 0x0001d052, 0x00800052, 0x01000052, 0x01800052, 0x0005c012, 0x00841012, 0x01041012, 0x01841012, 0x0001b052, 0x00800052, 0x01000052, 0x01800052, 0x0005a012, 0x00841012, 0x01041012, 0x01841012, 0x00019052, 0x00800052, 0x01000052, 0x01800052, 0x00058012, 0x00841012, 0x01041012, 0x01841012, 0x00017052, 0x00800052, 0x01000052, 0x01800052, 0x00056012, 0x00841012, 0x01041012, 0x01841012, 0x00015052, 0x00800052, 0x01000052, 0x01800052, 0x00054012, 0x00841012, 0x01041012, 0x01841012, 0x00013052, 0x00800052, 0x01000052, 0x01800052, 0x00052012, 0x00841012, 0x01041012, 0x01841012, 0x02011052, 0x02800052, 0x03000052, 0x03800052, 0x03000089, 0x003c0000, 0x01400411, 0x0042b405, 0x01400411, 0x00080800, 0xe0000809, 0x00380000, 0x01bc03d1, 0x003cf3d1, 0x0000000a }; + +static const uint32_t* programs[5] = { program_ec25519, program_gcm, program_aes, program_gcm_ad, NULL }; +static const uint32_t program_len[5] = { 134, 20, 58, 70, 0 }; static uint32_t program_offset[4]; /* @@ -303,6 +307,7 @@ struct sbusfpga_curve25519engine_session { #define SBUSFPGA_DO_MONTGOMERYJOB _IOWR(0, 0, struct sbusfpga_curve25519engine_montgomeryjob) #define SBUSFPGA_EC25519_CHECKGCM _IOW(0, 1, struct sbusfpga_curve25519engine_montgomeryjob) #define SBUSFPGA_EC25519_CHECKAES _IOW(0, 2, struct sbusfpga_curve25519engine_aesjob) +#define SBUSFPGA_EC25519_GCMAD _IOW(0, 3, struct sbusfpga_curve25519engine_aesjob) #define SBUSFPGA_EC25519_OPENSESSION _IOR(1, 0, struct sbusfpga_curve25519engine_session) #define SBUSFPGA_EC25519_CLOSESESSION _IOR(1, 1, struct sbusfpga_curve25519engine_session) @@ -397,7 +402,7 @@ sbusfpga_curve25519engine_ioctl (dev_t dev, u_long cmd, void *data, int flag, st } for (reg = 31 ; reg > 16 ; reg--) { for (i = 0 ; i < 8 ; i ++) { - bus_space_write_4(sc->sc_bustag, sc->sc_bhregs_regfile,SUBREG_ADDR(reg,i), job->keys[i]); + bus_space_write_4(sc->sc_bustag, sc->sc_bhregs_regfile,SUBREG_ADDR(reg,i), job->keys[i+8*(31-reg)]); } } @@ -419,6 +424,40 @@ sbusfpga_curve25519engine_ioctl (dev_t dev, u_long cmd, void *data, int flag, st } } break; + case SBUSFPGA_EC25519_GCMAD: { + const uint32_t base = 0; + struct sbusfpga_curve25519engine_aesjob* job = (struct sbusfpga_curve25519engine_aesjob*)data; + int reg, i; + + curve25519engine_mpstart_write(sc, program_offset[3]); /* GCM_AD */ + curve25519engine_mplen_write(sc, program_len[3]); /* GCM_AD */ + for (i = 0 ; i < 8 ; i ++) { + bus_space_write_4(sc->sc_bustag, sc->sc_bhregs_regfile,SUBREG_ADDR(0,i), job->data[i]); + } + for (reg = 31 ; reg > 16 ; reg--) { + for (i = 0 ; i < 8 ; i ++) { + bus_space_write_4(sc->sc_bustag, sc->sc_bhregs_regfile,SUBREG_ADDR(reg,i), job->keys[i+8*(31-reg)]); + } + } + + err = start_job(sc); + if (err) + return err; + delay(1); + err = wait_job(sc); + /* if (err) */ + /* return err; */ + + for (reg = 0 ; reg < 32 ; reg++) { + uint32_t buf[8]; + for (i = 0 ; i < 8 ; i ++) { + buf[i] = bus_space_read_4(sc->sc_bustag, sc->sc_bhregs_regfile,SUBREG_ADDR(reg,i)); + } + device_printf(sc->sc_dev, "GCM_AD %d: 0x%08x 0x%08x 0x%08x 0x%08x 0x%08x 0x%08x 0x%08x 0x%08x \n", reg, + buf[0], buf[1], buf[2], buf[3], buf[4], buf[5], buf[6], buf[7]); + } + } + break; case SBUSFPGA_EC25519_OPENSESSION:{ struct sbusfpga_curve25519engine_session* ses = (struct sbusfpga_curve25519engine_session*)data; int s = get_session(sc); diff --git a/sbus-to-ztex-gateware-migen/engine.py b/sbus-to-ztex-gateware-migen/engine.py index 212aa0a..891fee6 100644 --- a/sbus-to-ztex-gateware-migen/engine.py +++ b/sbus-to-ztex-gateware-migen/engine.py @@ -13,7 +13,7 @@ opcode_bits = 6 # number of bits used to encode the opcode field opcodes = { # mnemonic : [bit coding, docstring] "UDF" : [-1, "Placeholder for undefined opcodes"], "PSA" : [0, "Wd $\gets$ Ra // pass A"], - "PSB" : [1, "Wd $\gets$ Rb // pass B"], + "PSB" : [1, "Wd $\gets$ Rb // pass B"], # Is that needed ??? "MSK" : [2, "Wd $\gets$ Replicate(Ra[0], 256) & Rb // for doing cswap()"], "XOR" : [3, "Wd $\gets$ Ra ^ Rb // bitwise XOR"], "NOT" : [4, "Wd $\gets$ ~Ra // binary invert"], @@ -29,7 +29,7 @@ opcodes = { # mnemonic : [bit coding, docstring] "GCM_SHLMI": [14, "Shift A left by imm, insert B MSB as dest LSB; reg-reg or reg-imm; per 128-bits block"], # make SHL redundant: SHL %rd, %ra == GCM_SHLMI %rd, %ra, #0, #1 "GCM_SHRMI": [15, "Shift A right by imm, insert B LSB as dest MSB; reg-reg or reg-imm; per 128-bits block"], # "GCM_CMPD": [16, "Compute D:X0 from X1:X0; reg ; per 128-bits block"], # specific - "GCM_SWAP64": [17, "Swap doubleword (64 bits) ; reg-reg or imm-reg or reg-imm; per 128-bits block"], # + "GCM_SWAP64": [17, "Swap doubleword (64 bits) ; reg-reg or imm-reg or reg-imm; per 128-bits block ; imm != 0 -> BYTEREV*"], # "AESESMI" : [18, "AES ; reg-reg ; per 128-bits block; imm[0:2] indicates sub-round (as in rv32's aes32esmi) ; imm[2] is 1 for aesesi (shared opcode)" ], "MAX" : [19, "Maximum opcode number (for bounds checking)"], } @@ -235,6 +235,7 @@ class Curve25519Const(Module, AutoDoc): 8: [50, "fifty", "The number 50 (for pow22501)"], 9: [100, "one hundred", "The number 100 (for pow22501)"], 10: [254, "two hundred fifty four", "The number 254 (iteration count)"], + 11: [0x00000001_00000000_00000000_00000000_00000001_00000000_00000000_00000000, "increment for GCM counter (LE)", "increment for GCM counter (LE)"], } self.adr = Signal(5) self.const = Signal(256) @@ -1524,7 +1525,13 @@ class ExecGCMShifts(ExecUnit, AutoDoc): 0x7: self.q.eq(Cat(self.b[121:128], self.a[0:121], self.b[249:256], self.a[128:249])), }) ).Elif(self.instruction.opcode == opcodes["GCM_SWAP64"][0], - self.q.eq(Cat(self.b[64:128], self.a[0:64], self.b[192:256], self.a[128:192])) + # also gcm_brev* + Case(self.instruction.immediate[0:2], { + 0: self.q.eq(Cat(self.b[64:128], self.a[0:64], self.b[192:256], self.a[128:192])), + 1: self.q.eq(Cat(self.a[8:16], self.a[0:8], self.a[24:32], self.a[16:24], self.a[40:48], self.a[32:40], self.a[56:64], self.a[48:56], self.a[72:80], self.a[64:72], self.a[88:96], self.a[80:88], self.a[104:112], self.a[96:104], self.a[120:128], self.a[112:120], self.a[136:144], self.a[128:136], self.a[152:160], self.a[144:152], self.a[168:176], self.a[160:168], self.a[184:192], self.a[176:184], self.a[200:208], self.a[192:200], self.a[216:224], self.a[208:216], self.a[232:240], self.a[224:232], self.a[248:256], self.a[240:248])), + 2: self.q.eq(Cat(self.a[24:32], self.a[16:24], self.a[8:16], self.a[0:8], self.a[56:64], self.a[48:56], self.a[40:48], self.a[32:40], self.a[88:96], self.a[80:88], self.a[72:80], self.a[64:72], self.a[120:128], self.a[112:120], self.a[104:112], self.a[96:104], self.a[152:160], self.a[144:152], self.a[136:144], self.a[128:136], self.a[184:192], self.a[176:184], self.a[168:176], self.a[160:168], self.a[216:224], self.a[208:216], self.a[200:208], self.a[192:200], self.a[248:256], self.a[240:248], self.a[232:240], self.a[224:232])), + 3: self.q.eq(Cat(self.a[56:64], self.a[48:56], self.a[40:48], self.a[32:40], self.a[24:32], self.a[16:24], self.a[8:16], self.a[0:8], self.a[120:128], self.a[112:120], self.a[104:112], self.a[96:104], self.a[88:96], self.a[80:88], self.a[72:80], self.a[64:72], self.a[184:192], self.a[176:184], self.a[168:176], self.a[160:168], self.a[152:160], self.a[144:152], self.a[136:144], self.a[128:136], self.a[248:256], self.a[240:248], self.a[232:240], self.a[224:232], self.a[216:224], self.a[208:216], self.a[200:208], self.a[192:200])), + }) ) ] diff --git a/sbus-to-ztex-gateware-migen/engine_code/engine_code.rs b/sbus-to-ztex-gateware-migen/engine_code/engine_code.rs index 813a0d1..b563143 100644 --- a/sbus-to-ztex-gateware-migen/engine_code/engine_code.rs +++ b/sbus-to-ztex-gateware-migen/engine_code/engine_code.rs @@ -613,7 +613,8 @@ fn main() -> std::io::Result<()> { xor %0, %2, %1 // output in %0 fin - );let gcmcode = assemble_engine25519!( + ); + let aescode = assemble_engine25519!( start: // X in %0 // KEY in %31-%17 (backward) @@ -692,11 +693,118 @@ fn main() -> std::io::Result<()> { fin ); + let gcm_ad_code = assemble_engine25519!( + start: + // Input: rkeys in %31-%17 (backward) + // Transient: + // %0, %1, %2 are tmp + // init counter in %16 + // H will go in %15 + // T will go in %14 + psa %16, #0 + // use %2 as a flag + psa %2, #1 + genht: + xor %0, %16, %31 + + aesesmi %1, %0, %30, #0 + aesesmi %1, %0, %1, #1 + aesesmi %1, %0, %1, #2 + aesesmi %1, %0, %1, #3 + + aesesmi %0, %1, %29, #0 + aesesmi %0, %1, %0, #1 + aesesmi %0, %1, %0, #2 + aesesmi %0, %1, %0, #3 + + aesesmi %1, %0, %28, #0 + aesesmi %1, %0, %1, #1 + aesesmi %1, %0, %1, #2 + aesesmi %1, %0, %1, #3 + + aesesmi %0, %1, %27, #0 + aesesmi %0, %1, %0, #1 + aesesmi %0, %1, %0, #2 + aesesmi %0, %1, %0, #3 + + aesesmi %1, %0, %26, #0 + aesesmi %1, %0, %1, #1 + aesesmi %1, %0, %1, #2 + aesesmi %1, %0, %1, #3 + + aesesmi %0, %1, %25, #0 + aesesmi %0, %1, %0, #1 + aesesmi %0, %1, %0, #2 + aesesmi %0, %1, %0, #3 + + aesesmi %1, %0, %24, #0 + aesesmi %1, %0, %1, #1 + aesesmi %1, %0, %1, #2 + aesesmi %1, %0, %1, #3 + + aesesmi %0, %1, %23, #0 + aesesmi %0, %1, %0, #1 + aesesmi %0, %1, %0, #2 + aesesmi %0, %1, %0, #3 + + aesesmi %1, %0, %22, #0 + aesesmi %1, %0, %1, #1 + aesesmi %1, %0, %1, #2 + aesesmi %1, %0, %1, #3 + + aesesmi %0, %1, %21, #0 + aesesmi %0, %1, %0, #1 + aesesmi %0, %1, %0, #2 + aesesmi %0, %1, %0, #3 + + aesesmi %1, %0, %20, #0 + aesesmi %1, %0, %1, #1 + aesesmi %1, %0, %1, #2 + aesesmi %1, %0, %1, #3 + + aesesmi %0, %1, %19, #0 + aesesmi %0, %1, %0, #1 + aesesmi %0, %1, %0, #2 + aesesmi %0, %1, %0, #3 + + aesesmi %1, %0, %18, #0 + aesesmi %1, %0, %1, #1 + aesesmi %1, %0, %1, #2 + aesesmi %1, %0, %1, #3 + + aesesi %0, %1, %17, #0 + aesesi %0, %1, %0, #1 + aesesi %0, %1, %0, #2 + aesesi %0, %1, %0, #3 + + // if the %2 flag is cleared, we've just computed T + brz afterht, %2 + // store H in %15 + psa %15, %0 + // increment counter; should we have a gcm_inc_be ? + // for now byterev + special constant + gcm_brev32 %16, %16 + add %16, %16, #11 + gcm_brev32 %16, %16 + // clear flag & go encrypt t + psa %2, #0 + brz genht, #0 + + afterht: + // store T in %14 + psa %14, %0 + + // fully byte-revert H (first byte-in-dword, then dword-in-128bit) + gcm_brev64 %15, %15 + gcm_swap64 %15, %15, %15 + + fin + ); let mut pos = 0; - while pos < gcmcode.len() { - println!("0x{:08x},", gcmcode[pos]); + while pos < gcm_ad_code.len() { + println!("0x{:08x},", gcm_ad_code[pos]); pos = pos + 1; } Ok(())