func TestByteMatrix(t *testing.T) { m := SBox a := byte(0x63) // 0b01100011 if m.Mul(Row{byte(number.ByteFieldElem(0x53).Invert())})[0]^a != 0xED { t.Fatalf("Substitution value was wrong! 0x53 -> 0xED") } if m.Mul(Row{byte(number.ByteFieldElem(0x10).Invert())})[0]^a != 0xCA { t.Fatalf("Substitution value was wrong! 0x10 -> 0xCA") } }
func (tyi TyiTable) Get(i byte) (out [4]byte) { // Calculate dot product of i and [0x02 0x01 0x01 0x03] j := number.ByteFieldElem(i) a := byte(number.ByteFieldElem(0x02).Mul(j)) b := byte(number.ByteFieldElem(0x01).Mul(j)) c := byte(number.ByteFieldElem(0x03).Mul(j)) // Merge into one output and rotate according to column. res := [4]byte{a, b, b, c} copy(out[:], append(res[(4-tyi):], res[0:(4-tyi)]...)) return }
// FindPartialEncoding takes an affine encoded F and finds the values that strip its output encoding. It returns the // parameters it finds and the input encoding of f up to a key byte. func FindPartialEncoding(constr *chow.Construction, f table.Byte, L, AtildeInv matrix.Matrix) (number.ByteFieldElem, byte, encoding.ByteAffine) { fInv := table.Invert(f) id := encoding.ByteLinear(matrix.GenerateIdentity(8)) SInv := table.InvertibleTable(chow.InvTBox{saes.Construction{}, 0x00, 0x00}) S := table.Invert(SInv) // Brute force the constant part of the output encoding and the beta in Atilde = A_i <- D(beta) for c := 0; c < 256; c++ { for d := 1; d < 256; d++ { cand := encoding.ComposedBytes{ TableAsEncoding{f, fInv}, encoding.ByteAffine{id, byte(c)}, encoding.ByteLinear(AtildeInv), encoding.ByteMultiplication(byte(d)), // D below TableAsEncoding{SInv, S}, } if isAffine(cand) { a, b := DecomposeAffineEncoding(cand) return number.ByteFieldElem(d), byte(c), encoding.ByteAffine{encoding.ByteLinear(a), byte(b)} } } } panic("Failed to strip output encodings!") }
func UnMixColumns(i, j byte) [4]byte { k, l := number.ByteFieldElem(i), number.ByteFieldElem(j) var a, b, c, d number.ByteFieldElem a = number.ByteFieldElem(0x0e).Mul(k) b = number.ByteFieldElem(0x09).Mul(k) c = number.ByteFieldElem(0x0d).Mul(k) d = number.ByteFieldElem(0x0b).Mul(k) a = number.ByteFieldElem(0x0b).Mul(l).Add(a) b = number.ByteFieldElem(0x0e).Mul(l).Add(b) c = number.ByteFieldElem(0x09).Mul(l).Add(c) d = number.ByteFieldElem(0x0d).Mul(l).Add(d) return [4]byte{byte(a), byte(b), byte(c), byte(d)} }
func (constr *Construction) UnMixColumn(slice []byte) { column := number.ArrayFieldElem{ number.ByteFieldElem(slice[0]), number.ByteFieldElem(slice[1]), number.ByteFieldElem(slice[2]), number.ByteFieldElem(slice[3]), }.Mul(number.ArrayFieldElem{ number.ByteFieldElem(0x0e), number.ByteFieldElem(0x09), number.ByteFieldElem(0x0d), number.ByteFieldElem(0x0b), }) for i := 0; i < 4; i++ { if len(column) > i { slice[i] = byte(column[i]) } else { slice[i] = 0x00 } } }
func MixColumns(i, j byte) [4]byte { k, l := number.ByteFieldElem(i), number.ByteFieldElem(j) var a, b, c, d number.ByteFieldElem a = number.ByteFieldElem(0x02).Mul(k) b = number.ByteFieldElem(0x01).Mul(k) d = number.ByteFieldElem(0x03).Mul(k) a = number.ByteFieldElem(0x03).Mul(l).Add(a) c = number.ByteFieldElem(0x01).Mul(l) d = c.Add(d) c = c.Add(b) b = number.ByteFieldElem(0x02).Mul(l).Add(b) return [4]byte{byte(a), byte(b), byte(c), byte(d)} }
func (constr *Construction) SubByte(e byte) byte { // AES S-Box m := matrix.Matrix{ // Linear component. matrix.Row{0xF1}, // 0b11110001 matrix.Row{0xE3}, // 0b11100011 matrix.Row{0xC7}, // 0b11000111 matrix.Row{0x8F}, // 0b10001111 matrix.Row{0x1F}, // 0b00011111 matrix.Row{0x3E}, // 0b00111110 matrix.Row{0x7C}, // 0b01111100 matrix.Row{0xF8}, // 0b11111000 } a := byte(0x63) // 0b01100011 - Affine component. return m.Mul(matrix.Row{byte(number.ByteFieldElem(e).Invert())})[0] ^ a }
func (constr *Construction) UnSubByte(e byte) byte { // AES Inverse S-Box m := matrix.Matrix{ matrix.Row{0xA4}, matrix.Row{0x49}, matrix.Row{0x92}, matrix.Row{0x25}, matrix.Row{0x4a}, matrix.Row{0x94}, matrix.Row{0x29}, matrix.Row{0x52}, } a := byte(0x63) invVal := m.Mul(matrix.Row{e ^ a})[0] return byte(number.ByteFieldElem(invVal).Invert()) }
func (bm ByteMultiplication) Encode(i byte) byte { x, j := number.ByteFieldElem(bm), number.ByteFieldElem(i) return byte(x.Mul(j)) }