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 2011/05/03 09:26:38 UTC
svn commit: r1098947 - in /commons/sandbox/runtime/trunk/src/main/native:
include/acr/stdinc.h os/win32/arch_defs.h os/win32/arch_opts.h
os/win32/posix.c os/win32/util.c os/win32/winapi.c
Author: mturk
Date: Tue May 3 07:26:38 2011
New Revision: 1098947
URL: http://svn.apache.org/viewvc?rev=1098947&view=rev
Log:
Add more win32 utils
Modified:
commons/sandbox/runtime/trunk/src/main/native/include/acr/stdinc.h
commons/sandbox/runtime/trunk/src/main/native/os/win32/arch_defs.h
commons/sandbox/runtime/trunk/src/main/native/os/win32/arch_opts.h
commons/sandbox/runtime/trunk/src/main/native/os/win32/posix.c
commons/sandbox/runtime/trunk/src/main/native/os/win32/util.c
commons/sandbox/runtime/trunk/src/main/native/os/win32/winapi.c
Modified: commons/sandbox/runtime/trunk/src/main/native/include/acr/stdinc.h
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/include/acr/stdinc.h?rev=1098947&r1=1098946&r2=1098947&view=diff
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/include/acr/stdinc.h (original)
+++ commons/sandbox/runtime/trunk/src/main/native/include/acr/stdinc.h Tue May 3 07:26:38 2011
@@ -28,7 +28,7 @@
# define WIN32_LEAN_AND_MEAN
# endif
# if !defined(_WIN32_WINNT)
-# define _WIN32_WINNT 0x0501
+# define _WIN32_WINNT 0x0502
# endif
/* Ignore most warnings (back down to /W3) for poorly constructed headers
@@ -79,6 +79,7 @@
# include <mswsock.h>
# include <ws2tcpip.h>
# include <wincrypt.h>
+# include <winioctl.h>
#endif /* WIN32 */
/* GNU libc requires __STDC_LIMIT_MACROS
Modified: commons/sandbox/runtime/trunk/src/main/native/os/win32/arch_defs.h
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/os/win32/arch_defs.h?rev=1098947&r1=1098946&r2=1098947&view=diff
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/os/win32/arch_defs.h (original)
+++ commons/sandbox/runtime/trunk/src/main/native/os/win32/arch_defs.h Tue May 3 07:26:38 2011
@@ -86,13 +86,6 @@ typedef struct OVERLAPPED_VBUFF {
} else (void)0
-#define WAIT_OBJECT_SIGNAL WAIT_OBJECT_0
-#define WAIT_OBJECT_SIGPIPE (WAIT_OBJECT_0 + 1)
-#define WAIT_OBJECT_1 (WAIT_OBJECT_0 + 1)
-#define WAIT_OBJECT_2 (WAIT_OBJECT_0 + 2)
-#define WAIT_OBJECT_3 (WAIT_OBJECT_0 + 3)
-#define WAIT_OBJECT_4 (WAIT_OBJECT_0 + 4)
-
/*
* ---------------------------------------------------------------------
* begin of DDK declarations
@@ -161,12 +154,11 @@ static __inline int isblank(int c)
return c == ' ' || c == '\t';
}
-#define WAIT_OBJECT_SIGNAL WAIT_OBJECT_0
-#define WAIT_OBJECT_SIGPIPE (WAIT_OBJECT_0 + 1)
#define WAIT_OBJECT_1 (WAIT_OBJECT_0 + 1)
#define WAIT_OBJECT_2 (WAIT_OBJECT_0 + 2)
#define WAIT_OBJECT_3 (WAIT_OBJECT_0 + 3)
#define WAIT_OBJECT_4 (WAIT_OBJECT_0 + 4)
+#define WAIT_OBJECT_M (WAIT_OBJECT_0 + MAXIMUM_WAIT_OBJECTS)
/**
* Definitions matching the KeyAccessRights Java enum
Modified: commons/sandbox/runtime/trunk/src/main/native/os/win32/arch_opts.h
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/os/win32/arch_opts.h?rev=1098947&r1=1098946&r2=1098947&view=diff
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/os/win32/arch_opts.h (original)
+++ commons/sandbox/runtime/trunk/src/main/native/os/win32/arch_opts.h Tue May 3 07:26:38 2011
@@ -145,6 +145,39 @@ ACR_DECLARE_LATE_DLL_FUNC1(SYSDLL_KERNEL
(lpSymlinkFileName, lpTargetFileName, dwFlags));
#define CreateSymbolicLinkW _delayload_CreateSymbolicLinkW
+#if !defined(POLLERR)
+/* Event flag definitions for WSAPoll(). */
+#define POLLRDNORM 0x0100
+#define POLLRDBAND 0x0200
+#define POLLIN (POLLRDNORM | POLLRDBAND)
+#define POLLPRI 0x0400
+
+#define POLLWRNORM 0x0010
+#define POLLOUT (POLLWRNORM)
+#define POLLWRBAND 0x0020
+
+#define POLLERR 0x0001
+#define POLLHUP 0x0002
+#define POLLNVAL 0x0004
+
+typedef struct pollfd {
+ SOCKET fd;
+ SHORT events;
+ SHORT revents;
+
+} WSAPOLLFD, *PWSAPOLLFD, FAR *LPWSAPOLLFD;
+
+#endif /* !defined(POLLERR) */
+#ifdef WSAPoll
+#undef WSAPoll
+#endif
+ACR_DECLARE_LATE_DLL_FUNC1(SYSDLL_WS2_32, int, -1,
+ WSAAPI, WSAPoll, 0, (
+ IN OUT LPWSAPOLLFD fdArray,
+ IN ULONG fds,
+ IN INT timeout),
+ (fdArray, fds, timeout));
+#define WSAPoll _delayload_WSAPoll
extern HANDLE acr_raised_event;
extern volatile LONG acr_signal_waiters;
@@ -235,10 +268,14 @@ ACR_INLINE(void) MsecTimeToFileTime(LPFI
HANDLE AcrNullPipe(int flags, int fd);
int AcrPipePair(HANDLE *rd, HANDLE *wr, int flags, char *name);
+int AcrSocketPair(SOCKET *rd, SOCKET *wr, int nonblocking);
+int AcrDrainSocket(SOCKET sd);
int AcrNonblock(int sd, int on);
size_t wcslcpy(wchar_t *dst, const wchar_t *src, size_t siz);
size_t wcslcat(wchar_t *dst, const wchar_t *src, size_t siz);
const wchar_t *basename_w(const wchar_t *path);
wchar_t *dirname_w(const wchar_t *path, wchar_t *dname, size_t dlen);
+int symlink_w(const wchar_t *target, const wchar_t *lnkname);
+ssize_t readlink_w(const wchar_t *lnkname, wchar_t *buf, size_t len);
#endif /* _ACR_ARCH_OPTS_H_ */
Modified: commons/sandbox/runtime/trunk/src/main/native/os/win32/posix.c
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/os/win32/posix.c?rev=1098947&r1=1098946&r2=1098947&view=diff
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/os/win32/posix.c (original)
+++ commons/sandbox/runtime/trunk/src/main/native/os/win32/posix.c Tue May 3 07:26:38 2011
@@ -160,3 +160,212 @@ wcslcat(wchar_t *dst, const wchar_t *src
return(dlen + (s - src)); /* count does not include NUL */
}
+
+int
+symlink_w(const wchar_t *target, const wchar_t *lnkname)
+{
+ int rc = 0;
+ char *mpb = 0;
+ DWORD dwFlags = 0;
+ DWORD dwAttrs;
+ size_t tlen = wcslen(target);
+
+ dwAttrs = GetFileAttributesW(target);
+ if (dwAttrs == INVALID_FILE_ATTRIBUTES)
+ return -1;
+ if (dwAttrs & FILE_ATTRIBUTE_DIRECTORY)
+ dwFlags = SYMBOLIC_LINK_FLAG_DIRECTORY;
+
+ if (ACR_HAVE_LATE_DLL_FUNC(CreateSymbolicLinkW)) {
+ if (CreateSymbolicLinkW(lnkname, target, dwFlags))
+ return 0;
+ else
+ return -1;
+ }
+ /* Pre Vista. Let's do it the hard way...
+ * Note that this only works for linking directories.
+ */
+ if (dwFlags == SYMBOLIC_LINK_FLAG_DIRECTORY) {
+ HANDLE token = 0;
+ HANDLE hlink = INVALID_HANDLE_VALUE;
+ PREPARSE_DATA_BUFFER rdb;
+ DWORD dlen;
+ size_t blen = (MAXIMUM_REPARSE_DATA_BUFFER_SIZE - sizeof(PREPARSE_DATA_BUFFER)) / sizeof(wchar_t);
+
+ mpb = calloc(1, MAXIMUM_REPARSE_DATA_BUFFER_SIZE);
+ if (mpb == 0) {
+ goto cleanup;
+ }
+ /* Remove the link directory if already exists */
+ RemoveDirectoryW(lnkname);
+ if (!CreateDirectoryW(lnkname, 0)) {
+ /* Failed to create link name directory */
+ rc = ACR_GET_OS_ERROR();
+ goto cleanup;
+ }
+ if (OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES, &token)) {
+ TOKEN_PRIVILEGES tp;
+ if (LookupPrivilegeValue(0, SE_RESTORE_NAME, &tp.Privileges[0].Luid)) {
+ tp.PrivilegeCount = 1;
+ tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
+ AdjustTokenPrivileges(token, FALSE, &tp, sizeof(TOKEN_PRIVILEGES),
+ 0, 0);
+ }
+ CloseHandle(token);
+ }
+ hlink = CreateFileW(lnkname,
+ GENERIC_WRITE,
+ 0,
+ 0,
+ OPEN_EXISTING,
+ FILE_FLAG_OPEN_REPARSE_POINT | FILE_FLAG_BACKUP_SEMANTICS,
+ 0);
+ if (hlink == INVALID_HANDLE_VALUE) {
+ rc = ACR_GET_OS_ERROR();
+ goto cleanup;
+ }
+ rdb = (PREPARSE_DATA_BUFFER)mpb;
+ rdb->ReparseTag = IO_REPARSE_TAG_MOUNT_POINT;
+ wcslcpy(rdb->MountPointReparseBuffer.PathBuffer, L"\\??\\", blen);
+ wcslcat(rdb->MountPointReparseBuffer.PathBuffer, target, blen);
+ tlen = wcslen(rdb->MountPointReparseBuffer.PathBuffer);
+
+ rdb->MountPointReparseBuffer.SubstituteNameLength = (USHORT)(tlen * sizeof(wchar_t));
+ rdb->MountPointReparseBuffer.PrintNameOffset = (USHORT)((tlen + 1) * sizeof(wchar_t));
+ rdb->ReparseDataLength = (USHORT)(sizeof(rdb->MountPointReparseBuffer) + ((tlen + 1) * sizeof(wchar_t)));
+
+ if (!DeviceIoControl(hlink, FSCTL_SET_REPARSE_POINT,
+ rdb, rdb->ReparseDataLength + 8,
+ 0, 0, &dlen, 0)) {
+ rc = ACR_GET_OS_ERROR();
+ }
+ CloseHandle(hlink);
+ }
+ else {
+ /* XXX: How to figure out the target of the hard link? */
+ if (!CreateHardLinkW(lnkname, target, 0))
+ rc = ACR_GET_OS_ERROR();
+ }
+
+cleanup:
+ AcrFree(mpb);
+ if (rc != 0) {
+ ACR_SET_OS_ERROR(rc);
+ return -1;
+ }
+ else
+ return 0;
+}
+
+ssize_t
+readlink_w(const wchar_t *lnkname, wchar_t *buf, size_t len)
+{
+ int rc = 0;
+ char *mpb;
+ char *pb;
+ wchar_t *pname;
+ wchar_t *sname;
+ size_t noff;
+ size_t nlen;
+ size_t soff;
+ size_t slen;
+ int isabs = 0;
+ int isvol = 0;
+ ssize_t rv = (ssize_t)-1;
+ HANDLE sh;
+ DWORD dl;
+ PREPARSE_DATA_BUFFER repb;
+
+ sh = CreateFileW(lnkname,
+ GENERIC_READ,
+ FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE,
+ 0,
+ OPEN_EXISTING,
+ FILE_FLAG_OPEN_REPARSE_POINT | FILE_FLAG_BACKUP_SEMANTICS,
+ 0);
+ if (sh == INVALID_HANDLE_VALUE)
+ return rv;
+ mpb = calloc(1, MAXIMUM_REPARSE_DATA_BUFFER_SIZE + 64);
+ if (mpb == 0) {
+ CloseHandle(sh);
+ ACR_SET_OS_ERROR(ACR_ENOMEM);
+ return rv;
+ }
+ if (!DeviceIoControl(sh,
+ FSCTL_GET_REPARSE_POINT,
+ 0,
+ 0,
+ mpb,
+ MAXIMUM_REPARSE_DATA_BUFFER_SIZE,
+ &dl,
+ 0)) {
+ int es = ACR_GET_OS_ERROR();
+ CloseHandle(sh);
+ AcrFree(mpb);
+ ACR_SET_OS_ERROR(es);
+ return rv;
+ }
+ CloseHandle(sh);
+ repb = (PREPARSE_DATA_BUFFER)mpb;
+ switch (repb->ReparseTag) {
+ case IO_REPARSE_TAG_MOUNT_POINT:
+ isabs = 1;
+ pb = (char *)repb->MountPointReparseBuffer.PathBuffer;
+ nlen = repb->MountPointReparseBuffer.PrintNameLength / sizeof(WCHAR);
+ noff = repb->MountPointReparseBuffer.PrintNameOffset;
+ pname = (wchar_t *)(pb + noff);
+ slen = repb->MountPointReparseBuffer.SubstituteNameLength;
+ soff = repb->MountPointReparseBuffer.SubstituteNameOffset;
+ sname = (wchar_t *)(pb + soff);
+ break;
+ case IO_REPARSE_TAG_SYMLINK:
+ isabs = repb->SymbolicLinkReparseBuffer.Flags == 0 ? 1 : 0;
+ pb = (char *)repb->SymbolicLinkReparseBuffer.PathBuffer;
+ noff = repb->SymbolicLinkReparseBuffer.PrintNameOffset;
+ nlen = repb->SymbolicLinkReparseBuffer.PrintNameLength / sizeof(WCHAR);
+ pname = (wchar_t *)(pb + noff);
+ slen = repb->SymbolicLinkReparseBuffer.SubstituteNameLength / sizeof(WCHAR);
+ soff = repb->SymbolicLinkReparseBuffer.SubstituteNameOffset;
+ sname = (wchar_t *)(pb + soff);
+ break;
+ default:
+ rc = ACR_EBADF;
+ break;
+ }
+ if (rc == 0) {
+ sname[slen] = L'\0';
+#if 0
+ printf("\nSymlink : '%S'\n", lnkname);
+ printf("print name : '%S'\n", pname);
+ printf("substitute : '%S'\n", sname);
+#endif
+ if (isabs && slen > 4 && *sname == L'\\') {
+ if (wcsncmp(sname, L"\\??\\UNC\\", 8) == 0) {
+ sname += 6;
+ *sname = L'\\';
+ }
+ else if (wcsncmp(sname, L"\\??\\", 4) == 0 ||
+ wcsncmp(sname, L"\\\\?\\", 4) == 0) {
+ sname += 4;
+ if (wcsncmp(sname, L"Volume{", 7) == 0)
+ isvol = 1;
+ }
+ }
+ if (isvol == 0) {
+ rv = wcslcpy(buf, sname, len);
+ }
+ else {
+ /* XXX: What to do with Volume mount points ?
+ */
+ printf("volume : '%S'\n", sname);
+ rv = wcslcpy(buf, sname, len);
+ }
+#if 0
+ printf("resolved : '%S'\n", buf);
+ fflush(stdout);
+#endif
+ }
+ AcrFree(mpb);
+ ACR_SET_ERRNO_IF(rc);
+ return rv;
+}
Modified: commons/sandbox/runtime/trunk/src/main/native/os/win32/util.c
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/os/win32/util.c?rev=1098947&r1=1098946&r2=1098947&view=diff
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/os/win32/util.c (original)
+++ commons/sandbox/runtime/trunk/src/main/native/os/win32/util.c Tue May 3 07:26:38 2011
@@ -67,7 +67,7 @@ AcrGetLateDLL(SYSDLL_TOKEN libidx)
}
FARPROC
- AcrGetLateDLLAddress(SYSDLL_TOKEN libidx, const char *name, int undec)
+AcrGetLateDLLAddress(SYSDLL_TOKEN libidx, const char *name, int undec)
{
int rc = 0;
FARPROC fp = 0;
@@ -331,3 +331,164 @@ AcrNonblock(int sd, int on)
else
return 0;
}
+
+int
+AcrSocketPair(SOCKET *rd, SOCKET *wr, int nonblocking)
+{
+ FD_SET rs;
+ SOCKET ls;
+ struct timeval socktm;
+ struct sockaddr_in pa;
+ struct sockaddr_in la;
+ struct sockaddr_in ca;
+ int nrd;
+ int rv = 0;
+ int ll = ISIZEOF(la);
+ int cl = ISIZEOF(ca);
+ int bm = 1;
+ int uid[2];
+ int iid[2];
+
+ *rd = INVALID_SOCKET;
+ *wr = INVALID_SOCKET;
+
+ /* Create the unique socket identifier
+ * so that we know the connection originated
+ * from us.
+ */
+ uid[0] = GetCurrentProcessId() + GetCurrentThreadId();
+ uid[1] = InterlockedIncrement(&_pipe_id);
+ if ((ls = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) == INVALID_SOCKET) {
+ return ACR_GET_NETOS_ERROR();
+ }
+
+ pa.sin_family = AF_INET;
+ pa.sin_port = 0;
+ pa.sin_addr.s_addr = inet_addr("127.0.0.1");
+
+ if (bind(ls, (SOCKADDR *)&pa, ISIZEOF(pa)) == SOCKET_ERROR) {
+ rv = ACR_GET_NETOS_ERROR();
+ goto cleanup;
+ }
+ if (getsockname(ls, (SOCKADDR *)&la, &ll) == SOCKET_ERROR) {
+ rv = ACR_GET_NETOS_ERROR();
+ goto cleanup;
+ }
+ if (listen(ls, 1) == SOCKET_ERROR) {
+ rv = ACR_GET_NETOS_ERROR();
+ goto cleanup;
+ }
+ if ((*wr = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) == INVALID_SOCKET) {
+ rv = ACR_GET_NETOS_ERROR();
+ goto cleanup;
+ }
+ if (connect(*wr, (SOCKADDR *)&la, ISIZEOF(la)) == SOCKET_ERROR) {
+ rv = ACR_GET_NETOS_ERROR();
+ goto cleanup;
+ }
+ if (send(*wr, (char *)uid, ISIZEOF(uid), 0) != ISIZEOF(uid)) {
+ if ((rv = ACR_GET_NETOS_ERROR()) == 0) {
+ rv = ACR_EINCOMPLETE;
+ }
+ goto cleanup;
+ }
+ if (ioctlsocket(ls, FIONBIO, &bm) == SOCKET_ERROR) {
+ rv = ACR_GET_NETOS_ERROR();
+ goto cleanup;
+ }
+ for (;;) {
+ int ns;
+ /* Listening socket is nonblocking by now.
+ * The accept should create the socket
+ * immediatelly because we are connected already.
+ * However on buys systems this can take a while
+ * until winsock gets a chance to handle the events.
+ */
+ FD_ZERO(&rs);
+ FD_SET(ls, &rs);
+
+ socktm.tv_sec = 1;
+ socktm.tv_usec = 0;
+ if ((ns = select(0, &rs, NULL, NULL, &socktm)) == SOCKET_ERROR) {
+ /* Accept still not signaled */
+ Sleep(100);
+ continue;
+ }
+ if (ns == 0) {
+ /* No connections in the last second */
+ continue;
+ }
+ if ((*rd = accept(ls, (SOCKADDR *)&ca, &cl)) == INVALID_SOCKET) {
+ rv = ACR_GET_NETOS_ERROR();
+ goto cleanup;
+ }
+ /* Verify the connection by reading the send identification.
+ */
+ nrd = recv(*rd, (char *)iid, ISIZEOF(iid), 0);
+ if (nrd == ISIZEOF(iid)) {
+ if (memcmp(uid, iid, sizeof(uid)) == 0) {
+ /* Wow, we recived what we send.
+ */
+ break;
+ }
+ }
+ else if (nrd == SOCKET_ERROR) {
+ rv = ACR_GET_NETOS_ERROR();
+ goto cleanup;
+ }
+ closesocket(*rd);
+ }
+ if (nonblocking) {
+ /* Put the write side to the nonblocking mode
+ * if nonblocking mode was requested
+ */
+ bm = 1;
+ if (ioctlsocket(*wr, FIONBIO, &bm) == SOCKET_ERROR) {
+ rv = ACR_GET_NETOS_ERROR();
+ goto cleanup;
+ }
+ }
+ else {
+ /* Put the read side back to the blocking mode
+ */
+ bm = 0;
+ if (ioctlsocket(*rd, FIONBIO, &bm) == SOCKET_ERROR) {
+ rv = ACR_GET_NETOS_ERROR();
+ goto cleanup;
+ }
+ }
+ /* We don't need the listening socket any more
+ */
+ closesocket(ls);
+ return 0;
+
+cleanup:
+ /* Don't leak resources on failure
+ */
+ if (*rd != INVALID_SOCKET)
+ closesocket(*rd);
+ if (*wr != INVALID_SOCKET)
+ closesocket(*wr);
+
+ *rd = INVALID_SOCKET;
+ *wr = INVALID_SOCKET;
+ closesocket(ls);
+ return rv;
+}
+
+int
+AcrDrainSocket(SOCKET sd)
+{
+ char rb[512];
+ int nr = ISIZEOF(rb);
+ int rd;
+
+ while ((rd = recv(sd, rb, nr, 0)) != SOCKET_ERROR) {
+ if (rd != nr)
+ break;
+ }
+ if (rd == SOCKET_ERROR)
+ return ACR_GET_NETOS_ERROR();
+ else
+ return 0;
+}
Modified: commons/sandbox/runtime/trunk/src/main/native/os/win32/winapi.c
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/os/win32/winapi.c?rev=1098947&r1=1098946&r2=1098947&view=diff
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/os/win32/winapi.c (original)
+++ commons/sandbox/runtime/trunk/src/main/native/os/win32/winapi.c Tue May 3 07:26:38 2011
@@ -21,7 +21,7 @@
#include "acr/port.h"
#include "acr/clazz.h"
#include "acr/misc.h"
-#include "arch_defs.h"
+#include "arch_opts.h"
#include <sddl.h>