Skip to content

Latest commit

 

History

History
73 lines (58 loc) · 3.11 KB

AesStream.md

File metadata and controls

73 lines (58 loc) · 3.11 KB

AES Streams

AES is a 128-bit block cipher. It supports key of lenght 128 bits, 192 bits or 256 bits.
Initialization vector(iv), if present, must be 16 bytes (128 bits) length.

Create output(encrypting) stream

let encryptingStream = AesOutputStream(writingTo: anotherOuputStream,
                                        key: key,
                                        iv: iv)
try encryptingStream.open()
try encryptingStream.write(buffer, length: len)
try encryptingStream.close()

Create input(decrypting) stream

let decryptingStream = AesInputStream(readingFrom: anotherInputStream,
                                        key: key,
                                        iv: iv)
try decryptingStream.open()
        
var decryptedBytes = Array<UInt8>()
while decryptingStream.hasBytesAvailable {
    let tmpBufferLen = 1<<16
    var tmpBuffer = Array<UInt8>(repeating: 0, count: tmpBufferLen)
    let readLen = try decryptingStream.read(&tmpBuffer, maxLength: tmpBufferLen)
    decryptedBytes.append(contentsOf: readBuffer.prefix(readLen))
}

let decryptedData = Data(decryptedBytes)

Constructor accepts additional parameters

let aesOptions = AesOptions.PKCS7Padding // default
// let aesOptions = AesOptions.ECBMode
// let aesOptions = AesOptions.CBCMode

let encryptingStream = AesOutputStream(writingTo: anotherOuputStream,
                                        key: key,
                                        iv: iv,
                                        options: aesOptions,
                                        chunk: AesOutputStream.defaultChunkSize)

let decryptingStream = AesInputStream(readingFrom: anotherInputStream,
                                        key: key,
                                        iv: iv,
                                        options: aesOptions,
                                        chunk: AesInputStream.defaultChunkSize)

where:
AesOptions.ECBMode - doesn't use iv. Due to obvious weaknesses, it is generally not recommended. The source data is divided into blocks as the length of the block of AES, 128. So the ECB mode needs to pad data until it is same as the length of the block. Then every block will be encrypted with the same key and same algorithm. So if we encrypt the same plaintext, we will get the same ciphertext. So there is a high risk in this mode. And the plaintext and ciphertext blocks are a one-to-one correspondence. Because the encryption/ decryption is independent, so we can encrypt/decrypt the data in parallel. And if a block of plaintext or ciphertext is broken, it won’t affect other blocks.
AesOptions.CBCMode - uses iv and it must be the same length as the algorithm's block size. The total number of bytes does have to be aligned to the block size (128 bit), otherwise open() will return alignmentError. If iv is not present, a NULL (all zeroes) iv will be used
AesOptions.PKCS7Padding - the total number of bytes provided by all the calls to this function when encrypting can be arbitrary (i.e., the total number of bytes does not have to be block aligned).