Subject: Re: V3 secret keys

From: [email-masked] ("Hal Finney")
Date: Tue, 7 Feb 2006 12:19:45 -0800 (PST)

Ben Laurie writes:
> Hal Finney wrote:
> > The IV is used in the standard way.  You may be
> > thinking of symmetrically encrypted data packets, which work as you
> > say here.  V3 private keys are standard.
>
> Experiment and code reading/running says it is correct.

I rechecked my source code and I can confirm my statement.  The IV is
used in the standard way for V3 secret key CFB encryption.  The line is

	PGPInitCFB(*cfbp, key, buf + alglen);

This initializes the CFB context in the first argument, using the key
in the 2nd argument and the IV in the 3rd argument.  In this case the
IV is buf+alglen where buf is a pointer into the secret key data and
alglen is the offset past the S2K stuff.  If we were using an all-zeros
IV as Ben suggests then we would have had to set up a buffer to act as
the IV, fill it with zeros, and pass that to the PGPInitCFB function.
We don't do that.

(This is an important point because if it doesn't work as I have
described, then the spec is completely wrong and it would be extremely
important to change it ASAP.  So I hope Ben or others can confirm that
the spec is right on this matter.)

> > The last sentence is the one which is problematic.  What if we changed
> > it to:
> > 
> >    Furthermore, at the beginning of each MPI value after the first,
> >    the CFB state is re-synchronized to its initial state, with the IV
> >    for that MPI taken as the last 8 octets of the ciphertext of the
> >    previous MPI value.
> > 
> > Note that V3 keys only support ciphers with a block size of 8 bytes, so
> > I think it is OK to explicitly say "8 octets" here.

(As noted, I was mistaken about this 8-octet restriction.)

> "re-synchronised to its initial state" is perhaps not entirely clear -
> wouldn't it better to just say the IV is set to the last 8 octets of the
> previous ciphertext and not mention initial state?

The problem is that "IV" is not necessarily well defined in the middle
of a CFB.  You are using it synonymously with the chaining vector (or
whatever other term you want to use).  The "I" of "IV" means Initial,
so the IV is the value used "initially" to begin the CFB operation.
I am afraid that people would not know what to do if all we said was to
change the IV to such-and-such, in the middle of a CFB stream.  That's why
I said to go back to the "initial state" of the CFB and then what the IV
would be.  In the initial state, the concept of the IV is well defined.
I think that will be clearer to an implementor.

Maybe "re-synchronized" is unclear; how about if we said "... the CFB
state is reset to its initial state, with the IV for that MPI taken as..."

Hal Finney

---

From: Ben Laurie <[email-masked]>
Date: Wed, 15 Feb 2006 10:51:29 +0000

> the spec is right on this matter.)

No, I can't confirm that. I have code that works as we all expect CFB to
work (modulo "resync") on v4 secret keys. I had to make the change I
described to decrypt v3 keys. It seems to me rather unlikely that I have
it wrong given that I had to reverse engineer and write new code to get
a working implementation for v3!

Cheers,

Ben.

-- 
http://www.apache-ssl.org/ben.html       http://www.thebunker.net/

"There is no limit to what a man can do or how far he can go if he
doesn't mind who gets the credit." - Robert Woodruff