Considering an AES OFB encryption algorithm, suppose that I'm sending a message over HTTP (not HTTPS) and my message body contains the cyphertext. I'd like to know if transmitting a random initialization vector as a custom HTTP header is considered a bad practice, having into account that it's conventionally appended to the beginning of the cyphertext.


2 Answers 2


From a cryptographic standpoint, it doesn't matter how you transmit the IV. You can send it as a header, in the message body, as the path in the request method, or even the URG pointers in a few TCP packets. From the perspective of the encryption process itself, it doesn't care how it got the IV, no matter how silly the transmission method used, as long as it got it in the end.

From a web development standpoint, it's bad practice to include data that is applicable to the payload in the headers. Sending an IV in a custom HTTP header slightly increases overhead when compared to simply prepending it to the ciphertext and sending it all. You don't even need an elaborate serialization format. Just prepend the fixed-size IV and call it a day. This has the additional benefit of not breaking the HEAD method, which requests the HTTP headers but not body. I can't think of any reason why you could possibly want the IV sans ciphertext.

  • 2
    $\begingroup$ +1 for added complexity of splitting it up; the IV belongs with the ciphertext, so put it with the ciphertext. $\endgroup$ Sep 1, 2018 at 2:54
  • $\begingroup$ 7z puts the IV in the file along with the Salt - github.com/kornelski/7z/blob/master/CPP/7zip/Crypto/7zAes.cpp $\endgroup$ May 19, 2020 at 3:51
  • $\begingroup$ @Todd "In the file" essentially means that it is put there with the ciphertext. $\endgroup$
    – forest
    Jan 18, 2021 at 6:43
  • $\begingroup$ agreed - inline is fine. My link was added as evidence that supports your answer. If 7z does it "inline", then it should be considered secure for the OP context. $\endgroup$ Jan 22, 2021 at 4:13

The alternatives to sharing a random IV are:

  1. Share a static IV - eg. hardcoded into the app. This is the worst alternative, because it will weaken the encryption overall. Salt helps, but IV is also important to make it take longer to crack.

  2. Share a common method to derive an IV - eg. from the password. This is probably better than [1], but don't trust this alternative. The IV is supposed to be totally random, so use a secure random generator.

It might feel wrong to share the IV (as well as the Salt), but it's the only way to have a very random IV as required. You will absolutely be using the same key for each encryption session, but with a changing IV (and Salt), you can be sure that the ciphertext will always be different for the same plain text, and therefore an attacker won't see

By the way, it's possible to share the Salt longer term, but make sure the IV is always different for each new encryption session. And don't worry, this is practiced by 7z - github.com/kornelski/7z/blob/master/CPP/7zip/Crypto/7zAes.cpp


Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.