/* * create a challenge for a fid space */ void mkchallenge(Chan *cp) { int i; if(!didread && readnvram(&nvr, 0) >= 0) didread = 1; srand(truerand()); for(i = 0; i < CHALLEN; i++) cp->chal[i] = nrand(256); cp->idoffset = 0; cp->idvec = 0; }
char* getnvramkey(int flag, char **secstorepw) { char *s; Nvrsafe safe; char spw[CONFIGLEN+1]; int i; memset(&safe, 0, sizeof safe); /* * readnvram can return -1 meaning nvram wasn't written, * but safe still holds good data. */ if(readnvram(&safe, flag)<0 && safe.authid[0]==0) return nil; /* * we're using the config area to hold the secstore * password. if there's anything there, return it. */ memmove(spw, safe.config, CONFIGLEN); spw[CONFIGLEN] = 0; if(spw[0] != 0) *secstorepw = estrdup(spw); /* * only use nvram key if it is non-zero */ for(i = 0; i < DESKEYLEN; i++) if(safe.machkey[i] != 0) break; if(i == DESKEYLEN) return nil; s = emalloc(512); sprint(s, "key proto=p9sk1 user=%q dom=%q !hex=%.*H !password=______", safe.authid, safe.authdom, DESKEYLEN, safe.machkey); writehostowner(safe.authid); return s; }
int nvrcheck(void) { uchar csum; if (readnvram(&nvr, NVread) < 0) { fprint(2, "nvrcheck: can't read nvram\n"); return 1; } else gotnvr = 1; if(chatty) print("nvr read\n"); csum = nvcsum(nvr.machkey, sizeof nvr.machkey); if(csum != nvr.machsum) { fprint(2, "\n\n ** NVR key checksum is incorrect **\n"); fprint(2, " ** set password to allow attaches **\n\n"); memset(nvr.machkey, 0, sizeof nvr.machkey); return 1; } return 0; }
uint8_t RTC_DS1307::readnvram(uint8_t address) { uint8_t data; readnvram(&data, 1, address); return data; }
int main(int argc, char **argv) { int encrypt = 0; /* 0=decrypt, 1=encrypt */ int n, nkey, pass_stdin = 0, pass_nvram = 0; char *pass; unsigned char key[AESmaxkey], key2[SHA1dlen]; unsigned char buf[BUF+SHA1dlen]; /* assumption: CHK <= SHA1dlen */ AESstate aes; DigestState *dstate; Nvrsafe nvr; ARGBEGIN{ case 'e': encrypt = 1; break; case 'i': pass_stdin = 1; break; case 'n': pass_nvram = 1; break; }ARGEND; if(argc!=0){ fprint(2,"usage: %s -d < cipher.aes > clear.txt\n", argv0); fprint(2," or: %s -e < clear.txt > cipher.aes\n", argv0); exits("usage"); } Binit(&bin, 0, OREAD); Binit(&bout, 1, OWRITE); if(pass_stdin){ n = readn(3, buf, (sizeof buf)-1); if(n < 1) exits("usage: echo password |[3=1] auth/aescbc -i ..."); buf[n] = 0; while(buf[n-1] == '\n') buf[--n] = 0; }else if(pass_nvram){ if(readnvram(&nvr, 0) < 0) exits("readnvram: %r"); strecpy((char*)buf, (char*)buf+sizeof buf, (char*)nvr.config); n = strlen((char*)buf); }else{ pass = getpassm("aescbc key:"); n = strlen(pass); if(n >= BUF) exits("key too long"); strcpy((char*)buf, pass); memset(pass, 0, n); free(pass); } if(n <= 0) sysfatal("no key"); dstate = sha1((unsigned char*)"aescbc file", 11, nil, nil); sha1(buf, n, key2, dstate); memcpy(key, key2, 16); nkey = 16; md5(key, nkey, key2, 0); /* so even if HMAC_SHA1 is broken, encryption key is protected */ if(encrypt){ safewrite(v2hdr, AESbsize); genrandom(buf,2*AESbsize); /* CBC is semantically secure if IV is unpredictable. */ setupAESstate(&aes, key, nkey, buf); /* use first AESbsize bytes as IV */ aesCBCencrypt(buf+AESbsize, AESbsize, &aes); /* use second AESbsize bytes as initial plaintext */ safewrite(buf, 2*AESbsize); dstate = hmac_sha1(buf+AESbsize, AESbsize, key2, MD5dlen, 0, 0); for(;;){ n = Bread(&bin, buf, BUF); if(n < 0) sysfatal("read error"); aesCBCencrypt(buf, n, &aes); safewrite(buf, n); dstate = hmac_sha1(buf, n, key2, MD5dlen, 0, dstate); if(n < BUF) break; /* EOF */ } hmac_sha1(0, 0, key2, MD5dlen, buf, dstate); safewrite(buf, SHA1dlen); }else{ /* decrypt */ saferead(buf, AESbsize); if(memcmp(buf, v2hdr, AESbsize) == 0){ saferead(buf, 2*AESbsize); /* read IV and random initial plaintext */ setupAESstate(&aes, key, nkey, buf); dstate = hmac_sha1(buf+AESbsize, AESbsize, key2, MD5dlen, 0, 0); aesCBCdecrypt(buf+AESbsize, AESbsize, &aes); saferead(buf, SHA1dlen); while((n = Bread(&bin, buf+SHA1dlen, BUF)) > 0){ dstate = hmac_sha1(buf, n, key2, MD5dlen, 0, dstate); aesCBCdecrypt(buf, n, &aes); safewrite(buf, n); memmove(buf, buf+n, SHA1dlen); /* these bytes are not yet decrypted */ } hmac_sha1(0, 0, key2, MD5dlen, buf+SHA1dlen, dstate); if(memcmp(buf, buf+SHA1dlen, SHA1dlen) != 0) sysfatal("decrypted file failed to authenticate"); }else{ /* compatibility with past mistake */ // if file was encrypted with bad aescbc use this: // memset(key, 0, AESmaxkey); // else assume we're decrypting secstore files setupAESstate(&aes, key, AESbsize, buf); saferead(buf, CHK); aesCBCdecrypt(buf, CHK, &aes); while((n = Bread(&bin, buf+CHK, BUF)) > 0){ aesCBCdecrypt(buf+CHK, n, &aes); safewrite(buf, n); memmove(buf, buf+n, CHK); } if(memcmp(buf, "XXXXXXXXXXXXXXXX", CHK) != 0) sysfatal("decrypted file failed to authenticate"); } } exits(""); return 1; /* keep other compilers happy */ }