208 lines
6.4 KiB
Markdown
208 lines
6.4 KiB
Markdown
# Encipher, Decipher and Renew nKode
|
|
|
|
## Tenant Policy
|
|
- max nkode length: 10
|
|
- number of keys: 6
|
|
- properties per key: 9
|
|
- total number of properties: 54
|
|
|
|
---
|
|
|
|
## Deterministic CSPRNG
|
|
- AES-CTR DRBG
|
|
- ChaCha20
|
|
|
|
## User Cipher Keys
|
|
Derive keys in memory from PRNG above:
|
|
- property key: [ 6890 54130 42240 40467 46502 31074 10598 63689 27697 54461 21116 31999
|
|
10698 14870 50779 48637 29314 33075 52993 42014 2837 1935 34274 63380
|
|
36021 26329 20788 39848 7335 2619 61516 61122 39878 32506 19151 6611
|
|
2803 10730 53682 39987 11998 42378 6081 8624 34336 15222 35632 33233
|
|
4072 53750 54671 63845 2770 43728]
|
|
- passcode key: [10632 49355 48031 9925 15082 24190 5137 14304 24524 16141]
|
|
- user position key: [45632 9012 27470 28203 15901 7554 16974 54240 53827]
|
|
- mask key: [ 8177 54825 26281 51895 8940 16695 19756 63041 7376 54396]
|
|
|
|
---
|
|
|
|
## User Keypad
|
|
- keypad example:<br/>
|
|
- user passcode indices: [48 12 7 36]
|
|
|
|
---
|
|
|
|
## nKode Cipher
|
|
|
|
### Passcode Hash
|
|
```mermaid
|
|
block-beta
|
|
columns 2
|
|
prop["user_property_key\n[ 6890 54130 42240 40467 46502 31074 10598 63689 27697 54461 21116 31999
|
|
10698 14870 50779 48637 29314 33075 52993 42014 2837 1935 34274 63380
|
|
36021 26329 20788 39848 7335 2619 61516 61122 39878 32506 19151 6611
|
|
2803 10730 53682 39987 11998 42378 6081 8624 34336 15222 35632 33233
|
|
4072 53750 54671 63845 2770 43728]"]
|
|
pass["user_passcode_indices\n[48 12 7 36]"]
|
|
space:2
|
|
sel(("select\nproperties")):2
|
|
pass --> sel
|
|
prop --> sel
|
|
space:2
|
|
passcode["user passcode properties:\n[ 4072 10698 63689 2803]"]:2
|
|
sel --> passcode
|
|
space:2
|
|
pad["zero pad to\nmax nkode length: 10"]:2
|
|
passcode -->pad
|
|
space:2
|
|
paddedpasscode["padded passcode:\n[ 4072 10698 63689 2803 0 0 0 0 0 0]"]
|
|
pad --> paddedpasscode
|
|
passkey["passcode key:\n[10632 49355 48031 9925 15082 24190 5137 14304 24524 16141]"]
|
|
space:2
|
|
xor2(("XOR")):2
|
|
passkey --> xor2
|
|
paddedpasscode --> xor2
|
|
space:2
|
|
cipheredpass["ciphered passcode:\n[ 9824 59649 17238 11318 15082 24190 5137 14304 24524 16141]"]:2
|
|
xor2 --> cipheredpass
|
|
space:2
|
|
hash(("hash")):2
|
|
cipheredpass --> hash
|
|
space:2
|
|
cipheredhashed["hashed ciphered passcode:\n$2b$12$XcXlcNKMyXQziv.kQWKngO88KUcm.xrn4YRZOOhGgIyMmpMw7NPJa"]:2
|
|
hash --> cipheredhashed
|
|
```
|
|
|
|
### Mask Encipher
|
|
```mermaid
|
|
block-beta
|
|
columns 2
|
|
passcode_idx["passcode indices:\n[48 12 7 36]"]
|
|
|
|
space:3
|
|
propidx(["Get Position Idx:\nmap each to element mod props_per_key"])
|
|
passcode_idx-->propidx
|
|
space:3
|
|
passcode_position_idx["passcode poition indices:\n[3, 3, 7, 0]"]
|
|
propidx --> passcode_position_idx
|
|
|
|
space:3
|
|
pad1(("Pad with\nrandom indices"))
|
|
passcode_position_idx --> pad1
|
|
|
|
space:3
|
|
posidx["Padded Passcode Position Indices:\n[3, 3, 7, 0, 0, 0, 5, 8, 8, 8]"]
|
|
pad1 --> posidx
|
|
user_pos["user position key:\n[45632 9012 27470 28203 15901 7554 16974 54240 53827]"]
|
|
|
|
space:2
|
|
sel(("select positions"))
|
|
user_pos --> sel
|
|
posidx --> sel
|
|
space:3
|
|
passcode_pos["ordered user passcode positions:\n[28203 28203 54240 45632 45632 45632 7554 53827 53827 53827]"]
|
|
sel --> passcode_pos
|
|
mask_key["mask key\n[ 8177 54825 26281 51895 8940 16695 19756 63041 7376 54396]"]
|
|
space:2
|
|
xor2(("XOR"))
|
|
mask_key --> xor2
|
|
passcode_pos --> xor2
|
|
space:3
|
|
mask["enciphered mask:\n cdq4ArVJePcB2PN3D2LrwyLN6mE="]
|
|
xor2 --> mask
|
|
```
|
|
|
|
### Validate nKode
|
|
|
|
```mermaid
|
|
block-beta
|
|
columns 3
|
|
selected_keys["keys selected by user during login:\n[1, 3, 1, 4]"]
|
|
login_keypad["login keypad:\nKey 0: [ 9 28 2 39 49 32 42 34 44]
|
|
Key 1: [ 0 1 20 48 40 50 51 7 35]
|
|
Key 2: [18 19 47 21 13 14 24 25 8]
|
|
Key 3: [27 10 11 12 4 5 6 16 17]
|
|
Key 4: [36 37 38 3 22 23 33 43 53]
|
|
Key 5: [45 46 29 30 31 41 15 52 26]
|
|
"]
|
|
space:4
|
|
|
|
selectkeys(("filter keys"))
|
|
mask["enciphered mask:\n cdq4ArVJePcB2PN3D2LrwyLN6mE="]
|
|
mask_key["mask key:\n[ 8177 54825 26281 51895 8940 16695 19756 63041 7376 54396]"]
|
|
space:2
|
|
|
|
xor1(("XOR"))
|
|
mask --> xor1
|
|
mask_key --> xor1
|
|
selected_keys --> selectkeys
|
|
login_keypad --> selectkeys
|
|
space:3
|
|
|
|
ordered_keys["ordered keys:\n[[ 0 1 20 48 40 50 51 7 35]
|
|
[27 10 11 12 4 5 6 16 17]
|
|
[ 0 1 20 48 40 50 51 7 35]
|
|
[36 37 38 3 22 23 33 43 53]]"]
|
|
user_position_key["user position key:\n[45632 9012 27470 28203 15901 7554 16974 54240 53827]"]
|
|
passcode_pos["ordered user passcode positions:\n[28203 28203 54240 45632 45632 45632 7554 53827 53827 53827]"]
|
|
selectkeys --> ordered_keys
|
|
xor1 --> passcode_pos
|
|
space:8
|
|
|
|
get_passcode_idxs(("recover passcode\nposition indices"))
|
|
user_position_key --> get_passcode_idxs
|
|
passcode_pos --> get_passcode_idxs
|
|
space:8
|
|
|
|
passcode_pos_idxs["padded passcode position indices:\n[3, 3, 7, 0, 0, 0, 5, 8, 8, 8]"]
|
|
get_passcode_idxs --> passcode_pos_idxs
|
|
space:3
|
|
|
|
get_presumed_idxs(("recover passcode\nproperty indices"))
|
|
ordered_keys --> get_presumed_idxs
|
|
passcode_pos_idxs --> get_presumed_idxs
|
|
space:5
|
|
|
|
passcode_prop_idxs["presumed passcode property indices:\n[48 12 7 36]"]
|
|
prop["user_property_key\n[ 6890 54130 42240 40467 46502 31074 10598 63689 27697 54461 21116 31999
|
|
10698 14870 50779 48637 29314 33075 52993 42014 2837 1935 34274 63380
|
|
36021 26329 20788 39848 7335 2619 61516 61122 39878 32506 19151 6611
|
|
2803 10730 53682 39987 11998 42378 6081 8624 34336 15222 35632 33233
|
|
4072 53750 54671 63845 2770 43728]"]
|
|
cipheredhashed["hashed ciphered passcode:\n$2b$12$XcXlcNKMyXQziv.kQWKngO88KUcm.xrn4YRZOOhGgIyMmpMw7NPJa"]
|
|
get_presumed_idxs --> passcode_prop_idxs
|
|
space:3
|
|
|
|
sel(("select\nproperties"))
|
|
passcode_prop_idxs --> sel
|
|
prop --> sel
|
|
space:5
|
|
|
|
passcode_prop["presumed passcode properties:\n[ 4072 10698 63689 2803]"]
|
|
sel --> passcode_prop
|
|
space:5
|
|
|
|
cipher(("encipher"))
|
|
passcode_prop --> cipher
|
|
space:5
|
|
|
|
cipheredpass["ciphered passcode:\n[ 9824 59649 17238 11318 15082 24190 5137 14304 24524 16141]"]
|
|
cipher --> cipheredpass
|
|
space:7
|
|
|
|
|
|
comp{"compare"}
|
|
cipheredpass --> comp
|
|
cipheredhashed --> comp
|
|
space:5
|
|
|
|
suc(("success"))
|
|
comp --"Equal"--> suc
|
|
```
|
|
|
|
## Renew
|
|
A renewal happens every login
|
|
### Nonce Renew
|
|
With ChaCha20, we can renew the keys and hash every login with a new nonce
|
|
### Secret Renew
|
|
The secret is renewed less frequently. It's stored securely using a service like AWS Secrets Manager.
|