You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@commons.apache.org by mt...@apache.org on 2009/10/01 08:29:59 UTC
svn commit: r820546 - in /commons/sandbox/runtime/trunk/src/main/native/os:
unix/fsysio.c win32/fsysio.c
Author: mturk
Date: Thu Oct 1 06:29:59 2009
New Revision: 820546
URL: http://svn.apache.org/viewvc?rev=820546&view=rev
Log:
Throw exceptions on write in case of write error
Modified:
commons/sandbox/runtime/trunk/src/main/native/os/unix/fsysio.c
commons/sandbox/runtime/trunk/src/main/native/os/win32/fsysio.c
Modified: commons/sandbox/runtime/trunk/src/main/native/os/unix/fsysio.c
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/os/unix/fsysio.c?rev=820546&r1=820545&r2=820546&view=diff
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/os/unix/fsysio.c (original)
+++ commons/sandbox/runtime/trunk/src/main/native/os/unix/fsysio.c Thu Oct 1 06:29:59 2009
@@ -579,7 +579,7 @@
f->err = ACR_GET_OS_ERROR();
if (!ACR_STATUS_IS_EAGAIN(f->err)) {
/* Throw only if not EAGAIN
- */
+ */
ACR_THROW_IO_IF_ERR(f->err);
}
}
@@ -811,6 +811,7 @@
{
unsigned char c = (unsigned char)(b & 0xFF);
ssize_t wr;
+ int rc = 0;
acr_file_t *f = (acr_file_t *)ACR_IOH_FDATA(file);
if (ACR_IOH_FTYPE(file) != ACR_DT_FILE) {
@@ -824,23 +825,27 @@
wr = r_write(f->fd, &c, 1);
if (wr == -1 && (errno == EAGAIN || errno == EWOULDBLOCK) &&
f->timeout != 0) {
- int rc;
- if ((rc = wait_for_io_or_timeout(f, 0))) {
- f->err = rc;
- return rc == ACR_TIMEUP ? 0 : -1;
- }
- else {
+ if ((rc = wait_for_io_or_timeout(f, 0)) == 0) {
wr = r_write(f->fd, &c, 1);
}
}
- if (wr == -1) {
- f->err = ACR_GET_OS_ERROR();
- if (ACR_STATUS_IS_EAGAIN(f->err))
+ if (wr < 0) {
+ rc = ACR_GET_OS_ERROR();
+ if (ACR_STATUS_IS_EAGAIN(rc))
+ rc = ACR_TIMEUP;
+ }
+ switch (f->err = rc) {
+ case 0:
+ return (jint)wr;
+ break;
+ case ACR_TIMEUP:
return 0;
+ break;
+ default:
+ ACR_THROW_IO_IF_ERR(rc);
+ break;
}
- else if (wr == 1)
- f->err = 0;
- return wr;
+ return -1;
}
ACR_IO_EXPORT_DECLARE(jint, FileSystem, write1)(ACR_JNISTDARGS,
@@ -853,6 +858,7 @@
size_t po = (size_t)off;
size_t cs = (size_t)len;
ssize_t wr;
+ int rc = 0;
acr_file_t *f = (acr_file_t *)ACR_IOH_FDATA(file);
if (ACR_IOH_FTYPE(file) != ACR_DT_FILE) {
@@ -867,28 +873,32 @@
if (!bb) {
return -1;
}
+ f->err = 0;
wr = r_write(f->fd, bb + po, cs);
if (wr == -1 && (errno == EAGAIN || errno == EWOULDBLOCK) &&
f->timeout != 0) {
- int rc;
- if ((rc = wait_for_io_or_timeout(f, 0))) {
- f->err = rc;
- (*_E)->ReleaseByteArrayElements(_E, buf, bb, JNI_ABORT);
- return rc == ACR_TIMEUP ? 0 : -1;
- }
- else {
+ if ((rc = wait_for_io_or_timeout(f, 0)) == 0) {
wr = r_write(f->fd, bb + po, cs);
}
}
- if (wr == -1) {
- f->err = ACR_GET_OS_ERROR();
- if (ACR_STATUS_IS_EAGAIN(f->err))
- wr = 0;
+ if (wr < 0) {
+ rc = ACR_GET_OS_ERROR();
+ if (ACR_STATUS_IS_EAGAIN(rc))
+ rc = ACR_TIMEUP;
}
- else if (wr > 0)
- f->err = 0;
(*_E)->ReleaseByteArrayElements(_E, buf, bb, JNI_ABORT);
- return (jint)wr;
+ switch (f->err = rc) {
+ case 0:
+ return (jint)wr;
+ break;
+ case ACR_TIMEUP:
+ return 0;
+ break;
+ default:
+ ACR_THROW_IO_IF_ERR(rc);
+ break;
+ }
+ return -1;
}
ACR_IO_EXPORT_DECLARE(jint, FileSystem, write2)(ACR_JNISTDARGS,
@@ -902,6 +912,7 @@
size_t cs = (size_t)len;
jbyte *pb;
ssize_t wr;
+ int rc = 0;
acr_file_t *f = (acr_file_t *)ACR_IOH_FDATA(file);
if (ACR_IOH_FTYPE(file) != ACR_DT_FILE) {
@@ -924,23 +935,27 @@
wr = r_write(f->fd, pb + po, cs);
if (wr == -1 && (errno == EAGAIN || errno == EWOULDBLOCK) &&
f->timeout != 0) {
- int rc;
- if ((rc = wait_for_io_or_timeout(f, 0))) {
- f->err = rc;
- return rc == ACR_TIMEUP ? 0 : -1;
- }
- else {
+ if ((rc = wait_for_io_or_timeout(f, 0)) == 0) {
wr = r_write(f->fd, pb + po, cs);
}
}
- if (wr == -1) {
- f->err = ACR_GET_OS_ERROR();
- if (ACR_STATUS_IS_EAGAIN(f->err))
- wr = 0;
+ if (wr < 0) {
+ rc = ACR_GET_OS_ERROR();
+ if (ACR_STATUS_IS_EAGAIN(rc))
+ rc = ACR_TIMEUP;
+ }
+ switch (f->err = rc) {
+ case 0:
+ return (jint)wr;
+ break;
+ case ACR_TIMEUP:
+ return 0;
+ break;
+ default:
+ ACR_THROW_IO_IF_ERR(rc);
+ break;
}
- else if (wr > 0)
- f->err = 0;
- return (jint)wr;
+ return -1;
}
ACR_IO_EXPORT_DECLARE(jint, FileSystem, write3)(ACR_JNISTDARGS,
@@ -956,6 +971,7 @@
size_t cs = (size_t)len;
jbyte *pb;
ssize_t wr;
+ int rc = 0;
acr_file_t *f = (acr_file_t *)ACR_IOH_FDATA(file);
if (ACR_IOH_FTYPE(file) != ACR_DT_FILE) {
@@ -981,23 +997,27 @@
wr = r_write(f->fd, pb + po, cs);
if (wr == -1 && (errno == EAGAIN || errno == EWOULDBLOCK) &&
f->timeout != 0) {
- int rc;
- if ((rc = wait_for_io_or_timeout(f, 0))) {
- f->err = rc;
- return rc == ACR_TIMEUP ? 0 : -1;
- }
- else {
+ if ((rc = wait_for_io_or_timeout(f, 0)) == 0) {
wr = r_write(f->fd, pb + po, cs);
}
}
- if (wr == -1) {
- f->err = ACR_GET_OS_ERROR();
- if (ACR_STATUS_IS_EAGAIN(f->err))
- wr = 0;
+ if (wr < 0) {
+ rc = ACR_GET_OS_ERROR();
+ if (ACR_STATUS_IS_EAGAIN(rc))
+ rc = ACR_TIMEUP;
+ }
+ switch (f->err = rc) {
+ case 0:
+ return (jint)wr;
+ break;
+ case ACR_TIMEUP:
+ return 0;
+ break;
+ default:
+ ACR_THROW_IO_IF_ERR(rc);
+ break;
}
- else if (wr > 0)
- f->err = 0;
- return (jint)wr;
+ return -1;
}
#define ACR_IOVEC_ON_STACK 32
@@ -1012,6 +1032,7 @@
size_t po = (size_t)off;
size_t cs = (size_t)len;
ssize_t wr;
+ int rc = 0;
struct iovec *iov;
struct iovec onstack[ACR_IOVEC_ON_STACK];
jbyteArray bastack[ACR_IOVEC_ON_STACK];
@@ -1057,32 +1078,17 @@
} while (wr == -1 && errno == EAGAIN);
if (wr == -1 && (errno == EAGAIN || errno == EWOULDBLOCK) &&
f->timeout != 0) {
- int rc;
- if ((rc = wait_for_io_or_timeout(f, 0))) {
- f->err = rc;
- for (i = 0; i < cs; i++) {
- (*_E)->ReleaseByteArrayElements(_E, boa[i], iov[i].iov_base,
- JNI_ABORT);
- }
- if (iov != onstack) {
- x_free(iov);
- x_free(boa);
- }
- return rc == ACR_TIMEUP ? 0 : -1;
- }
- else {
+ if ((rc = wait_for_io_or_timeout(f, 0)) == 0) {
do {
wr = writev(f->fd, iov, pl);
} while (wr == -1 && errno == EAGAIN);
}
}
- if (wr == -1) {
- f->err = ACR_GET_OS_ERROR();
- if (ACR_STATUS_IS_EAGAIN(f->err))
- wr = 0;
+ if (wr < 0) {
+ rc = ACR_GET_OS_ERROR();
+ if (ACR_STATUS_IS_EAGAIN(rc))
+ rc = ACR_TIMEUP;
}
- else if (wr > 0)
- f->err = 0;
for (i = 0; i < cs; i++) {
(*_E)->ReleaseByteArrayElements(_E, boa[i], iov[i].iov_base, JNI_ABORT);
}
@@ -1090,7 +1096,18 @@
x_free(iov);
x_free(boa);
}
- return (jint)wr;
+ switch (f->err = rc) {
+ case 0:
+ return (jint)wr;
+ break;
+ case ACR_TIMEUP:
+ return 0;
+ break;
+ default:
+ ACR_THROW_IO_IF_ERR(rc);
+ break;
+ }
+ return -1;
}
ACR_IO_EXPORT_DECLARE(jint, FileSystem, write5)(ACR_JNISTDARGS,
@@ -1104,6 +1121,7 @@
size_t po = (size_t)off;
size_t cs = (size_t)len;
ssize_t wr;
+ int rc = 0;
struct iovec *iov;
struct iovec onstack[ACR_IOVEC_ON_STACK];
acr_file_t *f = (acr_file_t *)ACR_IOH_FDATA(file);
@@ -1139,29 +1157,31 @@
} while (wr == -1 && errno == EAGAIN);
if (wr == -1 && (errno == EAGAIN || errno == EWOULDBLOCK) &&
f->timeout != 0) {
- int rc;
- if ((rc = wait_for_io_or_timeout(f, 0))) {
- f->err = rc;
- if (iov != onstack)
- x_free(iov);
- return rc == ACR_TIMEUP ? 0 : -1;
- }
- else {
+ if ((rc = wait_for_io_or_timeout(f, 0)) == 0) {
do {
wr = writev(f->fd, iov, pl);
} while (wr == -1 && errno == EAGAIN);
}
}
- if (wr == -1) {
- f->err = ACR_GET_OS_ERROR();
- if (ACR_STATUS_IS_EAGAIN(f->err))
- wr = 0;
+ if (wr < 0) {
+ rc = ACR_GET_OS_ERROR();
+ if (ACR_STATUS_IS_EAGAIN(rc))
+ rc = ACR_TIMEUP;
}
- else if (wr > 0)
- f->err = 0;
if (iov != onstack)
x_free(iov);
- return (jint)wr;
+ switch (f->err = rc) {
+ case 0:
+ return (jint)wr;
+ break;
+ case ACR_TIMEUP:
+ return 0;
+ break;
+ default:
+ ACR_THROW_IO_IF_ERR(rc);
+ break;
+ }
+ return -1;
}
ACR_IO_EXPORT_DECLARE(jint, FileSystem, fullw0)(ACR_JNISTDARGS,
@@ -1176,6 +1196,7 @@
ssize_t cs = (ssize_t)len;
ssize_t wt = 0;
ssize_t wr;
+ int rc = 0;
acr_file_t *f = (acr_file_t *)ACR_IOH_FDATA(file);
if (ACR_IOH_FTYPE(file) != ACR_DT_FILE) {
@@ -1191,21 +1212,15 @@
return -1;
}
wb = bb + po;
- f->err = 0;
do {
wr = r_write(f->fd, wb, cs);
if (wr == -1 && (errno == EAGAIN || errno == EWOULDBLOCK) &&
f->timeout != 0) {
- int rc;
- if ((rc = wait_for_io_or_timeout(f, 0))) {
- f->err = rc;
- if (rc != ACR_TIMEUP) {
- break;
- }
- }
- else {
+ if ((rc = wait_for_io_or_timeout(f, 0)) == 0) {
wr = r_write(f->fd, wb, cs);
}
+ else if (rc != ACR_TIMEUP)
+ break;
}
if (wr > 0) {
wb += wr;
@@ -1213,10 +1228,24 @@
wt += wr;
}
} while (wr >= 0 && cs > 0);
- if (wt == 0)
- f->err = ACR_GET_OS_ERROR();
+ if (wt == 0) {
+ rc = ACR_GET_OS_ERROR();
+ if (ACR_STATUS_IS_EAGAIN(rc))
+ rc = ACR_TIMEUP;
+ }
(*_E)->ReleaseByteArrayElements(_E, buf, bb, JNI_ABORT);
- return (jint)wt;
+ switch (f->err = rc) {
+ case 0:
+ return (jint)wt;
+ break;
+ case ACR_TIMEUP:
+ return 0;
+ break;
+ default:
+ ACR_THROW_IO_IF_ERR(rc);
+ break;
+ }
+ return -1;
}
ACR_IO_EXPORT_DECLARE(jint, FileSystem, fullw1)(ACR_JNISTDARGS,
@@ -1231,6 +1260,7 @@
jbyte *pb;
ssize_t wr;
ssize_t wt = 0;
+ int rc = 0;
acr_file_t *f = (acr_file_t *)ACR_IOH_FDATA(file);
if (ACR_IOH_FTYPE(file) != ACR_DT_FILE) {
@@ -1251,20 +1281,15 @@
return -1;
}
pb = pb + po;
- f->err = 0;
do {
wr = r_write(f->fd, pb, cs);
if (wr == -1 && (errno == EAGAIN || errno == EWOULDBLOCK) &&
f->timeout != 0) {
- int rc;
- if ((rc = wait_for_io_or_timeout(f, 0))) {
- f->err = rc;
- if (rc != ACR_TIMEUP)
- break;
- }
- else {
+ if ((rc = wait_for_io_or_timeout(f, 0)) == 0) {
wr = r_write(f->fd, pb, cs);
}
+ else if (rc != ACR_TIMEUP)
+ break;
}
if (wr > 0) {
pb += wr;
@@ -1272,9 +1297,23 @@
wt += wr;
}
} while (wr >= 0 && cs > 0);
- if (wt == 0)
- f->err = ACR_GET_OS_ERROR();
- return (jint)wr;
+ if (wt == 0) {
+ rc = ACR_GET_OS_ERROR();
+ if (ACR_STATUS_IS_EAGAIN(rc))
+ rc = ACR_TIMEUP;
+ }
+ switch (f->err = rc) {
+ case 0:
+ return (jint)wt;
+ break;
+ case ACR_TIMEUP:
+ return 0;
+ break;
+ default:
+ ACR_THROW_IO_IF_ERR(rc);
+ break;
+ }
+ return -1;
}
ACR_IO_EXPORT_DECLARE(jint, FileSystem, fullw2)(ACR_JNISTDARGS,
@@ -1291,6 +1330,7 @@
jbyte *pb;
ssize_t wr;
ssize_t wt = 0;
+ int rc = 0;
acr_file_t *f = (acr_file_t *)ACR_IOH_FDATA(file);
if (ACR_IOH_FTYPE(file) != ACR_DT_FILE) {
@@ -1314,20 +1354,15 @@
}
#endif
pb = pb + po;
- f->err = 0;
do {
wr = r_write(f->fd, pb, cs);
if (wr == -1 && (errno == EAGAIN || errno == EWOULDBLOCK) &&
f->timeout != 0) {
- int rc;
- if ((rc = wait_for_io_or_timeout(f, 0))) {
- f->err = rc;
- if (rc != ACR_TIMEUP)
- break;
- }
- else {
+ if ((rc = wait_for_io_or_timeout(f, 0)) == 0) {
wr = r_write(f->fd, pb, cs);
}
+ else if (rc != ACR_TIMEUP)
+ break;
}
if (wr > 0) {
pb += wr;
@@ -1335,7 +1370,21 @@
wt += wr;
}
} while (wr >= 0 && cs > 0);
- if (wt == 0)
- f->err = ACR_GET_OS_ERROR();
- return (jint)wr;
+ if (wt == 0) {
+ rc = ACR_GET_OS_ERROR();
+ if (ACR_STATUS_IS_EAGAIN(rc))
+ rc = ACR_TIMEUP;
+ }
+ switch (f->err = rc) {
+ case 0:
+ return (jint)wt;
+ break;
+ case ACR_TIMEUP:
+ return 0;
+ break;
+ default:
+ ACR_THROW_IO_IF_ERR(rc);
+ break;
+ }
+ return -1;
}
Modified: commons/sandbox/runtime/trunk/src/main/native/os/win32/fsysio.c
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/os/win32/fsysio.c?rev=820546&r1=820545&r2=820546&view=diff
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/os/win32/fsysio.c (original)
+++ commons/sandbox/runtime/trunk/src/main/native/os/win32/fsysio.c Thu Oct 1 06:29:59 2009
@@ -335,6 +335,18 @@
}
+static int do_unlock(acr_file_t *f)
+{
+ int rc = 0;
+ OVERLAPPED opp;
+
+ memset(&opp, 0, sizeof(OVERLAPPED));
+ if (!UnlockFileEx(f->fd, 0, 0xFFFFFFFF, 0xFFFFFFFF, &opp))
+ rc = ACR_GET_OS_ERROR();
+ LeaveCriticalSection(&f->lock);
+ return rc;
+}
+
ACR_IO_EXPORT_DECLARE(jint, FileSystem, lock0)(ACR_JNISTDARGS,
jint file,
jint type)
@@ -1148,7 +1160,7 @@
jint b)
{
unsigned char c = (unsigned char)(b & 0xFF);
- DWORD rc;
+ DWORD rc = 0;
DWORD wr = 0;
int locked = 0;
LPOVERLAPPED lpo = NULL;
@@ -1184,7 +1196,7 @@
op.QuadPart = 0;
if (!SetFilePointerEx(f->fd, os, &op, FILE_END)) {
ACR_THROW_IO_ERRNO();
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
return -1;
}
f->pos = op.QuadPart;
@@ -1197,13 +1209,12 @@
if (IS_INVALID_HANDLE(lpo->hEvent)) {
ACR_THROW_IO_ERRNO();
if (locked)
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
return -1;
}
lpo->Offset = (DWORD)(f->pos);
lpo->OffsetHigh = (DWORD)(f->pos >> 32);
}
- f->err = 0;
if (WriteFile(f->fd, &c, 1, &wr, lpo)) {
/* All done. Update the position and return
*/
@@ -1211,9 +1222,9 @@
f->pos += wr;
goto finally;
}
- switch (f->err = GetLastError()) {
+ switch (rc = GetLastError()) {
case ERROR_IO_PENDING:
- if ((f->err = overlapped_wait(f, &wr)) == 0) {
+ if ((rc = overlapped_wait(f, &wr)) == 0) {
if (wr) {
f->pos += wr;
goto finally;
@@ -1226,11 +1237,19 @@
finally:
if (locked)
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
if (wr)
return (jint)wr;
- if (f->err)
- return f->err == ACR_TIMEUP ? 0 : -1;
+ switch (f->err = rc) {
+ case 0:
+ case ACR_TIMEUP:
+ return 0;
+ break;
+
+ default:
+ ACR_THROW_IO_IF_ERR(f->err);
+ break;
+ }
return -1;
}
@@ -1241,7 +1260,7 @@
jint len)
{
jbyte *bb;
- DWORD rc;
+ DWORD rc = 0;
DWORD po = (DWORD)off;
DWORD cs = (DWORD)len;
DWORD wr = 0;
@@ -1280,7 +1299,7 @@
op.QuadPart = 0;
if (!SetFilePointerEx(f->fd, os, &op, FILE_END)) {
ACR_THROW_IO_ERRNO();
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
return -1;
}
f->pos = op.QuadPart;
@@ -1293,7 +1312,7 @@
if (IS_INVALID_HANDLE(lpo->hEvent)) {
ACR_THROW_IO_ERRNO();
if (locked)
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
return -1;
}
lpo->Offset = (DWORD)(f->pos);
@@ -1303,10 +1322,9 @@
bb = (*_E)->GetByteArrayElements(_E, buf, NULL);
if (!bb) {
if (locked)
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
return -1;
}
- f->err = 0;
if (WriteFile(f->fd, bb + po, cs, &wr, lpo)) {
/* All done. Update the position and return
*/
@@ -1314,9 +1332,9 @@
f->pos += wr;
goto finally;
}
- switch (f->err = GetLastError()) {
+ switch (rc = GetLastError()) {
case ERROR_IO_PENDING:
- if ((f->err = overlapped_wait(f, &wr)) == 0) {
+ if ((rc = overlapped_wait(f, &wr)) == 0) {
if (wr) {
f->pos += wr;
goto finally;
@@ -1329,12 +1347,20 @@
finally:
if (locked)
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
(*_E)->ReleaseByteArrayElements(_E, buf, bb, JNI_ABORT);
if (wr)
return (jint)wr;
- if (f->err)
- return f->err == ACR_TIMEUP ? 0 : -1;
+ switch (f->err = rc) {
+ case 0:
+ case ACR_TIMEUP:
+ return 0;
+ break;
+
+ default:
+ ACR_THROW_IO_IF_ERR(f->err);
+ break;
+ }
return -1;
}
@@ -1346,7 +1372,7 @@
{
size_t pl;
jbyte *pb;
- DWORD rc;
+ DWORD rc = 0;
DWORD po = (DWORD)off;
DWORD cs = (DWORD)len;
DWORD wr = 0;
@@ -1384,7 +1410,7 @@
op.QuadPart = 0;
if (!SetFilePointerEx(f->fd, os, &op, FILE_END)) {
ACR_THROW_IO_ERRNO();
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
return -1;
}
f->pos = op.QuadPart;
@@ -1397,7 +1423,7 @@
if (IS_INVALID_HANDLE(lpo->hEvent)) {
ACR_THROW_IO_ERRNO();
if (locked)
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
return -1;
}
lpo->Offset = (DWORD)(f->pos);
@@ -1407,17 +1433,16 @@
if (!pb) {
ACR_ThrowException(_E, THROW_NMARK, ACR_EX_ENULL, 0);
if (locked)
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
return -1;
}
if ((po + cs) > (DWORD)pl) {
ACR_ThrowException(_E, THROW_NMARK, ACR_EX_EINDEX, 0);
if (locked)
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
return -1;
}
- f->err = 0;
if (WriteFile(f->fd, pb + po, cs, &wr, lpo)) {
/* All done. Update the position and return
*/
@@ -1425,9 +1450,9 @@
f->pos += wr;
goto finally;
}
- switch (f->err = GetLastError()) {
+ switch (rc = GetLastError()) {
case ERROR_IO_PENDING:
- if ((f->err = overlapped_wait(f, &wr)) == 0) {
+ if ((rc = overlapped_wait(f, &wr)) == 0) {
if (wr) {
f->pos += wr;
goto finally;
@@ -1440,11 +1465,19 @@
finally:
if (locked)
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
if (wr)
return (jint)wr;
- if (f->err)
- return f->err == ACR_TIMEUP ? 0 : -1;
+ switch (f->err = rc) {
+ case 0:
+ case ACR_TIMEUP:
+ return 0;
+ break;
+
+ default:
+ ACR_THROW_IO_IF_ERR(f->err);
+ break;
+ }
return -1;
}
@@ -1458,7 +1491,7 @@
DWORD pl;
#endif
jbyte *pb;
- DWORD rc;
+ DWORD rc = 0;
DWORD po = (DWORD)off;
DWORD cs = (DWORD)len;
DWORD wr = 0;
@@ -1496,7 +1529,7 @@
op.QuadPart = 0;
if (!SetFilePointerEx(f->fd, os, &op, FILE_END)) {
ACR_THROW_IO_ERRNO();
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
return -1;
}
f->pos = op.QuadPart;
@@ -1509,7 +1542,7 @@
if (IS_INVALID_HANDLE(lpo->hEvent)) {
ACR_THROW_IO_ERRNO();
if (locked)
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
return -1;
}
lpo->Offset = (DWORD)(f->pos);
@@ -1519,7 +1552,7 @@
if (!pb) {
ACR_ThrowException(_E, THROW_NMARK, ACR_EX_ENULL, 0);
if (locked)
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
return -1;
}
#if defined(_DEBUG)
@@ -1527,11 +1560,10 @@
if ((po + cs) > pl) {
ACR_ThrowException(_E, THROW_NMARK, ACR_EX_EINDEX, 0);
if (locked)
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
return -1;
}
#endif
- f->err = 0;
if (WriteFile(f->fd, pb + po, cs, &wr, lpo)) {
/* All done. Update the position and return
*/
@@ -1539,9 +1571,9 @@
f->pos += wr;
goto finally;
}
- switch (f->err = GetLastError()) {
+ switch (rc = GetLastError()) {
case ERROR_IO_PENDING:
- if ((f->err = overlapped_wait(f, &wr)) == 0) {
+ if ((rc = overlapped_wait(f, &wr)) == 0) {
if (wr) {
f->pos += wr;
goto finally;
@@ -1554,11 +1586,19 @@
finally:
if (locked)
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
if (wr)
return (jint)wr;
- if (f->err)
- return f->err == ACR_TIMEUP ? 0 : -1;
+ switch (f->err = rc) {
+ case 0:
+ case ACR_TIMEUP:
+ return 0;
+ break;
+
+ default:
+ ACR_THROW_IO_IF_ERR(f->err);
+ break;
+ }
return -1;
}
@@ -1570,7 +1610,7 @@
{
DWORD i;
DWORD pl;
- DWORD rc;
+ DWORD rc = 0;
DWORD wr;
DWORD po = (DWORD)off;
DWORD cs = (DWORD)len;
@@ -1596,8 +1636,6 @@
ACR_ThrowException(_E, THROW_NMARK, ACR_EX_EINDEX, 0);
return -1;
}
- if ((*_E)->EnsureLocalCapacity(_E, (jint)(cs * 2)))
- return -1;
if (f->flags & ACR_FOPEN_APPEND) {
LARGE_INTEGER os;
LARGE_INTEGER op;
@@ -1620,7 +1658,7 @@
op.QuadPart = 0;
if (!SetFilePointerEx(f->fd, os, &op, FILE_END)) {
ACR_THROW_IO_ERRNO();
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
return -1;
}
f->pos = op.QuadPart;
@@ -1633,12 +1671,11 @@
if (IS_INVALID_HANDLE(lpo->hEvent)) {
ACR_THROW_IO_ERRNO();
if (locked)
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
return -1;
}
}
- f->err = 0;
for (i = 0; i < cs, f->err == 0; i++) {
bae = (*_E)->GetObjectArrayElement(_E, vec, (jsize)(i + po));
bal = (DWORD)(*_E)->GetArrayLength(_E, bae);
@@ -1657,9 +1694,9 @@
}
}
else {
- switch (f->err = GetLastError()) {
+ switch (rc = GetLastError()) {
case ERROR_IO_PENDING:
- if ((f->err = overlapped_wait(f, &wr)) == 0) {
+ if ((rc = overlapped_wait(f, &wr)) == 0) {
if (wr) {
f->pos += wr;
nbytes += wr;
@@ -1671,14 +1708,23 @@
}
}
(*_E)->ReleaseByteArrayElements(_E, bae, bab, JNI_ABORT);
+ (*_E)->DeleteLocalRef(_E, bae);
}
if (locked)
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
if (nbytes)
return (jint)nbytes;
- if (f->err)
- return f->err == ACR_TIMEUP ? 0 : -1;
+ switch (f->err = rc) {
+ case 0:
+ case ACR_TIMEUP:
+ return 0;
+ break;
+
+ default:
+ ACR_THROW_IO_IF_ERR(f->err);
+ break;
+ }
return -1;
}
@@ -1690,7 +1736,7 @@
{
DWORD i;
DWORD pl;
- DWORD rc;
+ DWORD rc = 0;
DWORD wr;
DWORD po = (DWORD)off;
DWORD cs = (DWORD)len;
@@ -1716,8 +1762,6 @@
ACR_ThrowException(_E, THROW_NMARK, ACR_EX_EINDEX, 0);
return -1;
}
- if ((*_E)->EnsureLocalCapacity(_E, (jint)(cs * 2)))
- return -1;
if (f->flags & ACR_FOPEN_APPEND) {
LARGE_INTEGER os;
LARGE_INTEGER op;
@@ -1740,7 +1784,7 @@
op.QuadPart = 0;
if (!SetFilePointerEx(f->fd, os, &op, FILE_END)) {
ACR_THROW_IO_ERRNO();
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
return -1;
}
f->pos = op.QuadPart;
@@ -1753,12 +1797,11 @@
if (IS_INVALID_HANDLE(lpo->hEvent)) {
ACR_THROW_IO_ERRNO();
if (locked)
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
return -1;
}
}
- f->err = 0;
for (i = 0; i < cs, f->err == 0; i++) {
bbe = (*_E)->GetObjectArrayElement(_E, vec, (jsize)(i + po));
bbl = (DWORD)(*_E)->GetDirectBufferCapacity(_E, bbe);
@@ -1779,9 +1822,9 @@
}
}
else {
- switch (f->err = GetLastError()) {
+ switch (rc = GetLastError()) {
case ERROR_IO_PENDING:
- if ((f->err = overlapped_wait(f, &wr)) == 0) {
+ if ((rc = overlapped_wait(f, &wr)) == 0) {
if (wr) {
f->pos += wr;
nbytes += wr;
@@ -1795,10 +1838,404 @@
}
if (locked)
- LeaveCriticalSection(&f->lock);
+ do_unlock(f);
if (nbytes)
return (jint)nbytes;
- if (f->err)
- return f->err == ACR_TIMEUP ? 0 : -1;
+ switch (f->err = rc) {
+ case 0:
+ case ACR_TIMEUP:
+ return 0;
+ break;
+
+ default:
+ ACR_THROW_IO_IF_ERR(f->err);
+ break;
+ }
+ return -1;
+}
+
+ACR_IO_EXPORT_DECLARE(jint, FileSystem, fullw0)(ACR_JNISTDARGS,
+ jint file,
+ jbyteArray buf,
+ jint off,
+ jint len)
+{
+ jbyte *bb;
+ jbyte *wb;
+ DWORD rc = 0;
+ DWORD po = (DWORD)off;
+ DWORD cs = (DWORD)len;
+ DWORD wr;
+ DWORD nbytes = 0;
+ int locked = 0;
+ LPOVERLAPPED lpo = NULL;
+ acr_file_t *f = (acr_file_t *)ACR_IOH_FDATA(file);
+
+ if (ACR_IOH_FTYPE(file) != ACR_DT_FILE) {
+ ACR_THROW_IO_IF_ERR(ACR_EFTYPE);
+ return -1;
+ }
+ if (IS_INVALID_HANDLE(f)) {
+ ACR_THROW_IO_IF_ERR(ACR_EBADF);
+ return -1;
+ }
+ if (f->flags & ACR_FOPEN_APPEND) {
+ LARGE_INTEGER os;
+ LARGE_INTEGER op;
+
+ EnterCriticalSection(&f->lock);
+ /* apr_file_lock will mutex the file across processes.
+ * The call to apr_thread_mutex_lock is added to avoid
+ * a race condition between LockFile and WriteFile
+ * that occasionally leads to deadlocked threads.
+ */
+ rc = do_lock(f, LOCKFILE_EXCLUSIVE_LOCK);
+ if (rc) {
+ ACR_THROW_IO_IF_ERR(rc);
+ LeaveCriticalSection(&f->lock);
+ return -1;
+ }
+ /* Set the position to the file end
+ */
+ os.QuadPart = 0;
+ op.QuadPart = 0;
+ if (!SetFilePointerEx(f->fd, os, &op, FILE_END)) {
+ ACR_THROW_IO_ERRNO();
+ do_unlock(f);
+ return -1;
+ }
+ f->pos = op.QuadPart;
+ locked = 1;
+ }
+ if (f->blocking == BLK_OFF) {
+ lpo = &f->overlap;
+ if (IS_INVALID_HANDLE(lpo->hEvent))
+ lpo->hEvent = CreateEvent(NULL, TRUE, TRUE, NULL);
+ if (IS_INVALID_HANDLE(lpo->hEvent)) {
+ ACR_THROW_IO_ERRNO();
+ if (locked)
+ do_unlock(f);
+ return -1;
+ }
+ }
+ bb = (*_E)->GetByteArrayElements(_E, buf, NULL);
+ if (!bb) {
+ if (locked)
+ do_unlock(f);
+ return -1;
+ }
+ wb = bb + po;
+ do {
+ if (lpo) {
+ lpo->Offset = (DWORD)(f->pos);
+ lpo->OffsetHigh = (DWORD)(f->pos >> 32);
+ }
+ wr = 0;
+ if (WriteFile(f->fd, wb, cs, &wr, lpo)) {
+ /* All done. Update the position and return
+ */
+ if (wr) {
+ f->pos += wr;
+ nbytes += wr;
+ wb += wr;
+ cs -= wr;
+ }
+ }
+ else {
+ switch (rc = GetLastError()) {
+ case ERROR_IO_PENDING:
+ if ((rc = overlapped_wait_all(f, &wr)) == 0) {
+ if (wr) {
+ f->pos += wr;
+ nbytes += wr;
+ wb += wr;
+ cs -= wr;
+ }
+ }
+ break;
+ default:
+ break;
+ }
+ }
+ if (rc && rc != ACR_TIMEUP)
+ break;
+ } while (cs > 0);
+
+ if (locked)
+ do_unlock(f);
+ (*_E)->ReleaseByteArrayElements(_E, buf, bb, JNI_ABORT);
+ if (nbytes)
+ return (jint)nbytes;
+ switch (f->err = rc) {
+ case 0:
+ case ACR_TIMEUP:
+ return 0;
+ break;
+
+ default:
+ ACR_THROW_IO_IF_ERR(f->err);
+ break;
+ }
+ return -1;
+}
+
+ACR_IO_EXPORT_DECLARE(jint, FileSystem, fullw1)(ACR_JNISTDARGS,
+ jint file,
+ jobject ptr,
+ jlong off,
+ jlong len)
+{
+ size_t pl;
+ jbyte *pb;
+ DWORD rc = 0;
+ DWORD po = (DWORD)off;
+ DWORD cs = (DWORD)len;
+ DWORD wr;
+ DWORD nbytes = 0;
+ int locked = 0;
+ LPOVERLAPPED lpo = NULL;
+ acr_file_t *f = (acr_file_t *)ACR_IOH_FDATA(file);
+
+ if (ACR_IOH_FTYPE(file) != ACR_DT_FILE) {
+ ACR_THROW_IO_IF_ERR(ACR_EFTYPE);
+ return -1;
+ }
+ if (IS_INVALID_HANDLE(f)) {
+ ACR_THROW_IO_IF_ERR(ACR_EBADF);
+ return -1;
+ }
+ pb = (jbyte *)ACR_PointerGet(_E, ptr, &pl);
+ if (!pb) {
+ ACR_ThrowException(_E, THROW_NMARK, ACR_EX_ENULL, 0);
+ return -1;
+ }
+ if ((po + cs) > (DWORD)pl) {
+ ACR_ThrowException(_E, THROW_NMARK, ACR_EX_EINDEX, 0);
+ return -1;
+ }
+ pb = pb + po;
+ if (f->flags & ACR_FOPEN_APPEND) {
+ LARGE_INTEGER os;
+ LARGE_INTEGER op;
+
+ EnterCriticalSection(&f->lock);
+ /* apr_file_lock will mutex the file across processes.
+ * The call to apr_thread_mutex_lock is added to avoid
+ * a race condition between LockFile and WriteFile
+ * that occasionally leads to deadlocked threads.
+ */
+ rc = do_lock(f, LOCKFILE_EXCLUSIVE_LOCK);
+ if (rc) {
+ ACR_THROW_IO_IF_ERR(rc);
+ LeaveCriticalSection(&f->lock);
+ return -1;
+ }
+ /* Set the position to the file end
+ */
+ os.QuadPart = 0;
+ op.QuadPart = 0;
+ if (!SetFilePointerEx(f->fd, os, &op, FILE_END)) {
+ ACR_THROW_IO_ERRNO();
+ do_unlock(f);
+ return -1;
+ }
+ f->pos = op.QuadPart;
+ locked = 1;
+ }
+ if (f->blocking == BLK_OFF) {
+ lpo = &f->overlap;
+ if (IS_INVALID_HANDLE(lpo->hEvent))
+ lpo->hEvent = CreateEvent(NULL, TRUE, TRUE, NULL);
+ if (IS_INVALID_HANDLE(lpo->hEvent)) {
+ ACR_THROW_IO_ERRNO();
+ if (locked)
+ do_unlock(f);
+ return -1;
+ }
+ }
+
+ do {
+ if (lpo) {
+ lpo->Offset = (DWORD)(f->pos);
+ lpo->OffsetHigh = (DWORD)(f->pos >> 32);
+ }
+ wr = 0;
+ if (WriteFile(f->fd, pb, cs, &wr, lpo)) {
+ /* All done. Update the position and return
+ */
+ if (wr) {
+ f->pos += wr;
+ nbytes += wr;
+ pb += wr;
+ cs -= wr;
+ }
+ }
+ else {
+ switch (rc = GetLastError()) {
+ case ERROR_IO_PENDING:
+ if ((rc = overlapped_wait_all(f, &wr)) == 0) {
+ if (wr) {
+ f->pos += wr;
+ nbytes += wr;
+ pb += wr;
+ cs -= wr;
+ }
+ }
+ break;
+ default:
+ break;
+ }
+ }
+ if (rc && rc != ACR_TIMEUP)
+ break;
+ } while (cs > 0);
+
+ if (locked)
+ do_unlock(f);
+ if (nbytes)
+ return (jint)nbytes;
+ switch (f->err = rc) {
+ case 0:
+ case ACR_TIMEUP:
+ return 0;
+ break;
+
+ default:
+ ACR_THROW_IO_IF_ERR(f->err);
+ break;
+ }
+ return -1;
+}
+
+ACR_IO_EXPORT_DECLARE(jint, FileSystem, fullw2)(ACR_JNISTDARGS,
+ jint file,
+ jobject dbb,
+ jlong off,
+ jlong len)
+{
+#if defined(_DEBUG)
+ DWORD pl;
+#endif
+ jbyte *pb;
+ DWORD rc = 0;
+ DWORD po = (DWORD)off;
+ DWORD cs = (DWORD)len;
+ DWORD wr;
+ DWORD nbytes = 0;
+ int locked = 0;
+ LPOVERLAPPED lpo = NULL;
+ acr_file_t *f = (acr_file_t *)ACR_IOH_FDATA(file);
+
+ if (ACR_IOH_FTYPE(file) != ACR_DT_FILE) {
+ ACR_THROW_IO_IF_ERR(ACR_EFTYPE);
+ return -1;
+ }
+ if (IS_INVALID_HANDLE(f)) {
+ ACR_THROW_IO_IF_ERR(ACR_EBADF);
+ return -1;
+ }
+ pb = (jbyte *)(*_E)->GetDirectBufferAddress(_E, dbb);
+ if (!pb) {
+ ACR_ThrowException(_E, THROW_NMARK, ACR_EX_ENULL, 0);
+ return -1;
+ }
+#if defined(_DEBUG)
+ pl = (DWORD)(*_E)->GetDirectBufferCapacity(_E, dbb);
+ if ((po + cs) > pl) {
+ ACR_ThrowException(_E, THROW_NMARK, ACR_EX_EINDEX, 0);
+ return -1;
+ }
+#endif
+ pb = pb + po;
+ if (f->flags & ACR_FOPEN_APPEND) {
+ LARGE_INTEGER os;
+ LARGE_INTEGER op;
+
+ EnterCriticalSection(&f->lock);
+ /* apr_file_lock will mutex the file across processes.
+ * The call to apr_thread_mutex_lock is added to avoid
+ * a race condition between LockFile and WriteFile
+ * that occasionally leads to deadlocked threads.
+ */
+ rc = do_lock(f, LOCKFILE_EXCLUSIVE_LOCK);
+ if (rc) {
+ ACR_THROW_IO_IF_ERR(rc);
+ LeaveCriticalSection(&f->lock);
+ return -1;
+ }
+ /* Set the position to the file end
+ */
+ os.QuadPart = 0;
+ op.QuadPart = 0;
+ if (!SetFilePointerEx(f->fd, os, &op, FILE_END)) {
+ ACR_THROW_IO_ERRNO();
+ do_unlock(f);
+ return -1;
+ }
+ f->pos = op.QuadPart;
+ locked = 1;
+ }
+ if (f->blocking == BLK_OFF) {
+ lpo = &f->overlap;
+ if (IS_INVALID_HANDLE(lpo->hEvent))
+ lpo->hEvent = CreateEvent(NULL, TRUE, TRUE, NULL);
+ if (IS_INVALID_HANDLE(lpo->hEvent)) {
+ ACR_THROW_IO_ERRNO();
+ if (locked)
+ do_unlock(f);
+ return -1;
+ }
+ }
+
+ do {
+ if (lpo) {
+ lpo->Offset = (DWORD)(f->pos);
+ lpo->OffsetHigh = (DWORD)(f->pos >> 32);
+ }
+ wr = 0;
+ if (WriteFile(f->fd, pb, cs, &wr, lpo)) {
+ /* All done. Update the position and return
+ */
+ if (wr) {
+ f->pos += wr;
+ nbytes += wr;
+ pb += wr;
+ cs -= wr;
+ }
+ }
+ else {
+ switch (rc = GetLastError()) {
+ case ERROR_IO_PENDING:
+ if ((rc = overlapped_wait_all(f, &wr)) == 0) {
+ if (wr) {
+ f->pos += wr;
+ nbytes += wr;
+ pb += wr;
+ cs -= wr;
+ }
+ }
+ break;
+ default:
+ break;
+ }
+ }
+ if (rc && rc != ACR_TIMEUP)
+ break;
+ } while (cs > 0);
+
+ if (locked)
+ do_unlock(f);
+ if (nbytes)
+ return (jint)nbytes;
+ switch (f->err = rc) {
+ case 0:
+ case ACR_TIMEUP:
+ return 0;
+ break;
+
+ default:
+ ACR_THROW_IO_IF_ERR(f->err);
+ break;
+ }
return -1;
}