> > My own code uses bio pairs. We special case the connection
> > setup phase.
> > Otherwise, we basically just manage the four I/O streams and
> > the SSL code
> > does its part without any special effort. Of course, it's
> > multithreaded, but
> > then it has to run on high-end SMP machines.
> The connection setup phase shouldn't need to be "special" - but of course
> I don't know what interesting things you may be doing :-) If your model
> requires that this is unique and otherwise you've got I/O logic built
> around the smooth functioning of the dirty-to-clean and clean-to-dirty
> traffic, then it would fail (just as the connection setup would) in the
> event that the peer asked for a renegotiate of the session. The run-time
> logic needs to assume that data could start to bounce between peers
> without the continuing arrival of new data on the clean side of either
> peer. If your logic achieves that, then as a result the "connection setup
> phase" doesn't really need anything special beyond that (except of course
> a call to start the SSL handshake in the first place).
That's what I thought, but my test code deadlocked.
What I did at first is I wrote the code so that it's triggered by received
data (either plaintext from higher level code or ciphertext from lower level
code). When we get data to hand to the SSL code, we BIO_write it to the
appropriate side and then call a 'churn' loop. The 'churn' loop attempts one
BIO_read for each direction. If we get a successful read, we hand it to
lower or higher level code as appropriate.
Because my code only fetches 768 bytes per pass, I coded that read loop so
that if it read any data at all, it repeats. The code originally looked like
this (this is the code I would call _after_ any case where I did a BIO_write
to the SSL code):
bool done;
char buf[768];
done=false;
while(!done)
{
done=true;
// Does the SSL library want to send any encrypted data
r=BIO_read(bio_io, buf, 768);
if(r>0)
{
done=false;
PutOutbound(buf, r);
}
// Does the SSL library want to hand off any cleartext
r=BIO_read(ssl_bio, buf, 768);
if(r>0)
{
done=false;
PutInbound(buf, r);
}
}
However, this deadlocked during setup! So I changed it as follows:
int count=init_complete ? 1 : 2;
while(count>0)
{
count--;
// Does the SSL library want to send any encrypted data
r=BIO_read(bio_io, buf, 768);
if(r>0)
{
count++;
PutOutbound(buf, 768);
}
// Does the SSL library want to hand off any cleartext
r=BIO_read(ssl_bio, buf, 768);
if(r>0)
{
count++;
PutInbound(buf, 768);
}
}
And it no longer deadlocks. At least, not in any of my testing. Am I doing
something horribly wrong? Is there a better way? And why didn't my initial
code work?
DS
______________________________________________________________________
OpenSSL Project http://www.openssl.org
Development Mailing List [EMAIL PROTECTED]
Automated List Manager [EMAIL PROTECTED]