Skip to content

Commit dbe343b

Browse files
committed
stransport: store error information
We lose some error information from the read / write callbacks to stransport. Store our own error value in the object so that we can ensure that we rely upon it.
1 parent 6c0d5b1 commit dbe343b

File tree

1 file changed

+28
-11
lines changed

1 file changed

+28
-11
lines changed

src/libgit2/streams/stransport.c

Lines changed: 28 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,7 @@ typedef struct {
4444
git_stream parent;
4545
git_stream *io;
4646
int owned;
47+
int error;
4748
SSLContextRef ctx;
4849
CFDataRef der_data;
4950
git_cert_x509 cert_info;
@@ -61,7 +62,10 @@ static int stransport_connect(git_stream *stream)
6162
return error;
6263

6364
ret = SSLHandshake(st->ctx);
64-
if (ret != errSSLServerAuthCompleted) {
65+
66+
if (ret != errSSLServerAuthCompleted && st->error != 0)
67+
return -1;
68+
else if (ret != errSSLServerAuthCompleted) {
6569
git_error_set(GIT_ERROR_SSL, "unexpected return value from ssl handshake %d", (int)ret);
6670
return -1;
6771
}
@@ -147,10 +151,18 @@ static int stransport_set_proxy(
147151
*/
148152
static OSStatus write_cb(SSLConnectionRef conn, const void *data, size_t *len)
149153
{
150-
git_stream *io = (git_stream *) conn;
154+
stransport_stream *st = (stransport_stream *)conn;
155+
git_stream *io = st->io;
156+
OSStatus ret;
157+
158+
st->error = 0;
159+
160+
ret = git_stream__write_full(io, data, *len, 0);
151161

152-
if (git_stream__write_full(io, data, *len, 0) < 0)
153-
return -36; /* "ioErr" from MacErrors.h which is not available on iOS */
162+
if (ret < 0) {
163+
st->error = ret;
164+
return -36; /* ioErr */
165+
}
154166

155167
return noErr;
156168
}
@@ -182,18 +194,22 @@ static ssize_t stransport_write(git_stream *stream, const char *data, size_t len
182194
*/
183195
static OSStatus read_cb(SSLConnectionRef conn, void *data, size_t *len)
184196
{
185-
git_stream *io = (git_stream *) conn;
197+
stransport_stream *st = (stransport_stream *)conn;
198+
git_stream *io = st->io;
186199
OSStatus error = noErr;
187200
size_t off = 0;
188201
ssize_t ret;
189202

203+
st->error = 0;
204+
190205
do {
191206
ret = git_stream_read(io, data + off, *len - off);
207+
192208
if (ret < 0) {
193-
error = -36; /* "ioErr" from MacErrors.h which is not available on iOS */
209+
st->error = ret;
210+
error = -36; /* ioErr */
194211
break;
195-
}
196-
if (ret == 0) {
212+
} else if (ret == 0) {
197213
error = errSSLClosedGraceful;
198214
break;
199215
}
@@ -207,12 +223,13 @@ static OSStatus read_cb(SSLConnectionRef conn, void *data, size_t *len)
207223

208224
static ssize_t stransport_read(git_stream *stream, void *data, size_t len)
209225
{
210-
stransport_stream *st = (stransport_stream *) stream;
226+
stransport_stream *st = (stransport_stream *)stream;
211227
size_t processed;
212228
OSStatus ret;
213229

214-
if ((ret = SSLRead(st->ctx, data, len, &processed)) != noErr)
230+
if ((ret = SSLRead(st->ctx, data, len, &processed)) != noErr) {
215231
return stransport_error(ret);
232+
}
216233

217234
return processed;
218235
}
@@ -269,7 +286,7 @@ static int stransport_wrap(
269286
}
270287

271288
if ((ret = SSLSetIOFuncs(st->ctx, read_cb, write_cb)) != noErr ||
272-
(ret = SSLSetConnection(st->ctx, st->io)) != noErr ||
289+
(ret = SSLSetConnection(st->ctx, st)) != noErr ||
273290
(ret = SSLSetSessionOption(st->ctx, kSSLSessionOptionBreakOnServerAuth, true)) != noErr ||
274291
(ret = SSLSetProtocolVersionMin(st->ctx, kTLSProtocol1)) != noErr ||
275292
(ret = SSLSetProtocolVersionMax(st->ctx, kTLSProtocol12)) != noErr ||

0 commit comments

Comments
 (0)