Skip to content

Commit d85ea79

Browse files
tejksatbsideup
andauthored
Fix "docker-java-stream" thread stuck at UnixDomainSocket.recv() (#1476)
* Fix "docker-java-stream" thread stuck at UnixDomainSocket.recv() (OkHttp transport) (#1475) Prevent unnecessary recurring calls of `recv()` on UNIX socket, which sometimes results in blocking read and causes hanging of "docker-java-stream" thread. * Fix potential stuck at UnixDomainSocket.read() (HttpClient transport) (#1475) Prevent unnecessary recurring calls of `read()` on UNIX socket, which may result in blocking read and cause hanging of "docker-java-stream" thread. * Use data's length value instead of calculating length once again * Let UnixSocketInputStream.read(..) return -1 when the socket is disconnected or EOF is reached * Move isConnected() check to the beginning of read(..) method * Make UnixSocketInputStream.read() return -1 if EOF has been reached Co-authored-by: Alexander Koshevoy <Alexander.Koshevoy@jetbrains.com> Co-authored-by: Sergei Egorov <bsideup@gmail.com>
1 parent 0d08a33 commit d85ea79

File tree

2 files changed

+27
-35
lines changed

2 files changed

+27
-35
lines changed

docker-java-transport-httpclient5/src/main/java/com/github/dockerjava/httpclient5/UnixDomainSocket.java

Lines changed: 9 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -229,30 +229,19 @@ class UnixSocketInputStream extends InputStream {
229229

230230
@Override
231231
public int read(byte[] bytesEntry, int off, int len) throws IOException {
232+
if (!isConnected()) {
233+
return -1;
234+
}
232235
try {
233236
if (off > 0) {
234-
int bytes = 0;
235-
int remainingLength = len;
236-
int size;
237237
byte[] data = new byte[(len < 10240) ? len : 10240];
238-
do {
239-
if (!isConnected()) {
240-
return -1;
241-
}
242-
size = UnixDomainSocket.read(fd, data, (remainingLength < 10240) ? remainingLength : 10240);
243-
if (size <= 0) {
244-
return -1;
245-
}
246-
System.arraycopy(data, 0, bytesEntry, off, size);
247-
bytes += size;
248-
off += size;
249-
remainingLength -= size;
250-
} while ((remainingLength > 0) && (size > 0));
251-
return bytes;
252-
} else {
253-
if (!isConnected()) {
238+
int size = UnixDomainSocket.read(fd, data, data.length);
239+
if (size <= 0) {
254240
return -1;
255241
}
242+
System.arraycopy(data, 0, bytesEntry, off, size);
243+
return size;
244+
} else {
256245
int size = UnixDomainSocket.read(fd, bytesEntry, len);
257246
if (size <= 0) {
258247
return -1;
@@ -268,7 +257,7 @@ public int read(byte[] bytesEntry, int off, int len) throws IOException {
268257
public int read() throws IOException {
269258
byte[] bytes = new byte[1];
270259
int bytesRead = read(bytes);
271-
if (bytesRead == 0) {
260+
if (bytesRead <= 0) {
272261
return -1;
273262
}
274263
return bytes[0] & 0xff;

docker-java-transport-okhttp/src/main/java/com/github/dockerjava/okhttp/UnixDomainSocket.java

Lines changed: 18 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -230,24 +230,24 @@ class UnixSocketInputStream extends InputStream {
230230

231231
@Override
232232
public int read(byte[] bytesEntry, int off, int len) throws IOException {
233+
if (!isConnected()) {
234+
return -1;
235+
}
233236
try {
234237
if (off > 0) {
235-
int bytes = 0;
236-
int remainingLength = len;
237-
int size;
238238
byte[] data = new byte[(len < 10240) ? len : 10240];
239-
do {
240-
size = recv(fd, data, (remainingLength < 10240) ? remainingLength : 10240, 0);
241-
if (size > 0) {
242-
System.arraycopy(data, 0, bytesEntry, off, size);
243-
bytes += size;
244-
off += size;
245-
remainingLength -= size;
246-
}
247-
} while ((remainingLength > 0) && (size > 0));
248-
return bytes;
239+
int size = recv(fd, data, data.length, 0);
240+
if (size <= 0) {
241+
return -1;
242+
}
243+
System.arraycopy(data, 0, bytesEntry, off, size);
244+
return size;
249245
} else {
250-
return recv(fd, bytesEntry, len, 0);
246+
int size = recv(fd, bytesEntry, len, 0);
247+
if (size <= 0) {
248+
return -1;
249+
}
250+
return size;
251251
}
252252
} catch (LastErrorException lee) {
253253
throw new IOException("native read() failed : " + formatError(lee));
@@ -258,14 +258,17 @@ public int read(byte[] bytesEntry, int off, int len) throws IOException {
258258
public int read() throws IOException {
259259
byte[] bytes = new byte[1];
260260
int bytesRead = read(bytes);
261-
if (bytesRead == 0) {
261+
if (bytesRead <= 0) {
262262
return -1;
263263
}
264264
return bytes[0] & 0xff;
265265
}
266266

267267
@Override
268268
public int read(byte[] bytes) throws IOException {
269+
if (!isConnected()) {
270+
return -1;
271+
}
269272
return read(bytes, 0, bytes.length);
270273
}
271274
}

0 commit comments

Comments
 (0)