You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@apr.apache.org by Ioan Popescu <ip...@dataq.com> on 2007/10/09 17:50:58 UTC
[PATCH] libapr-1.2.11 on WinCE 5
Index: dso/win32/dso.c
===================================================================
--- dso/win32/dso.c (revision 574284)
+++ dso/win32/dso.c (working copy)
@@ -141,7 +141,7 @@
apr_wchar_t wsymname[256];
apr_status_t rv;
- rv = apr_conv_utf8_to_ucs2(wsymname, &wsymlen, symname, &symlen);
+ rv = apr_conv_utf8_to_ucs2(symname, &symlen, wsymname, &wsymlen);
if (rv != APR_SUCCESS) {
return rv;
}
Index: file_io/unix/tempdir.c
===================================================================
--- file_io/unix/tempdir.c (revision 574284)
+++ file_io/unix/tempdir.c (working copy)
@@ -17,8 +17,8 @@
#include "apr_file_io.h"
#include "apr_strings.h"
#include "apr_env.h"
+#include "apr_arch_file_io.h"
-
/* Try to open a temporary file in the temporary dir, write to it,
and then close it. */
static int test_tempdir(const char *temp_dir, apr_pool_t *p)
@@ -41,6 +41,7 @@
apr_pool_t *p)
{
apr_status_t apr_err;
+#ifndef _WIN32_WCE
const char *try_dirs[] = { "/tmp", "/usr/tmp", "/var/tmp" };
const char *try_envs[] = { "TMP", "TEMP", "TMPDIR" };
const char *dir;
@@ -126,5 +127,22 @@
end:
*temp_dir = apr_pstrdup(p, dir);
+#else
+ char *dir;
+ apr_wchar_t wdir[APR_PATH_MAX] = {0};
+ DWORD len;
+
+ len = GetTempPathW(APR_PATH_MAX, wdir);
+ if (!len)
+ return APR_EGENERAL;
+ /* Need to remove the trailing back-slash. */
+ wdir[len-1] = 0;
+ dir = apr_pcalloc(p, APR_PATH_MAX);
+ apr_err = unicode_to_utf8_path(dir, APR_PATH_MAX, wdir);
+ if (apr_err != APR_SUCCESS)
+ return apr_err;
+ if (test_tempdir(dir, p))
+ *temp_dir = dir;
+#endif
return APR_SUCCESS;
}
Index: file_io/win32/dir.c
===================================================================
--- file_io/win32/dir.c (revision 574284)
+++ file_io/win32/dir.c (working copy)
@@ -94,8 +94,14 @@
apr_pool_cleanup_register((*new)->pool, (void *)(*new), dir_cleanup,
apr_pool_cleanup_null);
+ /* CE fails apr_dir_read() on an *empty* directory
+ * (no "." nor ".." files).
+ */
rv = apr_dir_read(NULL, 0, *new);
- if (rv != APR_SUCCESS) {
+ if (rv == APR_FROM_OS_ERROR(ERROR_NO_MORE_FILES)) {
+ rv = APR_SUCCESS;
+ }
+ else if (rv != APR_SUCCESS) {
dir_cleanup(*new);
*new = NULL;
}
@@ -268,6 +274,12 @@
if (rv == APR_SUCCESS)
rv = apr_dir_read(NULL, 0, dir);
+ /* CE fails apr_dir_read() on an *empty* directory
+ * (no "." nor ".." files).
+ */
+ if (rv == APR_FROM_OS_ERROR(ERROR_NO_MORE_FILES)) {
+ rv = APR_SUCCESS;
+ }
return rv;
}
Index: file_io/win32/filepath.c
===================================================================
--- file_io/win32/filepath.c (revision 574284)
+++ file_io/win32/filepath.c (working copy)
@@ -265,7 +265,8 @@
return APR_EINCOMPLETE;
}
- /* Left with a path of '/', what drive are we asking about?
+#ifndef _WIN32_WCE
+ /* Left with a path of '/', what drive are we asking about?
*/
*inpath = testpath + 1;
newpath = apr_palloc(p, 2);
@@ -276,8 +277,37 @@
newpath[1] = '\0';
*rootpath = newpath;
return APR_EINCOMPLETE;
+#else
+ /* Evaluate path of '/' (root on CE). */
+ do {
+ apr_status_t rv;
+ /* Validate that '/' drive exists, test must be rooted
+ */
+ newpath = apr_palloc(p, 2);
+ newpath[0] = seperator[0];
+ newpath[1] = '\0';
+ if (flags & APR_FILEPATH_TRUENAME) {
+ rv = filepath_root_test(newpath, p);
+ if (rv)
+ return rv;
+ }
+
+ /* strip off remaining slashes that designate the root,
+ * give the caller back their original choice of slash
+ * unless this is NATIVED'ed
+ */
+ *inpath = testpath + 1;
+ while (**inpath == '/' || **inpath == '\\')
+ ++*inpath;
+ if (!(flags & APR_FILEPATH_NATIVE))
+ newpath[0] = testpath[0];
+ *rootpath = newpath;
+ return APR_SUCCESS;
+ } while(0);
+#endif
}
+#ifndef _WIN32_WCE
/* Evaluate path of 'd:[/]' */
if (IS_FNCHAR(*testpath) && testpath[1] == ':')
{
@@ -320,6 +350,7 @@
*rootpath = newpath;
return APR_SUCCESS;
}
+#endif
/* Nothing interesting */
return APR_ERELATIVE;
Index: file_io/win32/filestat.c
===================================================================
--- file_io/win32/filestat.c (revision 574284)
+++ file_io/win32/filestat.c (working copy)
@@ -15,15 +15,19 @@
*/
#include "apr.h"
+#include "apr_private.h"
+#if HAVE_ACLAPI
#include <aclapi.h>
-#include "apr_private.h"
+#endif
#include "apr_arch_file_io.h"
#include "apr_file_io.h"
#include "apr_general.h"
#include "apr_strings.h"
#include "apr_errno.h"
#include "apr_time.h"
+#ifndef _WIN32_WCE
#include <sys/stat.h>
+#endif
#include "apr_arch_atime.h"
#include "apr_arch_misc.h"
@@ -50,6 +54,7 @@
return APR_SUCCESS;
}
+#ifndef _WIN32_WCE
static apr_status_t free_localheap(void *heap) {
LocalFree(heap);
return APR_SUCCESS;
@@ -64,6 +69,7 @@
worldid = NULL;
}
}
+#endif
/* Left bit shifts from World scope to given scope */
typedef enum prot_scope_e {
@@ -88,6 +94,7 @@
return (prot << scope);
}
+#ifndef _WIN32_WCE
static void resolve_prot(apr_finfo_t *finfo, apr_int32_t wanted, PACL dacl)
{
TRUSTEE_W ident = {NULL, NO_MULTIPLE_TRUSTEE, TRUSTEE_IS_SID};
@@ -138,6 +145,7 @@
}
}
}
+#endif
static apr_status_t resolve_ident(apr_finfo_t *finfo, const char *fname,
apr_int32_t wanted, apr_pool_t *pool)
@@ -152,12 +160,12 @@
* We must open the file with READ_CONTROL if we plan to retrieve the
* user, group or permissions.
*/
-
- if ((rv = apr_file_open(&thefile, fname, APR_OPENINFO
- | ((wanted & APR_FINFO_LINK) ? APR_OPENLINK : 0)
- | ((wanted & (APR_FINFO_PROT | APR_FINFO_OWNER))
- ? APR_READCONTROL : 0),
- APR_OS_DEFAULT, pool)) == APR_SUCCESS) {
+ rv = apr_file_open(&thefile, fname, APR_OPENINFO
+ | ((wanted & APR_FINFO_LINK) ? APR_OPENLINK : 0)
+ | ((wanted & (APR_FINFO_PROT | APR_FINFO_OWNER))
+ ? APR_READCONTROL : 0),
+ APR_OS_DEFAULT, pool);
+ if (rv == APR_SUCCESS) {
rv = apr_file_info_get(finfo, wanted, thefile);
finfo->filehand = NULL;
apr_file_close(thefile);
@@ -167,9 +175,10 @@
/* We have a backup plan. Perhaps we couldn't grab READ_CONTROL?
* proceed without asking for that permission...
*/
- if ((rv = apr_file_open(&thefile, fname, APR_OPENINFO
- | ((wanted & APR_FINFO_LINK) ? APR_OPENLINK : 0),
- APR_OS_DEFAULT, pool)) == APR_SUCCESS) {
+ rv = apr_file_open(&thefile, fname, APR_OPENINFO
+ | ((wanted & APR_FINFO_LINK) ? APR_OPENLINK : 0),
+ APR_OS_DEFAULT, pool);
+ if (rv == APR_SUCCESS) {
rv = apr_file_info_get(finfo, wanted & ~(APR_FINFO_PROT
| APR_FINFO_OWNER),
thefile);
@@ -210,12 +219,15 @@
apr_status_t more_finfo(apr_finfo_t *finfo, const void *ufile,
apr_int32_t wanted, int whatfile)
{
+#ifndef _WIN32_WCE
PSID user = NULL, grp = NULL;
PACL dacl = NULL;
apr_status_t rv;
+#endif
if (apr_os_level < APR_WIN_NT)
guess_protection_bits(finfo);
+#ifndef _WIN32_WCE
else if (wanted & (APR_FINFO_PROT | APR_FINFO_OWNER))
{
/* On NT this request is incredibly expensive, but accurate.
@@ -288,6 +300,7 @@
else if (wanted & APR_FINFO_PROT)
guess_protection_bits(finfo);
}
+#endif
return ((wanted & ~finfo->valid) ? APR_INCOMPLETE : APR_SUCCESS);
}
@@ -389,6 +402,7 @@
if (finfo->filetype == APR_REG)
{
+#ifndef _WIN32_WCE
/* Go the extra mile to be -certain- that we have a real, regular
* file, since the attribute bits aren't a certain thing. Even
* though fillin should have hinted if we *must* do this, we
@@ -405,6 +419,7 @@
/* Otherwise leave the original conclusion alone
*/
}
+#endif
}
finfo->pool = thefile->pool;
@@ -481,7 +496,7 @@
* on a Junction always returns the junction, opening the target
* is the only way to resolve the target's attributes.
*/
- if ((ident_rv = resolve_ident(finfo, fname, wanted, pool))
+ if ((ident_rv = resolve_ident(finfo, fname, wanted, pool))
== APR_SUCCESS)
return ident_rv;
else if (ident_rv == APR_INCOMPLETE)
@@ -579,6 +594,7 @@
if (fillin_fileinfo(finfo, (WIN32_FILE_ATTRIBUTE_DATA *) &FileInfo,
0, wanted))
{
+#ifndef _WIN32_WCE
/* Go the extra mile to assure we have a file. WinNT/2000 seems
* to reliably translate char devices to the path '\\.\device'
* so go ask for the full path.
@@ -634,6 +650,9 @@
else {
finfo->valid &= ~APR_FINFO_TYPE;
}
+#else
+ finfo->valid &= ~APR_FINFO_TYPE;
+#endif
}
finfo->pool = pool;
}
@@ -646,7 +665,7 @@
if (wanted &= ~finfo->valid) {
/* Caller wants more than APR_FINFO_MIN | APR_FINFO_NAME */
#if APR_HAS_UNICODE_FS
- if (apr_os_level >= APR_WIN_NT)
+ if (apr_os_level > APR_WIN_UNICODE)
return more_finfo(finfo, wfname, wanted, MORE_OF_WFSPEC);
#endif
return more_finfo(finfo, fname, wanted, MORE_OF_FSPEC);
Index: file_io/win32/filesys.c
===================================================================
--- file_io/win32/filesys.c (revision 574284)
+++ file_io/win32/filesys.c (working copy)
@@ -66,6 +66,7 @@
apr_status_t filepath_root_test(char *path, apr_pool_t *p)
{
apr_status_t rv;
+#ifndef _WIN32_WCE
#if APR_HAS_UNICODE_FS
if (apr_os_level >= APR_WIN_NT)
{
@@ -81,6 +82,19 @@
if (rv == DRIVE_UNKNOWN || rv == DRIVE_NO_ROOT_DIR)
return APR_EBADPATH;
+#else
+ apr_wchar_t wpath[APR_PATH_MAX];
+ if (rv = utf8_to_unicode_path(wpath, sizeof(wpath)
+ / sizeof(apr_wchar_t), path))
+ return rv;
+ if (!CeGetCanonicalPathNameW(wpath, wpath, sizeof(wpath) / sizeof(apr_wchar_t), 0))
+ return apr_get_os_error();
+ /* CE doesn't have "drives"; instead, it uses unix-style paths with a root. Check
+ * for the root at the beginning of a canonical path.
+ */
+ if (wpath[0] != L'\\' && wpath[0] != L'/')
+ return APR_EBADPATH;
+#endif
return APR_SUCCESS;
}
@@ -92,10 +106,11 @@
#if APR_HAS_UNICODE_FS
IF_WIN_OS_IS_UNICODE
{
+ apr_wchar_t wpath[APR_PATH_MAX];
+ apr_status_t rv;
+#ifndef _WIN32_WCE
apr_wchar_t *ignored;
apr_wchar_t wdrive[8];
- apr_wchar_t wpath[APR_PATH_MAX];
- apr_status_t rv;
/* ???: This needs review, apparently "\\?\d:." returns "\\?\d:"
* as if that is useful for anything.
*/
@@ -103,6 +118,13 @@
wdrive[0] = (apr_wchar_t)(unsigned char)drive;
if (!GetFullPathNameW(wdrive, sizeof(wpath) / sizeof(apr_wchar_t), wpath, &ignored))
return apr_get_os_error();
+#else
+ apr_wchar_t wpath2[APR_PATH_MAX];
+ if ((rv = utf8_to_unicode_path(wpath2, sizeof(wpath2) / sizeof(apr_wchar_t), *rootpath)))
+ return rv;
+ if (!CeGetCanonicalPathNameW(wpath2, wpath, sizeof(wpath2) / sizeof(apr_wchar_t), 0))
+ return apr_get_os_error();
+#endif
if ((rv = unicode_to_utf8_path(path, sizeof(path), wpath)))
return rv;
}
@@ -136,7 +158,9 @@
#if APR_HAS_UNICODE_FS
IF_WIN_OS_IS_UNICODE
{
+#ifndef _WIN32_WCE
apr_wchar_t *ignored;
+#endif
apr_wchar_t wpath[APR_PATH_MAX];
apr_status_t rv;
apr_wchar_t wroot[APR_PATH_MAX];
@@ -146,8 +170,13 @@
if (rv = utf8_to_unicode_path(wroot, sizeof(wroot)
/ sizeof(apr_wchar_t), root))
return rv;
+#ifndef _WIN32_WCE
if (!GetFullPathNameW(wroot, sizeof(wpath) / sizeof(apr_wchar_t), wpath, &ignored))
return apr_get_os_error();
+#else
+ if (!CeGetCanonicalPathNameW(wroot, wpath, sizeof(wpath) / sizeof(apr_wchar_t), 0))
+ return apr_get_os_error();
+#endif
/* Borrow wroot as a char buffer (twice as big as necessary)
*/
@@ -173,6 +202,9 @@
APR_DECLARE(apr_status_t) apr_filepath_get(char **rootpath, apr_int32_t flags,
apr_pool_t *p)
{
+#ifdef _WIN32_WCE
+ return APR_ENOTIMPL;
+#else
char path[APR_PATH_MAX];
#if APR_HAS_UNICODE_FS
IF_WIN_OS_IS_UNICODE
@@ -200,12 +232,16 @@
}
*rootpath = apr_pstrdup(p, path);
return APR_SUCCESS;
+#endif
}
APR_DECLARE(apr_status_t) apr_filepath_set(const char *rootpath,
apr_pool_t *p)
{
+#ifdef _WIN32_WCE
+ return APR_ENOTIMPL;
+#else
#if APR_HAS_UNICODE_FS
IF_WIN_OS_IS_UNICODE
{
@@ -226,4 +262,5 @@
}
#endif
return APR_SUCCESS;
+#endif
}
Index: file_io/win32/flock.c
===================================================================
--- file_io/win32/flock.c (revision 574284)
+++ file_io/win32/flock.c (working copy)
@@ -18,23 +18,20 @@
APR_DECLARE(apr_status_t) apr_file_lock(apr_file_t *thefile, int type)
{
-#ifdef _WIN32_WCE
- /* The File locking is unsuported on WCE */
- return APR_ENOTIMPL;
-#else
const DWORD len = 0xffffffff;
DWORD flags;
flags = ((type & APR_FLOCK_NONBLOCK) ? LOCKFILE_FAIL_IMMEDIATELY : 0)
+ (((type & APR_FLOCK_TYPEMASK) == APR_FLOCK_SHARED)
? 0 : LOCKFILE_EXCLUSIVE_LOCK);
- if (apr_os_level >= APR_WIN_NT) {
+ if (apr_os_level >= APR_WIN_CE_5) {
/* Syntax is correct, len is passed for LengthLow and LengthHigh*/
OVERLAPPED offset;
memset (&offset, 0, sizeof(offset));
if (!LockFileEx(thefile->filehand, flags, 0, len, len, &offset))
return apr_get_os_error();
}
+#ifndef _WIN32_WCE
else {
/* On Win9x, LockFile() never blocks. Hack in a crufty poll.
*
@@ -57,30 +54,36 @@
return APR_FROM_OS_ERROR(err);
}
}
+#else
+ else {
+ return APR_ENOTIMPL;
+ }
+#endif
return APR_SUCCESS;
-#endif /* !defined(_WIN32_WCE) */
}
APR_DECLARE(apr_status_t) apr_file_unlock(apr_file_t *thefile)
{
-#ifdef _WIN32_WCE
- return APR_ENOTIMPL;
-#else
DWORD len = 0xffffffff;
- if (apr_os_level >= APR_WIN_NT) {
+ if (apr_os_level >= APR_WIN_CE_5) {
/* Syntax is correct, len is passed for LengthLow and LengthHigh*/
OVERLAPPED offset;
memset (&offset, 0, sizeof(offset));
if (!UnlockFileEx(thefile->filehand, 0, len, len, &offset))
return apr_get_os_error();
}
+#ifndef _WIN32_WCE
else {
if (!UnlockFile(thefile->filehand, 0, 0, len, 0))
return apr_get_os_error();
}
+#else
+ else {
+ return APR_ENOTIMPL;
+ }
+#endif
return APR_SUCCESS;
-#endif /* !defined(_WIN32_WCE) */
}
Index: file_io/win32/open.c
===================================================================
--- file_io/win32/open.c (revision 574284)
+++ file_io/win32/open.c (working copy)
@@ -226,11 +226,11 @@
apr_status_t flush_rv = APR_SUCCESS;
if (file->filehand != INVALID_HANDLE_VALUE) {
-
/* In order to avoid later segfaults with handle 'reuse',
* we must protect against the case that a dup2'ed handle
* is being closed, and invalidate the corresponding StdHandle
*/
+#ifndef _WIN32_WCE
if (file->filehand == GetStdHandle(STD_ERROR_HANDLE)) {
SetStdHandle(STD_ERROR_HANDLE, INVALID_HANDLE_VALUE);
}
@@ -240,12 +240,20 @@
if (file->filehand == GetStdHandle(STD_INPUT_HANDLE)) {
SetStdHandle(STD_INPUT_HANDLE, INVALID_HANDLE_VALUE);
}
-
+#endif
if (file->buffered) {
/* XXX: flush here is not mutex protected */
flush_rv = apr_file_flush((apr_file_t *)thefile);
}
+#ifdef _WIN32_WCE
+ if (file->filehand != STDIN_FILENO
+ && file->filehand != STDOUT_FILENO
+ && file->filehand != STDERR_FILENO) {
+ CloseHandle(file->filehand);
+ }
+#else
CloseHandle(file->filehand);
+#endif
file->filehand = INVALID_HANDLE_VALUE;
}
if (file->pOverlapped && file->pOverlapped->hEvent) {
@@ -272,8 +280,10 @@
if (flag & APR_WRITE) {
oflags |= GENERIC_WRITE;
}
- if (flag & APR_WRITEATTRS) {
- oflags |= FILE_WRITE_ATTRIBUTES;
+ if (apr_os_level < APR_WIN_CE_3 || apr_os_level >= APR_WIN_NT) {
+ if (flag & APR_WRITEATTRS) {
+ oflags |= FILE_WRITE_ATTRIBUTES;
+ }
}
if (apr_os_level >= APR_WIN_NT)
@@ -302,12 +312,14 @@
return APR_EACCES;
}
- if (flag & APR_DELONCLOSE) {
- attributes |= FILE_FLAG_DELETE_ON_CLOSE;
- }
+ if (apr_os_level < APR_WIN_CE_3 || apr_os_level >= APR_WIN_NT) {
+ if (flag & APR_DELONCLOSE) {
+ attributes |= FILE_FLAG_DELETE_ON_CLOSE;
+ }
- if (flag & APR_OPENLINK) {
- attributes |= FILE_FLAG_OPEN_REPARSE_POINT;
+ if (flag & APR_OPENLINK) {
+ attributes |= FILE_FLAG_OPEN_REPARSE_POINT;
+ }
}
/* Without READ or WRITE, we fail unless apr called apr_file_open
@@ -326,15 +338,19 @@
else {
return APR_EACCES;
}
- if (flag & APR_READCONTROL)
- oflags |= READ_CONTROL;
+ if (apr_os_level < APR_WIN_CE_3 || apr_os_level >= APR_WIN_NT) {
+ if (flag & APR_READCONTROL)
+ oflags |= READ_CONTROL;
+ }
}
- if (flag & APR_XTHREAD) {
- /* This win32 specific feature is required
- * to allow multiple threads to work with the file.
- */
- attributes |= FILE_FLAG_OVERLAPPED;
+ if (apr_os_level < APR_WIN_CE_3 || apr_os_level >= APR_WIN_NT) {
+ if (flag & APR_XTHREAD) {
+ /* This win32 specific feature is required
+ * to allow multiple threads to work with the file.
+ */
+ attributes |= FILE_FLAG_OVERLAPPED;
+ }
}
#if APR_HAS_UNICODE_FS
@@ -470,10 +486,28 @@
#ifndef _WIN32_WCE
if (MoveFileExW(wfrompath, wtopath, MOVEFILE_REPLACE_EXISTING |
MOVEFILE_COPY_ALLOWED))
+ return APR_SUCCESS;
#else
+ /* Windows CE does not support MoveFileEx, so we'll use
+ * the old MoveFile function. However, MoveFile requires that
+ * the new file not already exist...so we have to delete that
+ * file if it does. Perhaps we should back up the to-be-deleted
+ * file in case something happens?
+ */
+ do {
+ HANDLE handle = INVALID_HANDLE_VALUE;
+
+ if ((handle = CreateFileW(wtopath, GENERIC_WRITE, 0, 0,
+ OPEN_EXISTING, 0, 0 )) != INVALID_HANDLE_VALUE )
+ {
+ CloseHandle(handle);
+ if (!DeleteFileW(wtopath))
+ return apr_get_os_error();
+ }
+ } while (0);
if (MoveFileW(wfrompath, wtopath))
+ return APR_SUCCESS;
#endif
- return APR_SUCCESS;
#else
if (MoveFileEx(frompath, topath, MOVEFILE_REPLACE_EXISTING |
MOVEFILE_COPY_ALLOWED))
@@ -567,13 +601,14 @@
APR_DECLARE(apr_status_t) apr_file_open_stderr(apr_file_t **thefile, apr_pool_t *pool)
{
-#ifdef _WIN32_WCE
- return APR_ENOTIMPL;
-#else
apr_os_file_t file_handle;
apr_set_os_error(APR_SUCCESS);
+#ifndef _WIN32_WCE
file_handle = GetStdHandle(STD_ERROR_HANDLE);
+#else
+ file_handle = STDERR_FILENO;
+#endif
if (!file_handle || (file_handle == INVALID_HANDLE_VALUE)) {
apr_status_t rv = apr_get_os_error();
if (rv == APR_SUCCESS) {
@@ -583,18 +618,18 @@
}
return apr_os_file_put(thefile, &file_handle, 0, pool);
-#endif
}
APR_DECLARE(apr_status_t) apr_file_open_stdout(apr_file_t **thefile, apr_pool_t *pool)
{
-#ifdef _WIN32_WCE
- return APR_ENOTIMPL;
-#else
apr_os_file_t file_handle;
apr_set_os_error(APR_SUCCESS);
+#ifndef _WIN32_WCE
file_handle = GetStdHandle(STD_OUTPUT_HANDLE);
+#else
+ file_handle = STDOUT_FILENO;
+#endif
if (!file_handle || (file_handle == INVALID_HANDLE_VALUE)) {
apr_status_t rv = apr_get_os_error();
if (rv == APR_SUCCESS) {
@@ -604,18 +639,18 @@
}
return apr_os_file_put(thefile, &file_handle, 0, pool);
-#endif
}
APR_DECLARE(apr_status_t) apr_file_open_stdin(apr_file_t **thefile, apr_pool_t *pool)
{
-#ifdef _WIN32_WCE
- return APR_ENOTIMPL;
-#else
apr_os_file_t file_handle;
apr_set_os_error(APR_SUCCESS);
+#ifndef _WIN32_WCE
file_handle = GetStdHandle(STD_INPUT_HANDLE);
+#else
+ file_handle = STDIN_FILENO;
+#endif
if (!file_handle || (file_handle == INVALID_HANDLE_VALUE)) {
apr_status_t rv = apr_get_os_error();
if (rv == APR_SUCCESS) {
@@ -625,7 +660,6 @@
}
return apr_os_file_put(thefile, &file_handle, 0, pool);
-#endif
}
APR_POOL_IMPLEMENT_ACCESSOR(file);
Index: file_io/win32/readwrite.c
===================================================================
--- file_io/win32/readwrite.c (revision 574284)
+++ file_io/win32/readwrite.c (working copy)
@@ -40,6 +40,7 @@
* If data is available, go ahead and read it.
*/
if (file->pipe) {
+#ifndef _WIN32_WCE
DWORD bytes;
if (!PeekNamedPipe(file->filehand, NULL, 0, NULL, &bytes, NULL)) {
rv = apr_get_os_error();
@@ -58,6 +59,7 @@
len = bytes;
}
}
+#endif
}
else {
/* ToDo: Handle zero timeout non-blocking file i/o
@@ -72,13 +74,20 @@
file->pOverlapped->OffsetHigh = (DWORD)(file->filePtr >> 32);
}
+#ifndef _WIN32_WCE
rv = ReadFile(file->filehand, buf, len,
&bytesread, file->pOverlapped);
+#else
+ rv = ReadFile(file->filehand, buf, len,
+ &bytesread, NULL);
+#endif
*nbytes = bytesread;
if (!rv) {
rv = apr_get_os_error();
- if (rv == APR_FROM_OS_ERROR(ERROR_IO_PENDING)) {
+ if (0) {}
+#ifndef _WIN32_WCE
+ else if (rv == APR_FROM_OS_ERROR(ERROR_IO_PENDING)) {
/* Wait for the pending i/o */
if (file->timeout > 0) {
/* timeout in milliseconds... */
@@ -114,6 +123,7 @@
}
}
}
+#endif
else if (rv == APR_FROM_OS_ERROR(ERROR_BROKEN_PIPE)) {
/* Assume ERROR_BROKEN_PIPE signals an EOF reading from a pipe */
rv = APR_EOF;
@@ -144,6 +154,10 @@
return APR_SUCCESS;
}
+ /* CE doesn't support overlapped I/O, but "supports" thread-safe
+ * file access natively.
+ */
+#ifndef _WIN32_WCE
/* If the file is open for xthread support, allocate and
* initialize the overlapped and io completion event (hEvent).
* Threads should NOT share an apr_file_t or its hEvent.
@@ -157,6 +171,7 @@
return rv;
}
}
+#endif
/* Handle the ungetchar if there is one */
if (thefile->ungetchar != -1) {
@@ -235,6 +250,10 @@
apr_status_t rv;
DWORD bwrote;
+ /* CE doesn't support overlapped I/O, but "supports" thread-safe
+ * file access natively.
+ */
+#ifndef _WIN32_WCE
/* If the file is open for xthread support, allocate and
* initialize the overlapped and io completion event (hEvent).
* Threads should NOT share an apr_file_t or its hEvent.
@@ -248,6 +267,7 @@
return rv;
}
}
+#endif
if (thefile->buffered) {
char *pos = (char *)buf;
@@ -307,16 +327,37 @@
thefile->pOverlapped->Offset = (DWORD)thefile->filePtr;
thefile->pOverlapped->OffsetHigh = (DWORD)(thefile->filePtr >> 32);
}
+#ifndef _WIN32_WCE
rv = WriteFile(thefile->filehand, buf, (DWORD)*nbytes, &bwrote,
thefile->pOverlapped);
+#else
+ rv = WriteFile(thefile->filehand, buf, (DWORD)*nbytes, &bwrote,
+ NULL);
+ /* WriteFile() fails upon writing zero amount when "appending" to
+ * a file. Succeeds in writing zero amount in all other cases.
+ * Most likely has something to do with SetFilePointer() being
+ * called. Tried using SetEndOfFile(), but didn't help.
+ *
+ * Just pretend it succeeded in, essentially, not doing anything.
+ */
+ if (rv == 0 && *nbytes == 0) {
+ rv = 1;
+ bwrote = 0;
+ }
+#endif
if (thefile->append) {
apr_file_unlock(thefile);
apr_thread_mutex_unlock(thefile->mutex);
}
}
else {
+#ifndef _WIN32_WCE
rv = WriteFile(thefile->filehand, buf, (DWORD)*nbytes, &bwrote,
thefile->pOverlapped);
+#else
+ rv = WriteFile(thefile->filehand, buf, (DWORD)*nbytes, &bwrote,
+ NULL);
+#endif
}
if (rv) {
*nbytes = bwrote;
@@ -325,6 +366,7 @@
else {
(*nbytes) = 0;
rv = apr_get_os_error();
+#ifndef _WIN32_WCE
if (rv == APR_FROM_OS_ERROR(ERROR_IO_PENDING)) {
DWORD timeout_ms;
@@ -361,6 +403,7 @@
CancelIo(thefile->filehand);
}
}
+#endif
}
if (rv == APR_SUCCESS && thefile->pOverlapped && !thefile->pipe) {
thefile->filePtr += *nbytes;
@@ -492,6 +535,10 @@
bytesleft -= written;
buffer += written;
+ if (!FlushFileBuffers(thefile->filehand)) {
+ rc = apr_get_os_error();
+ break;
+ }
} while (bytesleft > 0);
if (rc == 0)
Index: file_io/win32/seek.c
===================================================================
--- file_io/win32/seek.c (revision 574284)
+++ file_io/win32/seek.c (working copy)
@@ -16,7 +16,6 @@
#include "win32/apr_arch_file_io.h"
#include "apr_file_io.h"
-#include <errno.h>
#include <string.h>
static apr_status_t setptr(apr_file_t *thefile, apr_off_t pos )
@@ -101,6 +100,10 @@
*offset = thefile->filePtr - thefile->dataRead + thefile->bufpos;
return rc;
}
+ /* CE doesn't support overlapped i/o, therefore, fallback to letting the
+ * OS handle the file pointer.
+ */
+#ifndef _WIN32_WCE
/* A file opened with APR_XTHREAD has been opened for overlapped i/o.
* APR must explicitly track the file pointer in this case.
*/
@@ -126,6 +129,7 @@
*offset = thefile->filePtr;
return rc;
}
+#endif
else {
DWORD howmove;
DWORD offlo = (DWORD)*offset;
Index: include/apr.hw
===================================================================
--- include/apr.hw (revision 574284)
+++ include/apr.hw (working copy)
@@ -74,12 +74,6 @@
#ifndef WIN32_LEAN_AND_MEAN
#define WIN32_LEAN_AND_MEAN
#endif
-#ifndef _WIN32_WINNT
-
-/* Restrict the server to a subset of Windows NT 4.0 header files by default
- */
-#define _WIN32_WINNT 0x0400
-#endif
#ifndef NOUSER
#define NOUSER
#endif
@@ -96,13 +90,9 @@
* winsock headers were excluded by WIN32_LEAN_AND_MEAN, so include them now
*/
#define SW_HIDE 0
-#ifndef _WIN32_WCE
#include <winsock2.h>
#include <mswsock.h>
#include <ws2tcpip.h>
-#else
-#include <winsock.h>
-#endif
#endif /* !_WINDOWS_ */
/**
@@ -217,7 +207,7 @@
#define APR_HAVE_IN_ADDR 1
#define APR_HAVE_INET_ADDR 1
#define APR_HAVE_INET_NETWORK 0
-#define APR_HAVE_IPV6 0
+#define APR_HAVE_IPV6 1
#define APR_HAVE_MEMMOVE 1
#define APR_HAVE_SETRLIMIT 0
#define APR_HAVE_SIGACTION 0
@@ -231,14 +221,12 @@
#define APR_HAVE_STRUCT_RLIMIT 0
#define APR_HAVE_UNION_SEMUN 0
#define APR_HAVE_SCTP 0
-
-#ifndef _WIN32_WCE
#define APR_HAVE_STRICMP 1
#define APR_HAVE_STRNICMP 1
+
+#ifndef _WIN32_WCE
#define APR_PROCATTR_USER_SET_REQUIRES_PASSWORD 1
#else
-#define APR_HAVE_STRICMP 0
-#define APR_HAVE_STRNICMP 0
#define APR_PROCATTR_USER_SET_REQUIRES_PASSWORD 0
#endif
@@ -503,7 +491,7 @@
#define STDOUT_FILENO 1
#define STDERR_FILENO 2
-#if APR_HAS_UNICODE_FS
+#if APR_HAS_UNICODE_FS && !defined(_WIN32_WCE)
/* An arbitrary size that is digestable. True max is a bit less than 32000 */
#define APR_PATH_MAX 8192
#else /* !APR_HAS_UNICODE_FS */
Index: include/apr_errno.h
===================================================================
--- include/apr_errno.h (revision 574284)
+++ include/apr_errno.h (working copy)
@@ -329,9 +329,13 @@
* APR was unable to open the dso object.
* For more information call apr_dso_error().
*/
-#if defined(WIN32)
+#if defined(_WIN32_WCE)
#define APR_STATUS_IS_EDSOOPEN(s) ((s) == APR_EDSOOPEN \
+ || APR_TO_OS_ERROR(s) == ERROR_INVALID_PARAMETER \
|| APR_TO_OS_ERROR(s) == ERROR_MOD_NOT_FOUND)
+#elif defined(WIN32)
+#define APR_STATUS_IS_EDSOOPEN(s) ((s) == APR_EDSOOPEN \
+ || APR_TO_OS_ERROR(s) == ERROR_MOD_NOT_FOUND)
#else
#define APR_STATUS_IS_EDSOOPEN(s) ((s) == APR_EDSOOPEN)
#endif
@@ -350,9 +354,13 @@
/** Could not find the requested symbol.
* For more information call apr_dso_error().
*/
-#if defined(WIN32)
+#if defined(_WIN32_WCE)
#define APR_STATUS_IS_ESYMNOTFOUND(s) ((s) == APR_ESYMNOTFOUND \
+ || APR_TO_OS_ERROR(s) == ERROR_INVALID_HANDLE \
|| APR_TO_OS_ERROR(s) == ERROR_PROC_NOT_FOUND)
+#elif defined(WIN32)
+#define APR_STATUS_IS_ESYMNOTFOUND(s) ((s) == APR_ESYMNOTFOUND \
+ || APR_TO_OS_ERROR(s) == ERROR_PROC_NOT_FOUND)
#else
#define APR_STATUS_IS_ESYMNOTFOUND(s) ((s) == APR_ESYMNOTFOUND)
#endif
Index: include/apr_general.h
===================================================================
--- include/apr_general.h (revision 574284)
+++ include/apr_general.h (working copy)
@@ -115,13 +115,21 @@
* have it
*/
#if (!APR_HAVE_STRCASECMP) && (APR_HAVE_STRICMP)
+#ifdef _WIN32_WCE
+#define strcasecmp(s1, s2) _stricmp(s1, s2)
+#else
#define strcasecmp(s1, s2) stricmp(s1, s2)
+#endif
#elif (!APR_HAVE_STRCASECMP)
int strcasecmp(const char *a, const char *b);
#endif
#if (!APR_HAVE_STRNCASECMP) && (APR_HAVE_STRNICMP)
+#ifdef _WIN32_WCE
+#define strncasecmp(s1, s2, n) _strnicmp(s1, s2, n)
+#else
#define strncasecmp(s1, s2, n) strnicmp(s1, s2, n)
+#endif
#elif (!APR_HAVE_STRNCASECMP)
int strncasecmp(const char *a, const char *b, size_t n);
#endif
Index: include/arch/win32/apr_arch_misc.h
===================================================================
--- include/arch/win32/apr_arch_misc.h (revision 574284)
+++ include/arch/win32/apr_arch_misc.h (working copy)
@@ -85,9 +85,12 @@
APR_WIN_UNICODE = 20, /* Prior versions support only narrow chars */
APR_WIN_CE_3 = 23, /* CE is an odd beast, not supporting */
- /* some pre-NT features, such as the */
- APR_WIN_NT = 30, /* narrow charset APIs (fooA fns), while */
- APR_WIN_NT_3_5 = 35, /* not supporting some NT-family features. */
+ APR_WIN_CE_4 = 24, /* some pre-NT features, such as the */
+ APR_WIN_CE_5 = 25, /* narrow charset APIs (fooA fns), while */
+ APR_WIN_CE_6 = 26, /* not supporting some NT-family features. */
+
+ APR_WIN_NT = 30,
+ APR_WIN_NT_3_5 = 35,
APR_WIN_NT_3_51 = 36,
APR_WIN_NT_4 = 40,
@@ -138,6 +141,8 @@
#define ELSE_WIN_OS_IS_ANSI
#endif /* WINNT */
+#if !defined(_WIN32_WCE)
+
typedef enum {
DLL_WINBASEAPI = 0, // kernel32 From WinBase.h
DLL_WINADVAPI = 1, // advapi32 From WinBase.h
@@ -159,8 +164,10 @@
{ if (!apr_winapi_pfn_##fn) \
apr_winapi_pfn_##fn = (apr_winapi_fpt_##fn) \
apr_load_dll_func(lib, #fn, ord); \
- return (*(apr_winapi_pfn_##fn)) names; }; \
+ return (*(apr_winapi_pfn_##fn)) names; };
+#endif /* !defined(_WIN32_WCE) */
+
/* Provide late bound declarations of every API function missing from
* one or more supported releases of the Win32 API
*
Index: include/arch/win32/apr_arch_networkio.h
===================================================================
--- include/arch/win32/apr_arch_networkio.h (revision 574284)
+++ include/arch/win32/apr_arch_networkio.h (working copy)
@@ -50,13 +50,17 @@
*/
OVERLAPPED *overlapped;
#endif
+#if _WIN32_WCE > 0x400
+ /* Needed in CE to implement blocking sockets that timeout. */
+ WSAOVERLAPPED *wsaoverlapped;
+#endif
sock_userdata_t *userdata;
/* if there is a timeout set, then this pollset is used */
apr_pollset_t *pollset;
};
-#ifdef _WIN32_WCE
+#if _WIN32_WCE < 0x500
#ifndef WSABUF
typedef struct _WSABUF {
u_long len; /* the length of the buffer */
Index: include/arch/win32/apr_private.h
===================================================================
--- include/arch/win32/apr_private.h (revision 574284)
+++ include/arch/win32/apr_private.h (working copy)
@@ -134,7 +134,9 @@
#if !APR_HAVE_ERRNO_H
APR_DECLARE_DATA int errno;
-#define ENOSPC 1
+#define ENOSPC 28
+#define EINVAL 22
+#define ERANGE 34
#endif
#if APR_HAVE_IPV6
@@ -161,6 +163,10 @@
#endif
#endif
+#if defined(_WIN32_WCE) && !defined(BUFSIZ)
+#define BUFSIZ 512
+#endif
+
/* used to check for DWORD overflow in 64bit compiles */
#define APR_DWORD_MAX 0xFFFFFFFFUL
Index: misc/win32/internal.c
===================================================================
--- misc/win32/internal.c (revision 574284)
+++ misc/win32/internal.c (working copy)
@@ -18,7 +18,9 @@
#include "apr_arch_misc.h"
#include "apr_arch_file_io.h"
+#ifndef _WIN32_WCE
#include <crtdbg.h>
+#endif
#include <assert.h>
/* This module is the source of -static- helper functions that are
@@ -52,8 +54,12 @@
;
}
+#ifndef _WIN32_WCE
newarr = _malloc_dbg((args + 1) * sizeof(char *),
_CRT_BLOCK, __FILE__, __LINE__);
+#else
+ newarr = malloc((args + 1) * sizeof(char *));
+#endif
for (arg = 0; arg < args; ++arg) {
newarr[arg] = (void*)(wcslen(arr[arg]) + 1);
@@ -66,8 +72,12 @@
* 4 ucs bytes will hold a wchar_t pair value (20 bits)
*/
elesize = elesize * 3 + 1;
+#ifndef _WIN32_WCE
ele = elements = _malloc_dbg(elesize * sizeof(char),
_CRT_BLOCK, __FILE__, __LINE__);
+#else
+ ele = elements = malloc(elesize * sizeof(char));
+#endif
for (arg = 0; arg < args; ++arg) {
apr_size_t len = (apr_size_t)newarr[arg];
@@ -87,8 +97,12 @@
/* Return to the free store if the heap realloc is the least bit optimized
*/
+#ifndef _WIN32_WCE
ele = _realloc_dbg(elements, ele - elements,
_CRT_BLOCK, __FILE__, __LINE__);
+#else
+ ele = realloc(elements, ele - elements);
+#endif
if (ele != elements) {
apr_size_t diff = ele - elements;
Index: misc/win32/misc.c
===================================================================
--- misc/win32/misc.c (revision 574284)
+++ misc/win32/misc.c (working copy)
@@ -16,7 +16,9 @@
#include "apr_private.h"
#include "apr_arch_misc.h"
+#ifndef _WIN32_WCE
#include "crtdbg.h"
+#endif
#include "apr_arch_file_io.h"
#include "assert.h"
#include "apr_lib.h"
@@ -31,8 +33,12 @@
oslev.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);
GetVersionEx(&oslev);
- if (oslev.dwPlatformId == VER_PLATFORM_WIN32_NT)
+ if (0)
{
+ }
+#ifdef WINNT
+ else if (oslev.dwPlatformId == VER_PLATFORM_WIN32_NT)
+ {
static unsigned int servpack = 0;
char *pservpack;
if (pservpack = oslev.szCSDVersion) {
@@ -96,7 +102,7 @@
apr_os_level = APR_WIN_XP;
}
}
-#ifndef WINNT
+#elif !defined(WINNT) && !defined(_WIN32_WCE)
else if (oslev.dwPlatformId == VER_PLATFORM_WIN32_WINDOWS) {
char *prevision;
if (prevision = oslev.szCSDVersion) {
@@ -122,16 +128,24 @@
apr_os_level = APR_WIN_ME;
}
}
-#endif
-#ifdef _WIN32_WCE
+#elif defined(_WIN32_WCE)
else if (oslev.dwPlatformId == VER_PLATFORM_WIN32_CE)
{
if (oslev.dwMajorVersion < 3) {
apr_os_level = APR_WIN_UNSUP;
}
- else {
+ else if (oslev.dwMajorVersion < 4) {
apr_os_level = APR_WIN_CE_3;
}
+ else if (oslev.dwMajorVersion < 5) {
+ apr_os_level = APR_WIN_CE_4;
+ }
+ else if (oslev.dwMajorVersion < 6) {
+ apr_os_level = APR_WIN_CE_5;
+ }
+ else {
+ apr_os_level = APR_WIN_CE_6;
+ }
}
#endif
else {
@@ -148,7 +162,7 @@
return APR_SUCCESS;
}
-
+#if !defined(_WIN32_WCE)
/* This is the helper code to resolve late bound entry points
* missing from one or more releases of the Win32 API
*/
@@ -170,6 +184,7 @@
else
return GetProcAddress(lateDllHandle[fnLib], fnName);
}
+#endif
/* Declared in include/arch/win32/apr_dbg_win32_handles.h
*/
@@ -196,11 +211,23 @@
(TlsSetValue)(tlsid, sbuf);
sbuf[1023] = '\0';
if (!fh) {
+/* CE only has Unicode API. */
+#ifdef _WIN32_WCE
+ wchar_t *wsbuf = malloc(1024);
+ wsbuf[1023] = L'\0';
+ (GetModuleFileNameW)(NULL, wsbuf, 250);
+ swprintf(wcschr(wsbuf, L'\0'), L".%d",
+ (GetCurrentProcessId)());
+ fh = (CreateFileW)(wsbuf, GENERIC_WRITE, 0, NULL,
+ CREATE_ALWAYS, 0, NULL);
+ free(wsbuf);
+#else
(GetModuleFileName)(NULL, sbuf, 250);
sprintf(strchr(sbuf, '\0'), ".%d",
(GetCurrentProcessId)());
fh = (CreateFile)(sbuf, GENERIC_WRITE, 0, NULL,
CREATE_ALWAYS, 0, NULL);
+#endif
(InitializeCriticalSection)(&cs);
}
}
Index: misc/win32/rand.c
===================================================================
--- misc/win32/rand.c (revision 574284)
+++ misc/win32/rand.c (working copy)
@@ -20,8 +20,10 @@
#include "apr_general.h"
#include "apr_portable.h"
#include "apr_arch_misc.h"
+#ifdef _WIN32_WCE
+#include <objbase.h>
+#endif
-
APR_DECLARE(apr_status_t) apr_generate_random_bytes(unsigned char * buf,
apr_size_t length)
{
@@ -32,7 +34,12 @@
* and will only work for Win2K and later.
*/
DWORD flags = CRYPT_VERIFYCONTEXT
+#ifndef _WIN32_WCE
| ((apr_os_level >= APR_WIN_2000) ? 0x40 : 0);
+#else
+ /* CRYPT_SILENT works on CE from the beginning of CryptAcquireContext(). */
+ | CRYPT_SILENT;
+#endif
if (!CryptAcquireContext(&hProv, NULL, NULL, PROV_RSA_FULL, flags)) {
return apr_get_os_error();
@@ -61,7 +68,11 @@
* Note that Win2000, XP and later no longer suffer from this problem,
* a scrambling fix is only needed for (apr_os_level < APR_WIN_2000)
*/
+#ifndef _WIN32_WCE
if (FAILED(UuidCreate((UUID *)uuid_data))) {
+#else
+ if (FAILED(CoCreateGuid((UUID *)uuid_data))) {
+#endif
return APR_EGENERAL;
}
return APR_SUCCESS;
Index: misc/win32/start.c
===================================================================
--- misc/win32/start.c (revision 574284)
+++ misc/win32/start.c (working copy)
@@ -24,7 +24,9 @@
#include "wchar.h"
#include "apr_arch_file_io.h" /* bring in unicode-ness */
#include "apr_arch_threadproc.h" /* bring in apr_threadproc_init */
+#ifndef _WIN32_WCE
#include "crtdbg.h"
+#endif
#include "assert.h"
/* This symbol is _private_, although it must be exported.
Index: mmap/win32/mmap.c
===================================================================
--- mmap/win32/mmap.c (revision 574284)
+++ mmap/win32/mmap.c (working copy)
@@ -75,6 +75,12 @@
DWORD mvaccess = 0;
DWORD offlo;
DWORD offhi;
+#ifdef _WIN32_WCE
+ apr_wchar_t wfname[APR_PATH_MAX];
+ apr_status_t rv;
+ DWORD oflags = 0;
+ HANDLE fhandle;
+#endif
if (size == 0)
return APR_EINVAL;
@@ -104,13 +110,40 @@
(*new)->pstart = (offset / memblock) * memblock;
(*new)->poffset = offset - (*new)->pstart;
(*new)->psize = (apr_size_t)((*new)->poffset) + size;
+#ifndef _WIN32_WCE
/* The size of the CreateFileMapping object is the current size
* of the size of the mmap object (e.g. file size), not the size
* of the mapped region!
*/
-
(*new)->mhandle = CreateFileMapping(file->filehand, NULL, fmaccess,
0, 0, NULL);
+#else
+ rv = utf8_to_unicode_path(wfname, APR_PATH_MAX, file->fname);
+ if (rv != APR_SUCCESS) {
+ *new = NULL;
+ return rv;
+ }
+ /* Need to use CreateFileForMapping() on CE to ensure MMap files work.
+ * CE ignores the sharemode parameter. Instead, it grants the same
+ * share mode as the desired access (open) flags.
+ */
+ if (flag & APR_MMAP_WRITE)
+ oflags = GENERIC_READ | GENERIC_WRITE;
+ else if (flag & APR_MMAP_READ)
+ oflags |= GENERIC_READ;
+ fhandle = CreateFileForMappingW(wfname, oflags, 0, NULL,
+ OPEN_EXISTING, 0, NULL);
+ if (!fhandle || fhandle == INVALID_HANDLE_VALUE) {
+ *new = NULL;
+ return apr_get_os_error();
+ }
+ /* The size of the CreateFileMapping object is the current size
+ * of the size of the mmap object (e.g. file size), not the size
+ * of the mapped region!
+ */
+ (*new)->mhandle = CreateFileMapping(fhandle, NULL, fmaccess,
+ 0, 0, NULL);
+#endif
if (!(*new)->mhandle || (*new)->mhandle == INVALID_HANDLE_VALUE)
{
*new = NULL;
Index: network_io/unix/multicast.c
===================================================================
--- network_io/unix/multicast.c (revision 574284)
+++ network_io/unix/multicast.c (working copy)
@@ -185,7 +185,11 @@
if (setsockopt(sock->socketdes, IPPROTO_IP, type,
(const void *) &mip4, sizeof(mip4)) == -1) {
+#ifndef _WIN32_WCE
rv = errno;
+#else
+ rv = apr_get_netos_error();
+#endif
}
}
#if APR_HAVE_IPV6 && defined(IPV6_JOIN_GROUP) && defined(IPV6_LEAVE_GROUP)
@@ -204,7 +208,11 @@
if (setsockopt(sock->socketdes, IPPROTO_IPV6, type,
&mip6, sizeof(mip6)) == -1) {
+#ifndef _WIN32_WCE
rv = errno;
+#else
+ rv = apr_get_netos_error();
+#endif
}
}
#endif
@@ -229,7 +237,11 @@
if (sock_is_ipv4(sock)) {
if (setsockopt(sock->socketdes, IPPROTO_IP, type,
(const void *) &value, sizeof(value)) == -1) {
+#ifndef _WIN32_WCE
rv = errno;
+#else
+ rv = apr_get_netos_error();
+#endif
}
}
#if APR_HAVE_IPV6
@@ -238,7 +250,11 @@
type = IPV6_MULTICAST_LOOP;
if (setsockopt(sock->socketdes, IPPROTO_IPV6, type,
&loopopt, sizeof(loopopt)) == -1) {
+#ifndef _WIN32_WCE
rv = errno;
+#else
+ rv = apr_get_netos_error();
+#endif
}
}
else if (sock_is_ipv6(sock)) {
@@ -251,7 +267,11 @@
if (setsockopt(sock->socketdes, IPPROTO_IPV6, type,
&value, sizeof(value)) == -1) {
+#ifndef _WIN32_WCE
rv = errno;
+#else
+ rv = apr_get_netos_error();
+#endif
}
}
#endif
@@ -316,7 +336,11 @@
if (setsockopt(sock->socketdes, IPPROTO_IP, IP_MULTICAST_IF,
(const void *) &iface->sa.sin.sin_addr,
sizeof(iface->sa.sin.sin_addr)) == -1) {
+#ifndef _WIN32_WCE
rv = errno;
+#else
+ rv = apr_get_netos_error();
+#endif
}
}
#if APR_HAVE_IPV6
@@ -324,7 +348,11 @@
unsigned int idx = find_if_index(iface);
if (setsockopt(sock->socketdes, IPPROTO_IPV6, IPV6_MULTICAST_IF,
&idx, sizeof(idx)) == -1) {
+#ifndef _WIN32_WCE
rv = errno;
+#else
+ rv = apr_get_netos_error();
+#endif
}
}
#endif
Index: network_io/unix/sockaddr.c
===================================================================
--- network_io/unix/sockaddr.c (revision 574284)
+++ network_io/unix/sockaddr.c (working copy)
@@ -58,16 +58,6 @@
#define GETHOSTBYNAME_BUFLEN 512
#endif
-#ifdef _WIN32_WCE
-/* XXX: BS solution. Need an HAVE_GETSERVBYNAME and actually
- * do something here, to provide the obvious proto mappings.
- */
-static void *getservbyname(const char *name, const char *proto)
-{
- return NULL;
-}
-#endif
-
static apr_status_t get_local_addr(apr_socket_t *sock)
{
sock->local_addr->salen = sizeof(sock->local_addr->sa);
@@ -706,7 +696,11 @@
sockaddr->sa.sin.sin_port = se->s_port;
return APR_SUCCESS;
}
+#ifndef _WIN32_WCE
return errno;
+#else
+ return apr_get_netos_error();
+#endif
}
#define V4MAPPED_EQUAL(a,b) \
Index: network_io/win32/sendrecv.c
===================================================================
--- network_io/win32/sendrecv.c (revision 574284)
+++ network_io/win32/sendrecv.c (working copy)
@@ -41,22 +41,52 @@
{
apr_ssize_t rv;
WSABUF wsaData;
- int lasterror;
DWORD dwBytes = 0;
+ apr_status_t wsarv;
wsaData.len = (u_long)*len;
wsaData.buf = (char*) buf;
#ifndef _WIN32_WCE
rv = WSASend(sock->socketdes, &wsaData, 1, &dwBytes, 0, NULL, NULL);
+#elif _WIN32_WCE > 0x400
+ rv = WSASend(sock->socketdes, &wsaData, 1, &dwBytes, 0,
+ sock->wsaoverlapped, NULL);
+ if (rv == SOCKET_ERROR) {
+ wsarv = apr_get_netos_error();
+ if (wsarv == APR_FROM_OS_ERROR(WSA_IO_PENDING)) {
+ rv = WSAWaitForMultipleEvents(1, &sock->wsaoverlapped->hEvent,
+ FALSE, sock->timeout_ms >= 0
+ ? sock->timeout_ms
+ : WSA_INFINITE, FALSE);
+ if (rv == WSA_WAIT_EVENT_0) {
+ if (WSAResetEvent(sock->wsaoverlapped->hEvent)) {
+ DWORD flags = 0;
+ if (!WSAGetOverlappedResult(sock->socketdes,
+ sock->wsaoverlapped, &dwBytes, FALSE, &flags)) {
+ rv = SOCKET_ERROR;
+ }
+ }
+ else {
+ rv = SOCKET_ERROR;
+ }
+ }
+ else {
+ apr_set_netos_error(rv);
+ rv = SOCKET_ERROR;
+ }
+ }
+ else {
+ apr_set_netos_error(wsarv);
+ }
+ }
#else
rv = send(sock->socketdes, wsaData.buf, wsaData.len, 0);
dwBytes = rv;
#endif
if (rv == SOCKET_ERROR) {
- lasterror = apr_get_netos_error();
*len = 0;
- return lasterror;
+ return apr_get_netos_error();
}
*len = dwBytes;
@@ -70,23 +100,53 @@
{
apr_ssize_t rv;
WSABUF wsaData;
- int lasterror;
DWORD dwBytes = 0;
DWORD flags = 0;
+ apr_status_t wsarv;
wsaData.len = (u_long)*len;
wsaData.buf = (char*) buf;
#ifndef _WIN32_WCE
rv = WSARecv(sock->socketdes, &wsaData, 1, &dwBytes, &flags, NULL, NULL);
+#elif _WIN32_WCE > 0x400
+ rv = WSARecv(sock->socketdes, &wsaData, 1, &dwBytes, &flags,
+ sock->wsaoverlapped, NULL);
+ if (rv == SOCKET_ERROR) {
+ wsarv = apr_get_netos_error();
+ if (wsarv == APR_FROM_OS_ERROR(WSA_IO_PENDING)) {
+ rv = WSAWaitForMultipleEvents(1, &sock->wsaoverlapped->hEvent,
+ FALSE, sock->timeout_ms >= 0
+ ? sock->timeout_ms
+ : WSA_INFINITE, FALSE);
+ if (rv == WSA_WAIT_EVENT_0) {
+ if (WSAResetEvent(sock->wsaoverlapped->hEvent)) {
+ flags = 0;
+ if (!WSAGetOverlappedResult(sock->socketdes,
+ sock->wsaoverlapped, &dwBytes, FALSE, &flags)) {
+ rv = SOCKET_ERROR;
+ }
+ }
+ else {
+ rv = SOCKET_ERROR;
+ }
+ }
+ else {
+ apr_set_netos_error(rv);
+ rv = SOCKET_ERROR;
+ }
+ }
+ else {
+ apr_set_netos_error(wsarv);
+ }
+ }
#else
rv = recv(sock->socketdes, wsaData.buf, wsaData.len, 0);
dwBytes = rv;
#endif
if (rv == SOCKET_ERROR) {
- lasterror = apr_get_netos_error();
*len = 0;
- return lasterror;
+ return apr_get_netos_error();
}
*len = dwBytes;
@@ -145,6 +205,34 @@
if (rv == SOCKET_ERROR) {
rc = apr_get_netos_error();
}
+#elif _WIN32_WCE > 0x400
+ rv = WSASend(sock->socketdes, pWsaBuf, nvec, &dwBytes, 0,
+ sock->wsaoverlapped, NULL);
+ rc = rv;
+ if (rv == SOCKET_ERROR) {
+ rc = apr_get_netos_error();
+ if (rc == APR_FROM_OS_ERROR(WSA_IO_PENDING)) {
+ rv = WSAWaitForMultipleEvents(1, &sock->wsaoverlapped->hEvent,
+ FALSE, sock->timeout_ms >= 0
+ ? sock->timeout_ms
+ : WSA_INFINITE, FALSE);
+ if (rv == WSA_WAIT_EVENT_0) {
+ if (WSAResetEvent(sock->wsaoverlapped->hEvent)) {
+ DWORD flags = 0;
+ if (!WSAGetOverlappedResult(sock->socketdes,
+ sock->wsaoverlapped, &dwBytes, FALSE, &flags)) {
+ rc = apr_get_netos_error();
+ }
+ }
+ else {
+ rc = apr_get_netos_error();
+ }
+ }
+ else {
+ rc = rv;
+ }
+ }
+ }
#else
for (i = 0; i < nvec; i++) {
rv = send(sock->socketdes, pWsaBuf[i].buf, pWsaBuf[i].len, 0);
@@ -169,10 +257,52 @@
apr_size_t *len)
{
apr_ssize_t rv;
+#if _WIN32_WCE > 0x400
+ apr_status_t wsarv;
+ WSABUF wsaData;
+ DWORD dwBytes = 0;
+ wsaData.len = (u_long)*len;
+ wsaData.buf = (char*) buf;
+
+ rv = WSASendTo(sock->socketdes, &wsaData, 1, &dwBytes, flags,
+ (const struct sockaddr*)&where->sa, where->salen,
+ sock->wsaoverlapped, NULL);
+ if (rv == SOCKET_ERROR) {
+ wsarv = apr_get_netos_error();
+ if (wsarv == APR_FROM_OS_ERROR(WSA_IO_PENDING)) {
+ rv = WSAWaitForMultipleEvents(1, &sock->wsaoverlapped->hEvent,
+ FALSE, sock->timeout_ms >= 0
+ ? sock->timeout_ms
+ : WSA_INFINITE, FALSE);
+ if (rv == WSA_WAIT_EVENT_0) {
+ if (WSAResetEvent(sock->wsaoverlapped->hEvent)) {
+ if (WSAGetOverlappedResult(sock->socketdes,
+ sock->wsaoverlapped, &dwBytes, FALSE, &flags)) {
+ rv = dwBytes;
+ }
+ else {
+ rv = SOCKET_ERROR;
+ }
+ }
+ else {
+ rv = SOCKET_ERROR;
+ }
+ }
+ else {
+ apr_set_netos_error(rv);
+ rv = SOCKET_ERROR;
+ }
+ }
+ else {
+ apr_set_netos_error(wsarv);
+ }
+ }
+#else
rv = sendto(sock->socketdes, buf, (int)*len, flags,
(const struct sockaddr*)&where->sa,
where->salen);
+#endif
if (rv == SOCKET_ERROR) {
*len = 0;
return apr_get_netos_error();
@@ -189,9 +319,54 @@
char *buf, apr_size_t *len)
{
apr_ssize_t rv;
+#if _WIN32_WCE > 0x400
+ apr_status_t wsarv;
+ WSABUF wsaData;
+ DWORD dwBytes = 0;
+ wsaData.len = (u_long)*len;
+ wsaData.buf = (char*) buf;
+
+ rv = WSARecvFrom(sock->socketdes, &wsaData, 1, &dwBytes, &flags,
+ (struct sockaddr*)&from->sa, &from->salen,
+ sock->wsaoverlapped, NULL);
+ if (rv == SOCKET_ERROR) {
+ wsarv = apr_get_netos_error();
+ if (wsarv == APR_FROM_OS_ERROR(WSA_IO_PENDING)) {
+ rv = WSAWaitForMultipleEvents(1, &sock->wsaoverlapped->hEvent,
+ FALSE, sock->timeout_ms >= 0
+ ? sock->timeout_ms
+ : WSA_INFINITE, FALSE);
+ if (rv == WSA_WAIT_EVENT_0) {
+ if (WSAResetEvent(sock->wsaoverlapped->hEvent)) {
+ if (WSAGetOverlappedResult(sock->socketdes,
+ sock->wsaoverlapped, &dwBytes, FALSE, &flags)) {
+ rv = dwBytes;
+ }
+ else {
+ rv = SOCKET_ERROR;
+ }
+ }
+ else {
+ rv = SOCKET_ERROR;
+ }
+ }
+ else {
+ apr_set_netos_error(rv);
+ rv = SOCKET_ERROR;
+ }
+ }
+ else {
+ apr_set_netos_error(wsarv);
+ }
+ }
+ else {
+ rv = dwBytes;
+ }
+#else
rv = recvfrom(sock->socketdes, buf, (int)*len, flags,
(struct sockaddr*)&from->sa, &from->salen);
+#endif
if (rv == SOCKET_ERROR) {
(*len) = 0;
return apr_get_netos_error();
Index: network_io/win32/sockets.c
===================================================================
--- network_io/win32/sockets.c (revision 574284)
+++ network_io/win32/sockets.c (working copy)
@@ -42,6 +42,12 @@
thesocket->overlapped = NULL;
}
#endif
+#if _WIN32_WCE > 0x400
+ if (thesocket->wsaoverlapped) {
+ WSACloseEvent(thesocket->wsaoverlapped->hEvent);
+ thesocket->wsaoverlapped = NULL;
+ }
+#endif
return APR_SUCCESS;
}
@@ -92,11 +98,23 @@
}
alloc_socket(new, cont);
+#if _WIN32_WCE > 0x400
+ (*new)->wsaoverlapped = (WSAOVERLAPPED *)apr_pcalloc((*new)->pool,
+ sizeof(WSAOVERLAPPED));
+ (*new)->wsaoverlapped->hEvent = WSACreateEvent();
+ if ((*new)->wsaoverlapped->hEvent == NULL) {
+ return apr_get_netos_error();
+ }
+ /* Need to use overlapped sockets to support blocking with timeout. */
+ (*new)->socketdes = WSASocket(family, type, protocol, NULL,
+ 0, WSA_FLAG_OVERLAPPED);
+#else
/* For right now, we are not using socket groups. We may later.
* No flags to use when creating a socket, so use 0 for that parameter as well.
*/
(*new)->socketdes = socket(family, type, protocol);
+#endif
#if APR_HAVE_IPV6
if ((*new)->socketdes == INVALID_SOCKET && downgrade) {
family = AF_INET;
@@ -177,12 +195,10 @@
return APR_BADARG;
}
#endif
- if (shutdown(thesocket->socketdes, winhow) == 0) {
- return APR_SUCCESS;
- }
- else {
+ if (shutdown(thesocket->socketdes, winhow) != 0) {
return apr_get_netos_error();
}
+ return APR_SUCCESS;
}
APR_DECLARE(apr_status_t) apr_socket_close(apr_socket_t *thesocket)
@@ -230,12 +246,24 @@
/* Don't allocate the memory until after we call accept. This allows
us to work with nonblocking sockets. */
+#if _WIN32_WCE > 0x400
+ s = WSAAccept(sock->socketdes, (struct sockaddr *)&sa, &salen, NULL, 0);
+#else
s = accept(sock->socketdes, (struct sockaddr *)&sa, &salen);
+#endif
if (s == INVALID_SOCKET) {
return apr_get_netos_error();
}
alloc_socket(new, p);
+#if _WIN32_WCE > 0x400
+ (*new)->wsaoverlapped = (WSAOVERLAPPED *)apr_pcalloc((*new)->pool,
+ sizeof(WSAOVERLAPPED));
+ (*new)->wsaoverlapped->hEvent = WSACreateEvent();
+ if ((*new)->wsaoverlapped->hEvent == NULL) {
+ return apr_get_netos_error();
+ }
+#endif
set_socket_vars(*new, sock->local_addr->sa.sin.sin_family, SOCK_STREAM,
sock->protocol);
@@ -306,9 +334,13 @@
if ((sock->socketdes == INVALID_SOCKET) || (!sock->local_addr)) {
return APR_ENOTSOCK;
}
-
+#if _WIN32_WCE > 0x400
+ if (WSAConnect(sock->socketdes, (const struct sockaddr *)&sa->sa.sin,
+ sa->salen, NULL, NULL, NULL, NULL) == SOCKET_ERROR) {
+#else
if (connect(sock->socketdes, (const struct sockaddr *)&sa->sa.sin,
sa->salen) == SOCKET_ERROR) {
+#endif
int rc;
struct timeval tv, *tvptr;
fd_set wfdset, efdset;
Index: network_io/win32/sockopt.c
===================================================================
--- network_io/win32/sockopt.c (revision 574284)
+++ network_io/win32/sockopt.c (working copy)
@@ -24,7 +24,12 @@
{
u_long zero = 0;
+#if _WIN32_WCE > 0x400
+ if (WSAIoctl(sd, FIONBIO, &zero, sizeof(zero),
+ NULL, 0, NULL, NULL, NULL) == SOCKET_ERROR) {
+#else
if (ioctlsocket(sd, FIONBIO, &zero) == SOCKET_ERROR) {
+#endif
return apr_get_netos_error();
}
return APR_SUCCESS;
@@ -34,7 +39,12 @@
{
u_long one = 1;
+#if _WIN32_WCE > 0x400
+ if (WSAIoctl(sd, FIONBIO, &one, sizeof(one),
+ NULL, 0, NULL, NULL, NULL) == SOCKET_ERROR) {
+#else
if (ioctlsocket(sd, FIONBIO, &one) == SOCKET_ERROR) {
+#endif
return apr_get_netos_error();
}
return APR_SUCCESS;
@@ -63,12 +73,14 @@
{
/* Win32 timeouts are in msec, represented as int */
sock->timeout_ms = (int)apr_time_as_msec(t);
+#ifndef _WIN32_WCE
setsockopt(sock->socketdes, SOL_SOCKET, SO_RCVTIMEO,
(char *) &sock->timeout_ms,
sizeof(sock->timeout_ms));
setsockopt(sock->socketdes, SOL_SOCKET, SO_SNDTIMEO,
(char *) &sock->timeout_ms,
sizeof(sock->timeout_ms));
+#endif
}
}
else if (t < 0) {
@@ -76,10 +88,12 @@
/* Set the socket to blocking with infinite timeouts */
if ((stat = soblock(sock->socketdes)) != APR_SUCCESS)
return stat;
+#ifndef _WIN32_WCE
setsockopt(sock->socketdes, SOL_SOCKET, SO_RCVTIMEO,
(char *) &zero, sizeof(zero));
setsockopt(sock->socketdes, SOL_SOCKET, SO_SNDTIMEO,
(char *) &zero, sizeof(zero));
+#endif
}
sock->timeout = t;
return APR_SUCCESS;
Index: shmem/win32/shm.c
===================================================================
--- shmem/win32/shm.c (revision 574284)
+++ shmem/win32/shm.c (working copy)
@@ -86,12 +86,11 @@
if (!file) {
/* Do Anonymous, which must be passed as a duplicated handle */
-#ifndef _WIN32_WCE
hFile = INVALID_HANDLE_VALUE;
-#endif
mapkey = NULL;
}
else {
+#ifndef _WIN32_WCE
/* Do file backed, which is not an inherited handle
* While we could open APR_EXCL, it doesn't seem that Unix
* ever did. Ignore that error here, but fail later when
@@ -105,7 +104,24 @@
return rv;
}
rv = apr_file_trunc(f, size);
+#else
+ apr_wchar_t wfname[APR_PATH_MAX];
+ rv = utf8_to_unicode_path(wfname, APR_PATH_MAX, file);
+ if (rv != APR_SUCCESS) {
+ return rv;
+ }
+ /* Need to use CreateFileForMapping() on CE to ensure MMap files
+ * work. CE ignores the sharemode parameter. Instead, it grants
+ * the same share mode as the desired access (open) flags.
+ */
+ hFile = CreateFileForMappingW(wfname, GENERIC_READ
+ | GENERIC_WRITE, 0, NULL, OPEN_ALWAYS, 0, NULL);
+ if (!hFile || hFile == INVALID_HANDLE_VALUE) {
+ return apr_get_os_error();
+ }
+#endif
+
/* res_name_from_filename turns file into a pseudo-name
* without slashes or backslashes, and prepends the \global
* prefix on Win2K and later
@@ -129,9 +145,11 @@
#endif
err = apr_get_os_error();
+#ifndef _WIN32_WCE
if (file) {
apr_file_close(f);
}
+#endif
if (hMap && APR_STATUS_IS_EEXIST(err)) {
CloseHandle(hMap);
Index: strings/apr_strings.c
===================================================================
--- strings/apr_strings.c (revision 574284)
+++ strings/apr_strings.c (working copy)
@@ -239,7 +239,13 @@
{
errno = 0;
*offset = APR_OFF_T_STRFN(nptr, endptr, base);
+#ifndef _WIN32_WCE
return APR_FROM_OS_ERROR(errno);
+#else
+ if (*offset == LONG_MAX || *offset == LONG_MIN)
+ return APR_FROM_OS_ERROR(ERROR_ARITHMETIC_OVERFLOW);
+ return APR_SUCCESS;
+#endif
}
APR_DECLARE(apr_int64_t) apr_strtoi64(const char *nptr, char **endptr, int base)
Index: threadproc/win32/proc.c
===================================================================
--- threadproc/win32/proc.c (revision 574284)
+++ threadproc/win32/proc.c (working copy)
@@ -613,9 +613,12 @@
* complete file path. That is; "c:\bin\aprtest.exe"
* would succeed, but "c:\bin\aprtest" or "aprtest.exe"
* can fail.
+ * Apparently, CE 5 already passes the program name as the first
+ * argument.
*/
- cmdline = apr_pstrcat(pool, argv0, cmdline, NULL);
-
+ if (apr_os_level < APR_WIN_CE_5) {
+ cmdline = apr_pstrcat(pool, argv0, cmdline, NULL);
+ }
if (attr->cmdtype == APR_PROGRAM_PATH) {
progname = NULL;
}
@@ -647,7 +650,8 @@
{
apr_wchar_t *pNext;
pEnvBlock = (char *)apr_palloc(pool, iEnvBlockLen * 2);
- dwCreationFlags |= CREATE_UNICODE_ENVIRONMENT;
+ if (apr_os_level >= APR_WIN_NT)
+ dwCreationFlags |= CREATE_UNICODE_ENVIRONMENT;
i = 0;
pNext = (apr_wchar_t*)pEnvBlock;
Index: threadproc/win32/thread.c
===================================================================
--- threadproc/win32/thread.c (revision 574284)
+++ threadproc/win32/thread.c (working copy)
@@ -114,10 +114,12 @@
return APR_FROM_OS_ERROR(_doserrno);
}
#else
- if ((handle = CreateThread(NULL,
+ if ((handle = CreateThread(NULL,
attr && attr->stacksize > 0 ? attr->stacksize : 0,
(unsigned int (APR_THREAD_FUNC *)(void *))dummy_worker,
- (*new), 0, &temp)) == 0) {
+ (*new), attr && attr->stacksize > 0
+ ? STACK_SIZE_PARAM_IS_A_RESERVATION : 0,
+ &temp)) == 0) {
return apr_get_os_error();
}
#endif
Index: time/win32/time.c
===================================================================
--- time/win32/time.c (revision 574284)
+++ time/win32/time.c (working copy)
@@ -91,9 +91,7 @@
#ifndef _WIN32_WCE
GetSystemTimeAsFileTime(&time);
#else
- SYSTEMTIME st;
- GetSystemTime(&st);
- SystemTimeToFileTime(&st, &time);
+ GetCurrentFT(&time);
#endif
FileTimeToAprTime(&aprtime, &time);
return aprtime;