Vendor import apr-1.5.1

This commit is contained in:
Peter Wemm 2014-05-27 07:00:33 +00:00
parent f2be5817e9
commit bc9ddba9ef
Notes: svn2git 2020-12-20 02:59:44 +00:00
svn path=/vendor/apr/dist/; revision=266733
svn path=/vendor/apr/apr-1.5.1/; revision=266734; tag=vendor/apr/apr-1.5.1
71 changed files with 13960 additions and 5489 deletions

289
CHANGES
View File

@ -1,235 +1,124 @@
-*- coding: utf-8 -*-
Changes for APR 1.4.8
Changes for APR 1.5.1
*) Fix compiltation with FreeBSD on ARM. [Olli Hauer <ohauer gmx.de>]
*) apr_os_proc_mutex_get() on Unix: Avoid segfault for cross-
process pthread mutexes. [Yann Ylavic <ylavic.dev gmail.com>]
*) Fix 1.4.7 regression in apr_mcast_hops() and apr_mcast_loopback()
for AF_INET (IPv4) sockets on most Unix platforms. [Joe Orton]
*) When using shmget-based shared memory, the ID used for ftok is
now an APR hash of the filename instead of the constant '1'.
We do this to help avoid collisions. PR 53996 [Jim Jagielski]
*) Fix the return value of apr_threadattr_detach_get() on some
platforms like OS X and Solaris. [Rainer Jung, <dusanv gmail com>]
*) apr_socket_atreadeof(): Fix breakage on OS X. [Jim Jagielski]
Changes for APR 1.4.7
*) Fix POSIX shared memory (shm_open) use for named shared memory.
Includes adding '--enable-posix-shm' to force POSIX shm if
available, and OS X compatibility. PR 55928.
[Jozef Hatala <jh-asf skrt org>, Jim Jagielski]
*) Fix apr_sockaddr_info_get() not returning an error in some cases.
PR 54779. [Jan Kaluža <jkaluza redhat com>]
*) Fix race condition when calling apr_dir_make_recursive from
multiple threads on Windows.
[Bert Huijben]
*) Fix amd64 assembler version of apr_atomic_xchgptr(). PR 51851. [Mattias
Engdegård <mattiase acm org>]
*) Fix apr_escape.c compilation errors on EBCDIC platforms.
[Eric Covener]
*) Fix PPC atomics to work with gcc 4.0. PR 54840. [Mattias Engdegård
<mattiase acm org>]
*) FreeBSD 10: Correct a regression in 1.5.0 which affected non-
blocking sockets in some applications, including httpd. [Jeff
Trawick]
*) configure: Fix detection of O_NONBLOCK inheritance on busy
systems. [Rainer Jung]
*) Windows cmake build: Fix incorrect installation of some .pdb
files. Fix incorrect use of some logic intended for Windows 9x,
including legacy filesystem interfaces and dynamic loading of
some Windows APIs. [Jeff Trawick]
*) Remove unused code, fix strict C compliance bug in SHA-256
implementation. [Jan Kaluza <jkaluza redhat.com>]
*) Fix apr_ipsubnet_test() false positives when comparing IPv4
subnet representation against an IPv6 address. PR 54047. [Joe Orton]
*) apr_socket_accept_filter: Return success when trying to again set
the filter to the same value as before, avoiding an unhelpful
APR_EINVAL. PR 37863. [Jeff Trawick]
*) configure: Fix Linux 3.x detection. PR 54001. [Gilles Espinasse
<g esp free fr>]
*) apr_time_exp_*() on Windows: Fix error in the tm_yday field of
apr_time_exp_t for times within leap years. PR 53175.
*) apr_skiplist: Add compatibility with C++ applications.
[Jeff Trawick]
*) Improve platform detection by updating config.guess and config.sub.
[Rainer Jung]
*) Correct a regression in 1.5.0 which affected out-of-tree
builds on Unix. [Rainer Jung]
*) Add support for OSX Mountain Lion (10.8) [Jim Jagielski]
*) Improve platform detection for bundled expat by updating
config.guess and config.sub. [Rainer Jung]
*) Add various gcc function attributes. [Stefan Fritsch]
Changes for APR 1.5.0
*) Fix some problems in apr_sockaddr_info_get() when trying to resolve
the loopback addresses of a protocol family that is not otherwise
configured on the system. PR 52709. [Nirgal Vourgère
<jmv_deb nirgal com>, Stefan Fritsch]
*) Fix Linux kernel version check to recognize more versions,
including versions 3.10 and later. PR 55690. [Joe Orton,
Arfrever Frehtes Taifersar Arahesis <arfrever.fta gmail.com>]
*) Fix file not being unlocked if truncate call on a file fails.
[Mladen Turk]
*) Add apr_sockaddr_is_wildcard() to check if a socket address
refers to the wildcard address for the protocol family (e.g.,
0.0.0.0/INADDR_ANY for IPv4). [Jeff Trawick]
*) apr_mcast_hops: Fix EINVAL for IPv6 sockets caused by using byte
instead integer for setsockopt. [Mladen Turk]
*) apr_file_dup2() on Windows: Fix debug RTL assertion when
attempting to _commit(stdout) or _commit(stderr). [Mike Rumph
<mike.rumph oracle.com>]
*) Windows: Fix compile-time checks for 64-bit builds, resolving a
crash in httpd's mod_rewrite. PR 49155. [<anindyabaruah gmail.com>]
*) apr_socket_connect() on Windows: Handle WSAEISCONN. PR 48736.
[<inoue ariel-networks.com>, Jeff Trawick]
Changes for APR 1.4.6
*) z/OS: threadsafe apr_pollset_poll support for sockets [Greg Ames]
*) Flush write buffer before truncate call on a file.
[Mladen Turk]
*) Windows: Don't obtain a mutex for buffered file I/O unless the
file was opened with the APR_FOPEN_XTHREAD flag. [Ivan Zhakov
<ivan visualsvn.com>]
*) Randomise hashes by providing a seed.
Assigned CVE-2012-0840, oCERT-2011-003, but not known to be exploitable.
[Bojan Smojver, Branko Čibej, Ruediger Pluem et al.]
*) apr_random: Prevent segfault if pool used to initialize apr_random is
destroyed before forking. [Stefan Fritsch]
*) testrand: Improve child randomness test case. [Rainer Jung]
*) apr_proc_fork, apr_random_after_fork: disambiguate what happens to the
proc structure passed in, and ensure that the pid is set correctly in
a newly created child; note that merely mixing a PID into the random
seed of a new child doesn't markedly increase entropy. [Sander Temme]
*) apr_file_open: Avoid fcntl() calls if support for O_CLOEXEC works.
PR 48557. [Mike Frysinger <vapier gentoo org>]
*) apr_dir_make_recursive: Fix race condition that could lead to EEXIST
being returned. PR 51254. [William Lee <william lee rainstor com>,
Wim Lewis <wiml omnigroup com>]
*) configure: Fix APR_RESTORE_THE_ENVIRONMENT if the original variable was
a single space. PR 50334. [Nathan Phillip Brink <binki gentoo org>]
*) apr_proc_create: Don't close any of the new stdin/stdout/stderr in the
child if it already has the correct FD. PR 51995.
[Dan Ports <drkp csail mit edu>]
*) Fix flag character '#' in combination with format character 'x' in
apr snprintf implementations. [Rainer Jung]
*) Improve platform detection by updating config.guess and config.sub.
[Rainer Jung]
*) Add libtool2 files to extraclean make target. [Rainer Jung]
*) Don't overwrite our config.guess and config.sub
when running buildconf. [Rainer Jung]
*) Silence autoconf 2.68 warnings. [Rainer Jung]
Changes for APR 1.4.5
*) Security: CVE-2011-1928
apr_fnmatch(): Fix high CPU loop. [William Rowe]
*) Fix top_builddir in installed apr_rules.mk. [Bojan Smojver]
Changes for APR 1.4.4
*) Windows: Fix command-line builds. [William Rowe]
Changes for APR 1.4.3
*) Security: CVE-2011-0419
Reimplement apr_fnmatch() from scratch using a non-recursive
algorithm; now has improved compliance with the fnmatch() spec.
[William Rowe]
*) Fix environment-related crash using some non-standard builds on
Windows 7/Server 2008. [Steve Hay <SteveHay planit.com>]
*) poll, pollset, pollcb on Windows: Handle calls with no file/socket
descriptors. PR 49882. [Stefan Ruppert <sr myarm.com>, Jeff Trawick]
*) Fix APR_IPV6_V6ONLY issues on Windows related to run-time behavior
on Windows older than Vista and SDK/MinGW levels without IPV6_V6ONLY.
PR 45321. [Sob <sob hisoftware.cz>]
*) Fix address handling when accepting an AF_INET socket from a socket
bound as AF_INET6. PR 49678. [Joe Orton]
*) Fix error return values from apr_sockaddr_info_get() on Windows for
IPv6 builds. [Ivan Zhakov <ivan visualsvn.com>]
*) Add new experimental configure option --enable-allocator-uses-mmap to
use mmap instead of malloc in apr_allocator_alloc(). This greatly reduces
memory fragmentation with malloc implementations (e.g. glibc) that
don't handle allocationss of a page-size-multiples in an efficient way.
It also makes apr_allocator_max_free_set() actually have some effect
on such platforms. [Stefan Fritsch]
*) configure: Support 64 and 32 bit universal builds for Darwin/
OS X 10.6+. [Jim Jagielski]
*) apr_sockaddr_info_get() on AIX: Fix a problem which could set
the port field in the native socket address to 1 when 0 was
specified. PR 46964. [Jeff Trawick]
*) configure: Make definition of apr_ino_t independent of
_FILE_OFFSET_BITS even on platforms where ino_t is 'unsigned int'.
[Stefan Fritsch]
*) apr_ring: Workaround for aliasing problem that causes gcc 4.5 to
miscompile some brigade related code. PR 50190. [Stefan Fritsch]
*) apr_file_flush_locked(): Handle short writes. [Stefan Fritsch]
*) apr_pollset_create_ex(): Trap errors from pollset providers.
PR 49094. [Sami Tolvanen <sami.tolvanen mywot.com>]
*) apr_pollset_create*(): Fix memory lifetime problem with the wakeup
pipe when the pollset was created with APR_POLLSET_NOCOPY.
[Neil Conway <nrc cs.berkeley.edu>]
*) Fix detection of some Linux variants when configure is built with
recent GNU tools. [Eric Covener]
*) Avoid a redundant fcntl() call in apr_file_open() where O_CLOEXEC
is supported. PR 46297. [Joe Orton]
*) Improve platform detection by updating config.guess and config.sub.
[Rainer Jung]
Changes for APR 1.4.2
*) Undo a crash-bug introduced in 1.4.1 affecting some applications of
the apr hash and table structures, reported to affect Subversion
by Bert Huijben <bert qqmail.nl>. [Graham Leggett]
Changes for APR 1.4.1
*) Win32: Properly handle the ERROR_DIRECTORY system error code.
[Brane Čibej]
Changes for APR 1.4.0
*) Windows: Default build configurations assume NT or higher at run-time.
*) Add apr_global_mutex_lockfile() for retrieving the file, if any,
associated with the mutex. Add apr_global_mutex_name() for retrieving
the name of the lock mechanism used by the underlying proc mutex.
*) Windows: Create named shared memory segments under the "Local"
namespace if the caller is unprivileged, fixing an inability of
unprivileged callers to use apr_shm_create() with named shared
memory segments under recent Windows. As before, shared memory
segments are created under the "Global" namespace for privileged
callers. Add apr_shm_create_ex() and apr_shm_attach_ex(), which
provide the ability to override the normal namespace selection.
[Jeff Trawick]
*) Add apr_socket_atreadeof to determine whether the receive part of the
socket has been closed by the peer.
[Ruediger Pluem, Mladen Turk, Joe Orton]
*) Update compile settings for MINT OS. PR 47181. [Alan Hourihane
<alanh fairlite.co.uk>]
*) Make apr_pollset and apr_pollcb implementations using providers.
Added apr_pollset_create_ex and apr_pollcb_create_ex that allows
choosing non-default providers.
[Mladen Turk]
*) Files and pipes on Windows: Don't create an unused pollset when
files and pipes are opened. [Mladen Turk]
*) Win32: Use WSAPoll as default pollset method if supported and found
inside winsock dll. [Mladen Turk]
*) apr_socket_timeout_set() on Windows: If the socket was in a non-
blocking state before, disable that setting so that timeouts work.
[Jeff Trawick]
*) apr_temp_dir_get() now checks the TMPDIR environment variable first,
instead of third. [Jim Jagielski]
*) File info APIs: Fix calculation of atime and mtime on AIX. PR 51146.
[Ruediger Pluem]
*) Add apr_file_sync() and apr_file_datasync() calls. [Bojan Smojver]
*) Add the apr_escape interface. [Graham Leggett]
*) apr_pollset_wakeup() on Windows: Fix core caused by closing the
file_socket_pipe with standard file_close.
[Arsen Chaloyan, Mladen Turk]
*) Cygwin build fixes. PRs 51016 and 55586. [Carlo Bramini
<carlo.bramix libero.it>]
*) Introduce apr_hash_do() for iterating over a hash table. [Mladen Turk]
*) Add apr_skiplist family. [Jim Jagielski]
*) Make sure WIN32 behaves the same as posix for file-backed shared memory
by removing the file on cleanup/remove. [Mladen Turk]
*) Add experimental cmake-based build system for Windows. Refer to
README.cmake for more information. [Jeff Trawick, Tom Donovan]
*) Introduce apr_pollset_wakeup() for interrupting the blocking
apr_pollset_poll() call. [Mladen Turk]
*) Add the apr_table_getm() call, which transparently handles the
merging of keys with multiple values. [Graham Leggett]
*) Add apr_file_link() function. PR 44841. [Mark Heily <mark heily.com>]
*) Add apr_hash_this_key(), apr_hash_this_key_len(), and
apr_hash_this_val() for easier access to those attributes from
a hash iterator. [Hyrum K. Wright <hyrum_wright mail.utexas.edu>]
*) MinGW/MSYS: Support shared builds of APR, other general improvements
to support of this toolchain. PR 46175. [Carlo Bramini
<carlo.bramix libero.it>]
*) Improve platform detection by updating config.guess and config.sub.
[Rainer Jung]
*) apr_socket_opt_set: Add support for APR_SO_BROADCAST. PR 46389.
[Armin Müller <mueller itestra com>]
*) Enable platform specific support for the opening of a file or
pipe in non-blocking mode through the APR_FOPEN_NONBLOCK flag.
[Graham Leggett]
Changes for APR 1.4.x and later:
*) http://svn.apache.org/viewvc/apr/apr/branches/1.4.x/CHANGES?view=markup
Changes for APR 1.3.x and later:

434
CMakeLists.txt Normal file
View File

@ -0,0 +1,434 @@
# Licensed to the Apache Software Foundation (ASF) under one or more
# contributor license agreements. See the NOTICE file distributed with
# this work for additional information regarding copyright ownership.
# The ASF licenses this file to You under the Apache License, Version 2.0
# (the "License"); you may not use this file except in compliance with
# the License. You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
# Read README.cmake before using this.
PROJECT(APR C)
CMAKE_MINIMUM_REQUIRED(VERSION 2.8)
OPTION(APR_INSTALL_PRIVATE_H "Install selected private .h files (for httpd)" OFF)
OPTION(APR_HAVE_IPV6 "IPv6 support" ON)
OPTION(INSTALL_PDB "Install .pdb files (if generated)" ON)
OPTION(APR_BUILD_TESTAPR "Build the test suite" OFF)
OPTION(TEST_STATIC_LIBS "Test programs use APR static libraries instead of shared libraries?" OFF)
SET(MIN_WINDOWS_VER "Vista"
CACHE STRING "Minimum Windows version")
# create 1-or-0 representation of feature tests for apr.h
SET(apr_have_ipv6_10 0)
IF(APR_HAVE_IPV6)
SET(apr_have_ipv6_10 1)
ENDIF()
IF("${MIN_WINDOWS_VER}" STREQUAL "")
SET(win32_winnt_str "0x0600")
ELSEIF(${MIN_WINDOWS_VER} STREQUAL "Vista")
SET(win32_winnt_str "0x0600")
ELSEIF(${MIN_WINDOWS_VER} STREQUAL "Windows7")
SET(win32_winnt_str "0x0601")
ELSE()
SET(win32_winnt_str ${MIN_WINDOWS_VER})
ENDIF()
CONFIGURE_FILE(include/apr.hwc
${PROJECT_BINARY_DIR}/apr.h)
ADD_EXECUTABLE(gen_test_char tools/gen_test_char.c)
GET_TARGET_PROPERTY(GEN_TEST_CHAR_EXE gen_test_char LOCATION)
ADD_CUSTOM_COMMAND(
COMMENT "Generating character tables, apr_escape_test_char.h, for current locale"
DEPENDS gen_test_char
COMMAND ${GEN_TEST_CHAR_EXE} > ${PROJECT_BINARY_DIR}/apr_escape_test_char.h
OUTPUT ${PROJECT_BINARY_DIR}/apr_escape_test_char.h
)
ADD_CUSTOM_TARGET(
test_char_header ALL
DEPENDS ${PROJECT_BINARY_DIR}/apr_escape_test_char.h
)
# Generated .h files are stored in PROJECT_BINARY_DIR, not the
# source tree.
#
# BROKEN: not searching PROJECT_BINARY_DIR first, so you have to
# manually delete apr.h in PROJECT_SOURCE_DIR/include if
# you've generated apr.h before using a different build
SET(APR_INCLUDE_DIRECTORIES
${PROJECT_BINARY_DIR}
${CMAKE_CURRENT_SOURCE_DIR}/include
${CMAKE_CURRENT_SOURCE_DIR}/include/arch/win32
${CMAKE_CURRENT_SOURCE_DIR}/include/arch/unix
${CMAKE_CURRENT_SOURCE_DIR}/include/private
)
SET(APR_SYSTEM_LIBS
ws2_32
mswsock
rpcrt4
)
INCLUDE_DIRECTORIES(${APR_INCLUDE_DIRECTORIES})
SET(APR_PUBLIC_HEADERS_STATIC
include/apr_allocator.h
include/apr_atomic.h
include/apr_dso.h
include/apr_env.h
include/apr_errno.h
include/apr_escape.h
include/apr_file_info.h
include/apr_file_io.h
include/apr_fnmatch.h
include/apr_general.h
include/apr_getopt.h
include/apr_global_mutex.h
include/apr_hash.h
include/apr_inherit.h
include/apr_lib.h
include/apr_mmap.h
include/apr_network_io.h
include/apr_poll.h
include/apr_pools.h
include/apr_portable.h
include/apr_proc_mutex.h
include/apr_random.h
include/apr_ring.h
include/apr_shm.h
include/apr_signal.h
include/apr_skiplist.h
include/apr_strings.h
include/apr_support.h
include/apr_tables.h
include/apr_thread_cond.h
include/apr_thread_mutex.h
include/apr_thread_proc.h
include/apr_thread_rwlock.h
include/apr_time.h
include/apr_user.h
include/apr_version.h
include/apr_want.h
)
SET(APR_PUBLIC_HEADERS_GENERATED
${PROJECT_BINARY_DIR}/apr.h
)
SET(APR_SOURCES
atomic/win32/apr_atomic.c
dso/win32/dso.c
encoding/apr_escape.c
file_io/unix/copy.c
file_io/unix/fileacc.c
file_io/unix/filepath_util.c
file_io/unix/fullrw.c
file_io/unix/mktemp.c
file_io/unix/tempdir.c
file_io/win32/buffer.c
file_io/win32/dir.c
file_io/win32/filedup.c
file_io/win32/filepath.c
file_io/win32/filestat.c
file_io/win32/filesys.c
file_io/win32/flock.c
file_io/win32/open.c
file_io/win32/pipe.c
file_io/win32/readwrite.c
file_io/win32/seek.c
locks/win32/proc_mutex.c
locks/win32/thread_cond.c
locks/win32/thread_mutex.c
locks/win32/thread_rwlock.c
memory/unix/apr_pools.c
misc/unix/errorcodes.c
misc/unix/getopt.c
misc/unix/otherchild.c
misc/unix/version.c
misc/win32/charset.c
misc/win32/env.c
misc/win32/internal.c
misc/win32/misc.c
misc/win32/rand.c
misc/win32/start.c
misc/win32/utf8.c
mmap/unix/common.c
mmap/win32/mmap.c
network_io/unix/inet_ntop.c
network_io/unix/inet_pton.c
network_io/unix/multicast.c
network_io/unix/sockaddr.c
network_io/unix/socket_util.c
network_io/win32/sendrecv.c
network_io/win32/sockets.c
network_io/win32/sockopt.c
passwd/apr_getpass.c
poll/unix/poll.c
poll/unix/pollcb.c
poll/unix/pollset.c
poll/unix/select.c
random/unix/apr_random.c
random/unix/sha2.c
random/unix/sha2_glue.c
shmem/win32/shm.c
strings/apr_cpystrn.c
strings/apr_fnmatch.c
strings/apr_snprintf.c
strings/apr_strings.c
strings/apr_strnatcmp.c
strings/apr_strtok.c
tables/apr_hash.c
tables/apr_skiplist.c
tables/apr_tables.c
threadproc/win32/proc.c
threadproc/win32/signals.c
threadproc/win32/thread.c
threadproc/win32/threadpriv.c
time/win32/time.c
time/win32/timestr.c
user/win32/groupinfo.c
user/win32/userinfo.c
)
SET(APR_TEST_SOURCES
test/abts.c
test/testargs.c
test/testatomic.c
test/testcond.c
test/testdir.c
test/testdso.c
test/testdup.c
test/testenv.c
test/testescape.c
test/testfile.c
test/testfilecopy.c
test/testfileinfo.c
test/testflock.c
test/testfmt.c
test/testfnmatch.c
test/testglobalmutex.c
test/testhash.c
test/testipsub.c
test/testlfs.c
test/testlock.c
test/testmmap.c
test/testnames.c
test/testoc.c
test/testpath.c
test/testpipe.c
test/testpoll.c
test/testpools.c
test/testproc.c
test/testprocmutex.c
test/testrand.c
test/testshm.c
test/testsleep.c
test/testsock.c
test/testsockets.c
test/testsockopt.c
test/teststr.c
test/teststrnatcmp.c
test/testtable.c
test/testtemp.c
test/testthread.c
test/testtime.c
test/testud.c
test/testuser.c
test/testutil.c
test/testvsn.c
)
SET(install_targets)
SET(install_bin_pdb)
SET(install_lib_pdb)
# libapr-1 is shared, apr-1 is static
ADD_LIBRARY(libapr-1 SHARED ${APR_SOURCES} ${APR_PUBLIC_HEADERS_GENERATED} libapr.rc)
SET(install_targets ${install_targets} libapr-1)
SET(install_bin_pdb ${install_bin_pdb} ${PROJECT_BINARY_DIR}/libapr-1.pdb)
TARGET_LINK_LIBRARIES(libapr-1 ${APR_SYSTEM_LIBS})
SET_TARGET_PROPERTIES(libapr-1 PROPERTIES COMPILE_DEFINITIONS "APR_DECLARE_EXPORT;WINNT")
ADD_DEPENDENCIES(libapr-1 test_char_header)
ADD_LIBRARY(apr-1 STATIC ${APR_SOURCES} ${APR_PUBLIC_HEADERS_GENERATED})
SET(install_targets ${install_targets} apr-1)
SET(install_lib_pdb ${install_lib_pdb} ${PROJECT_BINARY_DIR}/apr-1.pdb)
TARGET_LINK_LIBRARIES(apr-1 ${APR_SYSTEM_LIBS})
SET_TARGET_PROPERTIES(apr-1 PROPERTIES COMPILE_DEFINITIONS "APR_DECLARE_STATIC;WINNT")
ADD_DEPENDENCIES(apr-1 test_char_header)
# libaprapp-1 and aprapp-1 are static
ADD_LIBRARY(libaprapp-1 STATIC misc/win32/apr_app.c misc/win32/internal.c ${APR_PUBLIC_HEADERS_GENERATED})
SET(install_targets ${install_targets} libaprapp-1)
SET(install_lib_pdb ${install_lib_pdb} ${PROJECT_BINARY_DIR}/libaprapp-1.pdb)
SET_TARGET_PROPERTIES(libaprapp-1 PROPERTIES COMPILE_DEFINITIONS "APR_APP;WINNT")
ADD_LIBRARY(aprapp-1 STATIC misc/win32/apr_app.c misc/win32/internal.c ${APR_PUBLIC_HEADERS_GENERATED})
SET(install_targets ${install_targets} aprapp-1)
SET(install_lib_pdb ${install_lib_pdb} ${PROJECT_BINARY_DIR}/aprapp-1.pdb)
SET_TARGET_PROPERTIES(aprapp-1 PROPERTIES COMPILE_DEFINITIONS "APR_DECLARE_STATIC;APR_APP;WINNT")
IF(APR_BUILD_TESTAPR)
ENABLE_TESTING()
# Create a "check" target that displays test program output to the console.
ADD_CUSTOM_TARGET(check COMMAND ${CMAKE_CTEST_COMMAND} --verbose)
# copy data files to build directory so that we can run programs from there
EXECUTE_PROCESS(COMMAND ${CMAKE_COMMAND} -E make_directory
${PROJECT_BINARY_DIR}/data)
EXECUTE_PROCESS(COMMAND ${CMAKE_COMMAND} -E copy_if_different
${PROJECT_SOURCE_DIR}/test/data/file_datafile.txt
${PROJECT_BINARY_DIR}/data/file_datafile.txt)
EXECUTE_PROCESS(COMMAND ${CMAKE_COMMAND} -E copy_if_different
${PROJECT_SOURCE_DIR}/test/data/mmap_datafile.txt
${PROJECT_BINARY_DIR}/data/mmap_datafile.txt)
IF(TEST_STATIC_LIBS)
SET(whichapr apr-1)
SET(whichaprapp aprapp-1)
SET(apiflag -DAPR_DECLARE_STATIC)
ELSE()
SET(whichapr libapr-1)
SET(whichaprapp libaprapp-1)
SET(apiflag)
ENDIF()
ADD_EXECUTABLE(testapp test/testapp.c)
TARGET_LINK_LIBRARIES(testapp ${whichapr} ${whichaprapp} ${APR_SYSTEM_LIBS})
SET_TARGET_PROPERTIES(testapp PROPERTIES LINK_FLAGS /entry:wmainCRTStartup)
IF(apiflag)
SET_TARGET_PROPERTIES(testapp PROPERTIES COMPILE_FLAGS ${apiflag})
ENDIF()
ADD_TEST(NAME testapp COMMAND testapp)
ADD_EXECUTABLE(testall ${APR_TEST_SOURCES})
TARGET_LINK_LIBRARIES(testall ${whichapr} ${APR_SYSTEM_LIBS})
IF(apiflag)
SET_TARGET_PROPERTIES(testall PROPERTIES COMPILE_FLAGS ${apiflag})
ENDIF()
ADD_TEST(NAME testall COMMAND testall)
ADD_LIBRARY(mod_test MODULE test/mod_test.c)
TARGET_LINK_LIBRARIES(mod_test ${whichapr} ${APR_SYSTEM_LIBS})
SET_PROPERTY(TARGET mod_test APPEND PROPERTY LINK_FLAGS /export:print_hello)
# nasty work-around for difficulties adding more than one additional flag
# (they get joined in a bad way behind the scenes)
GET_PROPERTY(link_flags TARGET mod_test PROPERTY LINK_FLAGS)
SET(link_flags "${link_flags} /export:count_reps")
SET_TARGET_PROPERTIES(mod_test PROPERTIES LINK_FLAGS ${link_flags})
IF(apiflag)
SET_TARGET_PROPERTIES(mod_test PROPERTIES COMPILE_FLAGS ${apiflag})
ENDIF()
# Build all the single-source executable files with no special build
# requirements.
SET(single_source_programs
test/echod.c
test/sendfile.c
test/sockperf.c
test/testlockperf.c
test/testmutexscope.c
test/globalmutexchild.c
test/occhild.c
test/proc_child.c
test/readchild.c
test/sockchild.c
test/testshmproducer.c
test/testshmconsumer.c
test/tryread.c
test/internal/testucs.c
)
FOREACH(sourcefile ${single_source_programs})
STRING(REGEX REPLACE ".*/([^\\]+)\\.c" "\\1" proggie ${sourcefile})
ADD_EXECUTABLE(${proggie} ${sourcefile})
TARGET_LINK_LIBRARIES(${proggie} ${whichapr} ${APR_SYSTEM_LIBS})
IF(apiflag)
SET_TARGET_PROPERTIES(${proggie} PROPERTIES COMPILE_FLAGS ${apiflag})
ENDIF()
ENDFOREACH()
# Add tests for programs that run by themselves with no arguments.
SET(simple_tests
testmutexscope
testucs
)
FOREACH(simple ${simple_tests})
ADD_TEST(NAME ${simple} COMMAND ${simple})
ENDFOREACH()
# testlockperf takes forever on Windows with default counter limit
ADD_TEST(NAME testlockperf COMMAND testlockperf -c 50000)
# sendfile runs multiple times with different parameters.
FOREACH(sendfile_mode blocking nonblocking timeout)
ADD_TEST(NAME sendfile-${sendfile_mode} COMMAND sendfile client ${sendfile_mode} startserver)
ENDFOREACH()
# No test is added for echod+sockperf. Those will have to be run manually.
ENDIF (APR_BUILD_TESTAPR)
# Installation
INSTALL(TARGETS ${install_targets}
RUNTIME DESTINATION bin
LIBRARY DESTINATION lib
ARCHIVE DESTINATION lib
)
IF(INSTALL_PDB)
INSTALL(FILES ${install_bin_pdb}
DESTINATION bin
CONFIGURATIONS RelWithDebInfo Debug)
INSTALL(FILES ${install_lib_pdb}
DESTINATION lib
CONFIGURATIONS RelWithDebInfo Debug)
ENDIF()
INSTALL(FILES ${APR_PUBLIC_HEADERS_STATIC} ${APR_PUBLIC_HEADERS_GENERATED} DESTINATION include)
IF(APR_INSTALL_PRIVATE_H)
# Kludges for unexpected dependencies of httpd 2.x, not installed by default
SET(APR_PRIVATE_H_FOR_HTTPD
include/arch/win32/apr_arch_file_io.h
include/arch/win32/apr_arch_misc.h
include/arch/win32/apr_arch_utf8.h
include/arch/win32/apr_private.h
)
INSTALL(FILES ${APR_PRIVATE_H_FOR_HTTPD} DESTINATION include/arch/win32)
INSTALL(FILES include/arch/apr_private_common.h DESTINATION include/arch)
ENDIF()
STRING(TOUPPER "${CMAKE_BUILD_TYPE}" buildtype)
MESSAGE(STATUS "")
MESSAGE(STATUS "")
MESSAGE(STATUS "APR configuration summary:")
MESSAGE(STATUS "")
MESSAGE(STATUS " Build type ...................... : ${CMAKE_BUILD_TYPE}")
MESSAGE(STATUS " Install .pdb (if available)...... : ${INSTALL_PDB}")
MESSAGE(STATUS " Install prefix .................. : ${CMAKE_INSTALL_PREFIX}")
MESSAGE(STATUS " C compiler ...................... : ${CMAKE_C_COMPILER}")
MESSAGE(STATUS " IPv6 ............................ : ${APR_HAVE_IPV6}")
MESSAGE(STATUS " Minimum Windows version ......... : ${MIN_WINDOWS_VER}")
MESSAGE(STATUS " Build test suite ................ : ${APR_BUILD_TESTAPR}")
IF(TEST_STATIC_LIBS)
MESSAGE(STATUS " (testing static libraries)")
ELSE()
MESSAGE(STATUS " (testing dynamic libraries)")
ENDIF()
MESSAGE(STATUS " Install private .h for httpd .... : ${APR_INSTALL_PRIVATE_H}")

View File

@ -206,8 +206,8 @@ APACHE PORTABLE RUNTIME SUBCOMPONENTS:
The Apache Portable Runtime includes a number of subcomponents with
separate copyright notices and license terms. Your use of the source
code for the these subcomponents is subject to the terms and
conditions of the following licenses.
code for these subcomponents is subject to the terms and conditions
of the following licenses.
From strings/apr_fnmatch.c, include/apr_fnmatch.h, misc/unix/getopt.c,
file_io/unix/mktemp.c, strings/apr_strings.c:

View File

@ -18,7 +18,7 @@ APR_MAJOR_VERSION=@APR_MAJOR_VERSION@
INCDIR=./include
OSDIR=$(top_srcdir)/include/arch/@OSDIR@
DEFOSDIR=$(INCDIR)/arch/@DEFAULT_OSDIR@
INCLUDES=-I$(INCDIR) -I$(OSDIR) -I$(DEFOSDIR) -I$(top_srcdir)/include/arch/@DEFAULT_OSDIR@ -I$(top_srcdir)/include
INCLUDES=-I$(INCDIR) -I$(OSDIR) -I$(DEFOSDIR) -I$(top_srcdir)/include/arch/@DEFAULT_OSDIR@ -I$(top_srcdir)/include -I$(top_srcdir)/include/private -I$(top_blddir)/include/private
#
# Macros for target determination
@ -36,7 +36,7 @@ INSTALL_DATA = @INSTALL_DATA@
# Rules for building specific targets, starting with 'all' for
# building the entire package.
#
TARGETS = $(TARGET_LIB) apr.exp apr-config.out build/apr_rules.out
TARGETS = $(TARGET_LIB) include/private/apr_escape_test_char.h apr.exp apr-config.out build/apr_rules.out
LT_VERSION = @LT_VERSION@
@ -45,7 +45,9 @@ LT_VERSION = @LT_VERSION@
@INCLUDE_OUTPUTS@
CLEAN_TARGETS = apr-config.out apr.exp exports.c export_vars.c .make.dirs \
build/apr_rules.out
build/apr_rules.out tools/gen_test_char@EXEEXT@ \
tools/gen_test_char.o tools/gen_test_char.lo \
include/private/apr_escape_test_char.h
DISTCLEAN_TARGETS = config.cache config.log config.status \
include/apr.h include/arch/unix/apr_private.h \
libtool $(APR_CONFIG) build/apr_rules.mk apr.pc \
@ -99,6 +101,8 @@ install: $(TARGETS)
$(TARGET_LIB): $(OBJECTS)
$(LINK) @lib_target@ $(ALL_LIBS)
encoding/apr_escape.lo: include/private/apr_escape_test_char.h
exports.c: $(HEADERS)
$(APR_MKEXPORT) $(HEADERS) > $@
@ -125,5 +129,20 @@ check: $(TARGET_LIB)
etags:
etags `find . -name '*.[ch]'`
make_tools_dir:
$(APR_MKDIR) tools
OBJECTS_gen_test_char = tools/gen_test_char.lo $(LOCAL_LIBS)
tools/gen_test_char.lo: make_tools_dir
tools/gen_test_char@EXEEXT@: $(OBJECTS_gen_test_char)
$(LINK_PROG) $(OBJECTS_gen_test_char) $(ALL_LIBS)
include/private/apr_escape_test_char.h: tools/gen_test_char@EXEEXT@
$(APR_MKDIR) include/private
tools/gen_test_char@EXEEXT@ > $@
LINK_PROG = $(LIBTOOL) $(LTFLAGS) --mode=link $(COMPILE) $(LT_LDFLAGS) \
@LT_NO_INSTALL@ $(ALL_LDFLAGS) -o $@
# DO NOT REMOVE
docs: $(INCDIR)/*.h

View File

@ -7,7 +7,7 @@
# install - compile everything
# clean - mop up everything
#
# You can override the build mechansim, choose only one;
# You can override the build mechanism, choose only one;
#
# USEMAK=1 - compile from exported make files
# USEDSW=1 - compile from .dsw / .dsp VC6 projects

4
NOTICE
View File

@ -1,7 +1,7 @@
Apache Portable Runtime
Copyright (c) 2011 The Apache Software Foundation.
Copyright (c) 2000-2014 The Apache Software Foundation.
This product includes software developed by
This product includes software developed at
The Apache Software Foundation (http://www.apache.org/).
Portions of this software were developed at the National Center

112
README.cmake Normal file
View File

@ -0,0 +1,112 @@
Experimental cmake-based build support for APR on Microsoft Windows
Status
------
This build support is currently intended only for Microsoft Windows.
Only Windows NT-based systems can be targeted. (The traditional
Windows build support for APR can target Windows 9x as well.)
This build support is experimental. Specifically,
* It does not support all features of APR.
* Some components may not be built correctly and/or in a manner
compatible with the previous Windows build support.
* Build interfaces, such as the mechanisms which are used to enable
optional functionality or specify prerequisites, may change from
release to release as feedback is received from users and bugs and
limitations are resolved.
Important: Refer to the "Known Bugs and Limitations" section for further
information.
It is beyond the scope of this document to document or explain
how to utilize the various cmake features, such as different
build backends or provisions for finding support libraries.
Please refer to the cmake documentation for additional information
that applies to building any project with cmake.
Prerequisites
-------------
The following tools must be in PATH:
* cmake, version 2.8 or later
* If using a command-line compiler: compiler and linker and related tools
(Refer to the cmake documentation for more information.)
How to build
------------
1. cd to a clean directory for building (i.e., don't build in your
source tree)
2. Some cmake backends may want your compile tools in PATH. (Hint: "Visual
Studio Command Prompt")
3. cmake -G "some backend, like 'NMake Makefiles'"
-DCMAKE_INSTALL_PREFIX=d:/path/to/aprinst
-DAPR-specific-flags
d:/path/to/aprsource
Alternately, use cmake-gui and update settings in the GUI.
APR feature flags:
APR_INSTALL_PRIVATE_H Install extra .h files which are required when
building httpd and Subversion but which aren't
intended for use by applications.
Default: OFF
APR_HAVE_IPV6 Enable IPv6 support
Default: ON
APR_BUILD_TESTAPR Build APR test suite
Default: OFF
TEST_STATIC_LIBS Build the test suite to test the APR static
library instead of the APR dynamic library.
Default: OFF
In order to build the test suite against both
static and dynamic libraries, separate builds
will be required, one with TEST_STATIC_LIBS
set to ON.
MIN_WINDOWS_VER Minimum Windows version supported by this build
(This controls the setting of _WIN32_WINNT.)
"Vista" or "Windows7" or a numeric value like
"0x0601"
Default: "Vista"
For desktop/server equivalence or other values,
refer to
http://msdn.microsoft.com/en-us/library/windows/
desktop/aa383745(v=vs.85).aspx
INSTALL_PDB Install .pdb files if generated.
Default: ON
CMAKE_C_FLAGS_RELEASE, _DEBUG, _RELWITHDEBINFO, _MINSIZEREL
CMAKE_BUILD_TYPE
For NMake Makefiles the choices are at least DEBUG, RELEASE,
RELWITHDEBINFO, and MINSIZEREL
Other backends make have other selections.
4. build using chosen backend (e.g., "nmake install")
Known Bugs and Limitations
--------------------------
* If include/apr.h or other generated files have been created in the source
directory by another build system, they will be used unexpectedly and
cause the build to fail.
* Options should be provided for remaining features:
+ APR_POOL_DEBUG
* APR-CHANGES.txt, APR-LICENSE.txt, and APR-NOTICE.txt are not installed,
though perhaps that is a job for a higher-level script.
Generally:
* Many APR features have not been tested with this build.
* Developers need to examine the existing Windows build in great detail and see
what is missing from the cmake-based build, whether a feature or some build
nuance.
* Any feedback you can provide on your experiences with this build will be
helpful.

2474
apr.dep

File diff suppressed because it is too large Load Diff

159
apr.dsp
View File

@ -200,6 +200,15 @@ SOURCE=.\atomic\win32\apr_atomic.c
# Begin Source File
SOURCE=.\dso\win32\dso.c
# End Source File
# End Group
# Begin Group "encoding"
# PROP Default_Filter ""
# Begin Source File
SOURCE=.\encoding\apr_escape.c
# End Source File
# End Group
# Begin Group "file_io"
@ -492,6 +501,10 @@ SOURCE=.\tables\apr_hash.c
# End Source File
# Begin Source File
SOURCE=.\tables\apr_skiplist.c
# End Source File
# Begin Source File
SOURCE=.\tables\apr_tables.c
# End Source File
# End Group
@ -694,6 +707,85 @@ SOURCE=.\include\apr_errno.h
# End Source File
# Begin Source File
SOURCE=.\include\apr_escape.h
# End Source File
# Begin Source File
SOURCE=.\include\apr_escape.h
!IF "$(CFG)" == "apr - Win32 Release"
# Begin Custom Build - Creating gen_test_char.exe and apr_escape_test_char.h
InputPath=.\include\apr_escape.h
".\include\apr_escape_test_char.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
cl.exe /nologo /W3 /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /FD /I ".\include" /Fo.\LibR\gen_test_char /Fe.\LibR\gen_test_char.exe .\tools\gen_test_char.c
.\LibR\gen_test_char.exe > .\include\apr_escape_test_char.h
# End Custom Build
!ELSEIF "$(CFG)" == "apr - Win32 Debug"
# Begin Custom Build - Creating gen_test_char.exe and apr_escape_test_char.h
InputPath=.\include\apr_escape.h
".\include\apr_escape_test_char.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
cl.exe /nologo /W3 /EHsc /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /FD /I ".\include" /Fo.\LibD\gen_test_char /Fe.\LibD\gen_test_char.exe .\tools\gen_test_char.c
.\LibD\gen_test_char.exe > .\include\apr_escape_test_char.h
# End Custom Build
!ELSEIF "$(CFG)" == "apr - Win32 Release9x"
# Begin Custom Build - Creating gen_test_char.exe and apr_escape_test_char.h
InputPath=.\include\apr_escape.h
".\include\apr_escape_test_char.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
cl.exe /nologo /W3 /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /FD /I ".\include" /Fo.\9x\LibR\gen_test_char /Fe.\9x\LibR\gen_test_char.exe .\tools\gen_test_char.c
.\9x\LibR\gen_test_char.exe > .\include\apr_escape_test_char.h
# End Custom Build
!ELSEIF "$(CFG)" == "apr - Win32 Debug9x"
# Begin Custom Build - Creating gen_test_char.exe and apr_escape_test_char.h
InputPath=.\include\apr_escape.h
InputPath=.\include\apr_escape.h
".\include\apr_escape_test_char.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
cl.exe /nologo /W3 /EHsc /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /FD /I ".\include" /Fo.\9x\LibD\gen_test_char /Fe.\9x\LibD\gen_test_char.exe .\tools\gen_test_char.c
.\9x\LibD\gen_test_char.exe > .\include\apr_escape_test_char.h
# End Custom Build
!ELSEIF "$(CFG)" == "apr - x64 Release"
# Begin Custom Build - Creating gen_test_char.exe and apr_escape_test_char.h
InputPath=.\include\apr_escape.h
InputPath=.\include\apr_escape.h
".\include\apr_escape_test_char.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
cl.exe /nologo /W3 /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /FD /I ".\include" /Fo.\x64\LibR\gen_test_char /Fe.\x64\LibR\gen_test_char.exe .\tools\gen_test_char.c
.\x64\LibR\gen_test_char.exe > .\include\apr_escape_test_char.h
# End Custom Build
!ELSEIF "$(CFG)" == "apr - x64 Debug"
# Begin Custom Build - Creating gen_test_char.exe and apr_escape_test_char.h
InputPath=.\include\apr_escape.h
".\include\apr_escape_test_char.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
cl.exe /nologo /W3 /EHsc /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /FD /I ".\include" /Fo.\x64\LibD\gen_test_char /Fe.\x64\LibD\gen_test_char.exe .\tools\gen_test_char.c
.\x64\LibD\gen_test_char.exe > .\include\apr_escape_test_char.h
# End Custom Build
!ENDIF
# End Source File
# Begin Source File
SOURCE=.\include\apr_file_info.h
# End Source File
# Begin Source File
@ -770,6 +862,10 @@ SOURCE=.\include\apr_signal.h
# End Source File
# Begin Source File
SOURCE=.\include\apr_skiplist.h
# End Source File
# Begin Source File
SOURCE=.\include\apr_strings.h
# End Source File
# Begin Source File
@ -811,6 +907,69 @@ SOURCE=.\include\apr_version.h
# Begin Source File
SOURCE=.\include\apr_want.h
!IF "$(CFG)" == "apr - Win32 Release"
# Begin Custom Build
InputPath=.\include\apr_want.h
".\LibR\gen_test_char.exe" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
type .\include\apr.hw > .\include\apr.h
# End Custom Build
!ELSEIF "$(CFG)" == "apr - Win32 Debug"
# Begin Custom Build
InputPath=.\include\apr_want.h
".\LibD\gen_test_char.exe" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
type .\include\apr.hw > .\include\apr.h
# End Custom Build
!ELSEIF "$(CFG)" == "apr - Win32 Release9x"
# Begin Custom Build
InputPath=.\include\apr_want.h
".\9x\LibR\gen_test_char.exe" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
type .\include\apr.hw > .\include\apr.h
# End Custom Build
!ELSEIF "$(CFG)" == "apr - Win32 Debug9x"
# Begin Custom Build
InputPath=.\include\apr_want.h
".\9x\LibD\gen_test_char.exe" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
type .\include\apr.hw > .\include\apr.h
# End Custom Build
!ELSEIF "$(CFG)" == "apr - x64 Release"
# Begin Custom Build
InputPath=.\include\apr_want.h
".\x64\LibR\gen_test_char.exe" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
type .\include\apr.hw > .\include\apr.h
# End Custom Build
!ELSEIF "$(CFG)" == "apr - x64 Debug"
# Begin Custom Build
InputPath=.\include\apr_want.h
".\x64\LibD\gen_test_char.exe" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
type .\include\apr.hw > .\include\apr.h
# End Custom Build
!ENDIF
# End Source File
# End Group
# End Target

3747
apr.mak

File diff suppressed because it is too large Load Diff

View File

@ -3,7 +3,7 @@
Summary: Apache Portable Runtime library
Name: apr
Version: 1.4.8
Version: 1.5.1
Release: 1
License: Apache Software License
Group: System Environment/Libraries

View File

@ -1,5 +1,6 @@
# DO NOT EDIT. AUTOMATICALLY GENERATED.
encoding/apr_escape.lo: encoding/apr_escape.c .make.dirs include/apr_allocator.h include/apr_errno.h include/apr_escape.h include/apr_general.h include/apr_lib.h include/apr_pools.h include/apr_strings.h include/apr_thread_mutex.h include/apr_want.h
passwd/apr_getpass.lo: passwd/apr_getpass.c .make.dirs include/apr_allocator.h include/apr_errno.h include/apr_general.h include/apr_lib.h include/apr_pools.h include/apr_strings.h include/apr_thread_mutex.h include/apr_want.h
strings/apr_cpystrn.lo: strings/apr_cpystrn.c .make.dirs include/apr_allocator.h include/apr_errno.h include/apr_general.h include/apr_lib.h include/apr_pools.h include/apr_strings.h include/apr_thread_mutex.h include/apr_want.h
strings/apr_fnmatch.lo: strings/apr_fnmatch.c .make.dirs include/apr_allocator.h include/apr_errno.h include/apr_file_info.h include/apr_fnmatch.h include/apr_general.h include/apr_lib.h include/apr_pools.h include/apr_strings.h include/apr_tables.h include/apr_thread_mutex.h include/apr_time.h include/apr_user.h include/apr_want.h
@ -8,9 +9,10 @@ strings/apr_strings.lo: strings/apr_strings.c .make.dirs include/apr_allocator.h
strings/apr_strnatcmp.lo: strings/apr_strnatcmp.c .make.dirs include/apr_allocator.h include/apr_errno.h include/apr_general.h include/apr_lib.h include/apr_pools.h include/apr_strings.h include/apr_thread_mutex.h include/apr_want.h
strings/apr_strtok.lo: strings/apr_strtok.c .make.dirs include/apr_allocator.h include/apr_errno.h include/apr_general.h include/apr_pools.h include/apr_strings.h include/apr_thread_mutex.h include/apr_want.h
tables/apr_hash.lo: tables/apr_hash.c .make.dirs include/apr_allocator.h include/apr_errno.h include/apr_general.h include/apr_hash.h include/apr_pools.h include/apr_thread_mutex.h include/apr_time.h include/apr_want.h
tables/apr_skiplist.lo: tables/apr_skiplist.c .make.dirs include/apr_allocator.h include/apr_dso.h include/apr_errno.h include/apr_file_info.h include/apr_file_io.h include/apr_general.h include/apr_global_mutex.h include/apr_inherit.h include/apr_network_io.h include/apr_pools.h include/apr_portable.h include/apr_proc_mutex.h include/apr_shm.h include/apr_skiplist.h include/apr_tables.h include/apr_thread_mutex.h include/apr_thread_proc.h include/apr_time.h include/apr_user.h include/apr_want.h
tables/apr_tables.lo: tables/apr_tables.c .make.dirs include/apr_allocator.h include/apr_errno.h include/apr_general.h include/apr_lib.h include/apr_pools.h include/apr_strings.h include/apr_tables.h include/apr_thread_mutex.h include/apr_want.h
OBJECTS_all = passwd/apr_getpass.lo strings/apr_cpystrn.lo strings/apr_fnmatch.lo strings/apr_snprintf.lo strings/apr_strings.lo strings/apr_strnatcmp.lo strings/apr_strtok.lo tables/apr_hash.lo tables/apr_tables.lo
OBJECTS_all = encoding/apr_escape.lo passwd/apr_getpass.lo strings/apr_cpystrn.lo strings/apr_fnmatch.lo strings/apr_snprintf.lo strings/apr_strings.lo strings/apr_strnatcmp.lo strings/apr_strtok.lo tables/apr_hash.lo tables/apr_skiplist.lo tables/apr_tables.lo
dso/unix/dso.lo: dso/unix/dso.c .make.dirs include/apr_allocator.h include/apr_dso.h include/apr_errno.h include/apr_file_info.h include/apr_file_io.h include/apr_general.h include/apr_global_mutex.h include/apr_inherit.h include/apr_network_io.h include/apr_pools.h include/apr_portable.h include/apr_proc_mutex.h include/apr_shm.h include/apr_strings.h include/apr_tables.h include/apr_thread_mutex.h include/apr_thread_proc.h include/apr_time.h include/apr_user.h include/apr_want.h
@ -81,8 +83,9 @@ poll/unix/pollcb.lo: poll/unix/pollcb.c .make.dirs include/apr_allocator.h inclu
poll/unix/pollset.lo: poll/unix/pollset.c .make.dirs include/apr_allocator.h include/apr_dso.h include/apr_errno.h include/apr_file_info.h include/apr_file_io.h include/apr_general.h include/apr_global_mutex.h include/apr_inherit.h include/apr_network_io.h include/apr_poll.h include/apr_pools.h include/apr_portable.h include/apr_proc_mutex.h include/apr_shm.h include/apr_tables.h include/apr_thread_mutex.h include/apr_thread_proc.h include/apr_time.h include/apr_user.h include/apr_want.h
poll/unix/port.lo: poll/unix/port.c .make.dirs include/apr_allocator.h include/apr_atomic.h include/apr_dso.h include/apr_errno.h include/apr_file_info.h include/apr_file_io.h include/apr_general.h include/apr_global_mutex.h include/apr_inherit.h include/apr_network_io.h include/apr_poll.h include/apr_pools.h include/apr_portable.h include/apr_proc_mutex.h include/apr_shm.h include/apr_tables.h include/apr_thread_mutex.h include/apr_thread_proc.h include/apr_time.h include/apr_user.h include/apr_want.h
poll/unix/select.lo: poll/unix/select.c .make.dirs include/apr_allocator.h include/apr_dso.h include/apr_errno.h include/apr_file_info.h include/apr_file_io.h include/apr_general.h include/apr_global_mutex.h include/apr_inherit.h include/apr_network_io.h include/apr_poll.h include/apr_pools.h include/apr_portable.h include/apr_proc_mutex.h include/apr_shm.h include/apr_tables.h include/apr_thread_mutex.h include/apr_thread_proc.h include/apr_time.h include/apr_user.h include/apr_want.h
poll/unix/z_asio.lo: poll/unix/z_asio.c .make.dirs include/apr_allocator.h include/apr_dso.h include/apr_errno.h include/apr_file_info.h include/apr_file_io.h include/apr_general.h include/apr_global_mutex.h include/apr_hash.h include/apr_inherit.h include/apr_network_io.h include/apr_poll.h include/apr_pools.h include/apr_portable.h include/apr_proc_mutex.h include/apr_shm.h include/apr_tables.h include/apr_thread_mutex.h include/apr_thread_proc.h include/apr_time.h include/apr_user.h include/apr_want.h
OBJECTS_poll_unix = poll/unix/epoll.lo poll/unix/kqueue.lo poll/unix/poll.lo poll/unix/pollcb.lo poll/unix/pollset.lo poll/unix/port.lo poll/unix/select.lo
OBJECTS_poll_unix = poll/unix/epoll.lo poll/unix/kqueue.lo poll/unix/poll.lo poll/unix/pollcb.lo poll/unix/pollset.lo poll/unix/port.lo poll/unix/select.lo poll/unix/z_asio.lo
random/unix/apr_random.lo: random/unix/apr_random.c .make.dirs include/apr_allocator.h include/apr_errno.h include/apr_file_info.h include/apr_file_io.h include/apr_general.h include/apr_inherit.h include/apr_pools.h include/apr_random.h include/apr_tables.h include/apr_thread_mutex.h include/apr_thread_proc.h include/apr_time.h include/apr_user.h include/apr_want.h
random/unix/sha2.lo: random/unix/sha2.c .make.dirs
@ -90,7 +93,7 @@ random/unix/sha2_glue.lo: random/unix/sha2_glue.c .make.dirs include/apr_allocat
OBJECTS_random_unix = random/unix/apr_random.lo random/unix/sha2.lo random/unix/sha2_glue.lo
shmem/unix/shm.lo: shmem/unix/shm.c .make.dirs include/apr_allocator.h include/apr_errno.h include/apr_general.h include/apr_pools.h include/apr_strings.h include/apr_thread_mutex.h include/apr_user.h include/apr_want.h
shmem/unix/shm.lo: shmem/unix/shm.c .make.dirs include/apr_allocator.h include/apr_errno.h include/apr_general.h include/apr_hash.h include/apr_pools.h include/apr_strings.h include/apr_thread_mutex.h include/apr_user.h include/apr_want.h
OBJECTS_shmem_unix = shmem/unix/shm.lo
@ -308,11 +311,11 @@ OBJECTS_atomic_win32 = atomic/win32/apr_atomic.lo
OBJECTS_win32 = $(OBJECTS_all) $(OBJECTS_atomic_win32) $(OBJECTS_dso_win32) $(OBJECTS_file_io_win32) $(OBJECTS_locks_win32) $(OBJECTS_memory_unix) $(OBJECTS_misc_win32) $(OBJECTS_mmap_win32) $(OBJECTS_network_io_win32) $(OBJECTS_poll_unix) $(OBJECTS_random_unix) $(OBJECTS_shmem_win32) $(OBJECTS_support_unix) $(OBJECTS_threadproc_win32) $(OBJECTS_time_win32) $(OBJECTS_user_win32)
HEADERS = $(top_srcdir)/include/apr_allocator.h $(top_srcdir)/include/apr_atomic.h $(top_srcdir)/include/apr_dso.h $(top_srcdir)/include/apr_env.h $(top_srcdir)/include/apr_errno.h $(top_srcdir)/include/apr_file_info.h $(top_srcdir)/include/apr_file_io.h $(top_srcdir)/include/apr_fnmatch.h $(top_srcdir)/include/apr_general.h $(top_srcdir)/include/apr_getopt.h $(top_srcdir)/include/apr_global_mutex.h $(top_srcdir)/include/apr_hash.h $(top_srcdir)/include/apr_inherit.h $(top_srcdir)/include/apr_lib.h $(top_srcdir)/include/apr_mmap.h $(top_srcdir)/include/apr_network_io.h $(top_srcdir)/include/apr_poll.h $(top_srcdir)/include/apr_pools.h $(top_srcdir)/include/apr_portable.h $(top_srcdir)/include/apr_proc_mutex.h $(top_srcdir)/include/apr_random.h $(top_srcdir)/include/apr_ring.h $(top_srcdir)/include/apr_shm.h $(top_srcdir)/include/apr_signal.h $(top_srcdir)/include/apr_strings.h $(top_srcdir)/include/apr_support.h $(top_srcdir)/include/apr_tables.h $(top_srcdir)/include/apr_thread_cond.h $(top_srcdir)/include/apr_thread_mutex.h $(top_srcdir)/include/apr_thread_proc.h $(top_srcdir)/include/apr_thread_rwlock.h $(top_srcdir)/include/apr_time.h $(top_srcdir)/include/apr_user.h $(top_srcdir)/include/apr_version.h $(top_srcdir)/include/apr_want.h
HEADERS = $(top_srcdir)/include/apr_allocator.h $(top_srcdir)/include/apr_atomic.h $(top_srcdir)/include/apr_dso.h $(top_srcdir)/include/apr_env.h $(top_srcdir)/include/apr_errno.h $(top_srcdir)/include/apr_escape.h $(top_srcdir)/include/apr_file_info.h $(top_srcdir)/include/apr_file_io.h $(top_srcdir)/include/apr_fnmatch.h $(top_srcdir)/include/apr_general.h $(top_srcdir)/include/apr_getopt.h $(top_srcdir)/include/apr_global_mutex.h $(top_srcdir)/include/apr_hash.h $(top_srcdir)/include/apr_inherit.h $(top_srcdir)/include/apr_lib.h $(top_srcdir)/include/apr_mmap.h $(top_srcdir)/include/apr_network_io.h $(top_srcdir)/include/apr_poll.h $(top_srcdir)/include/apr_pools.h $(top_srcdir)/include/apr_portable.h $(top_srcdir)/include/apr_proc_mutex.h $(top_srcdir)/include/apr_random.h $(top_srcdir)/include/apr_ring.h $(top_srcdir)/include/apr_shm.h $(top_srcdir)/include/apr_signal.h $(top_srcdir)/include/apr_skiplist.h $(top_srcdir)/include/apr_strings.h $(top_srcdir)/include/apr_support.h $(top_srcdir)/include/apr_tables.h $(top_srcdir)/include/apr_thread_cond.h $(top_srcdir)/include/apr_thread_mutex.h $(top_srcdir)/include/apr_thread_proc.h $(top_srcdir)/include/apr_thread_rwlock.h $(top_srcdir)/include/apr_time.h $(top_srcdir)/include/apr_user.h $(top_srcdir)/include/apr_version.h $(top_srcdir)/include/apr_want.h
SOURCE_DIRS = random/unix misc/win32 mmap/win32 dso/os2 time/unix network_io/win32 dso/win32 locks/unix user/unix time/win32 locks/beos tables support/unix file_io/unix mmap/unix atomic/unix threadproc/win32 poll/os2 atomic/win32 dso/os390 atomic/os390 dso/beos poll/unix passwd network_io/beos threadproc/os2 network_io/os2 shmem/win32 threadproc/beos shmem/unix network_io/unix file_io/os2 dso/aix file_io/win32 threadproc/unix misc/unix locks/win32 shmem/beos dso/unix locks/os2 user/win32 shmem/os2 memory/unix strings $(EXTRA_SOURCE_DIRS)
SOURCE_DIRS = random/unix misc/win32 encoding dso/os2 time/unix network_io/win32 dso/win32 locks/unix user/unix time/win32 locks/beos tables support/unix file_io/unix mmap/unix atomic/unix threadproc/win32 poll/os2 atomic/win32 dso/os390 atomic/os390 dso/beos poll/unix passwd network_io/beos threadproc/os2 network_io/os2 shmem/win32 threadproc/beos shmem/unix network_io/unix file_io/os2 mmap/win32 dso/aix file_io/win32 threadproc/unix misc/unix locks/win32 shmem/beos dso/unix locks/os2 user/win32 shmem/os2 memory/unix strings $(EXTRA_SOURCE_DIRS)
BUILD_DIRS = atomic atomic/os390 atomic/unix atomic/win32 dso dso/aix dso/beos dso/os2 dso/os390 dso/unix dso/win32 file_io file_io/os2 file_io/unix file_io/win32 locks locks/beos locks/os2 locks/unix locks/win32 memory memory/unix misc misc/unix misc/win32 mmap mmap/unix mmap/win32 network_io network_io/beos network_io/os2 network_io/unix network_io/win32 passwd poll poll/os2 poll/unix random random/unix shmem shmem/beos shmem/os2 shmem/unix shmem/win32 strings support support/unix tables threadproc threadproc/beos threadproc/os2 threadproc/unix threadproc/win32 time time/unix time/win32 user user/unix user/win32
BUILD_DIRS = atomic atomic/os390 atomic/unix atomic/win32 dso dso/aix dso/beos dso/os2 dso/os390 dso/unix dso/win32 encoding file_io file_io/os2 file_io/unix file_io/win32 locks locks/beos locks/os2 locks/unix locks/win32 memory memory/unix misc misc/unix misc/win32 mmap mmap/unix mmap/win32 network_io network_io/beos network_io/os2 network_io/unix network_io/win32 passwd poll poll/os2 poll/unix random random/unix shmem shmem/beos shmem/os2 shmem/unix shmem/win32 strings support support/unix tables threadproc threadproc/beos threadproc/os2 threadproc/unix threadproc/win32 time time/unix time/win32 user user/unix user/win32
.make.dirs: $(srcdir)/build-outputs.mk
@for d in $(BUILD_DIRS); do test -d $$d || mkdir $$d; done

View File

@ -6,6 +6,7 @@
# paths to platform-independent .c files to build
paths =
encoding/*.c
passwd/*.c
strings/*.c
tables/*.c

348
configure vendored
View File

@ -639,6 +639,7 @@ DEFAULT_OSDIR
OSDIR
INCLUDES
LDLIBS
INTERNAL_CPPFLAGS
NOTEST_INCLUDES
NOTEST_LIBS
NOTEST_LDFLAGS
@ -919,6 +920,7 @@ enable_lfs
enable_nonportable_atomics
enable_threads
with_efence
enable_posix_shm
with_sendfile
enable_allocator_uses_mmap
enable_dso
@ -1563,7 +1565,8 @@ Optional Features:
--disable-lfs Disable large file support on 32-bit platforms
--enable-nonportable-atomics Use optimized atomic code which may produce nonportable binaries
--enable-threads Enable threading support in APR.
--enable-allocator-uses-mmap Use mmap in apr_allocator instead of malloc (experimental)
--enable-posix-shm Use POSIX shared memory (shm_open) if available
--enable-allocator-uses-mmap Use mmap in apr_allocator instead of malloc
--disable-dso Disable DSO support
--enable-other-child Enable reliable child processes
--disable-ipv6 Disable IPv6 support in APR.
@ -5933,10 +5936,10 @@ if test "x$apr_preload_done" != "xyes" ; then
*mint)
if test "x$CPPFLAGS" = "x"; then
test "x$silent" != "xyes" && echo " setting CPPFLAGS to \"-DMINT\""
CPPFLAGS="-DMINT"
test "x$silent" != "xyes" && echo " setting CPPFLAGS to \"-DMINT -D_GNU_SOURCE\""
CPPFLAGS="-DMINT -D_GNU_SOURCE"
else
apr_addto_bugger="-DMINT"
apr_addto_bugger="-DMINT -D_GNU_SOURCE"
for i in $apr_addto_bugger; do
apr_addto_duplicate="0"
for j in $CPPFLAGS; do
@ -5952,27 +5955,6 @@ if test "x$apr_preload_done" != "xyes" ; then
done
fi
if test "x$LIBS" = "x"; then
test "x$silent" != "xyes" && echo " setting LIBS to \"-lportlib\""
LIBS="-lportlib"
else
apr_addto_bugger="-lportlib"
for i in $apr_addto_bugger; do
apr_addto_duplicate="0"
for j in $LIBS; do
if test "x$i" = "x$j"; then
apr_addto_duplicate="1"
break
fi
done
if test $apr_addto_duplicate = "0"; then
test "x$silent" != "xyes" && echo " adding \"$i\" to LIBS"
LIBS="$LIBS $i"
fi
done
fi
;;
*MPE/iX*)
@ -9059,30 +9041,28 @@ $as_echo "#define HAVE_ZOS_PTHREADS 1" >>confdefs.h
fi
;;
*cygwin*)
*mingw*)
if test "x$CPPFLAGS" = "x"; then
test "x$silent" != "xyes" && echo " setting CPPFLAGS to \"-DCYGWIN\""
CPPFLAGS="-DCYGWIN"
if test "x$INTERNAL_CPPFLAGS" = "x"; then
test "x$silent" != "xyes" && echo " setting INTERNAL_CPPFLAGS to \"-DBINPATH=$apr_builddir/test/.libs\""
INTERNAL_CPPFLAGS="-DBINPATH=$apr_builddir/test/.libs"
else
apr_addto_bugger="-DCYGWIN"
apr_addto_bugger="-DBINPATH=$apr_builddir/test/.libs"
for i in $apr_addto_bugger; do
apr_addto_duplicate="0"
for j in $CPPFLAGS; do
for j in $INTERNAL_CPPFLAGS; do
if test "x$i" = "x$j"; then
apr_addto_duplicate="1"
break
fi
done
if test $apr_addto_duplicate = "0"; then
test "x$silent" != "xyes" && echo " adding \"$i\" to CPPFLAGS"
CPPFLAGS="$CPPFLAGS $i"
test "x$silent" != "xyes" && echo " adding \"$i\" to INTERNAL_CPPFLAGS"
INTERNAL_CPPFLAGS="$INTERNAL_CPPFLAGS $i"
fi
done
fi
;;
*mingw*)
if test "x$CPPFLAGS" = "x"; then
test "x$silent" != "xyes" && echo " setting CPPFLAGS to \"-DWIN32 -D__MSVCRT__\""
@ -17794,7 +17774,7 @@ fi
if test "x$use_libtool" = "xyes"; then
lt_compile='$(LIBTOOL) $(LTFLAGS) --mode=compile $(COMPILE) -o $@ -c $< && touch $@'
LT_VERSION="-version-info `$get_version libtool $version_hdr APR`"
link="\$(LIBTOOL) \$(LTFLAGS) --mode=link \$(LT_LDFLAGS) \$(COMPILE) \$(LT_VERSION) \$(ALL_LDFLAGS) -o \$@"
link="\$(LIBTOOL) \$(LTFLAGS) --mode=link \$(COMPILE) \$(LT_LDFLAGS) \$(LT_VERSION) \$(ALL_LDFLAGS) -o \$@"
so_ext='lo'
lib_target='-rpath $(libdir) $(OBJECTS)'
export_lib_target='-rpath \$(libdir) \$(OBJECTS)'
@ -17810,6 +17790,9 @@ case $host in
*-solaris2*)
apr_platform_runtime_link_flag="-R"
;;
*-mingw* | *-cygwin*)
LT_LDFLAGS="$LT_LDFLAGS -no-undefined"
;;
*)
;;
esac
@ -18314,6 +18297,53 @@ case "$host:$CC" in
AR="ar"
;;
*-mingw* | *-cygwin*)
if test "$enable_shared" = "yes"; then
if test "x$INTERNAL_CPPFLAGS" = "x"; then
test "x$silent" != "xyes" && echo " setting INTERNAL_CPPFLAGS to \"-DAPR_DECLARE_EXPORT\""
INTERNAL_CPPFLAGS="-DAPR_DECLARE_EXPORT"
else
apr_addto_bugger="-DAPR_DECLARE_EXPORT"
for i in $apr_addto_bugger; do
apr_addto_duplicate="0"
for j in $INTERNAL_CPPFLAGS; do
if test "x$i" = "x$j"; then
apr_addto_duplicate="1"
break
fi
done
if test $apr_addto_duplicate = "0"; then
test "x$silent" != "xyes" && echo " adding \"$i\" to INTERNAL_CPPFLAGS"
INTERNAL_CPPFLAGS="$INTERNAL_CPPFLAGS $i"
fi
done
fi
else
if test "x$CPPFLAGS" = "x"; then
test "x$silent" != "xyes" && echo " setting CPPFLAGS to \"-DAPR_DECLARE_STATIC\""
CPPFLAGS="-DAPR_DECLARE_STATIC"
else
apr_addto_bugger="-DAPR_DECLARE_STATIC"
for i in $apr_addto_bugger; do
apr_addto_duplicate="0"
for j in $CPPFLAGS; do
if test "x$i" = "x$j"; then
apr_addto_duplicate="1"
break
fi
done
if test $apr_addto_duplicate = "0"; then
test "x$silent" != "xyes" && echo " adding \"$i\" to CPPFLAGS"
CPPFLAGS="$CPPFLAGS $i"
fi
done
fi
fi
;;
esac
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether the compiler provides atomic builtins" >&5
@ -18791,7 +18821,17 @@ case $host in
fi
;;
*linux*)
os_version=`uname -r | sed -e 's/\(.\)\.\(.\)\.\(.\).*/\1\2\3/'`
os_major=`uname -r | sed -e 's/\([1-9][0-9]*\)\..*/\1/'`
os_minor=`uname -r | sed -e 's/[1-9][0-9]*\.\([0-9]\+\)\..*/\1/'`
if test $os_major -lt 2 -o \( $os_major -eq 2 -a $os_minor -lt 4 \); then
{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Configured for pre-2.4 Linux $os_major.$os_minor" >&5
$as_echo "$as_me: WARNING: Configured for pre-2.4 Linux $os_major.$os_minor" >&2;}
os_pre24linux=1
else
os_pre24linux=0
{ $as_echo "$as_me:${as_lineno-$LINENO}: Configured for Linux $os_major.$os_minor" >&5
$as_echo "$as_me: Configured for Linux $os_major.$os_minor" >&6;}
fi
;;
*os390)
os_version=`uname -r | sed -e 's/\.//g'`
@ -20391,7 +20431,10 @@ $as_echo "#define HAVE_DUP3 1" >>confdefs.h
fi
# test for accept4
# Test for accept4(). Create a non-blocking socket, bind it to
# an unspecified port & address (kernel picks), and attempt to
# call accept4() on it. If the syscall is wired up (i.e. the
# kernel is new enough), it should return EAGAIN.
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for accept4 support" >&5
$as_echo_n "checking for accept4 support... " >&6; }
if ${apr_cv_accept4+:} false; then :
@ -20403,75 +20446,41 @@ else
cat confdefs.h - <<_ACEOF >conftest.$ac_ext
/* end confdefs.h. */
#include <unistd.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <sys/un.h>
#include <sys/wait.h>
#include <signal.h>
#include <netinet/in.h>
#include <netinet/tcp.h>
#include <errno.h>
#include <string.h>
#include <unistd.h>
#include <fcntl.h>
#define A4_SOCK "./apr_accept4_test_socket"
int main()
int main(int argc, char **argv)
{
pid_t pid;
int fd;
struct sockaddr_un loc, rem;
socklen_t rem_sz;
int fd, flags;
struct sockaddr_in sin;
if ((pid = fork())) {
int status;
unlink(A4_SOCK);
if ((fd = socket(AF_UNIX, SOCK_STREAM, 0)) == -1)
goto cleanup_failure2;
loc.sun_family = AF_UNIX;
strncpy(loc.sun_path, A4_SOCK, sizeof(loc.sun_path) - 1);
if (bind(fd, (struct sockaddr *) &loc,
sizeof(struct sockaddr_un)) == -1)
goto cleanup_failure;
if (listen(fd, 5) == -1)
goto cleanup_failure;
rem_sz = sizeof(struct sockaddr_un);
if (accept4(fd, (struct sockaddr *) &rem, &rem_sz, 0) == -1) {
goto cleanup_failure;
}
else {
close(fd);
waitpid(pid, &status, 0);
unlink(A4_SOCK);
return 0;
}
cleanup_failure:
close(fd);
cleanup_failure2:
kill(pid, SIGKILL);
waitpid(pid, &status, 0);
unlink(A4_SOCK);
if ((fd = socket(AF_INET, SOCK_STREAM, 0)) == -1)
return 1;
}
else {
if ((fd = socket(AF_UNIX, SOCK_STREAM, 0)) == -1)
return 1; /* this will be bad: we'll hang */
flags = fcntl(fd, F_GETFL);
if (flags == -1 || fcntl(fd, F_SETFL, flags|O_NONBLOCK) == -1)
return 5;
loc.sun_family = AF_UNIX;
strncpy(loc.sun_path, A4_SOCK, sizeof(loc.sun_path) - 1);
memset(&sin, 0, sizeof sin);
sin.sin_family = AF_INET;
while(connect(fd, (struct sockaddr *) &loc,
sizeof(struct sockaddr_un)) == -1 &&
(errno==ENOENT || errno==ECONNREFUSED))
;
if (bind(fd, (struct sockaddr *) &sin, sizeof sin) == -1)
return 2;
close(fd);
if (listen(fd, 5) == -1)
return 3;
if (accept4(fd, NULL, 0, SOCK_NONBLOCK) == 0
|| errno == EAGAIN || errno == EWOULDBLOCK)
return 0;
}
return 4;
}
_ACEOF
if ac_fn_c_try_run "$LINENO"; then :
@ -20582,6 +20591,49 @@ $as_echo "#define HAVE_EPOLL_CREATE1 1" >>confdefs.h
fi
# Check for z/OS async i/o support.
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for asio -> message queue support" >&5
$as_echo_n "checking for asio -> message queue support... " >&6; }
if ${apr_cv_aio_msgq+:} false; then :
$as_echo_n "(cached) " >&6
else
if test "$cross_compiling" = yes; then :
apr_cv_aio_msgq=no
else
cat confdefs.h - <<_ACEOF >conftest.$ac_ext
/* end confdefs.h. */
#define _AIO_OS390
#include <aio.h>
int main()
{
struct aiocb a;
a.aio_notifytype = AIO_MSGQ; /* use IPC message queue for notification */
return aio_cancel(2, NULL) == -1;
}
_ACEOF
if ac_fn_c_try_run "$LINENO"; then :
apr_cv_aio_msgq=yes
else
apr_cv_aio_msgq=no
fi
rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \
conftest.$ac_objext conftest.beam conftest.$ac_ext
fi
fi
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $apr_cv_aio_msgq" >&5
$as_echo "$apr_cv_aio_msgq" >&6; }
if test "$apr_cv_aio_msgq" = "yes"; then
$as_echo "#define HAVE_AIO_MSGQ 1" >>confdefs.h
fi
# test for dup3
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for dup3 support" >&5
$as_echo_n "checking for dup3 support... " >&6; }
@ -21214,7 +21266,9 @@ case $host in
# that it has it.
# FIXME - find exact 2.3 version that MMANON was fixed in. It is
# confirmed fixed in 2.4 series.
if test $os_version -le "240"; then
if test $os_pre24linux -eq 1; then
{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Disabling anon mmap() support for Linux pre-2.4" >&5
$as_echo "$as_me: WARNING: Disabling anon mmap() support for Linux pre-2.4" >&2;}
ac_decision=''
for ac_item in USE_SHMEM_MMAP_ZERO USE_SHMEM_SHMGET_ANON; do
eval "ac_decision_this=\$ac_decision_${ac_item}"
@ -21520,13 +21574,28 @@ else
fi
# Check whether --enable-posix-shm was given.
if test "${enable_posix_shm+set}" = set; then :
enableval=$enable_posix_shm;
if test "$havemmapshm" = "1"; then
ac_decision=''
for ac_item in USE_SHMEM_MMAP_SHM; do
eval "ac_decision_this=\$ac_decision_${ac_item}"
if test ".$ac_decision_this" = .yes; then
ac_decision=$ac_item
eval "ac_decision_msg=\$ac_decision_${ac_item}_msg"
fi
done
fi
fi
case $host in
*linux* )
# Linux has problems with MM_SHMT_MMANON even though it reports
# that it has it.
# FIXME - find exact 2.3 version that MMANON was fixed in. It is
# confirmed fixed in 2.4 series.
if test $os_version -le "240"; then
# Linux pre-2.4 had problems with MM_SHMT_MMANON even though
# it reports that it has it.
if test $os_pre24linux -eq 1; then
ac_decision=''
for ac_item in USE_SHMEM_MMAP_TMP USE_SHMEM_MMAP_SHM USE_SHMEM_SHMGET; do
eval "ac_decision_this=\$ac_decision_${ac_item}"
@ -21932,7 +22001,9 @@ else
;;
s390-*-linux-gnu)
# disable sendfile support for 2.2 on S/390
if test $os_version -lt 240; then
if test $os_pre24linux -eq 1; then
{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Disabled sendfile support for Linux 2.2 on S/390" >&5
$as_echo "$as_me: WARNING: Disabled sendfile support for Linux 2.2 on S/390" >&2;}
sendfile="0"
fi
;;
@ -23435,9 +23506,14 @@ else
/* end confdefs.h. */
#include <stdio.h>
#include <sys/types.h>
#ifdef WIN32
#define binmode "b"
#else
#define binmode
#endif
main()
{
FILE *f=fopen("conftestval", "w");
FILE *f=fopen("conftestval", "w" binmode);
if (!f) exit(1);
fprintf(f, "%d\n", sizeof(pid_t));
exit(0);
@ -23665,9 +23741,14 @@ else
/* end confdefs.h. */
#include <stdio.h>
#include <sys/types.h>
#ifdef WIN32
#define binmode "b"
#else
#define binmode
#endif
main()
{
FILE *f=fopen("conftestval", "w");
FILE *f=fopen("conftestval", "w" binmode);
if (!f) exit(1);
fprintf(f, "%d\n", sizeof(ssize_t));
exit(0);
@ -23723,9 +23804,14 @@ else
/* end confdefs.h. */
#include <stdio.h>
#include <stddef.h>
#ifdef WIN32
#define binmode "b"
#else
#define binmode
#endif
main()
{
FILE *f=fopen("conftestval", "w");
FILE *f=fopen("conftestval", "w" binmode);
if (!f) exit(1);
fprintf(f, "%d\n", sizeof(size_t));
exit(0);
@ -23781,9 +23867,14 @@ else
/* end confdefs.h. */
#include <stdio.h>
#include <sys/types.h>
#ifdef WIN32
#define binmode "b"
#else
#define binmode
#endif
main()
{
FILE *f=fopen("conftestval", "w");
FILE *f=fopen("conftestval", "w" binmode);
if (!f) exit(1);
fprintf(f, "%d\n", sizeof(off_t));
exit(0);
@ -23910,9 +24001,14 @@ else
/* end confdefs.h. */
#include <stdio.h>
$ac_includes_default
#ifdef WIN32
#define binmode "b"
#else
#define binmode
#endif
main()
{
FILE *f=fopen("conftestval", "w");
FILE *f=fopen("conftestval", "w" binmode);
if (!f) exit(1);
fprintf(f, "%d\n", sizeof(ino_t));
exit(0);
@ -24192,9 +24288,14 @@ else
#include <stdio.h>
#include <sys/types.h>
#include <sys/uio.h>
#ifdef WIN32
#define binmode "b"
#else
#define binmode
#endif
main()
{
FILE *f=fopen("conftestval", "w");
FILE *f=fopen("conftestval", "w" binmode);
if (!f) exit(1);
fprintf(f, "%d\n", sizeof(struct iovec));
exit(0);
@ -27128,6 +27229,9 @@ else
#ifdef HAVE_SYS_SOCKET_H
#include <sys/socket.h>
#endif
#ifdef HAVE_SYS_TIME_H
#include <sys/time.h>
#endif
#ifdef HAVE_SYS_SELECT_H
#include <sys/select.h>
#endif
@ -27148,6 +27252,8 @@ int main(void) {
int listen_port, rc;
struct sockaddr_in sa;
socklen_t sa_len;
fd_set fds;
struct timeval tv;
listen_s = socket(AF_INET, SOCK_STREAM, 0);
if (listen_s < 0) {
@ -27826,7 +27932,7 @@ else
#include <sys/socket.h>
#endif
void main(void) {
int main(void) {
struct addrinfo hints, *ai;
int error;
@ -27889,7 +27995,7 @@ else
#include <netdb.h>
#endif
void main(void) {
int main(void) {
if (EAI_ADDRFAMILY < 0) {
exit(0);
}
@ -27950,7 +28056,7 @@ else
#include <netinet/in.h>
#endif
void main(void) {
int main(void) {
struct sockaddr_in sa;
char hbuf[256];
int error;
@ -28415,13 +28521,21 @@ fi
# Use -no-install to link the test programs on all platforms
# but Darwin, where it would cause the programs to be linked
# against installed versions of libapr instead of those just
# built.
# Use -no-install or -no-fast-install to link the test
# programs on all platforms but Darwin, where it would cause
# the programs to be linked against installed versions of
# libapr instead of those just built.
case $host in
*-apple-darwin*) LT_NO_INSTALL="" ;;
*) LT_NO_INSTALL="-no-install" ;;
*-apple-darwin*)
LT_NO_INSTALL=""
;;
*-mingw*)
LT_NO_INSTALL="-no-fast-install"
;;
*)
LT_NO_INSTALL="-no-install"
;;
esac

View File

@ -35,7 +35,7 @@ AH_TOP([
dnl Hard-coded inclusion at the tail end of apr_private.h:
AH_BOTTOM([
/* switch this on if we have a BeOS version below BONE */
#if BEOS && !HAVE_BONE_VERSION
#if defined(BEOS) && !defined(HAVE_BONE_VERSION)
#define BEOS_R5 1
#else
#define BEOS_BONE 1
@ -282,7 +282,7 @@ AC_ARG_WITH(libtool, [ --without-libtool avoid using libtool to link the
if test "x$use_libtool" = "xyes"; then
lt_compile='$(LIBTOOL) $(LTFLAGS) --mode=compile $(COMPILE) -o $@ -c $< && touch $@'
LT_VERSION="-version-info `$get_version libtool $version_hdr APR`"
link="\$(LIBTOOL) \$(LTFLAGS) --mode=link \$(LT_LDFLAGS) \$(COMPILE) \$(LT_VERSION) \$(ALL_LDFLAGS) -o \$@"
link="\$(LIBTOOL) \$(LTFLAGS) --mode=link \$(COMPILE) \$(LT_LDFLAGS) \$(LT_VERSION) \$(ALL_LDFLAGS) -o \$@"
so_ext='lo'
lib_target='-rpath $(libdir) $(OBJECTS)'
export_lib_target='-rpath \$(libdir) \$(OBJECTS)'
@ -298,6 +298,9 @@ case $host in
*-solaris2*)
apr_platform_runtime_link_flag="-R"
;;
*-mingw* | *-cygwin*)
LT_LDFLAGS="$LT_LDFLAGS -no-undefined"
;;
*)
;;
esac
@ -432,6 +435,18 @@ case "$host:$CC" in
APR_SETVAR(CC,mwcc)
APR_SETVAR(AR,ar)
;;
dnl If building static APR, both the APR build and the app build
dnl need -DAPR_DECLARE_STATIC to generate the right linkage from
dnl APR_DECLARE et al.
dnl If building dynamic APR, the APR build needs APR_DECLARE_EXPORT
dnl and the app build should have neither define.
*-mingw* | *-cygwin*)
if test "$enable_shared" = "yes"; then
APR_ADDTO(INTERNAL_CPPFLAGS, -DAPR_DECLARE_EXPORT)
else
APR_ADDTO(CPPFLAGS, -DAPR_DECLARE_STATIC)
fi
;;
esac
AC_CACHE_CHECK([whether the compiler provides atomic builtins], [ap_cv_atomic_builtins],
@ -649,7 +664,15 @@ case $host in
fi
;;
*linux*)
os_version=`uname -r | sed -e 's/\(.\)\.\(.\)\.\(.\).*/\1\2\3/'`
os_major=[`uname -r | sed -e 's/\([1-9][0-9]*\)\..*/\1/'`]
os_minor=[`uname -r | sed -e 's/[1-9][0-9]*\.\([0-9]\+\)\..*/\1/'`]
if test $os_major -lt 2 -o \( $os_major -eq 2 -a $os_minor -lt 4 \); then
AC_MSG_WARN([Configured for pre-2.4 Linux $os_major.$os_minor])
os_pre24linux=1
else
os_pre24linux=0
AC_MSG_NOTICE([Configured for Linux $os_major.$os_minor])
fi
;;
*os390)
os_version=`uname -r | sed -e 's/\.//g'`
@ -872,78 +895,47 @@ if test "$apr_cv_dup3" = "yes"; then
AC_DEFINE([HAVE_DUP3], 1, [Define if dup3 function is supported])
fi
# test for accept4
# Test for accept4(). Create a non-blocking socket, bind it to
# an unspecified port & address (kernel picks), and attempt to
# call accept4() on it. If the syscall is wired up (i.e. the
# kernel is new enough), it should return EAGAIN.
AC_CACHE_CHECK([for accept4 support], [apr_cv_accept4],
[AC_TRY_RUN([
#include <unistd.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <sys/un.h>
#include <sys/wait.h>
#include <signal.h>
#include <netinet/in.h>
#include <netinet/tcp.h>
#include <errno.h>
#include <string.h>
#include <unistd.h>
#include <fcntl.h>
#define A4_SOCK "./apr_accept4_test_socket"
int main()
int main(int argc, char **argv)
{
pid_t pid;
int fd;
struct sockaddr_un loc, rem;
socklen_t rem_sz;
int fd, flags;
struct sockaddr_in sin;
if ((pid = fork())) {
int status;
unlink(A4_SOCK);
if ((fd = socket(AF_UNIX, SOCK_STREAM, 0)) == -1)
goto cleanup_failure2;
loc.sun_family = AF_UNIX;
strncpy(loc.sun_path, A4_SOCK, sizeof(loc.sun_path) - 1);
if (bind(fd, (struct sockaddr *) &loc,
sizeof(struct sockaddr_un)) == -1)
goto cleanup_failure;
if (listen(fd, 5) == -1)
goto cleanup_failure;
rem_sz = sizeof(struct sockaddr_un);
if (accept4(fd, (struct sockaddr *) &rem, &rem_sz, 0) == -1) {
goto cleanup_failure;
}
else {
close(fd);
waitpid(pid, &status, 0);
unlink(A4_SOCK);
return 0;
}
cleanup_failure:
close(fd);
cleanup_failure2:
kill(pid, SIGKILL);
waitpid(pid, &status, 0);
unlink(A4_SOCK);
if ((fd = socket(AF_INET, SOCK_STREAM, 0)) == -1)
return 1;
}
else {
if ((fd = socket(AF_UNIX, SOCK_STREAM, 0)) == -1)
return 1; /* this will be bad: we'll hang */
flags = fcntl(fd, F_GETFL);
if (flags == -1 || fcntl(fd, F_SETFL, flags|O_NONBLOCK) == -1)
return 5;
loc.sun_family = AF_UNIX;
strncpy(loc.sun_path, A4_SOCK, sizeof(loc.sun_path) - 1);
memset(&sin, 0, sizeof sin);
sin.sin_family = AF_INET;
if (bind(fd, (struct sockaddr *) &sin, sizeof sin) == -1)
return 2;
if (listen(fd, 5) == -1)
return 3;
while(connect(fd, (struct sockaddr *) &loc,
sizeof(struct sockaddr_un)) == -1 &&
(errno==ENOENT || errno==ECONNREFUSED))
;
close(fd);
if (accept4(fd, NULL, 0, SOCK_NONBLOCK) == 0
|| errno == EAGAIN || errno == EWOULDBLOCK)
return 0;
}
return 4;
}], [apr_cv_accept4=yes], [apr_cv_accept4=no], [apr_cv_accept4=no])])
if test "$apr_cv_accept4" = "yes"; then
@ -983,6 +975,25 @@ if test "$apr_cv_epoll_create1" = "yes"; then
AC_DEFINE([HAVE_EPOLL_CREATE1], 1, [Define if epoll_create1 function is supported])
fi
# Check for z/OS async i/o support.
AC_CACHE_CHECK([for asio -> message queue support], [apr_cv_aio_msgq],
[AC_TRY_RUN([
#define _AIO_OS390
#include <aio.h>
int main()
{
struct aiocb a;
a.aio_notifytype = AIO_MSGQ; /* use IPC message queue for notification */
return aio_cancel(2, NULL) == -1;
}], [apr_cv_aio_msgq=yes], [apr_cv_aio_msgq=no], [apr_cv_aio_msgq=no])])
if test "$apr_cv_aio_msgq" = "yes"; then
AC_DEFINE([HAVE_AIO_MSGQ], 1, [Define if async i/o supports message q's])
fi
# test for dup3
AC_CACHE_CHECK([for dup3 support], [apr_cv_dup3],
[AC_TRY_RUN([
@ -1180,7 +1191,8 @@ case $host in
# that it has it.
# FIXME - find exact 2.3 version that MMANON was fixed in. It is
# confirmed fixed in 2.4 series.
if test $os_version -le "240"; then
if test $os_pre24linux -eq 1; then
AC_MSG_WARN([Disabling anon mmap() support for Linux pre-2.4])
APR_DECISION_OVERRIDE(USE_SHMEM_MMAP_ZERO USE_SHMEM_SHMGET_ANON)
fi
;;
@ -1244,13 +1256,18 @@ APR_IFALLYES(header:os2.h,
APR_IFALLYES(header:windows.h,
[havewin32shm="1"
APR_DECIDE(USE_SHMEM_WIN32, [Windows shared memory])])
AC_ARG_ENABLE(posix-shm,
[ --enable-posix-shm Use POSIX shared memory (shm_open) if available],
[
if test "$havemmapshm" = "1"; then
APR_DECISION_OVERRIDE(USE_SHMEM_MMAP_SHM)
fi
])
case $host in
*linux* )
# Linux has problems with MM_SHMT_MMANON even though it reports
# that it has it.
# FIXME - find exact 2.3 version that MMANON was fixed in. It is
# confirmed fixed in 2.4 series.
if test $os_version -le "240"; then
# Linux pre-2.4 had problems with MM_SHMT_MMANON even though
# it reports that it has it.
if test $os_pre24linux -eq 1; then
APR_DECISION_OVERRIDE(USE_SHMEM_MMAP_TMP USE_SHMEM_MMAP_SHM dnl
USE_SHMEM_SHMGET)
fi
@ -1347,7 +1364,8 @@ AC_ARG_WITH(sendfile, [ --with-sendfile Override decision to use sendfi
;;
s390-*-linux-gnu)
# disable sendfile support for 2.2 on S/390
if test $os_version -lt 240; then
if test $os_pre24linux -eq 1; then
AC_MSG_WARN([Disabled sendfile support for Linux 2.2 on S/390])
sendfile="0"
fi
;;
@ -1532,7 +1550,7 @@ if test "$netdbh" = "1"; then
fi
AC_ARG_ENABLE(allocator-uses-mmap,
[ --enable-allocator-uses-mmap Use mmap in apr_allocator instead of malloc (experimental)],
[ --enable-allocator-uses-mmap Use mmap in apr_allocator instead of malloc ],
[ if test "$enableval" = "yes"; then
APR_IFALLYES(header:sys/mman.h func:mmap func:munmap define:MAP_ANON,
[AC_DEFINE(APR_ALLOCATOR_USES_MMAP, 1,
@ -2726,6 +2744,7 @@ AC_SUBST(NOTEST_INCLUDES)
dnl ----------------------------- Construct the files
AC_SUBST(INTERNAL_CPPFLAGS)
AC_SUBST(LDLIBS)
AC_SUBST(INCLUDES)
AC_SUBST(AR)
@ -2735,13 +2754,20 @@ AC_SUBST(DEFAULT_OSDIR)
AC_SUBST(EXEEXT)
AC_SUBST(LIBTOOL_LIBS)
# Use -no-install to link the test programs on all platforms
# but Darwin, where it would cause the programs to be linked
# against installed versions of libapr instead of those just
# built.
# Use -no-install or -no-fast-install to link the test
# programs on all platforms but Darwin, where it would cause
# the programs to be linked against installed versions of
# libapr instead of those just built.
case $host in
*-apple-darwin*) LT_NO_INSTALL="" ;;
*) LT_NO_INSTALL="-no-install" ;;
*-apple-darwin*)
LT_NO_INSTALL=""
;;
*-mingw*)
LT_NO_INSTALL="-no-fast-install"
;;
*)
LT_NO_INSTALL="-no-install"
;;
esac
AC_SUBST(LT_NO_INSTALL)

View File

@ -104,9 +104,9 @@ used as the parent to create child entries to reduce the number of expensive
stat and case canonicalization calls to the OS.</p>
<p>The comparison operation provides that the APR can postpone correction
of case by simply relying upon the device and inode for equivilance. The
of case by simply relying upon the device and inode for equivalence. The
stat implementation provides that two files are the same, while their
strings are not equivilant, and eliminates the need for the operating
strings are not equivalent, and eliminates the need for the operating
system to return the proper form of the name.</p>
<p>In any case, returning the char* path, with a flag to request the proper
@ -153,4 +153,4 @@ For each of this path Segments
</pre>
</BODY>
</HTML>
</HTML>

1181
encoding/apr_escape.c Normal file

File diff suppressed because it is too large Load Diff

View File

@ -141,8 +141,7 @@ APR_DECLARE(apr_status_t) apr_file_setaside(apr_file_t **new_file,
apr_file_t *old_file,
apr_pool_t *p)
{
*new_file = (apr_file_t *)apr_palloc(p, sizeof(apr_file_t));
memcpy(*new_file, old_file, sizeof(apr_file_t));
*new_file = (apr_file_t *)apr_pmemdup(p, old_file, sizeof(apr_file_t));
(*new_file)->pool = p;
if (old_file->buffered) {
(*new_file)->buffer = apr_palloc(p, old_file->bufsize);

View File

@ -95,7 +95,7 @@ static void fill_out_finfo(apr_finfo_t *finfo, struct_stat *info,
#elif defined(HAVE_STRUCT_STAT_ST_ATIMENSEC)
finfo->atime += info->st_atimensec / APR_TIME_C(1000);
#elif defined(HAVE_STRUCT_STAT_ST_ATIME_N)
finfo->ctime += info->st_atime_n / APR_TIME_C(1000);
finfo->atime += info->st_atime_n / APR_TIME_C(1000);
#endif
apr_time_ansi_put(&finfo->mtime, info->st_mtime);
@ -104,7 +104,7 @@ static void fill_out_finfo(apr_finfo_t *finfo, struct_stat *info,
#elif defined(HAVE_STRUCT_STAT_ST_MTIMENSEC)
finfo->mtime += info->st_mtimensec / APR_TIME_C(1000);
#elif defined(HAVE_STRUCT_STAT_ST_MTIME_N)
finfo->ctime += info->st_mtime_n / APR_TIME_C(1000);
finfo->mtime += info->st_mtime_n / APR_TIME_C(1000);
#endif
apr_time_ansi_put(&finfo->ctime, info->st_ctime);

View File

@ -74,7 +74,7 @@
#if APR_HAVE_SYS_TYPES_H
#include <sys/types.h>
#endif
#if APR_HAVE_SYS_STAT_H
#ifdef HAVE_SYS_STAT_H
#include <sys/stat.h>
#endif
#if APR_HAVE_FCNTL_H

View File

@ -135,6 +135,14 @@ APR_DECLARE(apr_status_t) apr_file_open(apr_file_t **new,
}
#endif
if (flag & APR_FOPEN_NONBLOCK) {
#ifdef O_NONBLOCK
oflags |= O_NONBLOCK;
#else
return APR_ENOTIMPL;
#endif
}
#ifdef O_CLOEXEC
/* Introduced in Linux 2.6.23. Silently ignored on earlier Linux kernels.
*/

View File

@ -25,8 +25,8 @@
* but now fcntl does, hence we need to do this extra checking.
* The joys of beta programs. :-)
*/
#if BEOS
#if !BONE7
#if defined(BEOS)
#if !defined(BONE7)
# define BEOS_BLOCKING 1
#else
# define BEOS_BLOCKING 0
@ -35,7 +35,7 @@
static apr_status_t pipeblock(apr_file_t *thepipe)
{
#if !BEOS_BLOCKING
#if !defined(BEOS) || !BEOS_BLOCKING
int fd_flags;
fd_flags = fcntl(thepipe->filedes, F_GETFL, 0);
@ -71,7 +71,7 @@ static apr_status_t pipeblock(apr_file_t *thepipe)
static apr_status_t pipenonblock(apr_file_t *thepipe)
{
#if !BEOS_BLOCKING
#if !defined(BEOS) || !BEOS_BLOCKING
int fd_flags = fcntl(thepipe->filedes, F_GETFL, 0);
# if defined(O_NONBLOCK)

View File

@ -21,7 +21,7 @@
/* The only case where we don't use wait_for_io_or_timeout is on
* pre-BONE BeOS, so this check should be sufficient and simpler */
#if !BEOS_R5
#if !defined(BEOS_R5)
#define USE_WAIT_FOR_IO
#endif

View File

@ -116,7 +116,7 @@
* or the extern "C" namespace
*/
#if APR_HAVE_WINDOWS_H
#if APR_HAVE_WINDOWS_H && defined(WIN32)
/* If windows.h was already included, our preferences don't matter.
* If not, include a restricted set of windows headers to our tastes.
*/
@ -453,6 +453,8 @@ typedef apr_uint32_t apr_uintptr_t;
*/
#define APR_THREAD_FUNC @apr_thread_func@
#if defined(DOXYGEN) || !defined(WIN32)
/**
* The public APR functions are declared with APR_DECLARE(), so they may
* use the most appropriate calling convention. Public APR functions with
@ -505,6 +507,20 @@ typedef apr_uint32_t apr_uintptr_t;
*/
#define APR_DECLARE_DATA
#elif defined(APR_DECLARE_STATIC)
#define APR_DECLARE(type) type __stdcall
#define APR_DECLARE_NONSTD(type) type __cdecl
#define APR_DECLARE_DATA
#elif defined(APR_DECLARE_EXPORT)
#define APR_DECLARE(type) __declspec(dllexport) type __stdcall
#define APR_DECLARE_NONSTD(type) __declspec(dllexport) type __cdecl
#define APR_DECLARE_DATA __declspec(dllexport)
#else
#define APR_DECLARE(type) __declspec(dllimport) type __stdcall
#define APR_DECLARE_NONSTD(type) __declspec(dllimport) type __cdecl
#define APR_DECLARE_DATA __declspec(dllimport)
#endif
/* Define APR_SSIZE_T_FMT.
* If ssize_t is an integer we define it to be "d",
* if ssize_t is a long int we define it to be "ld",

641
include/apr.hwc Normal file
View File

@ -0,0 +1,641 @@
/* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#ifndef APR_H
#define APR_H
/* GENERATED FILE WARNING! DO NOT EDIT apr.h
*
* You must modify apr.hwc instead.
*
* And please, make an effort to stub apr.hnw and apr.h.in in the process.
*
* This is the Win32 specific version of apr.h. It is copied from
* apr.hw by the apr.dsp and libapr.dsp projects.
*/
/**
* @file apr.h
* @brief APR Platform Definitions
* @remark This is a generated header generated from include/apr.h.in by
* ./configure, or copied from include/apr.hw or include/apr.hnw
* for Win32 or Netware by those build environments, respectively.
*/
/* Make sure we have our platform identifier macro defined we ask for later.
*/
#if defined(_WIN32) && !defined(WIN32)
#define WIN32 1
#endif
#if defined(WIN32) || defined(DOXYGEN)
/* Ignore most warnings (back down to /W3) for poorly constructed headers
*/
#if defined(_MSC_VER) && _MSC_VER >= 1200
#pragma warning(push, 3)
#endif
/* disable or reduce the frequency of...
* C4057: indirection to slightly different base types
* C4075: slight indirection changes (unsigned short* vs short[])
* C4100: unreferenced formal parameter
* C4127: conditional expression is constant
* C4163: '_rotl64' : not available as an intrinsic function
* C4201: nonstandard extension nameless struct/unions
* C4244: int to char/short - precision loss
* C4514: unreferenced inline function removed
*/
#pragma warning(disable: 4100 4127 4163 4201 4514; once: 4057 4075 4244)
/* Ignore Microsoft's interpretation of secure development
* and the POSIX string handling API
*/
#if defined(_MSC_VER) && _MSC_VER >= 1400
#ifndef _CRT_SECURE_NO_DEPRECATE
#define _CRT_SECURE_NO_DEPRECATE
#endif
#pragma warning(disable: 4996)
#endif
/* Has windows.h already been included? If so, our preferences don't matter,
* but we will still need the winsock things no matter what was included.
* If not, include a restricted set of windows headers to our tastes.
*/
#ifndef _WINDOWS_
#ifndef WIN32_LEAN_AND_MEAN
#define WIN32_LEAN_AND_MEAN
#endif
#ifndef _WIN32_WINNT
#define _WIN32_WINNT @win32_winnt_str@
#endif
#ifndef NOUSER
#define NOUSER
#endif
#ifndef NOMCX
#define NOMCX
#endif
#ifndef NOIME
#define NOIME
#endif
#include <windows.h>
/*
* Add a _very_few_ declarations missing from the restricted set of headers
* (If this list becomes extensive, re-enable the required headers above!)
* winsock headers were excluded by WIN32_LEAN_AND_MEAN, so include them now
*/
#define SW_HIDE 0
#ifndef _WIN32_WCE
#include <winsock2.h>
#include <ws2tcpip.h>
#include <mswsock.h>
#else
#include <winsock.h>
#endif
#endif /* !_WINDOWS_ */
/**
* @defgroup APR Apache Portability Runtime library
* @{
*/
/**
* @defgroup apr_platform Platform Definitions
* @{
* @warning
* <strong><em>The actual values of macros and typedefs on this page<br>
* are platform specific and should NOT be relied upon!</em></strong>
*/
#define APR_INLINE __inline
#define APR_HAS_INLINE 1
#if !defined(__GNUC__) && !defined(__attribute__)
#define __attribute__(__x)
#endif
#ifndef _WIN32_WCE
#define APR_HAVE_ARPA_INET_H 0
#define APR_HAVE_CONIO_H 1
#define APR_HAVE_CRYPT_H 0
#define APR_HAVE_CTYPE_H 1
#define APR_HAVE_DIRENT_H 0
#define APR_HAVE_ERRNO_H 1
#define APR_HAVE_FCNTL_H 1
#define APR_HAVE_IO_H 1
#define APR_HAVE_LIMITS_H 1
#define APR_HAVE_NETDB_H 0
#define APR_HAVE_NETINET_IN_H 0
#define APR_HAVE_NETINET_SCTP_H 0
#define APR_HAVE_NETINET_SCTP_UIO_H 0
#define APR_HAVE_NETINET_TCP_H 0
#define APR_HAVE_PTHREAD_H 0
#define APR_HAVE_SEMAPHORE_H 0
#define APR_HAVE_SIGNAL_H 1
#define APR_HAVE_STDARG_H 1
#define APR_HAVE_STDINT_H 0
#define APR_HAVE_STDIO_H 1
#define APR_HAVE_STDLIB_H 1
#define APR_HAVE_STRING_H 1
#define APR_HAVE_STRINGS_H 0
#define APR_HAVE_SYS_IOCTL_H 0
#define APR_HAVE_SYS_SENDFILE_H 0
#define APR_HAVE_SYS_SIGNAL_H 0
#define APR_HAVE_SYS_SOCKET_H 0
#define APR_HAVE_SYS_SOCKIO_H 0
#define APR_HAVE_SYS_SYSLIMITS_H 0
#define APR_HAVE_SYS_TIME_H 0
#define APR_HAVE_SYS_TYPES_H 1
#define APR_HAVE_SYS_UIO_H 0
#define APR_HAVE_SYS_UN_H 0
#define APR_HAVE_SYS_WAIT_H 0
#define APR_HAVE_TIME_H 1
#define APR_HAVE_UNISTD_H 0
#define APR_HAVE_STDDEF_H 1
#define APR_HAVE_PROCESS_H 1
#else
#define APR_HAVE_ARPA_INET_H 0
#define APR_HAVE_CONIO_H 0
#define APR_HAVE_CRYPT_H 0
#define APR_HAVE_CTYPE_H 0
#define APR_HAVE_DIRENT_H 0
#define APR_HAVE_ERRNO_H 0
#define APR_HAVE_FCNTL_H 0
#define APR_HAVE_IO_H 0
#define APR_HAVE_LIMITS_H 0
#define APR_HAVE_NETDB_H 0
#define APR_HAVE_NETINET_IN_H 0
#define APR_HAVE_NETINET_SCTP_H 0
#define APR_HAVE_NETINET_SCTP_UIO_H 0
#define APR_HAVE_NETINET_TCP_H 0
#define APR_HAVE_PTHREAD_H 0
#define APR_HAVE_SEMAPHORE_H 0
#define APR_HAVE_SIGNAL_H 0
#define APR_HAVE_STDARG_H 0
#define APR_HAVE_STDINT_H 0
#define APR_HAVE_STDIO_H 1
#define APR_HAVE_STDLIB_H 1
#define APR_HAVE_STRING_H 1
#define APR_HAVE_STRINGS_H 0
#define APR_HAVE_SYS_IOCTL_H 0
#define APR_HAVE_SYS_SENDFILE_H 0
#define APR_HAVE_SYS_SIGNAL_H 0
#define APR_HAVE_SYS_SOCKET_H 0
#define APR_HAVE_SYS_SOCKIO_H 0
#define APR_HAVE_SYS_SYSLIMITS_H 0
#define APR_HAVE_SYS_TIME_H 0
#define APR_HAVE_SYS_TYPES_H 0
#define APR_HAVE_SYS_UIO_H 0
#define APR_HAVE_SYS_UN_H 0
#define APR_HAVE_SYS_WAIT_H 0
#define APR_HAVE_TIME_H 0
#define APR_HAVE_UNISTD_H 0
#define APR_HAVE_STDDEF_H 0
#define APR_HAVE_PROCESS_H 0
#endif
/** @} */
/** @} */
/* We don't include our conditional headers within the doxyblocks
* or the extern "C" namespace
*/
#if APR_HAVE_STDLIB_H
#include <stdlib.h>
#endif
#if APR_HAVE_STDIO_H
#include <stdio.h>
#endif
#if APR_HAVE_SYS_TYPES_H
#include <sys/types.h>
#endif
#if APR_HAVE_STDDEF_H
#include <stddef.h>
#endif
#if APR_HAVE_TIME_H
#include <time.h>
#endif
#if APR_HAVE_PROCESS_H
#include <process.h>
#endif
#ifdef __cplusplus
extern "C" {
#endif
/**
* @addtogroup apr_platform
* @ingroup APR
* @{
*/
#define APR_HAVE_SHMEM_MMAP_TMP 0
#define APR_HAVE_SHMEM_MMAP_SHM 0
#define APR_HAVE_SHMEM_MMAP_ZERO 0
#define APR_HAVE_SHMEM_SHMGET_ANON 0
#define APR_HAVE_SHMEM_SHMGET 0
#define APR_HAVE_SHMEM_MMAP_ANON 0
#define APR_HAVE_SHMEM_BEOS 0
#define APR_USE_SHMEM_MMAP_TMP 0
#define APR_USE_SHMEM_MMAP_SHM 0
#define APR_USE_SHMEM_MMAP_ZERO 0
#define APR_USE_SHMEM_SHMGET_ANON 0
#define APR_USE_SHMEM_SHMGET 0
#define APR_USE_SHMEM_MMAP_ANON 0
#define APR_USE_SHMEM_BEOS 0
#define APR_USE_FLOCK_SERIALIZE 0
#define APR_USE_POSIXSEM_SERIALIZE 0
#define APR_USE_SYSVSEM_SERIALIZE 0
#define APR_USE_FCNTL_SERIALIZE 0
#define APR_USE_PROC_PTHREAD_SERIALIZE 0
#define APR_USE_PTHREAD_SERIALIZE 0
#define APR_HAS_FLOCK_SERIALIZE 0
#define APR_HAS_SYSVSEM_SERIALIZE 0
#define APR_HAS_POSIXSEM_SERIALIZE 0
#define APR_HAS_FCNTL_SERIALIZE 0
#define APR_HAS_PROC_PTHREAD_SERIALIZE 0
#define APR_PROCESS_LOCK_IS_GLOBAL 0
#define APR_HAVE_CORKABLE_TCP 0
#define APR_HAVE_GETRLIMIT 0
#define APR_HAVE_ICONV 0
#define APR_HAVE_IN_ADDR 1
#define APR_HAVE_INET_ADDR 1
#define APR_HAVE_INET_NETWORK 0
#define APR_HAVE_IPV6 @apr_have_ipv6_10@
#define APR_HAVE_MEMMOVE 1
#define APR_HAVE_SETRLIMIT 0
#define APR_HAVE_SIGACTION 0
#define APR_HAVE_SIGSUSPEND 0
#define APR_HAVE_SIGWAIT 0
#define APR_HAVE_SA_STORAGE 0
#define APR_HAVE_STRCASECMP 0
#define APR_HAVE_STRDUP 1
#define APR_HAVE_STRNCASECMP 0
#define APR_HAVE_STRSTR 1
#define APR_HAVE_MEMCHR 1
#define APR_HAVE_STRUCT_RLIMIT 0
#define APR_HAVE_UNION_SEMUN 0
#define APR_HAVE_SCTP 0
#define APR_HAVE_IOVEC 0
#ifndef _WIN32_WCE
#define APR_HAVE_STRICMP 1
#define APR_HAVE_STRNICMP 1
#else
#define APR_HAVE_STRICMP 0
#define APR_HAVE_STRNICMP 0
#endif
/* APR Feature Macros */
#define APR_HAS_SHARED_MEMORY 1
#define APR_HAS_THREADS 1
#define APR_HAS_MMAP 1
#define APR_HAS_FORK 0
#define APR_HAS_RANDOM 1
#define APR_HAS_OTHER_CHILD 1
#define APR_HAS_DSO 1
#define APR_HAS_SO_ACCEPTFILTER 0
#define APR_HAS_UNICODE_FS 1
#define APR_HAS_PROC_INVOKED 1
#define APR_HAS_OS_UUID 1
#ifndef _WIN32_WCE
#define APR_HAS_SENDFILE 1
#define APR_HAS_USER 1
#define APR_HAS_LARGE_FILES 1
#define APR_HAS_XTHREAD_FILES 1
#define APR_PROCATTR_USER_SET_REQUIRES_PASSWORD 1
#else
#define APR_HAS_SENDFILE 0
#define APR_HAS_USER 0
#define APR_HAS_LARGE_FILES 0
#define APR_HAS_XTHREAD_FILES 0
#define APR_PROCATTR_USER_SET_REQUIRES_PASSWORD 0
#endif
/* APR sets APR_FILES_AS_SOCKETS to 1 on systems where it is possible
* to poll on files/pipes.
*/
#define APR_FILES_AS_SOCKETS 0
/* This macro indicates whether or not EBCDIC is the native character set.
*/
#define APR_CHARSET_EBCDIC 0
/* If we have a TCP implementation that can be "corked", what flag
* do we use?
*/
#define APR_TCP_NOPUSH_FLAG @apr_tcp_nopush_flag@
/* Is the TCP_NODELAY socket option inherited from listening sockets?
*/
#define APR_TCP_NODELAY_INHERITED 1
/* Is the O_NONBLOCK flag inherited from listening sockets?
*/
#define APR_O_NONBLOCK_INHERITED 1
/* Typedefs that APR needs. */
typedef unsigned char apr_byte_t;
typedef short apr_int16_t;
typedef unsigned short apr_uint16_t;
typedef int apr_int32_t;
typedef unsigned int apr_uint32_t;
typedef __int64 apr_int64_t;
typedef unsigned __int64 apr_uint64_t;
typedef size_t apr_size_t;
#if APR_HAVE_STDDEF_H
typedef ptrdiff_t apr_ssize_t;
#else
typedef int apr_ssize_t;
#endif
#if APR_HAS_LARGE_FILES
typedef __int64 apr_off_t;
#else
typedef int apr_off_t;
#endif
typedef int apr_socklen_t;
typedef apr_uint64_t apr_ino_t;
#ifdef _WIN64
#define APR_SIZEOF_VOIDP 8
#else
#define APR_SIZEOF_VOIDP 4
#endif
#if APR_SIZEOF_VOIDP == 8
typedef apr_uint64_t apr_uintptr_t;
#else
typedef apr_uint32_t apr_uintptr_t;
#endif
/* Are we big endian? */
/* XXX: Fatal assumption on Alpha platforms */
#define APR_IS_BIGENDIAN 0
/* Mechanisms to properly type numeric literals */
#ifndef __GNUC__
#define APR_INT64_C(val) (val##i64)
#define APR_UINT64_C(val) (val##Ui64)
#else
#define APR_INT64_C(val) (val##LL)
#define APR_UINT64_C(val) (val##ULL)
#endif
#ifdef INT16_MIN
#define APR_INT16_MIN INT16_MIN
#else
#define APR_INT16_MIN (-0x7fff - 1)
#endif
#ifdef INT16_MAX
#define APR_INT16_MAX INT16_MAX
#else
#define APR_INT16_MAX (0x7fff)
#endif
#ifdef UINT16_MAX
#define APR_UINT16_MAX UINT16_MAX
#else
#define APR_UINT16_MAX (0xffff)
#endif
#ifdef INT32_MIN
#define APR_INT32_MIN INT32_MIN
#else
#define APR_INT32_MIN (-0x7fffffff - 1)
#endif
#ifdef INT32_MAX
#define APR_INT32_MAX INT32_MAX
#else
#define APR_INT32_MAX 0x7fffffff
#endif
#ifdef UINT32_MAX
#define APR_UINT32_MAX UINT32_MAX
#else
#define APR_UINT32_MAX (0xffffffffU)
#endif
#ifdef INT64_MIN
#define APR_INT64_MIN INT64_MIN
#else
#define APR_INT64_MIN (APR_INT64_C(-0x7fffffffffffffff) - 1)
#endif
#ifdef INT64_MAX
#define APR_INT64_MAX INT64_MAX
#else
#define APR_INT64_MAX APR_INT64_C(0x7fffffffffffffff)
#endif
#ifdef UINT64_MAX
#define APR_UINT64_MAX UINT64_MAX
#else
#define APR_UINT64_MAX APR_UINT64_C(0xffffffffffffffff)
#endif
#define APR_SIZE_MAX (~((apr_size_t)0))
/* Definitions that APR programs need to work properly. */
/**
* APR public API wrap for C++ compilers.
*/
#ifdef __cplusplus
#define APR_BEGIN_DECLS extern "C" {
#define APR_END_DECLS }
#else
#define APR_BEGIN_DECLS
#define APR_END_DECLS
#endif
/**
* Thread callbacks from APR functions must be declared with APR_THREAD_FUNC,
* so that they follow the platform's calling convention.
* <PRE>
*
* void* APR_THREAD_FUNC my_thread_entry_fn(apr_thread_t *thd, void *data);
*
* </PRE>
*/
#define APR_THREAD_FUNC __stdcall
#if defined(DOXYGEN) || !defined(WIN32)
/**
* The public APR functions are declared with APR_DECLARE(), so they may
* use the most appropriate calling convention. Public APR functions with
* variable arguments must use APR_DECLARE_NONSTD().
*
* @remark Both the declaration and implementations must use the same macro.
*
* <PRE>
* APR_DECLARE(rettype) apr_func(args)
* </PRE>
* @see APR_DECLARE_NONSTD @see APR_DECLARE_DATA
* @remark Note that when APR compiles the library itself, it passes the
* symbol -DAPR_DECLARE_EXPORT to the compiler on some platforms (e.g. Win32)
* to export public symbols from the dynamic library build.\n
* The user must define the APR_DECLARE_STATIC when compiling to target
* the static APR library on some platforms (e.g. Win32.) The public symbols
* are neither exported nor imported when APR_DECLARE_STATIC is defined.\n
* By default, compiling an application and including the APR public
* headers, without defining APR_DECLARE_STATIC, will prepare the code to be
* linked to the dynamic library.
*/
#define APR_DECLARE(type) type
/**
* The public APR functions using variable arguments are declared with
* APR_DECLARE_NONSTD(), as they must follow the C language calling convention.
* @see APR_DECLARE @see APR_DECLARE_DATA
* @remark Both the declaration and implementations must use the same macro.
* <PRE>
*
* APR_DECLARE_NONSTD(rettype) apr_func(args, ...);
*
* </PRE>
*/
#define APR_DECLARE_NONSTD(type) type
/**
* The public APR variables are declared with AP_MODULE_DECLARE_DATA.
* This assures the appropriate indirection is invoked at compile time.
* @see APR_DECLARE @see APR_DECLARE_NONSTD
* @remark Note that the declaration and implementations use different forms,
* but both must include the macro.
*
* <PRE>
*
* extern APR_DECLARE_DATA type apr_variable;\n
* APR_DECLARE_DATA type apr_variable = value;
*
* </PRE>
*/
#define APR_DECLARE_DATA
#elif defined(APR_DECLARE_STATIC)
#define APR_DECLARE(type) type __stdcall
#define APR_DECLARE_NONSTD(type) type __cdecl
#define APR_DECLARE_DATA
#elif defined(APR_DECLARE_EXPORT)
#define APR_DECLARE(type) __declspec(dllexport) type __stdcall
#define APR_DECLARE_NONSTD(type) __declspec(dllexport) type __cdecl
#define APR_DECLARE_DATA __declspec(dllexport)
#else
#define APR_DECLARE(type) __declspec(dllimport) type __stdcall
#define APR_DECLARE_NONSTD(type) __declspec(dllimport) type __cdecl
#define APR_DECLARE_DATA __declspec(dllimport)
#endif
#ifdef _WIN64
#define APR_SSIZE_T_FMT "I64d"
#define APR_SIZE_T_FMT "I64u"
#else
#define APR_SSIZE_T_FMT "d"
#define APR_SIZE_T_FMT "u"
#endif
#if APR_HAS_LARGE_FILES
#define APR_OFF_T_FMT "I64d"
#else
#define APR_OFF_T_FMT "d"
#endif
#define APR_PID_T_FMT "d"
#define APR_INT64_T_FMT "I64d"
#define APR_UINT64_T_FMT "I64u"
#define APR_UINT64_T_HEX_FMT "I64x"
/* No difference between PROC and GLOBAL mutex */
#define APR_PROC_MUTEX_IS_GLOBAL 1
/* Local machine definition for console and log output. */
#define APR_EOL_STR "\r\n"
typedef int apr_wait_t;
#if APR_HAS_UNICODE_FS
/* An arbitrary size that is digestable. True max is a bit less than 32000 */
#define APR_PATH_MAX 8192
#else /* !APR_HAS_UNICODE_FS */
#define APR_PATH_MAX MAX_PATH
#endif
#define APR_DSOPATH "PATH"
/** @} */
/* Definitions that only Win32 programs need to compile properly. */
/* XXX These simply don't belong here, perhaps in apr_portable.h
* based on some APR_HAVE_PID/GID/UID?
*/
#ifndef __GNUC__
typedef int pid_t;
#endif
typedef int uid_t;
typedef int gid_t;
/* Win32 .h ommissions we really need */
#define STDIN_FILENO 0
#define STDOUT_FILENO 1
#define STDERR_FILENO 2
#if APR_HAVE_IPV6
/* Appears in later flavors, not the originals. */
#ifndef in_addr6
#define in6_addr in_addr6
#endif
#ifndef WS2TCPIP_INLINE
#define IN6_IS_ADDR_V4MAPPED(a) \
( (*(const apr_uint64_t *)(const void *)(&(a)->s6_addr[0]) == 0) \
&& (*(const apr_uint32_t *)(const void *)(&(a)->s6_addr[8]) == ntohl(0x0000ffff)))
#endif
#endif /* APR_HAS_IPV6 */
#ifdef __cplusplus
}
#endif
/* Done with badly written headers
*/
#if defined(_MSC_VER) && _MSC_VER >= 1200
#pragma warning(pop)
#pragma warning(disable: 4996)
#endif
#endif /* WIN32 */
#endif /* APR_H */

View File

@ -131,7 +131,7 @@ APR_DECLARE(apr_pool_t *) apr_allocator_owner_get(apr_allocator_t *allocator)
/**
* Set the current threshold at which the allocator should start
* giving blocks back to the system.
* @param allocator The allocator the set the threshold on
* @param allocator The allocator to set the threshold on
* @param size The threshold. 0 == unlimited.
*/
APR_DECLARE(void) apr_allocator_max_free_set(apr_allocator_t *allocator,

View File

@ -45,7 +45,7 @@ typedef int apr_status_t;
/**
* Return a human readable string describing the specified error.
* @param statcode The error code the get a string for.
* @param statcode The error code to get a string for.
* @param buf A buffer to hold the error string.
* @param bufsize Size of the buffer to hold the string.
*/
@ -126,7 +126,7 @@ APR_DECLARE(char *) apr_strerror(apr_status_t statcode, char *buf,
* use within apr-util. This space is reserved above that used by APR
* internally.
* @note This number MUST be smaller than APR_OS_ERRSPACE_SIZE by a
* large enough amount that APR has sufficient room for it's
* large enough amount that APR has sufficient room for its
* codes.
*/
#define APR_UTIL_ERRSPACE_SIZE 20000
@ -135,7 +135,7 @@ APR_DECLARE(char *) apr_strerror(apr_status_t statcode, char *buf,
*/
#define APR_OS_START_STATUS (APR_OS_START_ERROR + APR_OS_ERRSPACE_SIZE)
/**
* APR_UTIL_START_STATUS is where APR-Util starts defining it's
* APR_UTIL_START_STATUS is where APR-Util starts defining its
* status codes.
*/
#define APR_UTIL_START_STATUS (APR_OS_START_STATUS + \

374
include/apr_escape.h Normal file
View File

@ -0,0 +1,374 @@
/* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
/**
* @file apr_escape.h
* @brief APR-UTIL Escaping
*/
#ifndef APR_ESCAPE_H
#define APR_ESCAPE_H
#include "apr.h"
#include "apr_general.h"
#ifdef __cplusplus
extern "C" {
#endif
/**
* @defgroup APR_Util_Escaping Escape functions
* @ingroup APR
* @{
*/
/* Simple escape/unescape functions.
*
*/
/**
* When passing a string to one of the escape functions, this value can be
* passed to indicate a string-valued key, and have the length computed
* automatically.
*/
#define APR_ESCAPE_STRING (-1)
/**
* Perform shell escaping on the provided string.
*
* Shell escaping causes characters to be prefixed with a '\' character.
* @param escaped Optional buffer to write the encoded string, can be
* NULL
* @param str The original string
* @param slen The length of the original string, or APR_ESCAPE_STRING
* @param len If present, returns the length of the string
* @return APR_SUCCESS, or APR_NOTFOUND if no changes to the string were
* detected or the string was NULL
*/
APR_DECLARE(apr_status_t) apr_escape_shell(char *escaped, const char *str,
apr_ssize_t slen, apr_size_t *len);
/**
* Perform shell escaping on the provided string, returning the result
* from the pool.
*
* Shell escaping causes characters to be prefixed with a '\' character.
*
* If no characters were escaped, the original string is returned.
* @param p Pool to allocate from
* @param str The original string
* @return the encoded string, allocated from the pool, or the original
* string if no escaping took place or the string was NULL.
*/
APR_DECLARE(const char *) apr_pescape_shell(apr_pool_t *p, const char *str)
__attribute__((nonnull(1)));
/**
* Unescapes a URL, leaving reserved characters intact.
* @param escaped Optional buffer to write the encoded string, can be
* NULL
* @param url String to be unescaped
* @param slen The length of the original url, or APR_ESCAPE_STRING
* @param forbid Optional list of forbidden characters, in addition to
* 0x00
* @param reserved Optional list of reserved characters that will be
* left unescaped
* @param plus If non zero, '+' is converted to ' ' as per
* application/x-www-form-urlencoded encoding
* @param len If set, the length of the escaped string will be returned
* @return APR_SUCCESS on success, APR_NOTFOUND if no characters are
* decoded or the string is NULL, APR_EINVAL if a bad escape sequence is
* found, APR_BADCH if a character on the forbid list is found.
*/
APR_DECLARE(apr_status_t) apr_unescape_url(char *escaped, const char *url,
apr_ssize_t slen, const char *forbid, const char *reserved, int plus,
apr_size_t *len);
/**
* Unescapes a URL, leaving reserved characters intact, returning the
* result from a pool.
* @param p Pool to allocate from
* @param url String to be unescaped in place
* @param forbid Optional list of forbidden characters, in addition to
* 0x00
* @param reserved Optional list of reserved characters that will be
* left unescaped
* @param plus If non zero, '+' is converted to ' ' as per
* application/x-www-form-urlencoded encoding
* @return A string allocated from the pool on success, the original string
* if no characters are decoded, or NULL if a bad escape sequence is found
* or if a character on the forbid list is found, or if the original string
* was NULL.
*/
APR_DECLARE(const char *) apr_punescape_url(apr_pool_t *p, const char *url,
const char *forbid, const char *reserved, int plus)
__attribute__((nonnull(1)));
/**
* Escape a path segment, as defined in RFC1808.
* @param escaped Optional buffer to write the encoded string, can be
* NULL
* @param str The original string
* @param slen The length of the original string, or APR_ESCAPE_STRING
* @param len If present, returns the length of the string
* @return APR_SUCCESS, or APR_NOTFOUND if no changes to the string were
* detected or the string was NULL
*/
APR_DECLARE(apr_status_t) apr_escape_path_segment(char *escaped,
const char *str, apr_ssize_t slen, apr_size_t *len);
/**
* Escape a path segment, as defined in RFC1808, returning the result from a
* pool.
* @param p Pool to allocate from
* @param str String to be escaped
* @return A string allocated from the pool on success, the original string
* if no characters are encoded or the string is NULL.
*/
APR_DECLARE(const char *) apr_pescape_path_segment(apr_pool_t *p,
const char *str) __attribute__((nonnull(1)));
/**
* Converts an OS path to a URL, in an OS dependent way, as defined in RFC1808.
* In all cases if a ':' occurs before the first '/' in the URL, the URL should
* be prefixed with "./" (or the ':' escaped). In the case of Unix, this means
* leaving '/' alone, but otherwise doing what escape_path_segment() does. For
* efficiency reasons, we don't use escape_path_segment(), which is provided for
* reference. Again, RFC 1808 is where this stuff is defined.
*
* If partial is set, os_escape_path() assumes that the path will be appended to
* something with a '/' in it (and thus does not prefix "./").
* @param escaped Optional buffer to write the encoded string, can be
* NULL
* @param path The original string
* @param slen The length of the original string, or APR_ESCAPE_STRING
* @param partial If non zero, suppresses the prepending of "./"
* @param len If present, returns the length of the string
* @return APR_SUCCESS, or APR_NOTFOUND if no changes to the string were
* detected or if the string was NULL
*/
APR_DECLARE(apr_status_t) apr_escape_path(char *escaped, const char *path,
apr_ssize_t slen, int partial, apr_size_t *len);
/**
* Converts an OS path to a URL, in an OS dependent way, as defined in RFC1808,
* returning the result from a pool.
*
* In all cases if a ':' occurs before the first '/' in the URL, the URL should
* be prefixed with "./" (or the ':' escaped). In the case of Unix, this means
* leaving '/' alone, but otherwise doing what escape_path_segment() does. For
* efficiency reasons, we don't use escape_path_segment(), which is provided for
* reference. Again, RFC 1808 is where this stuff is defined.
*
* If partial is set, os_escape_path() assumes that the path will be appended to
* something with a '/' in it (and thus does not prefix "./").
* @param p Pool to allocate from
* @param str The original string
* @param partial If non zero, suppresses the prepending of "./"
* @return A string allocated from the pool on success, the original string
* if no characters are encoded or if the string was NULL.
*/
APR_DECLARE(const char *) apr_pescape_path(apr_pool_t *p, const char *str,
int partial) __attribute__((nonnull(1)));
/**
* Urlencode a string, as defined in
* http://www.w3.org/TR/html401/interact/forms.html#h-17.13.4.1.
* @param escaped Optional buffer to write the encoded string, can be
* NULL
* @param str The original string
* @param slen The length of the original string, or APR_ESCAPE_STRING
* @param len If present, returns the length of the string
* @return APR_SUCCESS, or APR_NOTFOUND if no changes to the string were
* detected or if the stirng was NULL
*/
APR_DECLARE(apr_status_t) apr_escape_urlencoded(char *escaped, const char *str,
apr_ssize_t slen, apr_size_t *len);
/**
* Urlencode a string, as defined in
* http://www.w3.org/TR/html401/interact/forms.html#h-17.13.4.1, returning
* the result from a pool.
* @param p Pool to allocate from
* @param str String to be escaped
* @return A string allocated from the pool on success, the original string
* if no characters are encoded or if the string was NULL.
*/
APR_DECLARE(const char *) apr_pescape_urlencoded(apr_pool_t *p,
const char *str) __attribute__((nonnull(1)));
/**
* Apply entity encoding to a string. Characters are replaced as follows:
* '<' becomes '&lt;', '>' becomes '&gt;', '&' becomes '&amp;', the
* double quote becomes '&quot;" and the single quote becomes '&apos;'.
*
* If toasc is not zero, any non ascii character will be encoded as
* '%\#ddd;', where ddd is the decimal code of the character.
* @param escaped Optional buffer to write the encoded string, can be
* NULL
* @param str The original string
* @param slen The length of the original string, or APR_ESCAPE_STRING
* @param toasc If non zero, encode non ascii characters
* @param len If present, returns the length of the string
* @return APR_SUCCESS, or APR_NOTFOUND if no changes to the string were
* detected or the string was NULL
*/
APR_DECLARE(apr_status_t) apr_escape_entity(char *escaped, const char *str,
apr_ssize_t slen, int toasc, apr_size_t *len);
/**
* Apply entity encoding to a string, returning the result from a pool.
* Characters are replaced as follows: '<' becomes '&lt;', '>' becomes
* '&gt;', '&' becomes '&amp;', the double quote becomes '&quot;" and the
* single quote becomes '&apos;'.
* @param p Pool to allocate from
* @param str The original string
* @param toasc If non zero, encode non ascii characters
* @return A string allocated from the pool on success, the original string
* if no characters are encoded or the string is NULL.
*/
APR_DECLARE(const char *) apr_pescape_entity(apr_pool_t *p, const char *str,
int toasc) __attribute__((nonnull(1)));
/**
* Decodes html entities or numeric character references in a string. If
* the string to be unescaped is syntactically incorrect, then the
* following fixups will be made:
* unknown entities will be left undecoded;
* references to unused numeric characters will be deleted.
* In particular, &#00; will not be decoded, but will be deleted.
* @param unescaped Optional buffer to write the encoded string, can be
* NULL
* @param str The original string
* @param slen The length of the original string, or APR_ESCAPE_STRING
* @param len If present, returns the length of the string
* @return APR_SUCCESS, or APR_NOTFOUND if no changes to the string were
* detected or the string was NULL
*/
APR_DECLARE(apr_status_t) apr_unescape_entity(char *unescaped, const char *str,
apr_ssize_t slen, apr_size_t *len);
/**
* Decodes html entities or numeric character references in a string. If
* the string to be unescaped is syntactically incorrect, then the
* following fixups will be made:
* unknown entities will be left undecoded;
* references to unused numeric characters will be deleted.
* In particular, &#00; will not be decoded, but will be deleted.
* @param p Pool to allocate from
* @param str The original string
* @return A string allocated from the pool on success, the original string
* if no characters are encoded or the string is NULL.
*/
APR_DECLARE(const char *) apr_punescape_entity(apr_pool_t *p, const char *str)
__attribute__((nonnull(1)));
/**
* Escape control characters in a string, as performed by the shell's
* 'echo' command. Characters are replaced as follows:
* \\a alert (bell), \\b backspace, \\f form feed, \\n new line, \\r carriage
* return, \\t horizontal tab, \\v vertical tab, \\ backslash.
*
* Any non ascii character will be encoded as '\\xHH', where HH is the hex
* code of the character.
*
* If quote is not zero, the double quote character will also be escaped.
* @param escaped Optional buffer to write the encoded string, can be
* NULL
* @param str The original string
* @param slen The length of the original string, or APR_ESCAPE_STRING
* @param quote If non zero, encode double quotes
* @param len If present, returns the length of the string
* @return APR_SUCCESS, or APR_NOTFOUND if no changes to the string were
* detected or the string was NULL
*/
APR_DECLARE(apr_status_t) apr_escape_echo(char *escaped, const char *str,
apr_ssize_t slen, int quote, apr_size_t *len);
/**
* Escape control characters in a string, as performed by the shell's
* 'echo' command, and return the results from a pool. Characters are
* replaced as follows: \\a alert (bell), \\b backspace, \\f form feed,
* \\n new line, \\r carriage return, \\t horizontal tab, \\v vertical tab,
* \\ backslash.
*
* Any non ascii character will be encoded as '\\xHH', where HH is the hex
* code of the character.
*
* If quote is not zero, the double quote character will also be escaped.
* @param p Pool to allocate from
* @param str The original string
* @param quote If non zero, encode double quotes
* @return A string allocated from the pool on success, the original string
* if no characters are encoded or the string is NULL.
*/
APR_DECLARE(const char *) apr_pescape_echo(apr_pool_t *p, const char *str,
int quote);
/**
* Convert binary data to a hex encoding.
* @param dest The destination buffer, can be NULL
* @param src The original buffer
* @param srclen The length of the original buffer
* @param colon If not zero, insert colon characters between hex digits.
* @param len If present, returns the length of the string
* @return APR_SUCCESS, or APR_NOTFOUND if the string was NULL
*/
APR_DECLARE(apr_status_t) apr_escape_hex(char *dest, const void *src,
apr_size_t srclen, int colon, apr_size_t *len);
/**
* Convert binary data to a hex encoding, and return the results from a
* pool.
* @param p Pool to allocate from
* @param src The original buffer
* @param slen The length of the original buffer
* @param colon If not zero, insert colon characters between hex digits.
* @return A zero padded buffer allocated from the pool on success, or
* NULL if src was NULL.
*/
APR_DECLARE(const char *) apr_pescape_hex(apr_pool_t *p, const void *src,
apr_size_t slen, int colon) __attribute__((nonnull(1)));
/**
* Convert hex encoded string to binary data.
* @param dest The destination buffer, can be NULL
* @param str The original buffer
* @param slen The length of the original buffer
* @param colon If not zero, ignore colon characters between hex digits.
* @param len If present, returns the length of the string
* @return APR_SUCCESS, or APR_NOTFOUND if the string was NULL, or APR_BADCH
* if a non hex character is present.
*/
APR_DECLARE(apr_status_t) apr_unescape_hex(void *dest, const char *str,
apr_ssize_t slen, int colon, apr_size_t *len);
/**
* Convert hex encoding to binary data, and return the results from a pool.
* If the colon character appears between pairs of hex digits, it will be
* ignored.
* @param p Pool to allocate from
* @param str The original string
* @param colon If not zero, ignore colon characters between hex digits.
* @param len If present, returns the length of the final buffer
* @return A buffer allocated from the pool on success, or NULL if src was
* NULL, or a bad character was present.
*/
APR_DECLARE(const void *) apr_punescape_hex(apr_pool_t *p, const char *str,
int colon, apr_size_t *len);
/** @} */
#ifdef __cplusplus
}
#endif
#endif /* !APR_ESCAPE_H */

View File

@ -208,7 +208,7 @@ struct apr_finfo_t {
const char *fname;
/** The file's name (no path) in filesystem case */
const char *name;
/** The file's handle, if accessed (can be submitted to apr_duphandle) */
/** Unused */
struct apr_file_t *filehand;
};
@ -316,7 +316,7 @@ APR_DECLARE(apr_status_t) apr_dir_rewind(apr_dir_t *thedir);
* @param filepath the pathname to parse for its root component
* @param flags the desired rules to apply, from
* <PRE>
* APR_FILEPATH_NATIVE Use native path seperators (e.g. '\' on Win32)
* APR_FILEPATH_NATIVE Use native path separators (e.g. '\' on Win32)
* APR_FILEPATH_TRUENAME Tests that the root exists, and makes it proper
* </PRE>
* @param p the pool to allocate the new path string from
@ -328,7 +328,7 @@ APR_DECLARE(apr_status_t) apr_dir_rewind(apr_dir_t *thedir);
* test for the validity of that root (e.g., that a drive d:/ or network
* share //machine/foovol/).
* The function returns APR_ERELATIVE if filepath isn't rooted (an
* error), APR_EINCOMPLETE if the root path is ambigious (but potentially
* error), APR_EINCOMPLETE if the root path is ambiguous (but potentially
* legitimate, e.g. "/" on Windows is incomplete because it doesn't specify
* the drive letter), or APR_EBADPATH if the root is simply invalid.
* APR_SUCCESS is returned if filepath is an absolute path.
@ -362,7 +362,7 @@ APR_DECLARE(apr_status_t) apr_filepath_merge(char **newpath,
* @param pathelts the returned components of the search path
* @param liststr the search path (e.g., <tt>getenv("PATH")</tt>)
* @param p the pool to allocate the array and path components from
* @remark empty path componenta do not become part of @a pathelts.
* @remark empty path components do not become part of @a pathelts.
* @remark the path separator in @a liststr is system specific;
* e.g., ':' on Unix, ';' on Windows, etc.
*/

View File

@ -57,8 +57,10 @@ extern "C" {
#define APR_FOPEN_APPEND 0x00008 /**< Append to the end of the file */
#define APR_FOPEN_TRUNCATE 0x00010 /**< Open the file and truncate
to 0 length */
#define APR_FOPEN_BINARY 0x00020 /**< Open the file in binary mode */
#define APR_FOPEN_EXCL 0x00040 /**< Open should fail if APR_CREATE
#define APR_FOPEN_BINARY 0x00020 /**< Open the file in binary mode
(This flag is ignored on UNIX
because it has no meaning)*/
#define APR_FOPEN_EXCL 0x00040 /**< Open should fail if #APR_FOPEN_CREATE
and file exists. */
#define APR_FOPEN_BUFFERED 0x00080 /**< Open the file for buffered I/O */
#define APR_FOPEN_DELONCLOSE 0x00100 /**< Delete the file after close */
@ -70,7 +72,10 @@ extern "C" {
access to support writes across
process/machines */
#define APR_FOPEN_NOCLEANUP 0x00800 /**< Do not register a cleanup
when the file is opened */
when the file is opened. The
apr_os_file_t handle in apr_file_t
will not be closed when the pool
is destroyed. */
#define APR_FOPEN_SENDFILE_ENABLED 0x01000 /**< Advisory flag that this
file should support
apr_socket_sendfile operation */
@ -80,6 +85,9 @@ extern "C" {
#define APR_FOPEN_SPARSE 0x08000 /**< Platform dependent flag to enable
* sparse file support, see WARNING below
*/
#define APR_FOPEN_NONBLOCK 0x40000 /**< Platform dependent flag to enable
* non blocking file io */
/* backcompat */
#define APR_READ APR_FOPEN_READ /**< @deprecated @see APR_FOPEN_READ */
@ -97,17 +105,19 @@ extern "C" {
#define APR_SENDFILE_ENABLED APR_FOPEN_SENDFILE_ENABLED /**< @deprecated @see APR_FOPEN_SENDFILE_ENABLED */
#define APR_LARGEFILE APR_FOPEN_LARGEFILE /**< @deprecated @see APR_FOPEN_LARGEFILE */
/** @warning APR_FOPEN_LARGEFILE flag only has effect on some
/** @def APR_FOPEN_LARGEFILE
* @warning APR_FOPEN_LARGEFILE flag only has effect on some
* platforms where sizeof(apr_off_t) == 4. Where implemented, it
* allows opening and writing to a file which exceeds the size which
* can be represented by apr_off_t (2 gigabytes). When a file's size
* does exceed 2Gb, apr_file_info_get() will fail with an error on the
* descriptor, likewise apr_stat()/apr_lstat() will fail on the
* filename. apr_dir_read() will fail with APR_INCOMPLETE on a
* filename. apr_dir_read() will fail with #APR_INCOMPLETE on a
* directory entry for a large file depending on the particular
* APR_FINFO_* flags. Generally, it is not recommended to use this
* flag.
*
* @def APR_FOPEN_SPARSE
* @warning APR_FOPEN_SPARSE may, depending on platform, convert a
* normal file to a sparse file. Some applications may be unable
* to decipher a sparse file, so it's critical that the sparse file
@ -117,6 +127,10 @@ extern "C" {
* if it was previously created and written without the sparse flag.
* On platforms which do not understand, or on file systems which
* cannot handle sparse files, the flag is ignored by apr_file_open().
*
* @def APR_FOPEN_NONBLOCK
* @warning APR_FOPEN_NONBLOCK is not implemented on all platforms.
* Callers should be prepared for it to fail with #APR_ENOTIMPL.
*/
/** @} */
@ -200,33 +214,34 @@ typedef struct apr_file_t apr_file_t;
* @param newf The opened file descriptor.
* @param fname The full path to the file (using / on all systems)
* @param flag Or'ed value of:
* <PRE>
* APR_READ open for reading
* APR_WRITE open for writing
* APR_CREATE create the file if not there
* APR_APPEND file ptr is set to end prior to all writes
* APR_TRUNCATE set length to zero if file exists
* APR_BINARY not a text file (This flag is ignored on
* UNIX because it has no meaning)
* APR_BUFFERED buffer the data. Default is non-buffered
* APR_EXCL return error if APR_CREATE and file exists
* APR_DELONCLOSE delete the file after closing.
* APR_XTHREAD Platform dependent tag to open the file
* @li #APR_FOPEN_READ open for reading
* @li #APR_FOPEN_WRITE open for writing
* @li #APR_FOPEN_CREATE create the file if not there
* @li #APR_FOPEN_APPEND file ptr is set to end prior to all writes
* @li #APR_FOPEN_TRUNCATE set length to zero if file exists
* @li #APR_FOPEN_BINARY not a text file
* @li #APR_FOPEN_BUFFERED buffer the data. Default is non-buffered
* @li #APR_FOPEN_EXCL return error if #APR_FOPEN_CREATE and file exists
* @li #APR_FOPEN_DELONCLOSE delete the file after closing
* @li #APR_FOPEN_XTHREAD Platform dependent tag to open the file
* for use across multiple threads
* APR_SHARELOCK Platform dependent support for higher
* @li #APR_FOPEN_SHARELOCK Platform dependent support for higher
* level locked read/write access to support
* writes across process/machines
* APR_FILE_NOCLEANUP Do not register a cleanup with the pool
* passed in on the <EM>pool</EM> argument (see below).
* The apr_os_file_t handle in apr_file_t will not
* be closed when the pool is destroyed.
* APR_SENDFILE_ENABLED Open with appropriate platform semantics
* @li #APR_FOPEN_NOCLEANUP Do not register a cleanup with the pool
* passed in on the @a pool argument (see below)
* @li #APR_FOPEN_SENDFILE_ENABLED Open with appropriate platform semantics
* for sendfile operations. Advisory only,
* apr_socket_sendfile does not check this flag.
* </PRE>
* apr_socket_sendfile does not check this flag
* @li #APR_FOPEN_LARGEFILE Platform dependent flag to enable large file
* support, see WARNING below
* @li #APR_FOPEN_SPARSE Platform dependent flag to enable sparse file
* support, see WARNING below
* @li #APR_FOPEN_NONBLOCK Platform dependent flag to enable
* non blocking file io
* @param perm Access permissions for file.
* @param pool The pool to use.
* @remark If perm is APR_OS_DEFAULT and the file is being created,
* @remark If perm is #APR_FPROT_OS_DEFAULT and the file is being created,
* appropriate default permissions will be used.
* @remark By default, the returned file descriptor will not be
* inherited by child processes created by apr_proc_create(). This
@ -279,7 +294,7 @@ APR_DECLARE(apr_status_t) apr_file_link(const char *from_path,
* @param to_path The full path to the new file (using / on all systems)
* @param perms Access permissions for the new file if it is created.
* In place of the usual or'd combination of file permissions, the
* value APR_FILE_SOURCE_PERMS may be given, in which case the source
* value #APR_FPROT_FILE_SOURCE_PERMS may be given, in which case the source
* file's permissions are copied.
* @param pool The pool to use.
* @remark The new file does not need to exist, it will be created if required.
@ -296,7 +311,7 @@ APR_DECLARE(apr_status_t) apr_file_copy(const char *from_path,
* @param to_path The full path to the destination file (use / on all systems)
* @param perms Access permissions for the destination file if it is created.
* In place of the usual or'd combination of file permissions, the
* value APR_FILE_SOURCE_PERMS may be given, in which case the source
* value #APR_FPROT_FILE_SOURCE_PERMS may be given, in which case the source
* file's permissions are copied.
* @param pool The pool to use.
* @remark The new file does not need to exist, it will be created if required.
@ -309,7 +324,7 @@ APR_DECLARE(apr_status_t) apr_file_append(const char *from_path,
/**
* Are we at the end of the file
* @param fptr The apr file we are testing.
* @remark Returns APR_EOF if we are at the end of file, APR_SUCCESS otherwise.
* @remark Returns #APR_EOF if we are at the end of file, #APR_SUCCESS otherwise.
*/
APR_DECLARE(apr_status_t) apr_file_eof(apr_file_t *fptr);
@ -336,7 +351,7 @@ APR_DECLARE(apr_status_t) apr_file_open_stderr(apr_file_t **thefile,
* @param thefile The apr file to use as stdout.
* @param pool The pool to allocate the file out of.
*
* @remark See remarks for apr_file_open_stderr.
* @remark See remarks for apr_file_open_stderr().
*/
APR_DECLARE(apr_status_t) apr_file_open_stdout(apr_file_t **thefile,
apr_pool_t *pool);
@ -346,7 +361,7 @@ APR_DECLARE(apr_status_t) apr_file_open_stdout(apr_file_t **thefile,
* @param thefile The apr file to use as stdin.
* @param pool The pool to allocate the file out of.
*
* @remark See remarks for apr_file_open_stderr.
* @remark See remarks for apr_file_open_stderr().
*/
APR_DECLARE(apr_status_t) apr_file_open_stdin(apr_file_t **thefile,
apr_pool_t *pool);
@ -354,13 +369,19 @@ APR_DECLARE(apr_status_t) apr_file_open_stdin(apr_file_t **thefile,
/**
* open standard error as an apr file pointer, with flags.
* @param thefile The apr file to use as stderr.
* @param flags The flags to open the file with. Only the APR_EXCL,
* APR_BUFFERED, APR_XTHREAD, APR_SHARELOCK,
* APR_SENDFILE_ENABLED and APR_LARGEFILE flags should
* be used. The APR_WRITE flag will be set unconditionally.
* @param flags The flags to open the file with. Only the
* @li #APR_FOPEN_EXCL
* @li #APR_FOPEN_BUFFERED
* @li #APR_FOPEN_XTHREAD
* @li #APR_FOPEN_SHARELOCK
* @li #APR_FOPEN_SENDFILE_ENABLED
* @li #APR_FOPEN_LARGEFILE
*
* flags should be used. The #APR_FOPEN_WRITE flag will
* be set unconditionally.
* @param pool The pool to allocate the file out of.
*
* @remark See remarks for apr_file_open_stderr.
* @remark See remarks for apr_file_open_stderr().
*/
APR_DECLARE(apr_status_t) apr_file_open_flags_stderr(apr_file_t **thefile,
apr_int32_t flags,
@ -369,13 +390,19 @@ APR_DECLARE(apr_status_t) apr_file_open_flags_stderr(apr_file_t **thefile,
/**
* open standard output as an apr file pointer, with flags.
* @param thefile The apr file to use as stdout.
* @param flags The flags to open the file with. Only the APR_EXCL,
* APR_BUFFERED, APR_XTHREAD, APR_SHARELOCK,
* APR_SENDFILE_ENABLED and APR_LARGEFILE flags should
* be used. The APR_WRITE flag will be set unconditionally.
* @param flags The flags to open the file with. Only the
* @li #APR_FOPEN_EXCL
* @li #APR_FOPEN_BUFFERED
* @li #APR_FOPEN_XTHREAD
* @li #APR_FOPEN_SHARELOCK
* @li #APR_FOPEN_SENDFILE_ENABLED
* @li #APR_FOPEN_LARGEFILE
*
* flags should be used. The #APR_FOPEN_WRITE flag will
* be set unconditionally.
* @param pool The pool to allocate the file out of.
*
* @remark See remarks for apr_file_open_stderr.
* @remark See remarks for apr_file_open_stderr().
*/
APR_DECLARE(apr_status_t) apr_file_open_flags_stdout(apr_file_t **thefile,
apr_int32_t flags,
@ -384,13 +411,19 @@ APR_DECLARE(apr_status_t) apr_file_open_flags_stdout(apr_file_t **thefile,
/**
* open standard input as an apr file pointer, with flags.
* @param thefile The apr file to use as stdin.
* @param flags The flags to open the file with. Only the APR_EXCL,
* APR_BUFFERED, APR_XTHREAD, APR_SHARELOCK,
* APR_SENDFILE_ENABLED and APR_LARGEFILE flags should
* be used. The APR_READ flag will be set unconditionally.
* @param flags The flags to open the file with. Only the
* @li #APR_FOPEN_EXCL
* @li #APR_FOPEN_BUFFERED
* @li #APR_FOPEN_XTHREAD
* @li #APR_FOPEN_SHARELOCK
* @li #APR_FOPEN_SENDFILE_ENABLED
* @li #APR_FOPEN_LARGEFILE
*
* flags should be used. The #APR_FOPEN_WRITE flag will
* be set unconditionally.
* @param pool The pool to allocate the file out of.
*
* @remark See remarks for apr_file_open_stderr.
* @remark See remarks for apr_file_open_stderr().
*/
APR_DECLARE(apr_status_t) apr_file_open_flags_stdin(apr_file_t **thefile,
apr_int32_t flags,
@ -403,15 +436,15 @@ APR_DECLARE(apr_status_t) apr_file_open_flags_stdin(apr_file_t **thefile,
* @param nbytes On entry, the number of bytes to read; on exit, the number
* of bytes read.
*
* @remark apr_file_read will read up to the specified number of
* @remark apr_file_read() will read up to the specified number of
* bytes, but never more. If there isn't enough data to fill that
* number of bytes, all of the available data is read. The third
* argument is modified to reflect the number of bytes read. If a
* char was put back into the stream via ungetc, it will be the first
* character returned.
*
* @remark It is not possible for both bytes to be read and an APR_EOF
* or other error to be returned. APR_EINTR is never returned.
* @remark It is not possible for both bytes to be read and an #APR_EOF
* or other error to be returned. #APR_EINTR is never returned.
*/
APR_DECLARE(apr_status_t) apr_file_read(apr_file_t *thefile, void *buf,
apr_size_t *nbytes);
@ -423,13 +456,13 @@ APR_DECLARE(apr_status_t) apr_file_read(apr_file_t *thefile, void *buf,
* @param nbytes On entry, the number of bytes to write; on exit, the number
* of bytes written.
*
* @remark apr_file_write will write up to the specified number of
* @remark apr_file_write() will write up to the specified number of
* bytes, but never more. If the OS cannot write that many bytes, it
* will write as many as it can. The third argument is modified to
* reflect the * number of bytes written.
*
* @remark It is possible for both bytes to be written and an error to
* be returned. APR_EINTR is never returned.
* be returned. #APR_EINTR is never returned.
*/
APR_DECLARE(apr_status_t) apr_file_write(apr_file_t *thefile, const void *buf,
apr_size_t *nbytes);
@ -439,14 +472,14 @@ APR_DECLARE(apr_status_t) apr_file_write(apr_file_t *thefile, const void *buf,
* @param thefile The file descriptor to write to.
* @param vec The array from which to get the data to write to the file.
* @param nvec The number of elements in the struct iovec array. This must
* be smaller than APR_MAX_IOVEC_SIZE. If it isn't, the function
* will fail with APR_EINVAL.
* be smaller than #APR_MAX_IOVEC_SIZE. If it isn't, the function
* will fail with #APR_EINVAL.
* @param nbytes The number of bytes written.
*
* @remark It is possible for both bytes to be written and an error to
* be returned. APR_EINTR is never returned.
* be returned. #APR_EINTR is never returned.
*
* @remark apr_file_writev is available even if the underlying
* @remark apr_file_writev() is available even if the underlying
* operating system doesn't provide writev().
*/
APR_DECLARE(apr_status_t) apr_file_writev(apr_file_t *thefile,
@ -461,7 +494,7 @@ APR_DECLARE(apr_status_t) apr_file_writev(apr_file_t *thefile,
* @param nbytes The number of bytes to read.
* @param bytes_read If non-NULL, this will contain the number of bytes read.
*
* @remark apr_file_read will read up to the specified number of
* @remark apr_file_read_full() will read up to the specified number of
* bytes, but never more. If there isn't enough data to fill that
* number of bytes, then the process/thread will block until it is
* available or EOF is reached. If a char was put back into the
@ -471,7 +504,7 @@ APR_DECLARE(apr_status_t) apr_file_writev(apr_file_t *thefile,
* returned. And if *bytes_read is less than nbytes, an accompanying
* error is _always_ returned.
*
* @remark APR_EINTR is never returned.
* @remark #APR_EINTR is never returned.
*/
APR_DECLARE(apr_status_t) apr_file_read_full(apr_file_t *thefile, void *buf,
apr_size_t nbytes,
@ -485,7 +518,7 @@ APR_DECLARE(apr_status_t) apr_file_read_full(apr_file_t *thefile, void *buf,
* @param nbytes The number of bytes to write.
* @param bytes_written If non-NULL, set to the number of bytes written.
*
* @remark apr_file_write will write up to the specified number of
* @remark apr_file_write_full() will write up to the specified number of
* bytes, but never more. If the OS cannot write that many bytes, the
* process/thread will block until they can be written. Exceptional
* error such as "out of space" or "pipe closed" will terminate with
@ -495,7 +528,7 @@ APR_DECLARE(apr_status_t) apr_file_read_full(apr_file_t *thefile, void *buf,
* be returned. And if *bytes_written is less than nbytes, an
* accompanying error is _always_ returned.
*
* @remark APR_EINTR is never returned.
* @remark #APR_EINTR is never returned.
*/
APR_DECLARE(apr_status_t) apr_file_write_full(apr_file_t *thefile,
const void *buf,
@ -509,11 +542,11 @@ APR_DECLARE(apr_status_t) apr_file_write_full(apr_file_t *thefile,
* @param thefile The file descriptor to write to.
* @param vec The array from which to get the data to write to the file.
* @param nvec The number of elements in the struct iovec array. This must
* be smaller than APR_MAX_IOVEC_SIZE. If it isn't, the function
* will fail with APR_EINVAL.
* be smaller than #APR_MAX_IOVEC_SIZE. If it isn't, the function
* will fail with #APR_EINVAL.
* @param nbytes The number of bytes written.
*
* @remark apr_file_writev_full is available even if the underlying
* @remark apr_file_writev_full() is available even if the underlying
* operating system doesn't provide writev().
*/
APR_DECLARE(apr_status_t) apr_file_writev_full(apr_file_t *thefile,
@ -621,7 +654,7 @@ APR_DECLARE(apr_status_t) apr_file_setaside(apr_file_t **new_file,
* @param buffer The buffer
* @param bufsize The size of the buffer
* @remark It is possible to add a buffer to previously unbuffered
* file handles, the APR_BUFFERED flag will be added to
* file handles, the #APR_FOPEN_BUFFERED flag will be added to
* the file handle's flags. Likewise, with buffer=NULL and
* bufsize=0 arguments it is possible to make a previously
* buffered file handle unbuffered.
@ -640,11 +673,9 @@ APR_DECLARE(apr_size_t) apr_file_buffer_size_get(apr_file_t *thefile);
* Move the read/write file offset to a specified byte within a file.
* @param thefile The file descriptor
* @param where How to move the pointer, one of:
* <PRE>
* APR_SET -- set the offset to offset
* APR_CUR -- add the offset to the current position
* APR_END -- add the offset to the current file size
* </PRE>
* @li #APR_SET -- set the offset to offset
* @li #APR_CUR -- add the offset to the current position
* @li #APR_END -- add the offset to the current file size
* @param offset The offset to move the pointer to.
* @remark The third argument is modified to be the offset the pointer
was actually moved to.
@ -664,7 +695,7 @@ APR_DECLARE(apr_status_t) apr_file_seek(apr_file_t *thefile,
* @bug Some platforms cannot toggle between blocking and nonblocking,
* and when passing a pipe as a standard handle to an application which
* does not expect it, a non-blocking stream will fluxor the client app.
* @deprecated @see apr_file_pipe_create_ex
* @deprecated @see apr_file_pipe_create_ex()
*/
APR_DECLARE(apr_status_t) apr_file_pipe_create(apr_file_t **in,
apr_file_t **out,
@ -675,20 +706,18 @@ APR_DECLARE(apr_status_t) apr_file_pipe_create(apr_file_t **in,
* @param in The newly created pipe's file for reading.
* @param out The newly created pipe's file for writing.
* @param blocking one of these values defined in apr_thread_proc.h;
* @li #APR_FULL_BLOCK
* @li #APR_READ_BLOCK
* @li #APR_WRITE_BLOCK
* @li #APR_FULL_NONBLOCK
* @param pool The pool to operate on.
* <pre>
* APR_FULL_BLOCK
* APR_READ_BLOCK
* APR_WRITE_BLOCK
* APR_FULL_NONBLOCK
* </pre>
* @remark By default, the returned file descriptors will be inherited
* by child processes created using apr_proc_create(). This can be
* changed using apr_file_inherit_unset().
* @remark Some platforms cannot toggle between blocking and nonblocking,
* and when passing a pipe as a standard handle to an application which
* does not expect it, a non-blocking stream will fluxor the client app.
* Use this function rather than apr_file_pipe_create to create pipes
* Use this function rather than apr_file_pipe_create() to create pipes
* where one or both ends require non-blocking semantics.
*/
APR_DECLARE(apr_status_t) apr_file_pipe_create_ex(apr_file_t **in,
@ -789,11 +818,11 @@ APR_DECLARE_NONSTD(int) apr_file_printf(apr_file_t *fptr,
* @param perms The permission bits to apply to the file.
*
* @warning Some platforms may not be able to apply all of the
* available permission bits; APR_INCOMPLETE will be returned if some
* available permission bits; #APR_INCOMPLETE will be returned if some
* permissions are specified which could not be set.
*
* @warning Platforms which do not implement this feature will return
* APR_ENOTIMPL.
* #APR_ENOTIMPL.
*/
APR_DECLARE(apr_status_t) apr_file_perms_set(const char *fname,
apr_fileperms_t perms);
@ -802,11 +831,9 @@ APR_DECLARE(apr_status_t) apr_file_perms_set(const char *fname,
* Set attributes of the specified file.
* @param fname The full path to the file (using / on all systems)
* @param attributes Or'd combination of
* <PRE>
* APR_FILE_ATTR_READONLY - make the file readonly
* APR_FILE_ATTR_EXECUTABLE - make the file executable
* APR_FILE_ATTR_HIDDEN - make the file hidden
* </PRE>
* @li #APR_FILE_ATTR_READONLY - make the file readonly
* @li #APR_FILE_ATTR_EXECUTABLE - make the file executable
* @li #APR_FILE_ATTR_HIDDEN - make the file hidden
* @param attr_mask Mask of valid bits in attributes.
* @param pool the pool to use.
* @remark This function should be used in preference to explicit manipulation
@ -814,7 +841,7 @@ APR_DECLARE(apr_status_t) apr_file_perms_set(const char *fname,
* attributes are platform specific and may involve more than simply
* setting permission bits.
* @warning Platforms which do not implement this feature will return
* APR_ENOTIMPL.
* #APR_ENOTIMPL.
*/
APR_DECLARE(apr_status_t) apr_file_attrs_set(const char *fname,
apr_fileattrs_t attributes,
@ -827,7 +854,7 @@ APR_DECLARE(apr_status_t) apr_file_attrs_set(const char *fname,
* @param mtime The mtime to apply to the file.
* @param pool The pool to use.
* @warning Platforms which do not implement this feature will return
* APR_ENOTIMPL.
* #APR_ENOTIMPL.
*/
APR_DECLARE(apr_status_t) apr_file_mtime_set(const char *fname,
apr_time_t mtime,
@ -865,7 +892,7 @@ APR_DECLARE(apr_status_t) apr_dir_remove(const char *path, apr_pool_t *pool);
/**
* get the specified file's stats.
* @param finfo Where to store the information about the file.
* @param wanted The desired apr_finfo_t fields, as a bit flag of APR_FINFO_ values
* @param wanted The desired apr_finfo_t fields, as a bit flag of APR_FINFO_* values
* @param thefile The file to get information about.
*/
APR_DECLARE(apr_status_t) apr_file_info_get(apr_finfo_t *finfo,
@ -910,7 +937,8 @@ APR_DECLARE_INHERIT_UNSET(file);
* @param templ The template to use when creating a temp file.
* @param flags The flags to open the file with. If this is zero,
* the file is opened with
* APR_CREATE | APR_READ | APR_WRITE | APR_EXCL | APR_DELONCLOSE
* #APR_FOPEN_CREATE | #APR_FOPEN_READ | #APR_FOPEN_WRITE |
* #APR_FOPEN_EXCL | #APR_FOPEN_DELONCLOSE
* @param p The pool to allocate the file out of.
* @remark
* This function generates a unique temporary file name from template.

View File

@ -60,9 +60,7 @@ extern "C" {
#define APR_FNM_NOESCAPE 0x01 /**< Disable backslash escaping. */
#define APR_FNM_PATHNAME 0x02 /**< Slash must be matched by slash. */
#define APR_FNM_PERIOD 0x04 /**< Period must be matched by period. */
#define APR_FNM_CASE_BLIND 0x08 /**< Compare characters case-insensitively.
* @remark This flag is an Apache addition
*/
#define APR_FNM_CASE_BLIND 0x08 /**< Compare characters case-insensitively. */
/**
* Try to match the string to the given pattern, return APR_SUCCESS if
@ -130,13 +128,19 @@ APR_DECLARE(apr_status_t) apr_fnmatch(const char *pattern,
APR_DECLARE(int) apr_fnmatch_test(const char *pattern);
/**
* Find all files that match a specified pattern.
* @param pattern The pattern to use for finding files.
* Find all files that match a specified pattern in a directory.
* @param dir_pattern The pattern to use for finding files, appended
* to the search directory. The pattern is anything following the
* final forward or backward slash in the parameter. If no slash
* is found, the current directory is searched.
* @param result Array to use when storing the results
* @param p The pool to use.
* @return non-zero if pattern has any glob characters in it
* @return APR_SUCCESS if no processing errors occurred, APR error
* code otherwise
* @remark The returned array may be empty even if APR_SUCCESS was
* returned.
*/
APR_DECLARE(apr_status_t) apr_match_glob(const char *pattern,
APR_DECLARE(apr_status_t) apr_match_glob(const char *dir_pattern,
apr_array_header_t **result,
apr_pool_t *p);

View File

@ -166,6 +166,27 @@ APR_DECLARE(apr_hash_index_t *) apr_hash_next(apr_hash_index_t *hi);
APR_DECLARE(void) apr_hash_this(apr_hash_index_t *hi, const void **key,
apr_ssize_t *klen, void **val);
/**
* Get the current entry's key from the iteration state.
* @param hi The iteration state
* @return The pointer to the key
*/
APR_DECLARE(const void*) apr_hash_this_key(apr_hash_index_t *hi);
/**
* Get the current entry's key length from the iteration state.
* @param hi The iteration state
* @return The key length
*/
APR_DECLARE(apr_ssize_t) apr_hash_this_key_len(apr_hash_index_t *hi);
/**
* Get the current entry's value from the iteration state.
* @param hi The iteration state
* @return The pointer to the value
*/
APR_DECLARE(void*) apr_hash_this_val(apr_hash_index_t *hi);
/**
* Get the number of key/value pairs in the hash table.
* @param ht The hash table

View File

@ -28,7 +28,7 @@
* Prototype for type-specific declarations of apr_foo_inherit_set
* functions.
* @remark Doxygen unwraps this macro (via doxygen.conf) to provide
* actual help for each specific occurance of apr_foo_inherit_set.
* actual help for each specific occurrence of apr_foo_inherit_set.
* @remark the linkage is specified for APR. It would be possible to expand
* the macros to support other linkages.
*/
@ -40,7 +40,7 @@
* Prototype for type-specific declarations of apr_foo_inherit_unset
* functions.
* @remark Doxygen unwraps this macro (via doxygen.conf) to provide
* actual help for each specific occurance of apr_foo_inherit_unset.
* actual help for each specific occurrence of apr_foo_inherit_unset.
* @remark the linkage is specified for APR. It would be possible to expand
* the macros to support other linkages.
*/

View File

@ -111,19 +111,19 @@ APR_DECLARE(const char *) apr_filepath_name_get(const char *pathname);
* <PRE>
* The extensions are:
*
* %%pA takes a struct in_addr *, and prints it as a.b.c.d
* %%pI takes an apr_sockaddr_t * and prints it as a.b.c.d:port or
* [ipv6-address]:port
* %%pT takes an apr_os_thread_t * and prints it in decimal
* ('0' is printed if !APR_HAS_THREADS)
* %%pt takes an apr_os_thread_t * and prints it in hexadecimal
* ('0' is printed if !APR_HAS_THREADS)
* %%pm takes an apr_status_t * and prints the appropriate error
* string (from apr_strerror) corresponding to that error code.
* %%pp takes a void * and outputs it in hex
* %%pB takes a apr_uint32_t * as bytes and outputs it's apr_strfsize
* %%pF same as above, but takes a apr_off_t *
* %%pS same as above, but takes a apr_size_t *
* - %%pA takes a struct in_addr *, and prints it as a.b.c.d
* - %%pI takes an apr_sockaddr_t * and prints it as a.b.c.d:port or
* \[ipv6-address\]:port
* - %%pT takes an apr_os_thread_t * and prints it in decimal
* ('0' is printed if !APR_HAS_THREADS)
* - %%pt takes an apr_os_thread_t * and prints it in hexadecimal
* ('0' is printed if !APR_HAS_THREADS)
* - %%pm takes an apr_status_t * and prints the appropriate error
* string (from apr_strerror) corresponding to that error code.
* - %%pp takes a void * and outputs it in hex
* - %%pB takes a apr_uint32_t * as bytes and outputs it's apr_strfsize
* - %%pF same as above, but takes a apr_off_t *
* - %%pS same as above, but takes a apr_size_t *
*
* %%pA, %%pI, %%pT, %%pp are available from APR 1.0.0 onwards (and in 0.9.x).
* %%pt is only available from APR 1.2.0 onwards.

View File

@ -120,7 +120,7 @@ struct apr_mmap_t {
/**
* Create a new mmap'ed file out of an existing APR file.
* @param newmmap The newly created mmap'ed file.
* @param file The file turn into an mmap.
* @param file The file to turn into an mmap.
* @param offset The offset into the file to start the data pointer at.
* @param size The size of the file
* @param flag bit-wise or of:

View File

@ -99,6 +99,8 @@ extern "C" {
* until data is available.
* @see apr_socket_accept_filter
*/
#define APR_SO_BROADCAST 65536 /**< Allow broadcast
*/
/** @} */
@ -278,6 +280,9 @@ struct apr_hdtr_t {
* @param type The type of the socket (e.g., SOCK_STREAM).
* @param protocol The protocol of the socket (e.g., APR_PROTO_TCP).
* @param cont The pool for the apr_socket_t and associated storage.
* @note The pool will be used by various functions that operate on the
* socket. The caller must ensure that it is not used by other threads
* at the same time.
*/
APR_DECLARE(apr_status_t) apr_socket_create(apr_socket_t **new_sock,
int family, int type,
@ -333,6 +338,9 @@ APR_DECLARE(apr_status_t) apr_socket_listen(apr_socket_t *sock,
* be used for all future communication.
* @param sock The socket we are listening on.
* @param connection_pool The pool for the new socket.
* @note The pool will be used by various functions that operate on the
* socket. The caller must ensure that it is not used by other threads
* at the same time.
*/
APR_DECLARE(apr_status_t) apr_socket_accept(apr_socket_t **new_sock,
apr_socket_t *sock,
@ -397,6 +405,8 @@ APR_DECLARE(apr_status_t) apr_sockaddr_info_get(apr_sockaddr_t **sa,
* @param hostname The hostname.
* @param sa The apr_sockaddr_t.
* @param flags Special processing flags.
* @remark Results can vary significantly between platforms
* when processing wildcard socket addresses.
*/
APR_DECLARE(apr_status_t) apr_getnameinfo(char **hostname,
apr_sockaddr_t *sa,
@ -489,7 +499,7 @@ APR_DECLARE(apr_status_t) apr_socket_send(apr_socket_t *sock, const char *buf,
apr_size_t *len);
/**
* Send multiple packets of data over a network.
* Send multiple buffers over a network.
* @param sock The socket to send the data over.
* @param vec The array of iovec structs containing the data to send
* @param nvec The number of iovec structs in the array
@ -499,7 +509,7 @@ APR_DECLARE(apr_status_t) apr_socket_send(apr_socket_t *sock, const char *buf,
* This functions acts like a blocking write by default. To change
* this behavior, use apr_socket_timeout_set() or the APR_SO_NONBLOCK
* socket option.
* The number of bytes actually sent is stored in argument 3.
* The number of bytes actually sent is stored in argument 4.
*
* It is possible for both bytes to be sent and an error to be returned.
*
@ -671,7 +681,7 @@ APR_DECLARE(apr_status_t) apr_socket_atmark(apr_socket_t *sock,
/**
* Return an address associated with a socket; either the address to
* which the socket is bound locally or the the address of the peer
* which the socket is bound locally or the address of the peer
* to which the socket is connected.
* @param sa The returned apr_sockaddr_t.
* @param which Whether to retrieve the local or remote address
@ -712,6 +722,16 @@ APR_DECLARE(apr_status_t) apr_sockaddr_ip_getbuf(char *buf, apr_size_t buflen,
APR_DECLARE(int) apr_sockaddr_equal(const apr_sockaddr_t *addr1,
const apr_sockaddr_t *addr2);
/**
* See if the IP address in an APR socket address refers to the wildcard
* address for the protocol family (e.g., INADDR_ANY for IPv4).
*
* @param addr The APR socket address to examine.
* @remark The return value will be non-zero if the address is
* initialized and is the wildcard address.
*/
APR_DECLARE(int) apr_sockaddr_is_wildcard(const apr_sockaddr_t *addr);
/**
* Return the type of the socket.
* @param sock The socket to query.

View File

@ -42,7 +42,9 @@ extern "C" {
*/
/**
* Poll options
* @defgroup pollopts Poll options
* @ingroup apr_poll
* @{
*/
#define APR_POLLIN 0x001 /**< Can read without blocking */
#define APR_POLLPRI 0x002 /**< Priority data available */
@ -50,9 +52,12 @@ extern "C" {
#define APR_POLLERR 0x010 /**< Pending error */
#define APR_POLLHUP 0x020 /**< Hangup occurred */
#define APR_POLLNVAL 0x040 /**< Descriptor invalid */
/** @} */
/**
* Pollset Flags
* @defgroup pollflags Pollset Flags
* @ingroup apr_poll
* @{
*/
#define APR_POLLSET_THREADSAFE 0x001 /**< Adding or removing a descriptor is
* thread-safe
@ -67,6 +72,7 @@ extern "C" {
* the specified non-default method cannot be
* used
*/
/** @} */
/**
* Pollset Methods
@ -77,7 +83,8 @@ typedef enum {
APR_POLLSET_KQUEUE, /**< Poll uses kqueue method */
APR_POLLSET_PORT, /**< Poll uses Solaris event port method */
APR_POLLSET_EPOLL, /**< Poll uses epoll method */
APR_POLLSET_POLL /**< Poll uses poll method */
APR_POLLSET_POLL, /**< Poll uses poll method */
APR_POLLSET_AIO_MSGQ /**< Poll uses z/OS asio method */
} apr_pollset_method_e;
/** Used in apr_pollfd_t to determine what the apr_descriptor is */
@ -131,7 +138,7 @@ typedef struct apr_pollset_t apr_pollset_t;
* @remark If flags contains APR_POLLSET_WAKEABLE, then a pollset is
* created with an additional internal pipe object used for the
* apr_pollset_wakeup() call. The actual size of pollset is
* in that case size + 1. This feature is only supported on some
* in that case @a size + 1. This feature is only supported on some
* platforms; the apr_pollset_create() call will fail with
* APR_ENOTIMPL on platforms where it is not supported.
* @remark If flags contains APR_POLLSET_NOCOPY, then the apr_pollfd_t
@ -226,6 +233,7 @@ APR_DECLARE(apr_status_t) apr_pollset_add(apr_pollset_t *pollset,
* Remove a descriptor from a pollset
* @param pollset The pollset from which to remove the descriptor
* @param descriptor The descriptor to remove
* @remark If the descriptor is not found, APR_NOTFOUND is returned.
* @remark If the pollset has been created with APR_POLLSET_THREADSAFE
* and thread T1 is blocked in a call to apr_pollset_poll() for
* this same pollset that is being modified via apr_pollset_remove()
@ -259,8 +267,6 @@ APR_DECLARE(apr_status_t) apr_pollset_remove(apr_pollset_t *pollset,
* @remark Multiple signalled conditions for the same descriptor may be reported
* in one or more returned apr_pollfd_t structures, depending on the
* implementation.
* @bug With versions 1.4.2 and prior on Windows, a call with no descriptors
* and timeout will return immediately with the wrong error code.
*/
APR_DECLARE(apr_status_t) apr_pollset_poll(apr_pollset_t *pollset,
apr_interval_time_t timeout,
@ -290,8 +296,6 @@ APR_DECLARE(apr_status_t) apr_pollset_wakeup(apr_pollset_t *pollset);
* descriptor has been signalled or the timeout has expired.
* @remark The rtnevents field in the apr_pollfd_t array will only be filled-
* in if the return value is APR_SUCCESS.
* @bug With versions 1.4.2 and prior on Windows, a call with no descriptors
* and timeout will return immediately with the wrong error code.
*/
APR_DECLARE(apr_status_t) apr_poll(apr_pollfd_t *aprset, apr_int32_t numsock,
apr_int32_t *nsds,
@ -309,7 +313,7 @@ APR_DECLARE(const char *) apr_pollset_method_name(apr_pollset_t *pollset);
*/
APR_DECLARE(const char *) apr_poll_method_defname(void);
/** Opaque structure used for pollset API */
/** Opaque structure used for pollcb API */
typedef struct apr_pollcb_t apr_pollcb_t;
/**
@ -397,8 +401,6 @@ typedef apr_status_t (*apr_pollcb_cb_t)(void *baton, apr_pollfd_t *descriptor);
* @remark Multiple signalled conditions for the same descriptor may be reported
* in one or more calls to the callback function, depending on the
* implementation.
* @bug With versions 1.4.2 and prior on Windows, a call with no descriptors
* and timeout will return immediately with the wrong error code.
*/
APR_DECLARE(apr_status_t) apr_pollcb_poll(apr_pollcb_t *pollcb,
apr_interval_time_t timeout,

View File

@ -71,10 +71,10 @@ typedef struct apr_pool_t apr_pool_t;
* <pre>
* APR_POOL_DECLARE_ACCESSOR(file);
* becomes:
* APR_DECLARE(apr_pool_t *) apr_file_pool_get(apr_file_t *ob);
* APR_DECLARE(apr_pool_t *) apr_file_pool_get(const apr_file_t *thefile);
* </pre>
* @remark Doxygen unwraps this macro (via doxygen.conf) to provide
* actual help for each specific occurance of apr_foo_pool_get.
* actual help for each specific occurrence of apr_foo_pool_get.
* @remark the linkage is specified for APR. It would be possible to expand
* the macros to support other linkages.
*/
@ -118,15 +118,15 @@ typedef struct apr_pool_t apr_pool_t;
*
* | | | | | x | | | | Pool owner checking. On each use of a
* pool, check if the current thread is the
* pools owner. If not, abort(). In
* pool's owner. If not, abort(). In
* combination with the verbose flag above,
* it will output OWNER in such an event
* prior to aborting. Use the debug
* function apr_pool_owner_set() to switch
* a pools ownership.
* a pool's ownership.
*
* When no debug level was specified, assume general debug mode.
* If level 0 was specified, debugging is switched off
* If level 0 was specified, debugging is switched off.
* </pre>
*/
#if defined(APR_POOL_DEBUG)
@ -212,12 +212,16 @@ APR_DECLARE(apr_status_t) apr_pool_create_core_ex(apr_pool_t **newpool,
* @param newpool The pool we have just created.
* @param abort_fn A function to use if the pool cannot allocate more memory.
* @param allocator The allocator to use with the new pool. If NULL a
* new allocator will be crated with newpool as owner.
* new allocator will be created with the new pool as owner.
* @remark An unmanaged pool is a special pool without a parent; it will
* NOT be destroyed upon apr_terminate. It must be explicitly
* destroyed by calling apr_pool_destroy, to prevent memory leaks.
* Use of this function is discouraged, think twice about whether
* you really really need it.
* @warning Any child cleanups registered against the new pool, or
* against sub-pools thereof, will not be executed during an
* invocation of apr_proc_create(), so resources created in an
* "unmanaged" pool hierarchy will leak to child processes.
*/
APR_DECLARE(apr_status_t) apr_pool_create_unmanaged_ex(apr_pool_t **newpool,
apr_abortfunc_t abort_fn,
@ -233,7 +237,7 @@ APR_DECLARE(apr_status_t) apr_pool_create_unmanaged_ex(apr_pool_t **newpool,
* @param file_line Where the function is called from.
* This is usually APR_POOL__FILE_LINE__.
* @remark Only available when APR_POOL_DEBUG is defined.
* Call this directly if you have you apr_pool_create_ex
* Call this directly if you have your apr_pool_create_ex
* calls in a wrapper function and wish to override
* the file_line argument to reflect the caller of
* your wrapper function. If you do not have
@ -270,7 +274,7 @@ APR_DECLARE(apr_status_t) apr_pool_create_core_ex_debug(apr_pool_t **newpool,
* @param file_line Where the function is called from.
* This is usually APR_POOL__FILE_LINE__.
* @remark Only available when APR_POOL_DEBUG is defined.
* Call this directly if you have you apr_pool_create_unmanaged_ex
* Call this directly if you have your apr_pool_create_unmanaged_ex
* calls in a wrapper function and wish to override
* the file_line argument to reflect the caller of
* your wrapper function. If you do not have
@ -321,7 +325,7 @@ APR_DECLARE(apr_status_t) apr_pool_create(apr_pool_t **newpool,
#endif
/**
* Create a new pool.
* Create a new unmanaged pool.
* @param newpool The pool we have just created.
*/
#if defined(DOXYGEN)
@ -366,7 +370,7 @@ APR_DECLARE(void) apr_pool_clear(apr_pool_t *p) __attribute__((nonnull(1)));
* @param file_line Where the function is called from.
* This is usually APR_POOL__FILE_LINE__.
* @remark Only available when APR_POOL_DEBUG is defined.
* Call this directly if you have you apr_pool_clear
* Call this directly if you have your apr_pool_clear
* calls in a wrapper function and wish to override
* the file_line argument to reflect the caller of
* your wrapper function. If you do not have
@ -396,7 +400,7 @@ APR_DECLARE(void) apr_pool_destroy(apr_pool_t *p) __attribute__((nonnull(1)));
* @param file_line Where the function is called from.
* This is usually APR_POOL__FILE_LINE__.
* @remark Only available when APR_POOL_DEBUG is defined.
* Call this directly if you have you apr_pool_destroy
* Call this directly if you have your apr_pool_destroy
* calls in a wrapper function and wish to override
* the file_line argument to reflect the caller of
* your wrapper function. If you do not have
@ -614,7 +618,7 @@ APR_DECLARE(apr_status_t) apr_pool_userdata_get(void **data, const char *key,
/**
* Register a function to be called when a pool is cleared or destroyed
* @param p The pool register the cleanup with
* @param p The pool to register the cleanup with
* @param data The data to pass to the cleanup function.
* @param plain_cleanup The function to call when the pool is cleared
* or destroyed
@ -630,11 +634,11 @@ APR_DECLARE(void) apr_pool_cleanup_register(
/**
* Register a function to be called when a pool is cleared or destroyed.
*
* Unlike apr_pool_cleanup_register which register a cleanup
* that is called AFTER all subpools are destroyed this function register
* a function that will be called before any of the subpool is destoryed.
* Unlike apr_pool_cleanup_register which registers a cleanup
* that is called AFTER all subpools are destroyed, this function registers
* a function that will be called before any of the subpools are destroyed.
*
* @param p The pool register the cleanup with
* @param p The pool to register the cleanup with
* @param data The data to pass to the cleanup function.
* @param plain_cleanup The function to call when the pool is cleared
* or destroyed

View File

@ -43,7 +43,8 @@ extern "C" {
typedef struct apr_shm_t apr_shm_t;
/**
* Create and make accessable a shared memory segment.
* Create and make accessible a shared memory segment with default
* properties.
* @param m The shared memory structure to create.
* @param reqsize The desired size of the segment.
* @param filename The file to use for shared memory on platforms that
@ -70,6 +71,52 @@ APR_DECLARE(apr_status_t) apr_shm_create(apr_shm_t **m,
const char *filename,
apr_pool_t *pool);
/**
* Special processing flags for apr_shm_create_ex() and apr_shm_attach_ex().
*/
#define APR_SHM_NS_LOCAL 1 /* Create or attach to named shared memory
* segment in the "Local" namespace on
* Windows. (Ignored on other platforms.)
* By default, the "Global" namespace is
* used for privileged processes and the
* "Local" namespace is used otherwise.
*/
#define APR_SHM_NS_GLOBAL 2 /* Create or attach to named shared memory
* segment in the "Global" namespace on
* Windows. (Ignored on other platforms.)
*/
/**
* Create and make accessible a shared memory segment with platform-
* specific processing.
* @param m The shared memory structure to create.
* @param reqsize The desired size of the segment.
* @param filename The file to use for shared memory on platforms that
* require it.
* @param pool the pool from which to allocate the shared memory
* structure.
* @param flags mask of APR_SHM_* (defined above)
* @remark A note about Anonymous vs. Named shared memory segments:
* Not all plaforms support anonymous shared memory segments, but in
* some cases it is prefered over other types of shared memory
* implementations. Passing a NULL 'file' parameter to this function
* will cause the subsystem to use anonymous shared memory segments.
* If such a system is not available, APR_ENOTIMPL is returned.
* @remark A note about allocation sizes:
* On some platforms it is necessary to store some metainformation
* about the segment within the actual segment. In order to supply
* the caller with the requested size it may be necessary for the
* implementation to request a slightly greater segment length
* from the subsystem. In all cases, the apr_shm_baseaddr_get()
* function will return the first usable byte of memory.
*
*/
APR_DECLARE(apr_status_t) apr_shm_create_ex(apr_shm_t **m,
apr_size_t reqsize,
const char *filename,
apr_pool_t *pool,
apr_int32_t flags);
/**
* Remove named resource associated with a shared memory segment,
* preventing attachments to the resource, but not destroying it.
@ -80,7 +127,7 @@ APR_DECLARE(apr_status_t) apr_shm_create(apr_shm_t **m,
* name-based shared memory segments, and will return APR_ENOTIMPL on
* platforms without such support. Removing the file while the shm
* is in use is not entirely portable, caller may use this to enhance
* obscurity of the resource, but be prepared for the the call to fail,
* obscurity of the resource, but be prepared for the call to fail,
* and for concurrent attempts to create a resource of the same name
* to also fail. The pool cleanup of apr_shm_create (apr_shm_destroy)
* also removes the named resource.
@ -107,6 +154,21 @@ APR_DECLARE(apr_status_t) apr_shm_attach(apr_shm_t **m,
const char *filename,
apr_pool_t *pool);
/**
* Attach to a shared memory segment that was created
* by another process, with platform-specific processing.
* @param m The shared memory structure to create.
* @param filename The file used to create the original segment.
* (This MUST match the original filename.)
* @param pool the pool from which to allocate the shared memory
* structure for this process.
* @param flags mask of APR_SHM_* (defined above)
*/
APR_DECLARE(apr_status_t) apr_shm_attach_ex(apr_shm_t **m,
const char *filename,
apr_pool_t *pool,
apr_int32_t flags);
/**
* Detach from a shared memory segment without destroying it.
* @param m The shared memory structure representing the segment

259
include/apr_skiplist.h Normal file
View File

@ -0,0 +1,259 @@
/* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#ifndef APR_SKIPLIST_H
#define APR_SKIPLIST_H
/**
* @file apr_skiplist.h
* @brief APR skip list implementation
*/
#include "apr.h"
#include "apr_portable.h"
#include <stdlib.h>
#ifdef __cplusplus
extern "C" {
#endif /* __cplusplus */
/**
* @defgroup apr_skiplist Skip list implementation
* Refer to http://en.wikipedia.org/wiki/Skip_list for information
* about the purpose of and ideas behind skip lists.
* @ingroup APR
* @{
*/
/**
* apr_skiplist_compare is the function type that must be implemented
* per object type that is used in a skip list for comparisons to maintain
* order
* */
typedef int (*apr_skiplist_compare) (void *, void *);
/**
* apr_skiplist_freefunc is the function type that must be implemented
* to handle elements as they are removed from a skip list.
*/
typedef void (*apr_skiplist_freefunc) (void *);
/** Opaque structure used to represent the skip list */
struct apr_skiplist;
/** Opaque structure used to represent the skip list */
typedef struct apr_skiplist apr_skiplist;
/**
* Opaque structure used to represent abstract nodes in the skip list
* (an abstraction above the raw elements which are collected in the
* skip list).
*/
struct apr_skiplistnode;
/** Opaque structure */
typedef struct apr_skiplistnode apr_skiplistnode;
/**
* Allocate memory using the same mechanism as the skip list.
* @param sl The skip list
* @param size The amount to allocate
* @remark If a pool was provided to apr_skiplist_init(), memory will
* be allocated from the pool or from a free list maintained with
* the skip list. Otherwise, memory will be allocated using the
* C standard library heap functions.
*/
APR_DECLARE(void *) apr_skiplist_alloc(apr_skiplist *sl, size_t size);
/**
* Free memory using the same mechanism as the skip list.
* @param sl The skip list
* @param mem The object to free
* @remark If a pool was provided to apr_skiplist_init(), memory will
* be added to a free list maintained with the skip list and be available
* to operations on the skip list or to other calls to apr_skiplist_alloc().
* Otherwise, memory will be freed using the C standard library heap
* functions.
*/
APR_DECLARE(void) apr_skiplist_free(apr_skiplist *sl, void *mem);
/**
* Allocate a new skip list
* @param sl The pointer in which to return the newly created skip list
* @param p The pool from which to allocate the skip list (optional).
* @remark Unlike most APR functions, a pool is optional. If no pool
* is provided, the C standard library heap functions will be used instead.
*/
APR_DECLARE(apr_status_t) apr_skiplist_init(apr_skiplist **sl, apr_pool_t *p);
/**
* Set the comparison functions to be used for searching the skip list.
* @param sl The skip list
* @param XXX1 FIXME
* @param XXX2 FIXME
*
* @remark If existing comparison functions are being replaced, the index
* will be replaced during this call. That is a potentially expensive
* operation.
*/
APR_DECLARE(void) apr_skiplist_set_compare(apr_skiplist *sl, apr_skiplist_compare XXX1,
apr_skiplist_compare XXX2);
/**
* Set the indexing functions to the specified comparison functions and
* rebuild the index.
* @param sl The skip list
* @param XXX1 FIXME
* @param XXX2 FIXME
*
* @remark If an index already exists, it will not be replaced and the
* comparison functions will not be changed.
*/
APR_DECLARE(void) apr_skiplist_add_index(apr_skiplist *sl, apr_skiplist_compare XXX1,
apr_skiplist_compare XXX2);
/**
* Return the list maintained by the skip list abstraction.
* @param sl The skip list
*/
APR_DECLARE(apr_skiplistnode *) apr_skiplist_getlist(apr_skiplist *sl);
/**
* Return the next matching element in the skip list using the specified
* comparison function.
* @param sl The skip list
* @param data The value to search for
* @param iter A pointer to the returned skip list node representing the element
* found
* @param func The comparison function to use
*/
APR_DECLARE(void *) apr_skiplist_find_compare(apr_skiplist *sl,
void *data,
apr_skiplistnode **iter,
apr_skiplist_compare func);
/**
* Return the next matching element in the skip list using the current comparison
* function.
* @param sl The skip list
* @param data The value to search for
* @param iter A pointer to the returned skip list node representing the element
* found
*/
APR_DECLARE(void *) apr_skiplist_find(apr_skiplist *sl, void *data, apr_skiplistnode **iter);
/**
* Return the next element in the skip list.
* @param sl The skip list
* @param iter On entry, a pointer to the skip list node to start with; on return,
* a pointer to the skip list node representing the element returned
* @remark If iter points to a NULL value on entry, NULL will be returned.
*/
APR_DECLARE(void *) apr_skiplist_next(apr_skiplist *sl, apr_skiplistnode **iter);
/**
* Return the previous element in the skip list.
* @param sl The skip list
* @param iter On entry, a pointer to the skip list node to start with; on return,
* a pointer to the skip list node representing the element returned
* @remark If iter points to a NULL value on entry, NULL will be returned.
*/
APR_DECLARE(void *) apr_skiplist_previous(apr_skiplist *sl, apr_skiplistnode **iter);
/**
* Insert an element into the skip list using the specified comparison function.
* @param sl The skip list
* @param data The element to insert
* @param comp The comparison function to use for placement into the skip list
*/
APR_DECLARE(apr_skiplistnode *) apr_skiplist_insert_compare(apr_skiplist *sl,
void *data, apr_skiplist_compare comp);
/**
* Insert an element into the skip list using the existing comparison function.
* @param sl The skip list
* @param data The element to insert
* @remark If no comparison function has been set for the skip list, the element
* will not be inserted and NULL will be returned.
*/
APR_DECLARE(apr_skiplistnode *) apr_skiplist_insert(apr_skiplist* sl, void *data);
/**
* Remove an element from the skip list using the specified comparison function for
* locating the element.
* @param sl The skip list
* @param data The element to remove
* @param myfree A function to be called for each removed element
* @param comp The comparison function to use for placement into the skip list
* @remark If the element is not found, 0 will be returned. Otherwise, the heightXXX
* will be returned.
*/
APR_DECLARE(int) apr_skiplist_remove_compare(apr_skiplist *sl, void *data,
apr_skiplist_freefunc myfree, apr_skiplist_compare comp);
/**
* Remove an element from the skip list using the existing comparison function for
* locating the element.
* @param sl The skip list
* @param data The element to remove
* @param myfree A function to be called for each removed element
* @remark If the element is not found, 0 will be returned. Otherwise, the heightXXX
* will be returned.
* @remark If no comparison function has been set for the skip list, the element
* will not be removed and 0 will be returned.
*/
APR_DECLARE(int) apr_skiplist_remove(apr_skiplist *sl, void *data, apr_skiplist_freefunc myfree);
/**
* Remove all elements from the skip list.
* @param sl The skip list
* @param myfree A function to be called for each removed element
*/
APR_DECLARE(void) apr_skiplist_remove_all(apr_skiplist *sl, apr_skiplist_freefunc myfree);
/**
* Remove each element from the skip list.
* @param sl The skip list
* @param myfree A function to be called for each removed element
*/
APR_DECLARE(void) apr_skiplist_destroy(apr_skiplist *sl, apr_skiplist_freefunc myfree);
/**
* Return the first element in the skip list, leaving the element in the skip list.
* @param sl The skip list
* @param myfree A function to be called for the removed element
* @remark NULL will be returned if there are no elements
*/
APR_DECLARE(void *) apr_skiplist_pop(apr_skiplist *sl, apr_skiplist_freefunc myfree);
/**
* Return the first element in the skip list, leaving the element in the skip list.
* @param sl The skip list
* @remark NULL will be returned if there are no elements
*/
APR_DECLARE(void *) apr_skiplist_peek(apr_skiplist *sl);
/**
* Merge two skip lists. XXX SEMANTICS
* @param sl1 One of two skip lists to be merged
* @param sl2 The other of two skip lists to be merged
*/
APR_DECLARE(apr_skiplist *) apr_skiplist_merge(apr_skiplist *sl1, apr_skiplist *sl2);
/** @} */
#ifdef __cplusplus
}
#endif
#endif /* ! APR_SKIPLIST_H */

View File

@ -90,7 +90,7 @@ APR_DECLARE(int) apr_strnatcasecmp(char const *a, char const *b);
* duplicate a string into memory allocated out of a pool
* @param p The pool to allocate out of
* @param s The string to duplicate
* @return The new string
* @return The new string or NULL if s == NULL
*/
APR_DECLARE(char *) apr_pstrdup(apr_pool_t *p, const char *s);
@ -100,7 +100,7 @@ APR_DECLARE(char *) apr_pstrdup(apr_pool_t *p, const char *s);
* @param p The pool to allocate out of
* @param s The block of characters to duplicate
* @param n The number of characters to duplicate
* @return The new string
* @return The new string or NULL if s == NULL
* @remark This is a faster alternative to apr_pstrndup, for use
* when you know that the string being duplicated really
* has 'n' or more characters. If the string might contain
@ -118,7 +118,7 @@ APR_DECLARE(char *) apr_pstrmemdup(apr_pool_t *p, const char *s, apr_size_t n)
* @param p The pool to allocate out of
* @param s The string to duplicate
* @param n The maximum number of characters to duplicate
* @return The new string
* @return The new string or NULL if s == NULL
* @remark The amount of memory allocated from the pool is the length
* of the returned string including the NUL terminator
*/
@ -130,7 +130,7 @@ APR_DECLARE(char *) apr_pstrndup(apr_pool_t *p, const char *s, apr_size_t n);
* @param p The pool to allocate from
* @param m The memory to duplicate
* @param n The number of bytes to duplicate
* @return The new block of memory
* @return The new block of memory or NULL if m == NULL
*/
APR_DECLARE(void *) apr_pmemdup(apr_pool_t *p, const void *m, apr_size_t n)
#if defined(__GNUC__) && (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 4))
@ -235,8 +235,14 @@ APR_DECLARE(apr_status_t) apr_tokenize_to_argv(const char *arg_str,
* first call to apr_strtok() for a given string, and NULL
* on subsequent calls.
* @param sep The set of delimiters
* @param last Internal state saved by apr_strtok() between calls.
* @param last State saved by apr_strtok() between calls.
* @return The next token from the string
* @note the 'last' state points to the trailing NUL char of the final
* token, otherwise it points to the character following the current
* token (all successive or empty occurances of sep are skiped on the
* subsequent call to apr_strtok). Therefore it is possible to avoid
* a strlen() determination, with the following logic;
* toklen = last - retval; if (*last) --toklen;
*/
APR_DECLARE(char *) apr_strtok(char *str, const char *sep, char **last);

View File

@ -267,6 +267,18 @@ APR_DECLARE(void) apr_table_clear(apr_table_t *t);
*/
APR_DECLARE(const char *) apr_table_get(const apr_table_t *t, const char *key);
/**
* Get values associated with a given key from the table. If more than one
* value exists, return a comma separated list of values. After this call, the
* data is still in the table.
* @param p The pool to allocate the combined value from, if necessary
* @param t The table to search for the key
* @param key The key to search for (case does not matter)
* @return The value associated with the key, or NULL if the key does not exist.
*/
APR_DECLARE(const char *) apr_table_getm(apr_pool_t *p, const apr_table_t *t,
const char *key);
/**
* Add a key/value pair to a table. If another element already exists with the
* same key, this will overwrite the old data.

View File

@ -59,7 +59,7 @@ typedef struct apr_thread_mutex_t apr_thread_mutex_t;
* </PRE>
* @param pool the pool from which to allocate the mutex.
* @warning Be cautious in using APR_THREAD_MUTEX_DEFAULT. While this is the
* most optimial mutex based on a given platform's performance charateristics,
* most optimal mutex based on a given platform's performance characteristics,
* it will behave as either a nested or an unnested lock.
*/
APR_DECLARE(apr_status_t) apr_thread_mutex_create(apr_thread_mutex_t **mutex,

View File

@ -114,7 +114,7 @@ typedef enum {
#define APR_OC_REASON_DEATH 0 /**< child has died, caller must call
* unregister still */
#define APR_OC_REASON_UNWRITABLE 1 /**< write_fd is unwritable */
#define APR_OC_REASON_RESTART 2 /**< a restart is occuring, perform
#define APR_OC_REASON_RESTART 2 /**< a restart is occurring, perform
* any necessary cleanup (including
* sending a special signal to child)
*/
@ -123,7 +123,7 @@ typedef enum {
* kill the child) */
#define APR_OC_REASON_LOST 4 /**< somehow the child exited without
* us knowing ... buggy os? */
#define APR_OC_REASON_RUNNING 5 /**< a health check is occuring,
#define APR_OC_REASON_RUNNING 5 /**< a health check is occurring,
* for most maintainence functions
* this is a no-op.
*/
@ -197,7 +197,9 @@ typedef struct apr_other_child_rec_t apr_other_child_rec_t;
typedef void *(APR_THREAD_FUNC *apr_thread_start_t)(apr_thread_t*, void*);
typedef enum {
APR_KILL_NEVER, /**< process is never sent any signals */
APR_KILL_NEVER, /**< process is never killed (i.e., never sent
* any signals), but it will be reaped if it exits
* before the pool is cleaned up */
APR_KILL_ALWAYS, /**< process is sent SIGKILL on apr_pool_t cleanup */
APR_KILL_AFTER_TIMEOUT, /**< SIGTERM, wait 3 seconds, SIGKILL */
APR_JUST_WAIT, /**< wait forever for the process to complete */
@ -632,7 +634,7 @@ APR_DECLARE(apr_status_t) apr_proc_create(apr_proc_t *new_proc,
* APR_NOWAIT -- return immediately regardless of if the
* child is dead or not.
* </PRE>
* @remark The childs status is in the return code to this process. It is one of:
* @remark The child's status is in the return code to this process. It is one of:
* <PRE>
* APR_CHILD_DONE -- child is no longer running.
* APR_CHILD_NOTDONE -- child is still running.

View File

@ -42,7 +42,7 @@ APR_DECLARE_DATA extern const char apr_month_snames[12][4];
APR_DECLARE_DATA extern const char apr_day_snames[7][4];
/** number of microseconds since 00:00:00 january 1, 1970 UTC */
/** number of microseconds since 00:00:00 January 1, 1970 UTC */
typedef apr_int64_t apr_time_t;
@ -93,7 +93,7 @@ typedef struct apr_time_exp_t apr_time_exp_t;
/**
* a structure similar to ANSI struct tm with the following differences:
* - tm_usec isn't an ANSI field
* - tm_gmtoff isn't an ANSI field (it's a bsdism)
* - tm_gmtoff isn't an ANSI field (it's a BSDism)
*/
struct apr_time_exp_t {
/** microseconds past tm_sec */
@ -110,9 +110,9 @@ struct apr_time_exp_t {
apr_int32_t tm_mon;
/** year since 1900 */
apr_int32_t tm_year;
/** (0-6) days since sunday */
/** (0-6) days since Sunday */
apr_int32_t tm_wday;
/** (0-365) days since jan 1 */
/** (0-365) days since January 1 */
apr_int32_t tm_yday;
/** daylight saving time */
apr_int32_t tm_isdst;
@ -121,7 +121,7 @@ struct apr_time_exp_t {
};
/**
* convert an ansi time_t to an apr_time_t
* Convert an ansi time_t to an apr_time_t
* @param result the resulting apr_time_t
* @param input the time_t to convert
*/
@ -129,8 +129,8 @@ APR_DECLARE(apr_status_t) apr_time_ansi_put(apr_time_t *result,
time_t input);
/**
* convert a time to its human readable components using an offset
* from GMT
* Convert a time to its human readable components using an offset
* from GMT.
* @param result the exploded time
* @param input the time to explode
* @param offs the number of seconds offset to apply
@ -140,7 +140,7 @@ APR_DECLARE(apr_status_t) apr_time_exp_tz(apr_time_exp_t *result,
apr_int32_t offs);
/**
* convert a time to its human readable components in GMT timezone
* Convert a time to its human readable components (GMT).
* @param result the exploded time
* @param input the time to explode
*/
@ -148,7 +148,7 @@ APR_DECLARE(apr_status_t) apr_time_exp_gmt(apr_time_exp_t *result,
apr_time_t input);
/**
* convert a time to its human readable components in local timezone
* Convert a time to its human readable components in the local timezone.
* @param result the exploded time
* @param input the time to explode
*/
@ -156,8 +156,8 @@ APR_DECLARE(apr_status_t) apr_time_exp_lt(apr_time_exp_t *result,
apr_time_t input);
/**
* Convert time value from human readable format to a numeric apr_time_t
* e.g. elapsed usec since epoch
* Convert time value from human readable format to a numeric apr_time_t
* (elapsed microseconds since the epoch).
* @param result the resulting imploded time
* @param input the input exploded time
*/
@ -166,7 +166,7 @@ APR_DECLARE(apr_status_t) apr_time_exp_get(apr_time_t *result,
/**
* Convert time value from human readable format to a numeric apr_time_t that
* always represents GMT
* always represents GMT.
* @param result the resulting imploded time
* @param input the input exploded time
*/
@ -185,7 +185,7 @@ APR_DECLARE(void) apr_sleep(apr_interval_time_t t);
/**
* apr_rfc822_date formats dates in the RFC822
* format in an efficient manner. It is a fixed length
* format which requires the indicated amount of storage,
* format which requires APR_RFC822_DATA_LEN bytes of storage,
* including the trailing NUL terminator.
* @param date_str String to write to.
* @param t the time to convert
@ -196,18 +196,18 @@ APR_DECLARE(apr_status_t) apr_rfc822_date(char *date_str, apr_time_t t);
#define APR_CTIME_LEN (25)
/**
* apr_ctime formats dates in the ctime() format
* in an efficient manner. it is a fixed length format
* and requires the indicated amount of storage including
* in an efficient manner. It is a fixed length format
* and requires APR_CTIME_LEN bytes of storage including
* the trailing NUL terminator.
* Unlike ANSI/ISO C ctime(), apr_ctime() does not include
* a \n at the end of the string.
* a \\n at the end of the string.
* @param date_str String to write to.
* @param t the time to convert
*/
APR_DECLARE(apr_status_t) apr_ctime(char *date_str, apr_time_t t);
/**
* formats the exploded time according to the format specified
* Formats the exploded time according to the format specified
* @param s string to write to
* @param retsize The length of the returned string
* @param max The maximum length of the string
@ -220,7 +220,7 @@ APR_DECLARE(apr_status_t) apr_strftime(char *s, apr_size_t *retsize,
/**
* Improve the clock resolution for the lifetime of the given pool.
* Generally this is only desireable on benchmarking and other very
* Generally this is only desirable on benchmarking and other very
* time-sensitive applications, and has no impact on most platforms.
* @param p The pool to associate the finer clock resolution
*/

View File

@ -81,7 +81,7 @@ APR_DECLARE(apr_status_t) apr_uid_name_get(char **username, apr_uid_t userid,
* Get the userid (and groupid) for the specified username
* @param userid Returns the user id
* @param groupid Returns the user's group id
* @param username The username to lookup
* @param username The username to look up
* @param p The pool from which to allocate working space
* @remark This function is available only if APR_HAS_USER is defined.
*/
@ -103,7 +103,7 @@ APR_DECLARE(apr_status_t) apr_uid_homepath_get(char **dirname,
* Compare two user identifiers for equality.
* @param left One uid to test
* @param right Another uid to test
* @return APR_SUCCESS if the apr_uid_t strutures identify the same user,
* @return APR_SUCCESS if the apr_uid_t structures identify the same user,
* APR_EMISMATCH if not, APR_BADARG if an apr_uid_t is invalid.
* @remark This function is available only if APR_HAS_USER is defined.
*/
@ -137,7 +137,7 @@ APR_DECLARE(apr_status_t) apr_gid_get(apr_gid_t *groupid,
* Compare two group identifiers for equality.
* @param left One gid to test
* @param right Another gid to test
* @return APR_SUCCESS if the apr_gid_t strutures identify the same group,
* @return APR_SUCCESS if the apr_gid_t structures identify the same group,
* APR_EMISMATCH if not, APR_BADARG if an apr_gid_t is invalid.
* @remark This function is available only if APR_HAS_USER is defined.
*/

View File

@ -38,7 +38,7 @@
*/
#define APR_COPYRIGHT "Copyright (c) 2013 The Apache Software " \
#define APR_COPYRIGHT "Copyright (c) 2000-2014 The Apache Software " \
"Foundation or its licensors, as applicable."
/* The numeric compile-time version constants. These constants are the
@ -56,13 +56,13 @@
* Minor API changes that do not cause binary compatibility problems.
* Reset to 0 when upgrading APR_MAJOR_VERSION
*/
#define APR_MINOR_VERSION 4
#define APR_MINOR_VERSION 5
/** patch level
* The Patch Level never includes API changes, simply bug fixes.
* Reset to 0 when upgrading APR_MINOR_VERSION
*/
#define APR_PATCH_VERSION 8
#define APR_PATCH_VERSION 1
/**
* The symbol APR_IS_DEV_VERSION is only defined for internal,

View File

@ -45,6 +45,11 @@
#define HAS_PIPES(dt) (dt == APR_POLL_FILE) ? 1 : 0
#endif
#if defined(HAVE_AIO_H) && defined(HAVE_AIO_MSGQ)
#define _AIO_OS390 /* enable a bunch of z/OS aio.h definitions */
#include <aio.h> /* aiocb */
#endif
/* Choose the best method platform specific to use in apr_pollset */
#ifdef HAVE_KQUEUE
#define POLLSET_USES_KQUEUE
@ -55,6 +60,9 @@
#elif defined(HAVE_EPOLL)
#define POLLSET_USES_EPOLL
#define POLLSET_DEFAULT_METHOD APR_POLLSET_EPOLL
#elif defined(HAVE_AIO_MSGQ)
#define POLLSET_USES_AIO_MSGQ
#define POLLSET_DEFAULT_METHOD APR_POLLSET_AIO_MSGQ
#elif defined(HAVE_POLL)
#define POLLSET_USES_POLL
#define POLLSET_DEFAULT_METHOD APR_POLLSET_POLL
@ -75,7 +83,7 @@
#endif
#endif
#if defined(POLLSET_USES_KQUEUE) || defined(POLLSET_USES_EPOLL) || defined(POLLSET_USES_PORT)
#if defined(POLLSET_USES_KQUEUE) || defined(POLLSET_USES_EPOLL) || defined(POLLSET_USES_PORT) || defined(POLLSET_USES_AIO_MSGQ)
#include "apr_ring.h"
@ -107,6 +115,7 @@ struct pfd_elem_t {
typedef struct apr_pollset_private_t apr_pollset_private_t;
typedef struct apr_pollset_provider_t apr_pollset_provider_t;
typedef struct apr_pollcb_provider_t apr_pollcb_provider_t;
struct apr_pollset_t
{
apr_pool_t *pool;

View File

@ -39,7 +39,7 @@
#if APR_HAVE_STRING_H
#include <string.h>
#endif
#if HAVE_SCHED_H
#ifdef HAVE_SCHED_H
#include <sched.h>
#endif
/* End System Headers */

View File

@ -83,6 +83,9 @@
/* Define if accept4 function is supported */
#undef HAVE_ACCEPT4
/* Define if async i/o supports message q's */
#undef HAVE_AIO_MSGQ
/* Define to 1 if you have `alloca', as a function or macro. */
#undef HAVE_ALLOCA
@ -929,7 +932,7 @@
/* switch this on if we have a BeOS version below BONE */
#if BEOS && !HAVE_BONE_VERSION
#if defined(BEOS) && !defined(HAVE_BONE_VERSION)
#define BEOS_R5 1
#else
#define BEOS_BONE 1

2481
libapr.dep

File diff suppressed because it is too large Load Diff

View File

@ -254,6 +254,14 @@ SOURCE=.\atomic\win32\apr_atomic.c
SOURCE=.\dso\win32\dso.c
# End Source File
# End Group
# Begin Group "encoding"
# PROP Default_Filter ""
# Begin Source File
SOURCE=.\encoding\apr_escape.c
# End Source File
# End Group
# Begin Group "file_io"
# PROP Default_Filter ""
@ -546,6 +554,10 @@ SOURCE=.\tables\apr_hash.c
SOURCE=.\tables\apr_tables.c
# End Source File
# Begin Source File
SOURCE=.\tables\apr_skiplist.c
# End Source File
# End Group
# Begin Group "threadproc"
@ -746,6 +758,79 @@ SOURCE=.\include\apr_errno.h
# End Source File
# Begin Source File
SOURCE=.\include\apr_escape.h
!IF "$(CFG)" == "libapr - Win32 Release"
# Begin Custom Build - Creating gen_test_char.exe and apr_escape_test_char.h
InputPath=.\include\apr_escape.h
".\Release\gen_test_char.exe" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
cl.exe /nologo /W3 /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /FD /I ".\include" /Fo.\Release\gen_test_char /Fe.\Release\gen_test_char.exe .\tools\gen_test_char.c
.\Release\gen_test_char.exe > .\include\apr_escape_test_char.h
# End Custom Build
!ELSEIF "$(CFG)" == "libapr - Win32 Debug"
# Begin Custom Build - Creating gen_test_char.exe and apr_escape_test_char.h
InputPath=.\include\apr_escape.h
".\Debug\gen_test_char.exe" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
cl.exe /nologo /W3 /EHsc /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /FD /I ".\include" /Fo.\Debug\gen_test_char /Fe.\Debug\gen_test_char.exe .\tools\gen_test_char.c
.\Debug\gen_test_char.exe > .\include\apr_escape_test_char.h
# End Custom Build
!ELSEIF "$(CFG)" == "libapr - Win32 Release9x"
# Begin Custom Build - Creating gen_test_char.exe and apr_escape_test_char.h
InputPath=.\include\apr_escape.h
".\9x\Release\gen_test_char.exe" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
cl.exe /nologo /W3 /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /FD /I ".\include" /Fo.\9x\Release\gen_test_char /Fe.\9x\Release\gen_test_char.exe .\tools\gen_test_char.c
.\9x\Release\gen_test_char.exe > .\include\apr_escape_test_char.h
# End Custom Build
!ELSEIF "$(CFG)" == "libapr - Win32 Debug9x"
# Begin Custom Build - Creating gen_test_char.exe and apr_escape_test_char.h
InputPath=.\include\apr_escape.h
".\9x\Debug\gen_test_char.exe" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
cl.exe /nologo /W3 /EHsc /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /FD /I ".\include" /Fo.\9x\Debug\gen_test_char /Fe.\9x\Debug\gen_test_char.exe .\tools\gen_test_char.c
.\9x\Debug\gen_test_char.exe > .\include\apr_escape_test_char.h
# End Custom Build
!ELSEIF "$(CFG)" == "libapr - x64 Release"
# Begin Custom Build - Creating gen_test_char.exe and apr_escape_test_char.h
InputPath=.\include\apr_escape.h
".\x64\Release\gen_test_char.exe" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
cl.exe /nologo /W3 /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /FD /I ".\include" /Fo.\x64\Release\gen_test_char /Fe.\x64\Release\gen_test_char.exe .\tools\gen_test_char.c
.\x64\Release\gen_test_char.exe > .\include\apr_escape_test_char.h
# End Custom Build
!ELSEIF "$(CFG)" == "libapr - x64 Debug"
# Begin Custom Build - Creating gen_test_char.exe and apr_escape_test_char.h
InputPath=.\include\apr_escape.h
".\x64\Debug\gen_test_char.exe" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
cl.exe /nologo /W3 /EHsc /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /FD /I ".\include" /Fo.\x64\Debug\gen_test_char /Fe.\x64\Debug\gen_test_char.exe .\tools\gen_test_char.c
.\x64\Debug\gen_test_char.exe > .\include\apr_escape_test_char.h
# End Custom Build
!ENDIF
# End Source File
# Begin Source File
SOURCE=.\include\apr_file_info.h
# End Source File
# Begin Source File
@ -822,6 +907,10 @@ SOURCE=.\include\apr_signal.h
# End Source File
# Begin Source File
SOURCE=.\include\apr_skiplist.h
# End Source File
# Begin Source File
SOURCE=.\include\apr_strings.h
# End Source File
# Begin Source File
@ -863,6 +952,69 @@ SOURCE=.\include\apr_version.h
# Begin Source File
SOURCE=.\include\apr_want.h
!IF "$(CFG)" == "libapr - Win32 Release"
# Begin Custom Build
InputPath=.\include\apr_want.h
".\include\apr_escape_test_char.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
type .\include\apr.hw > .\include\apr.h
# End Custom Build
!ELSEIF "$(CFG)" == "libapr - Win32 Debug"
# Begin Custom Build
InputPath=.\include\apr_want.h
".\include\apr_escape_test_char.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
type .\include\apr.hw > .\include\apr.h
# End Custom Build
!ELSEIF "$(CFG)" == "libapr - Win32 Release9x"
# Begin Custom Build
InputPath=.\include\apr_want.h
".\include\apr_escape_test_char.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
type .\include\apr.hw > .\include\apr.h
# End Custom Build
!ELSEIF "$(CFG)" == "libapr - Win32 Debug9x"
# Begin Custom Build
InputPath=.\include\apr_want.h
".\include\apr_escape_test_char.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
type .\include\apr.hw > .\include\apr.h
# End Custom Build
!ELSEIF "$(CFG)" == "libapr - x64 Release"
# Begin Custom Build
InputPath=.\include\apr_want.h
".\include\apr_escape_test_char.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
type .\include\apr.hw > .\include\apr.h
# End Custom Build
!ELSEIF "$(CFG)" == "libapr - x64 Debug"
# Begin Custom Build
InputPath=.\include\apr_want.h
".\include\apr_escape_test_char.h" : $(SOURCE) "$(INTDIR)" "$(OUTDIR)"
type .\include\apr.hw > .\include\apr.h
# End Custom Build
!ENDIF
# End Source File
# End Group
# Begin Source File

4035
libapr.mak

File diff suppressed because it is too large Load Diff

View File

@ -102,8 +102,8 @@ static apr_status_t proc_mutex_posix_create(apr_proc_mutex_t *new_mutex,
apr_ssize_t flen = strlen(fname);
char *p = apr_pstrndup(new_mutex->pool, fname, strlen(fname));
unsigned int h1, h2;
h1 = apr_hashfunc_default((const char *)p, &flen);
h2 = rshash(p);
h1 = (apr_hashfunc_default((const char *)p, &flen) & 0xffffffff);
h2 = (rshash(p) & 0xffffffff);
apr_snprintf(semname, sizeof(semname), "/ApR.%xH%x", h1, h2);
} else {
apr_time_t now;
@ -951,7 +951,12 @@ APR_DECLARE(apr_status_t) apr_os_proc_mutex_get(apr_os_proc_mutex_t *ospmutex,
apr_proc_mutex_t *pmutex)
{
#if APR_HAS_SYSVSEM_SERIALIZE || APR_HAS_FCNTL_SERIALIZE || APR_HAS_FLOCK_SERIALIZE || APR_HAS_POSIXSEM_SERIALIZE
ospmutex->crossproc = pmutex->interproc->filedes;
if (pmutex->interproc) {
ospmutex->crossproc = pmutex->interproc->filedes;
}
else {
ospmutex->crossproc = -1;
}
#endif
#if APR_HAS_PROC_PTHREAD_SERIALIZE
ospmutex->pthread_interproc = pmutex->pthread_interproc;

View File

@ -552,7 +552,7 @@ apr_status_t apr_socket_sendfile(apr_socket_t * sock, apr_file_t * file,
/* On early versions of FreeBSD sendfile, the number of bytes to send
* must include the length of the headers. Don't look at the man page
* for this :( Instead, look at the the logic in
* for this :( Instead, look at the logic in
* src/sys/kern/uipc_syscalls::sendfile().
*
* This was fixed in the middle of 4.6-STABLE

View File

@ -839,6 +839,35 @@ APR_DECLARE(int) apr_sockaddr_equal(const apr_sockaddr_t *addr1,
return 0; /* not equal */
}
APR_DECLARE(int) apr_sockaddr_is_wildcard(const apr_sockaddr_t *addr)
{
static const char inaddr_any[
#if APR_HAVE_IPV6
sizeof(struct in6_addr)
#else
sizeof(struct in_addr)
#endif
] = {0};
if (addr->ipaddr_ptr /* IP address initialized */
&& addr->ipaddr_len <= sizeof inaddr_any) { /* else bug elsewhere? */
if (!memcmp(inaddr_any, addr->ipaddr_ptr, addr->ipaddr_len)) {
return 1;
}
#if APR_HAVE_IPV6
if (addr->family == AF_INET6
&& IN6_IS_ADDR_V4MAPPED((struct in6_addr *)addr->ipaddr_ptr)) {
struct in_addr *v4 = (struct in_addr *)&((apr_uint32_t *)addr->ipaddr_ptr)[3];
if (!memcmp(inaddr_any, v4, sizeof *v4)) {
return 1;
}
}
#endif
}
return 0;
}
static apr_status_t parse_network(apr_ipsubnet_t *ipsub, const char *network)
{
/* legacy syntax for ip addrs: a.b.c. ==> a.b.c.0/24 for example */

View File

@ -46,7 +46,8 @@ APR_DECLARE(apr_status_t) apr_socket_atreadeof(apr_socket_t *sock, int *atreadeo
/* Some other error -> unexpected error. */
return rv;
}
else if (nfds == 1 && pfds[0].rtnevents == APR_POLLIN) {
/* Many platforms return only APR_POLLIN; OS X returns APR_POLLHUP|APR_POLLIN */
else if (nfds == 1 && (pfds[0].rtnevents & APR_POLLIN) == APR_POLLIN) {
apr_sockaddr_t unused;
apr_size_t len = 1;
char buf;

View File

@ -207,7 +207,20 @@ apr_status_t apr_socket_accept(apr_socket_t **new, apr_socket_t *sock,
sa.salen = sizeof(sa.sa);
#ifdef HAVE_ACCEPT4
s = accept4(sock->socketdes, (struct sockaddr *)&sa.sa, &sa.salen, SOCK_CLOEXEC);
{
int flags = SOCK_CLOEXEC;
#if defined(SOCK_NONBLOCK) && APR_O_NONBLOCK_INHERITED
/* With FreeBSD accept4() (avail in 10+), O_NONBLOCK is not inherited
* (unlike Linux). Mimic the accept() behavior here in a way that
* may help other platforms.
*/
if (apr_is_option_set(sock, APR_SO_NONBLOCK) == 1) {
flags |= SOCK_NONBLOCK;
}
#endif
s = accept4(sock->socketdes, (struct sockaddr *)&sa.sa, &sa.salen, flags);
}
#else
s = accept(sock->socketdes, (struct sockaddr *)&sa.sa, &sa.salen);
#endif

View File

@ -141,6 +141,18 @@ apr_status_t apr_socket_opt_set(apr_socket_t *sock,
apr_set_option(sock, APR_SO_DEBUG, on);
}
break;
case APR_SO_BROADCAST:
#ifdef SO_BROADCAST
if (on != apr_is_option_set(sock, APR_SO_BROADCAST)) {
if (setsockopt(sock->socketdes, SOL_SOCKET, SO_BROADCAST, (void *)&one, sizeof(int)) == -1) {
return errno;
}
apr_set_option(sock, APR_SO_BROADCAST, on);
}
#else
return APR_ENOTIMPL;
#endif
break;
case APR_SO_REUSEADDR:
if (on != apr_is_option_set(sock, APR_SO_REUSEADDR)) {
if (setsockopt(sock->socketdes, SOL_SOCKET, SO_REUSEADDR, (void *)&one, sizeof(int)) == -1) {

View File

@ -51,6 +51,9 @@
#if APR_HAVE_STRINGS_H
#include <strings.h>
#endif
#if APR_HAVE_STDIO_H
#include <stdio.h>
#endif
/* Disable getpass() support when PASS_MAX is defined and is "small",
* for an arbitrary definition of "small".
@ -80,9 +83,9 @@
#if !defined(HAVE_GETPASS) && !defined(HAVE_GETPASSPHRASE) && !defined(HAVE_GETPASS_R)
/* MPE, Win32, NetWare and BeOS all lack a native getpass() */
/* MPE, Win32, and BeOS all lack a native getpass() */
#if !defined(HAVE_TERMIOS_H) && !defined(WIN32) && !defined(NETWARE)
#if !defined(HAVE_TERMIOS_H) && !defined(WIN32)
/*
* MPE lacks getpass() and a way to suppress stdin echo. So for now, just
* issue the prompt and read the results with echo. (Ugh).
@ -98,46 +101,7 @@ static char *get_password(const char *prompt)
return (char *) &password;
}
#elif defined (HAVE_TERMIOS_H)
#include <stdio.h>
static char *get_password(const char *prompt)
{
struct termios attr;
static char password[MAX_STRING_LEN];
int n=0;
fputs(prompt, stderr);
fflush(stderr);
if (tcgetattr(STDIN_FILENO, &attr) != 0)
return NULL;
attr.c_lflag &= ~(ECHO);
if (tcsetattr(STDIN_FILENO, TCSAFLUSH, &attr) != 0)
return NULL;
while ((password[n] = getchar()) != '\n') {
if (n < sizeof(password) - 1 && password[n] >= ' ' && password[n] <= '~') {
n++;
} else {
fprintf(stderr,"\n");
fputs(prompt, stderr);
fflush(stderr);
n = 0;
}
}
password[n] = '\0';
printf("\n");
if (n > (MAX_STRING_LEN - 1)) {
password[MAX_STRING_LEN - 1] = '\0';
}
attr.c_lflag |= ECHO;
tcsetattr(STDIN_FILENO, TCSANOW, &attr);
return (char*) &password;
}
#else
#elif defined(WIN32)
/*
* Windows lacks getpass(). So we'll re-implement it here.
@ -208,6 +172,44 @@ static char *get_password(const char *prompt)
#endif
}
#elif defined (HAVE_TERMIOS_H)
static char *get_password(const char *prompt)
{
struct termios attr;
static char password[MAX_STRING_LEN];
int n=0;
fputs(prompt, stderr);
fflush(stderr);
if (tcgetattr(STDIN_FILENO, &attr) != 0)
return NULL;
attr.c_lflag &= ~(ECHO);
if (tcsetattr(STDIN_FILENO, TCSAFLUSH, &attr) != 0)
return NULL;
while ((password[n] = getchar()) != '\n') {
if (n < sizeof(password) - 1 && password[n] >= ' ' && password[n] <= '~') {
n++;
} else {
fprintf(stderr,"\n");
fputs(prompt, stderr);
fflush(stderr);
n = 0;
}
}
password[n] = '\0';
printf("\n");
if (n > (MAX_STRING_LEN - 1)) {
password[MAX_STRING_LEN - 1] = '\0';
}
attr.c_lflag |= ECHO;
tcsetattr(STDIN_FILENO, TCSANOW, &attr);
return (char*) &password;
}
#endif /* no getchar or _getch */
#endif /* no getpass or getpassphrase or getpass_r */

View File

@ -66,6 +66,7 @@ static apr_pollcb_provider_t *pollcb_provider(apr_pollset_method_e method)
#endif
break;
case APR_POLLSET_SELECT:
case APR_POLLSET_AIO_MSGQ:
case APR_POLLSET_DEFAULT:
break;
}

View File

@ -163,6 +163,9 @@ extern apr_pollset_provider_t *apr_pollset_provider_port;
#if defined(HAVE_EPOLL)
extern apr_pollset_provider_t *apr_pollset_provider_epoll;
#endif
#if defined(HAVE_AIO_MSGQ)
extern apr_pollset_provider_t *apr_pollset_provider_aio_msgq;
#endif
#if defined(HAVE_POLL)
extern apr_pollset_provider_t *apr_pollset_provider_poll;
#endif
@ -185,6 +188,11 @@ static apr_pollset_provider_t *pollset_provider(apr_pollset_method_e method)
case APR_POLLSET_EPOLL:
#if defined(HAVE_EPOLL)
provider = apr_pollset_provider_epoll;
#endif
break;
case APR_POLLSET_AIO_MSGQ:
#if defined(HAVE_AIO_MSGQ)
provider = apr_pollset_provider_aio_msgq;
#endif
break;
case APR_POLLSET_POLL:

772
poll/unix/z_asio.c Normal file
View File

@ -0,0 +1,772 @@
/* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
*
******************************************************************************
*
* This implementation is based on a design by John Brooks (IBM Pok) which uses
* the z/OS sockets async i/o facility. When a
* socket is added to the pollset, an async poll is issued for that individual
* socket. It specifies that the kernel should send an IPC message when the
* socket becomes ready. The IPC messages are sent to a single message queue
* that is part of the pollset. apr_pollset_poll waits on the arrival of IPC
* messages or the specified timeout.
*
* Since z/OS does not support async i/o for pipes or files at present, this
* implementation falls back to using ordinary poll() when
* APR_POLLSET_THREADSAFE is unset.
*
* Greg Ames
* April 2012
*/
#include "apr.h"
#include "apr_hash.h"
#include "apr_poll.h"
#include "apr_time.h"
#include "apr_portable.h"
#include "apr_arch_inherit.h"
#include "apr_arch_file_io.h"
#include "apr_arch_networkio.h"
#include "apr_arch_poll_private.h"
#ifdef HAVE_AIO_MSGQ
#include <sys/msg.h> /* msgget etc */
#include <time.h> /* timestruct */
#include <poll.h> /* pollfd */
#include <limits.h> /* MAX_INT */
struct apr_pollset_private_t
{
int msg_q; /* IPC message queue. The z/OS kernel sends messages
* to this queue when our async polls on individual
* file descriptors complete
*/
apr_pollfd_t *result_set;
apr_uint32_t size;
#if APR_HAS_THREADS
/* A thread mutex to protect operations on the rings and the hash */
apr_thread_mutex_t *ring_lock;
#endif
/* A hash of all active elements used for O(1) _remove operations */
apr_hash_t *elems;
APR_RING_HEAD(ready_ring_t, asio_elem_t) ready_ring;
APR_RING_HEAD(prior_ready_ring_t, asio_elem_t) prior_ready_ring;
APR_RING_HEAD(free_ring_t, asio_elem_t) free_ring;
/* for pipes etc with no asio */
struct pollfd *pollset;
apr_pollfd_t *query_set;
};
typedef enum {
ASIO_INIT = 0,
ASIO_REMOVED,
ASIO_COMPLETE
} asio_state_e;
typedef struct asio_elem_t asio_elem_t;
struct asio_msgbuf_t {
long msg_type; /* must be > 0 */
asio_elem_t *msg_elem;
};
struct asio_elem_t
{
APR_RING_ENTRY(asio_elem_t) link;
apr_pollfd_t pfd;
struct pollfd os_pfd;
struct aiocb a;
asio_state_e state;
struct asio_msgbuf_t msg;
};
#define DEBUG 0
/* DEBUG settings: 0 - no debug messages at all,
* 1 - should not occur messages,
* 2 - apr_pollset_* entry and exit messages,
* 3 - state changes, memory usage,
* 4 - z/OS, APR, and internal calls,
* 5 - everything else except the timer pop path,
* 6 - everything, including the Event 1 sec timer pop path
*
* each DEBUG level includes all messages produced by lower numbered levels
*/
#if DEBUG
#include <assert.h>
#include <unistd.h> /* getpid */
#define DBG_BUFF char dbg_msg_buff[256];
#define DBG_TEST(lvl) if (lvl <= DEBUG) {
#define DBG_CORE(msg) sprintf(dbg_msg_buff, "% 8d " __FUNCTION__ \
" " msg, getpid()), \
fprintf(stderr, "%s", dbg_msg_buff);
#define DBG_CORE1(msg, var1) sprintf(dbg_msg_buff, "% 8d " __FUNCTION__ \
" " msg, getpid(), var1), \
fprintf(stderr, "%s", dbg_msg_buff);
#define DBG_CORE2(msg, var1, var2) sprintf(dbg_msg_buff, "% 8d " __FUNCTION__ \
" " msg, getpid(), var1, var2), \
fprintf(stderr, "%s", dbg_msg_buff);
#define DBG_CORE3(msg, var1, var2, var3) \
sprintf(dbg_msg_buff, "% 8d " __FUNCTION__ \
" " msg, getpid(), var1, var2, var3), \
fprintf(stderr, "%s", dbg_msg_buff);
#define DBG_CORE4(msg, var1, var2, var3, var4) \
sprintf(dbg_msg_buff, "% 8d " __FUNCTION__ \
" " msg, getpid(), var1, var2, var3, var4),\
fprintf(stderr, "%s", dbg_msg_buff);
#define DBG_END }
#define DBG(lvl, msg) DBG_TEST(lvl) \
DBG_CORE(msg) \
DBG_END
#define DBG1(lvl, msg, var1) DBG_TEST(lvl) \
DBG_CORE1(msg, var1) \
DBG_END
#define DBG2(lvl, msg, var1, var2) DBG_TEST(lvl) \
DBG_CORE2(msg, var1, var2) \
DBG_END
#define DBG3(lvl, msg, var1, var2, var3) \
DBG_TEST(lvl) \
DBG_CORE3(msg, var1, var2, var3) \
DBG_END
#define DBG4(lvl, msg, var1, var2, var3, var4) \
DBG_TEST(lvl) \
DBG_CORE4(msg, var1, var2, var3, var4) \
DBG_END
#else /* DEBUG is 0 */
#define DBG_BUFF
#define DBG(lvl, msg) ((void)0)
#define DBG1(lvl, msg, var1) ((void)0)
#define DBG2(lvl, msg, var1, var2) ((void)0)
#define DBG3(lvl, msg, var1, var2, var3) ((void)0)
#define DBG4(lvl, msg, var1, var2, var3, var4) ((void)0)
#endif /* DEBUG */
static int asyncio(struct aiocb *a)
{
DBG_BUFF
int rv;
#ifdef _LP64
#define AIO BPX4AIO
#else
#define AIO BPX1AIO
#endif
AIO(sizeof(struct aiocb), a, &rv, &errno, __err2ad());
DBG2(4, "BPX4AIO aiocb %p rv %d\n",
a, rv);
#ifdef DEBUG
if (rv < 0) {
DBG2(4, "errno %d errnojr %08x\n",
errno, *__err2ad());
}
#endif
return rv;
}
static apr_int16_t get_event(apr_int16_t event)
{
DBG_BUFF
apr_int16_t rv = 0;
DBG(4, "entered\n");
if (event & APR_POLLIN)
rv |= POLLIN;
if (event & APR_POLLPRI)
rv |= POLLPRI;
if (event & APR_POLLOUT)
rv |= POLLOUT;
if (event & APR_POLLERR)
rv |= POLLERR;
if (event & APR_POLLHUP)
rv |= POLLHUP;
if (event & APR_POLLNVAL)
rv |= POLLNVAL;
DBG(4, "exiting\n");
return rv;
}
static apr_int16_t get_revent(apr_int16_t event)
{
DBG_BUFF
apr_int16_t rv = 0;
DBG(4, "entered\n");
if (event & POLLIN)
rv |= APR_POLLIN;
if (event & POLLPRI)
rv |= APR_POLLPRI;
if (event & POLLOUT)
rv |= APR_POLLOUT;
if (event & POLLERR)
rv |= APR_POLLERR;
if (event & POLLHUP)
rv |= APR_POLLHUP;
if (event & POLLNVAL)
rv |= APR_POLLNVAL;
DBG(4, "exiting\n");
return rv;
}
static apr_status_t asio_pollset_cleanup(apr_pollset_t *pollset)
{
DBG_BUFF
int rv;
DBG(4, "entered\n");
rv = msgctl(pollset->p->msg_q, IPC_RMID, NULL);
DBG1(4, "exiting, msgctl(IPC_RMID) returned %d\n", rv);
return rv;
}
static apr_status_t asio_pollset_create(apr_pollset_t *pollset,
apr_uint32_t size,
apr_pool_t *p,
apr_uint32_t flags)
{
DBG_BUFF
apr_status_t rv;
apr_pollset_private_t *priv;
DBG1(2, "entered, flags: %x\n", flags);
priv = pollset->p = apr_palloc(p, sizeof(*priv));
if (flags & APR_POLLSET_THREADSAFE) {
#if APR_HAS_THREADS
if (rv = apr_thread_mutex_create(&(priv->ring_lock),
APR_THREAD_MUTEX_DEFAULT,
p) != APR_SUCCESS) {
DBG1(1, "apr_thread_mutex_create returned %d\n", rv);
pollset = NULL;
return rv;
}
rv = msgget(IPC_PRIVATE, S_IWUSR+S_IRUSR); /* user r/w perms */
if (rv < 0) {
#if DEBUG
perror(__FUNCTION__ " msgget returned < 0 ");
#endif
pollset = NULL;
return rv;
}
DBG2(4, "pollset %p msgget was OK, rv=%d\n", pollset, rv);
priv->msg_q = rv;
priv->elems = apr_hash_make(p);
APR_RING_INIT(&priv->free_ring, asio_elem_t, link);
APR_RING_INIT(&priv->prior_ready_ring, asio_elem_t, link);
#else /* APR doesn't have threads but caller wants a threadsafe pollset */
pollset = NULL;
return APR_ENOTIMPL;
#endif
} else { /* APR_POLLSET_THREADSAFE not set, i.e. no async i/o,
* init fields only needed in old style pollset
*/
priv->pollset = apr_palloc(p, size * sizeof(struct pollfd));
priv->query_set = apr_palloc(p, size * sizeof(apr_pollfd_t));
if ((!priv->pollset) || (!priv->query_set)) {
return APR_ENOMEM;
}
}
pollset->nelts = 0;
pollset->flags = flags;
pollset->pool = p;
priv->size = size;
priv->result_set = apr_palloc(p, size * sizeof(apr_pollfd_t));
if (!priv->result_set) {
return APR_ENOMEM;
}
DBG2(2, "exiting, pollset: %p, type: %s\n",
pollset,
flags & APR_POLLSET_THREADSAFE ? "async" : "POSIX");
return APR_SUCCESS;
} /* end of asio_pollset_create */
static apr_status_t posix_add(apr_pollset_t *pollset,
const apr_pollfd_t *descriptor)
{
DBG_BUFF
int fd;
apr_pool_t *p = pollset->pool;
apr_pollset_private_t *priv = pollset->p;
DBG(4, "entered\n");
if (pollset->nelts == priv->size) {
return APR_ENOMEM;
}
priv->query_set[pollset->nelts] = *descriptor;
if (descriptor->desc_type == APR_POLL_SOCKET) {
fd = descriptor->desc.s->socketdes;
}
else {
fd = descriptor->desc.f->filedes;
}
priv->pollset[pollset->nelts].fd = fd;
priv->pollset[pollset->nelts].events =
get_event(descriptor->reqevents);
pollset->nelts++;
DBG2(4, "exiting, fd %d added to pollset %p\n", fd, pollset);
return APR_SUCCESS;
} /* end of posix_add */
static apr_status_t asio_pollset_add(apr_pollset_t *pollset,
const apr_pollfd_t *descriptor)
{
DBG_BUFF
asio_elem_t *elem;
apr_status_t rv = APR_SUCCESS;
apr_pollset_private_t *priv = pollset->p;
pollset_lock_rings();
DBG(2, "entered\n");
if (pollset->flags & APR_POLLSET_THREADSAFE) {
if (!APR_RING_EMPTY(&(priv->free_ring), asio_elem_t, link)) {
elem = APR_RING_FIRST(&(priv->free_ring));
APR_RING_REMOVE(elem, link);
DBG1(3, "used recycled memory at %08p\n", elem);
elem->state = ASIO_INIT;
}
else {
elem = (asio_elem_t *) apr_pcalloc(pollset->pool, sizeof(asio_elem_t));
DBG1(3, "alloced new memory at %08p\n", elem);
elem->a.aio_notifytype = AIO_MSGQ;
elem->a.aio_msgev_qid = priv->msg_q;
DBG1(5, "aio_msgev_quid = %d \n", elem->a.aio_msgev_qid);
elem->a.aio_msgev_size = sizeof(asio_elem_t *);
elem->a.aio_msgev_flag = 0; /* wait if queue is full */
elem->a.aio_msgev_addr = &(elem->msg);
elem->a.aio_buf = &(elem->os_pfd);
elem->a.aio_nbytes = 1; /* number of pfds to poll */
elem->msg.msg_type = 1;
elem->msg.msg_elem = elem;
}
/* z/OS only supports async I/O for sockets for now */
elem->os_pfd.fd = descriptor->desc.s->socketdes;
APR_RING_ELEM_INIT(elem, link);
elem->a.aio_cmd = AIO_SELPOLL;
elem->a.aio_cflags &= ~AIO_OK2COMPIMD; /* not OK to complete inline*/
elem->pfd = *descriptor;
elem->os_pfd.events = get_event(descriptor->reqevents);
if (0 != asyncio(&elem->a)) {
rv = errno;
DBG3(4, "pollset %p asio failed fd %d, errno %p\n",
pollset, elem->os_pfd.fd, rv);
#if DEBUG
perror(__FUNCTION__ " asio failure");
#endif
}
else {
DBG2(4, "good asio call, adding fd %d to pollset %p\n",
elem->os_pfd.fd, pollset);
pollset->nelts++;
apr_hash_set(priv->elems, &(elem->os_pfd.fd), sizeof(int), elem);
}
}
else {
/* APR_POLLSET_THREADSAFE isn't set. use POSIX poll in case
* pipes or files are used with this pollset
*/
rv = posix_add(pollset, descriptor);
}
DBG1(2, "exiting, rv = %d\n", rv);
pollset_unlock_rings();
return rv;
} /* end of asio_pollset_add */
static posix_remove(apr_pollset_t *pollset, const apr_pollfd_t *descriptor)
{
DBG_BUFF
apr_uint32_t i;
apr_pollset_private_t *priv = pollset->p;
DBG(4, "entered\n");
for (i = 0; i < pollset->nelts; i++) {
if (descriptor->desc.s == priv->query_set[i].desc.s) {
/* Found an instance of the fd: remove this and any other copies */
apr_uint32_t dst = i;
apr_uint32_t old_nelts = pollset->nelts;
pollset->nelts--;
for (i++; i < old_nelts; i++) {
if (descriptor->desc.s == priv->query_set[i].desc.s) {
pollset->nelts--;
}
else {
priv->pollset[dst] = priv->pollset[i];
priv->query_set[dst] = priv->query_set[i];
dst++;
}
}
DBG(4, "returning OK\n");
return APR_SUCCESS;
}
}
DBG(1, "returning APR_NOTFOUND\n");
return APR_NOTFOUND;
} /* end of posix_remove */
static apr_status_t asio_pollset_remove(apr_pollset_t *pollset,
const apr_pollfd_t *descriptor)
{
DBG_BUFF
asio_elem_t *elem;
apr_status_t rv = APR_SUCCESS;
apr_pollset_private_t *priv = pollset->p;
struct aiocb cancel_a; /* AIO_CANCEL is synchronous, so autodata works fine */
int fd;
DBG(2, "entered\n");
if (!(pollset->flags & APR_POLLSET_THREADSAFE)) {
return posix_remove(pollset, descriptor);
}
pollset_lock_rings();
#if DEBUG
assert(descriptor->desc_type == APR_POLL_SOCKET);
#endif
/* zOS 1.12 doesn't support files for async i/o */
fd = descriptor->desc.s->socketdes;
elem = apr_hash_get(priv->elems, &(fd), sizeof(int));
if (elem == NULL) {
DBG1(1, "couldn't find fd %d\n", fd);
rv = APR_NOTFOUND;
} else {
DBG1(5, "hash found fd %d\n", fd);
/* delete this fd from the hash */
apr_hash_set(priv->elems, &(fd), sizeof(int), NULL);
if (elem->state == ASIO_INIT) {
/* asyncio call to cancel */
cancel_a.aio_cmd = AIO_CANCEL;
cancel_a.aio_buf = &elem->a; /* point to original aiocb */
cancel_a.aio_cflags = 0;
cancel_a.aio_cflags2 = 0;
/* we want the original aiocb to show up on the pollset message queue
* before recycling its memory to eliminate race conditions
*/
rv = asyncio(&cancel_a);
DBG1(4, "asyncio returned %d\n", rv);
#if DEBUG
assert(rv == 1);
#endif
}
elem->state = ASIO_REMOVED;
rv = APR_SUCCESS;
}
DBG1(2, "exiting, rv: %d\n", rv);
pollset_unlock_rings();
return rv;
} /* end of asio_pollset_remove */
static posix_poll(apr_pollset_t *pollset,
apr_interval_time_t timeout,
apr_int32_t *num,
const apr_pollfd_t **descriptors)
{
DBG_BUFF
int rv;
apr_uint32_t i, j;
apr_pollset_private_t *priv = pollset->p;
DBG(4, "entered\n");
if (timeout > 0) {
timeout /= 1000;
}
rv = poll(priv->pollset, pollset->nelts, timeout);
(*num) = rv;
if (rv < 0) {
return apr_get_netos_error();
}
if (rv == 0) {
return APR_TIMEUP;
}
j = 0;
for (i = 0; i < pollset->nelts; i++) {
if (priv->pollset[i].revents != 0) {
priv->result_set[j] = priv->query_set[i];
priv->result_set[j].rtnevents =
get_revent(priv->pollset[i].revents);
j++;
}
}
if (descriptors)
*descriptors = priv->result_set;
DBG(4, "exiting ok\n");
return APR_SUCCESS;
} /* end of posix_poll */
static process_msg(apr_pollset_t *pollset, struct asio_msgbuf_t *msg)
{
DBG_BUFF
asio_elem_t *elem = msg->msg_elem;
switch(elem->state) {
case ASIO_REMOVED:
DBG2(5, "for cancelled elem, recycling memory - elem %08p, fd %d\n",
elem, elem->os_pfd.fd);
APR_RING_INSERT_TAIL(&(pollset->p->free_ring), elem,
asio_elem_t, link);
break;
case ASIO_INIT:
DBG2(4, "adding to ready ring: elem %08p, fd %d\n",
elem, elem->os_pfd.fd);
elem->state = ASIO_COMPLETE;
APR_RING_INSERT_TAIL(&(pollset->p->ready_ring), elem,
asio_elem_t, link);
break;
default:
DBG3(1, "unexpected state: elem %08p, fd %d, state %d\n",
elem, elem->os_pfd.fd, elem->state);
#if DEBUG
assert(0);
#endif
}
}
static apr_status_t asio_pollset_poll(apr_pollset_t *pollset,
apr_interval_time_t timeout,
apr_int32_t *num,
const apr_pollfd_t **descriptors)
{
DBG_BUFF
int i, ret;
asio_elem_t *elem, *next_elem;
struct asio_msgbuf_t msg_buff;
struct timespec tv;
apr_status_t rv = APR_SUCCESS;
apr_pollset_private_t *priv = pollset->p;
DBG(6, "entered\n"); /* chatty - traces every second w/Event */
if ((pollset->flags & APR_POLLSET_THREADSAFE) == 0 ) {
return posix_poll(pollset, timeout, num, descriptors);
}
pollset_lock_rings();
APR_RING_INIT(&(priv->ready_ring), asio_elem_t, link);
while (!APR_RING_EMPTY(&(priv->prior_ready_ring), asio_elem_t, link)) {
elem = APR_RING_FIRST(&(priv->prior_ready_ring));
DBG3(5, "pollset %p elem %p fd %d on prior ready ring\n",
pollset,
elem,
elem->os_pfd.fd);
APR_RING_REMOVE(elem, link);
/*
* since USS does not remember what's in our pollset, we have
* to re-add fds which have not been apr_pollset_remove'd
*
* there may have been too many ready fd's to return in the
* result set last time. re-poll inline for both cases
*/
if (elem->state == ASIO_REMOVED) {
/*
* async i/o is done since it was found on prior_ready
* the state says the caller is done with it too
* so recycle the elem
*/
APR_RING_INSERT_TAIL(&(priv->free_ring), elem,
asio_elem_t, link);
continue; /* do not re-add if it has been _removed */
}
elem->state = ASIO_INIT;
elem->a.aio_cflags = AIO_OK2COMPIMD;
if (0 != (ret = asyncio(&elem->a))) {
if (ret == 1) {
DBG(4, "asyncio() completed inline\n");
/* it's ready now */
APR_RING_INSERT_TAIL(&(priv->ready_ring), elem, asio_elem_t,
link);
}
else {
DBG2(1, "asyncio() failed, ret: %d, errno: %d\n",
ret, errno);
pollset_unlock_rings();
return errno;
}
}
DBG1(4, "asyncio() completed rc %d\n", ret);
}
DBG(6, "after prior ready loop\n"); /* chatty w/timeouts, hence 6 */
/* Gather async poll completions that have occurred since the last call */
while (0 < msgrcv(priv->msg_q, &msg_buff, sizeof(asio_elem_t *), 0,
IPC_NOWAIT)) {
process_msg(pollset, &msg_buff);
}
/* Suspend if nothing is ready yet. */
if (APR_RING_EMPTY(&(priv->ready_ring), asio_elem_t, link)) {
if (timeout >= 0) {
tv.tv_sec = apr_time_sec(timeout);
tv.tv_nsec = apr_time_usec(timeout) * 1000;
} else {
tv.tv_sec = INT_MAX; /* block until something is ready */
}
DBG2(6, "nothing on the ready ring "
"- blocking for %d seconds %d ns\n",
tv.tv_sec, tv.tv_nsec);
pollset_unlock_rings(); /* allow other apr_pollset_* calls while blocked */
if (0 >= (ret = __msgrcv_timed(priv->msg_q, &msg_buff,
sizeof(asio_elem_t *), 0, NULL, &tv))) {
#if DEBUG
if (errno == EAGAIN) {
DBG(6, "__msgrcv_timed timed out\n"); /* timeout path, so 6 */
}
else {
DBG(1, "__msgrcv_timed failed!\n");
}
#endif
return (errno == EAGAIN) ? APR_TIMEUP : errno;
}
pollset_lock_rings();
process_msg(pollset, &msg_buff);
}
APR_RING_INIT(&priv->prior_ready_ring, asio_elem_t, link);
(*num) = 0;
elem = APR_RING_FIRST(&(priv->ready_ring));
for (i = 0;
i < priv->size
&& elem != APR_RING_SENTINEL(&(priv->ready_ring), asio_elem_t, link);
i++) {
DBG2(5, "ready ring: elem %08p, fd %d\n", elem, elem->os_pfd.fd);
priv->result_set[i] = elem->pfd;
priv->result_set[i].rtnevents
= get_revent(elem->os_pfd.revents);
(*num)++;
elem = APR_RING_NEXT(elem, link);
#if DEBUG
if (elem == APR_RING_SENTINEL(&(priv->ready_ring), asio_elem_t, link)) {
DBG(5, "end of ready ring reached\n");
}
#endif
}
if (descriptors) {
*descriptors = priv->result_set;
}
/* if the result size is too small, remember which descriptors
* haven't had results reported yet. we will look
* at these descriptors on the next apr_pollset_poll call
*/
APR_RING_CONCAT(&priv->prior_ready_ring, &(priv->ready_ring), asio_elem_t, link);
DBG1(2, "exiting, rv = %d\n", rv);
pollset_unlock_rings();
return rv;
} /* end of asio_pollset_poll */
static apr_pollset_provider_t impl = {
asio_pollset_create,
asio_pollset_add,
asio_pollset_remove,
asio_pollset_poll,
asio_pollset_cleanup,
"asio"
};
apr_pollset_provider_t *apr_pollset_provider_aio_msgq = &impl;
#endif /* HAVE_AIO_MSGQ */

View File

@ -20,6 +20,62 @@
#include "apr_errno.h"
#include "apr_user.h"
#include "apr_strings.h"
#include "apr_hash.h"
#if APR_USE_SHMEM_MMAP_SHM
/*
* For portable use, a shared memory object should be identified by a name of
* the form /somename; that is, a null-terminated string of up to NAME_MAX
* (i.e., 255) characters consisting of an initial slash, followed by one or
* more characters, none of which are slashes.
*/
#ifndef NAME_MAX
#define NAME_MAX 255
#endif
/* See proc_mutex.c and sem_open for the reason for all this! */
static unsigned int rshash (const char *p) {
/* hash function from Robert Sedgwicks 'Algorithms in C' book */
unsigned int b = 378551;
unsigned int a = 63689;
unsigned int retval = 0;
for( ; *p; p++) {
retval = retval * a + (*p);
a *= b;
}
return retval;
}
static const char *make_shm_open_safe_name(const char *filename,
apr_pool_t *pool)
{
apr_ssize_t flen;
unsigned int h1, h2;
if (filename == NULL) {
return NULL;
}
flen = strlen(filename);
h1 = (apr_hashfunc_default(filename, &flen) & 0xffffffff);
h2 = (rshash(filename) & 0xffffffff);
return apr_psprintf(pool, "/ShM.%xH%x", h1, h2);
}
#endif
#if APR_USE_SHMEM_SHMGET
static key_t our_ftok(const char *filename)
{
/* to help avoid collisions while still using
* an easily recreated proj_id */
apr_ssize_t slen = strlen(filename);
return ftok(filename,
(int)apr_hashfunc_default(filename, &slen));
}
#endif
static apr_status_t shm_cleanup_owner(void *m_)
{
@ -58,7 +114,7 @@ static apr_status_t shm_cleanup_owner(void *m_)
if (munmap(m->base, m->realsize) == -1) {
return errno;
}
if (shm_unlink(m->filename) == -1) {
if (shm_unlink(make_shm_open_safe_name(m->filename, m->pool)) == -1 && errno != ENOENT) {
return errno;
}
return APR_SUCCESS;
@ -220,7 +276,9 @@ APR_DECLARE(apr_status_t) apr_shm_create(apr_shm_t **m,
new_m->pool = pool;
new_m->reqsize = reqsize;
new_m->filename = apr_pstrdup(pool, filename);
#if APR_USE_SHMEM_MMAP_SHM
const char *shm_name = make_shm_open_safe_name(filename, pool);
#endif
#if APR_USE_SHMEM_MMAP_TMP || APR_USE_SHMEM_MMAP_SHM
new_m->realsize = reqsize +
APR_ALIGN_DEFAULT(sizeof(apr_size_t)); /* room for metadata */
@ -245,7 +303,7 @@ APR_DECLARE(apr_status_t) apr_shm_create(apr_shm_t **m,
}
status = apr_file_trunc(file, new_m->realsize);
if (status != APR_SUCCESS) {
if (status != APR_SUCCESS && status != APR_ESPIPE) {
apr_file_close(file); /* ignore errors, we're failing */
apr_file_remove(new_m->filename, new_m->pool);
return status;
@ -261,7 +319,8 @@ APR_DECLARE(apr_status_t) apr_shm_create(apr_shm_t **m,
}
#endif /* APR_USE_SHMEM_MMAP_TMP */
#if APR_USE_SHMEM_MMAP_SHM
tmpfd = shm_open(filename, O_RDWR | O_CREAT | O_EXCL, 0644);
/* FIXME: SysV uses 0600... should we? */
tmpfd = shm_open(shm_name, O_RDWR | O_CREAT | O_EXCL, 0644);
if (tmpfd == -1) {
return errno;
}
@ -274,11 +333,11 @@ APR_DECLARE(apr_status_t) apr_shm_create(apr_shm_t **m,
}
status = apr_file_trunc(file, new_m->realsize);
if (status != APR_SUCCESS) {
shm_unlink(filename); /* we're failing, remove the object */
if (status != APR_SUCCESS && status != APR_ESPIPE) {
shm_unlink(shm_name); /* we're failing, remove the object */
return status;
}
new_m->base = mmap(NULL, reqsize, PROT_READ | PROT_WRITE,
new_m->base = mmap(NULL, new_m->realsize, PROT_READ | PROT_WRITE,
MAP_SHARED, tmpfd, 0);
/* FIXME: check for errors */
@ -312,28 +371,33 @@ APR_DECLARE(apr_status_t) apr_shm_create(apr_shm_t **m,
/* ftok() (on solaris at least) requires that the file actually
* exist before calling ftok(). */
shmkey = ftok(filename, 1);
shmkey = our_ftok(filename);
if (shmkey == (key_t)-1) {
apr_file_close(file);
return errno;
}
if ((new_m->shmid = shmget(shmkey, new_m->realsize,
SHM_R | SHM_W | IPC_CREAT | IPC_EXCL)) < 0) {
apr_file_close(file);
return errno;
}
if ((new_m->base = shmat(new_m->shmid, NULL, 0)) == (void *)-1) {
apr_file_close(file);
return errno;
}
new_m->usable = new_m->base;
if (shmctl(new_m->shmid, IPC_STAT, &shmbuf) == -1) {
apr_file_close(file);
return errno;
}
apr_uid_current(&uid, &gid, pool);
shmbuf.shm_perm.uid = uid;
shmbuf.shm_perm.gid = gid;
if (shmctl(new_m->shmid, IPC_SET, &shmbuf) == -1) {
apr_file_close(file);
return errno;
}
@ -341,6 +405,7 @@ APR_DECLARE(apr_status_t) apr_shm_create(apr_shm_t **m,
status = apr_file_write(file, (const void *)&reqsize,
&nbytes);
if (status != APR_SUCCESS) {
apr_file_close(file);
return status;
}
status = apr_file_close(file);
@ -359,6 +424,15 @@ APR_DECLARE(apr_status_t) apr_shm_create(apr_shm_t **m,
}
}
APR_DECLARE(apr_status_t) apr_shm_create_ex(apr_shm_t **m,
apr_size_t reqsize,
const char *filename,
apr_pool_t *p,
apr_int32_t flags)
{
return apr_shm_create(m, reqsize, filename, p);
}
APR_DECLARE(apr_status_t) apr_shm_remove(const char *filename,
apr_pool_t *pool)
{
@ -372,7 +446,8 @@ APR_DECLARE(apr_status_t) apr_shm_remove(const char *filename,
#if APR_USE_SHMEM_MMAP_TMP
return apr_file_remove(filename, pool);
#elif APR_USE_SHMEM_MMAP_SHM
if (shm_unlink(filename) == -1) {
const char *shm_name = make_shm_open_safe_name(filename, pool);
if (shm_unlink(shm_name) == -1) {
return errno;
}
return APR_SUCCESS;
@ -386,7 +461,7 @@ APR_DECLARE(apr_status_t) apr_shm_remove(const char *filename,
/* ftok() (on solaris at least) requires that the file actually
* exist before calling ftok(). */
shmkey = ftok(filename, 1);
shmkey = our_ftok(filename);
if (shmkey == (key_t)-1) {
goto shm_remove_failed;
}
@ -467,7 +542,23 @@ APR_DECLARE(apr_status_t) apr_shm_attach(apr_shm_t **m,
new_m = apr_palloc(pool, sizeof(apr_shm_t));
new_m->pool = pool;
new_m->filename = apr_pstrdup(pool, filename);
#if APR_USE_SHMEM_MMAP_SHM
const char *shm_name = make_shm_open_safe_name(filename, pool);
/* FIXME: SysV uses 0600... should we? */
tmpfd = shm_open(shm_name, O_RDWR, 0644);
if (tmpfd == -1) {
return errno;
}
status = apr_os_file_put(&file, &tmpfd,
APR_READ | APR_WRITE,
pool);
if (status != APR_SUCCESS) {
return status;
}
#elif APR_USE_SHMEM_MMAP_TMP
status = apr_file_open(&file, filename,
APR_READ | APR_WRITE,
APR_OS_DEFAULT, pool);
@ -478,6 +569,9 @@ APR_DECLARE(apr_status_t) apr_shm_attach(apr_shm_t **m,
if (status != APR_SUCCESS) {
return status;
}
#else
return APR_ENOTIMPL;
#endif
nbytes = sizeof(new_m->realsize);
status = apr_file_read(file, (void *)&(new_m->realsize),
@ -540,7 +634,7 @@ APR_DECLARE(apr_status_t) apr_shm_attach(apr_shm_t **m,
new_m->filename = apr_pstrdup(pool, filename);
new_m->pool = pool;
shmkey = ftok(filename, 1);
shmkey = our_ftok(filename);
if (shmkey == (key_t)-1) {
return errno;
}
@ -564,6 +658,14 @@ APR_DECLARE(apr_status_t) apr_shm_attach(apr_shm_t **m,
}
}
APR_DECLARE(apr_status_t) apr_shm_attach_ex(apr_shm_t **m,
const char *filename,
apr_pool_t *pool,
apr_int32_t flags)
{
return apr_shm_attach(m, filename, pool);
}
APR_DECLARE(apr_status_t) apr_shm_detach(apr_shm_t *m)
{
apr_status_t rv = shm_cleanup_attach(m);

View File

@ -38,6 +38,7 @@
* (3) Instead of returning the pointer to the beginning of
* the destination string, we return a pointer to the
* terminating '\0' to allow us to "check" for truncation
* (4) If src is NULL, null terminate dst (empty string copy)
*
* apr_cpystrn() follows the same call structure as strncpy().
*/
@ -45,19 +46,20 @@
APR_DECLARE(char *) apr_cpystrn(char *dst, const char *src, apr_size_t dst_size)
{
char *d, *end;
char *d = dst, *end;
if (dst_size == 0) {
return (dst);
}
d = dst;
end = dst + dst_size - 1;
if (src) {
end = dst + dst_size - 1;
for (; d < end; ++d, ++src) {
if (!(*d = *src)) {
return (d);
}
for (; d < end; ++d, ++src) {
if (!(*d = *src)) {
return (d);
}
}
}
*d = '\0'; /* always null terminate */

View File

@ -75,8 +75,7 @@ APR_DECLARE(char *) apr_pstrdup(apr_pool_t *a, const char *s)
return NULL;
}
len = strlen(s) + 1;
res = apr_palloc(a, len);
memcpy(res, s, len);
res = apr_pmemdup(a, s, len);
return res;
}

View File

@ -22,7 +22,7 @@
/* The only case where we don't use wait_for_io_or_timeout is on
* pre-BONE BeOS, so this check should be sufficient and simpler */
#if !BEOS_R5
#if !defined(BEOS_R5) && !defined(OS2) && APR_FILES_AS_SOCKETS
#define USE_WAIT_FOR_IO
#endif

View File

@ -162,6 +162,29 @@ APR_DECLARE(void) apr_hash_this(apr_hash_index_t *hi,
if (val) *val = (void *)hi->this->val;
}
APR_DECLARE(const void *) apr_hash_this_key(apr_hash_index_t *hi)
{
const void *key;
apr_hash_this(hi, &key, NULL, NULL);
return key;
}
APR_DECLARE(apr_ssize_t) apr_hash_this_key_len(apr_hash_index_t *hi)
{
apr_ssize_t klen;
apr_hash_this(hi, NULL, &klen, NULL);
return klen;
}
APR_DECLARE(void *) apr_hash_this_val(apr_hash_index_t *hi)
{
void *val;
apr_hash_this(hi, NULL, NULL, &val);
return val;
}
/*
* Expanding a hash table

650
tables/apr_skiplist.c Normal file
View File

@ -0,0 +1,650 @@
/* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
/*
* Modified to use APR and APR pools.
* TODO: Is malloc() better? Will long running skiplists grow too much?
* Keep the skiplist_alloc() and skiplist_free() until we know
* Yeah, if using pools it means some bogus cycles for checks
* (and an useless function call for skiplist_free) which we
* can removed if/when needed.
*/
#include "apr_skiplist.h"
struct apr_skiplist {
apr_skiplist_compare compare;
apr_skiplist_compare comparek;
int height;
int preheight;
int size;
apr_skiplistnode *top;
apr_skiplistnode *bottom;
/* These two are needed for appending */
apr_skiplistnode *topend;
apr_skiplistnode *bottomend;
apr_skiplist *index;
apr_array_header_t *memlist;
apr_pool_t *pool;
};
struct apr_skiplistnode {
void *data;
apr_skiplistnode *next;
apr_skiplistnode *prev;
apr_skiplistnode *down;
apr_skiplistnode *up;
apr_skiplistnode *previndex;
apr_skiplistnode *nextindex;
apr_skiplist *sl;
};
#ifndef MIN
#define MIN(a,b) ((a<b)?(a):(b))
#endif
static int get_b_rand(void)
{
static int ph = 32; /* More bits than we will ever use */
static apr_uint32_t randseq;
if (ph > 31) { /* Num bits in return of rand() */
ph = 0;
randseq = (apr_uint32_t) rand();
}
ph++;
return ((randseq & (1 << (ph - 1))) >> (ph - 1));
}
typedef struct {
size_t size;
apr_array_header_t *list;
} memlist_t;
typedef struct {
void *ptr;
char inuse;
} chunk_t;
APR_DECLARE(void *) apr_skiplist_alloc(apr_skiplist *sl, size_t size)
{
if (sl->pool) {
void *ptr;
int found_size = 0;
int i;
chunk_t *newchunk;
memlist_t *memlist = (memlist_t *)sl->memlist->elts;
for (i = 0; i < sl->memlist->nelts; i++) {
if (memlist->size == size) {
int j;
chunk_t *chunk = (chunk_t *)memlist->list->elts;
found_size = 1;
for (j = 0; j < memlist->list->nelts; j++) {
if (!chunk->inuse) {
chunk->inuse = 1;
return chunk->ptr;
}
chunk++;
}
break; /* no free of this size; punt */
}
memlist++;
}
/* no free chunks */
ptr = apr_pcalloc(sl->pool, size);
if (!ptr) {
return ptr;
}
/*
* is this a new sized chunk? If so, we need to create a new
* array of them. Otherwise, re-use what we already have.
*/
if (!found_size) {
memlist = apr_array_push(sl->memlist);
memlist->size = size;
memlist->list = apr_array_make(sl->pool, 20, sizeof(chunk_t));
}
newchunk = apr_array_push(memlist->list);
newchunk->ptr = ptr;
newchunk->inuse = 1;
return ptr;
}
else {
return calloc(1, size);
}
}
APR_DECLARE(void) apr_skiplist_free(apr_skiplist *sl, void *mem)
{
if (!sl->pool) {
free(mem);
}
else {
int i;
memlist_t *memlist = (memlist_t *)sl->memlist->elts;
for (i = 0; i < sl->memlist->nelts; i++) {
int j;
chunk_t *chunk = (chunk_t *)memlist->list->elts;
for (j = 0; j < memlist->list->nelts; j++) {
if (chunk->ptr == mem) {
chunk->inuse = 0;
return;
}
chunk++;
}
memlist++;
}
}
}
static apr_status_t skiplisti_init(apr_skiplist **s, apr_pool_t *p)
{
apr_skiplist *sl;
if (p) {
sl = apr_pcalloc(p, sizeof(apr_skiplist));
sl->memlist = apr_array_make(p, 20, sizeof(memlist_t));
}
else {
sl = calloc(1, sizeof(apr_skiplist));
}
#if 0
sl->compare = (apr_skiplist_compare) NULL;
sl->comparek = (apr_skiplist_compare) NULL;
sl->height = 0;
sl->preheight = 0;
sl->size = 0;
sl->top = NULL;
sl->bottom = NULL;
sl->index = NULL;
#endif
sl->pool = p;
*s = sl;
return APR_SUCCESS;
}
static int indexing_comp(void *a, void *b)
{
void *ac = (void *) (((apr_skiplist *) a)->compare);
void *bc = (void *) (((apr_skiplist *) b)->compare);
return ((ac < bc) ? -1 : ((ac > bc) ? 1 : 0));
}
static int indexing_compk(void *ac, void *b)
{
void *bc = (void *) (((apr_skiplist *) b)->compare);
return ((ac < bc) ? -1 : ((ac > bc) ? 1 : 0));
}
APR_DECLARE(apr_status_t) apr_skiplist_init(apr_skiplist **s, apr_pool_t *p)
{
apr_skiplist *sl;
skiplisti_init(s, p);
sl = *s;
skiplisti_init(&(sl->index), p);
apr_skiplist_set_compare(sl->index, indexing_comp, indexing_compk);
return APR_SUCCESS;
}
APR_DECLARE(void) apr_skiplist_set_compare(apr_skiplist *sl,
apr_skiplist_compare comp,
apr_skiplist_compare compk)
{
if (sl->compare && sl->comparek) {
apr_skiplist_add_index(sl, comp, compk);
}
else {
sl->compare = comp;
sl->comparek = compk;
}
}
APR_DECLARE(void) apr_skiplist_add_index(apr_skiplist *sl,
apr_skiplist_compare comp,
apr_skiplist_compare compk)
{
apr_skiplistnode *m;
apr_skiplist *ni;
int icount = 0;
apr_skiplist_find(sl->index, (void *)comp, &m);
if (m) {
return; /* Index already there! */
}
skiplisti_init(&ni, sl->pool);
apr_skiplist_set_compare(ni, comp, compk);
/* Build the new index... This can be expensive! */
m = apr_skiplist_insert(sl->index, ni);
while (m->prev) {
m = m->prev;
icount++;
}
for (m = apr_skiplist_getlist(sl); m; apr_skiplist_next(sl, &m)) {
int j = icount - 1;
apr_skiplistnode *nsln;
nsln = apr_skiplist_insert(ni, m->data);
/* skip from main index down list */
while (j > 0) {
m = m->nextindex;
j--;
}
/* insert this node in the indexlist after m */
nsln->nextindex = m->nextindex;
if (m->nextindex) {
m->nextindex->previndex = nsln;
}
nsln->previndex = m;
m->nextindex = nsln;
}
}
APR_DECLARE(apr_skiplistnode *) apr_skiplist_getlist(apr_skiplist *sl)
{
if (!sl->bottom) {
return NULL;
}
return sl->bottom->next;
}
APR_DECLARE(void *) apr_skiplist_find(apr_skiplist *sl, void *data, apr_skiplistnode **iter)
{
void *ret;
apr_skiplistnode *aiter;
if (!sl->compare) {
return 0;
}
if (iter) {
ret = apr_skiplist_find_compare(sl, data, iter, sl->compare);
}
else {
ret = apr_skiplist_find_compare(sl, data, &aiter, sl->compare);
}
return ret;
}
static int skiplisti_find_compare(apr_skiplist *sl, void *data,
apr_skiplistnode **ret,
apr_skiplist_compare comp)
{
apr_skiplistnode *m = NULL;
int count = 0;
m = sl->top;
while (m) {
int compared;
compared = (m->next) ? comp(data, m->next->data) : -1;
if (compared == 0) {
m = m->next;
while (m->down) {
m = m->down;
}
*ret = m;
return count;
}
if ((m->next == NULL) || (compared < 0)) {
m = m->down;
count++;
}
else {
m = m->next;
count++;
}
}
*ret = NULL;
return count;
}
APR_DECLARE(void *) apr_skiplist_find_compare(apr_skiplist *sli, void *data,
apr_skiplistnode **iter,
apr_skiplist_compare comp)
{
apr_skiplistnode *m = NULL;
apr_skiplist *sl;
if (comp == sli->compare || !sli->index) {
sl = sli;
}
else {
apr_skiplist_find(sli->index, (void *)comp, &m);
sl = (apr_skiplist *) m->data;
}
skiplisti_find_compare(sl, data, iter, sl->comparek);
return (iter && *iter) ? ((*iter)->data) : NULL;
}
APR_DECLARE(void *) apr_skiplist_next(apr_skiplist *sl, apr_skiplistnode **iter)
{
if (!*iter) {
return NULL;
}
*iter = (*iter)->next;
return (*iter) ? ((*iter)->data) : NULL;
}
APR_DECLARE(void *) apr_skiplist_previous(apr_skiplist *sl, apr_skiplistnode **iter)
{
if (!*iter) {
return NULL;
}
*iter = (*iter)->prev;
return (*iter) ? ((*iter)->data) : NULL;
}
APR_DECLARE(apr_skiplistnode *) apr_skiplist_insert(apr_skiplist *sl, void *data)
{
if (!sl->compare) {
return 0;
}
return apr_skiplist_insert_compare(sl, data, sl->compare);
}
APR_DECLARE(apr_skiplistnode *) apr_skiplist_insert_compare(apr_skiplist *sl, void *data,
apr_skiplist_compare comp)
{
apr_skiplistnode *m, *p, *tmp, *ret = NULL, **stack;
int nh = 1, ch, stacki;
if (!sl->top) {
sl->height = 1;
sl->topend = sl->bottomend = sl->top = sl->bottom =
(apr_skiplistnode *)apr_skiplist_alloc(sl, sizeof(apr_skiplistnode));
#if 0
sl->top->next = (apr_skiplistnode *)NULL;
sl->top->data = (apr_skiplistnode *)NULL;
sl->top->prev = (apr_skiplistnode *)NULL;
sl->top->up = (apr_skiplistnode *)NULL;
sl->top->down = (apr_skiplistnode *)NULL;
sl->top->nextindex = (apr_skiplistnode *)NULL;
sl->top->previndex = (apr_skiplistnode *)NULL;
#endif
sl->top->sl = sl;
}
if (sl->preheight) {
while (nh < sl->preheight && get_b_rand()) {
nh++;
}
}
else {
while (nh <= sl->height && get_b_rand()) {
nh++;
}
}
/* Now we have the new height at which we wish to insert our new node */
/*
* Let us make sure that our tree is a least that tall (grow if
* necessary)
*/
for (; sl->height < nh; sl->height++) {
sl->top->up =
(apr_skiplistnode *)apr_skiplist_alloc(sl, sizeof(apr_skiplistnode));
sl->top->up->down = sl->top;
sl->top = sl->topend = sl->top->up;
#if 0
sl->top->prev = sl->top->next = sl->top->nextindex =
sl->top->previndex = sl->top->up = NULL;
sl->top->data = NULL;
#endif
sl->top->sl = sl;
}
ch = sl->height;
/* Find the node (or node after which we would insert) */
/* Keep a stack to pop back through for insertion */
/* malloc() is OK since we free the temp stack */
m = sl->top;
stack = (apr_skiplistnode **)malloc(sizeof(apr_skiplistnode *) * (nh));
stacki = 0;
while (m) {
int compared = -1;
if (m->next) {
compared = comp(data, m->next->data);
}
if (compared == 0) {
free(stack); /* OK. was malloc'ed */
return 0;
}
if ((m->next == NULL) || (compared < 0)) {
if (ch <= nh) {
/* push on stack */
stack[stacki++] = m;
}
m = m->down;
ch--;
}
else {
m = m->next;
}
}
/* Pop the stack and insert nodes */
p = NULL;
for (; stacki > 0; stacki--) {
m = stack[stacki - 1];
tmp = (apr_skiplistnode *)apr_skiplist_alloc(sl, sizeof(apr_skiplistnode));
tmp->next = m->next;
if (m->next) {
m->next->prev = tmp;
}
tmp->prev = m;
tmp->up = NULL;
tmp->nextindex = tmp->previndex = NULL;
tmp->down = p;
if (p) {
p->up = tmp;
}
tmp->data = data;
tmp->sl = sl;
m->next = tmp;
/* This sets ret to the bottom-most node we are inserting */
if (!p) {
ret = tmp;
sl->size++; /* this seems to go here got each element to be counted */
}
p = tmp;
}
free(stack); /* OK. was malloc'ed */
if (sl->index != NULL) {
/*
* this is a external insertion, we must insert into each index as
* well
*/
apr_skiplistnode *ni, *li;
li = ret;
for (p = apr_skiplist_getlist(sl->index); p; apr_skiplist_next(sl->index, &p)) {
ni = apr_skiplist_insert((apr_skiplist *) p->data, ret->data);
li->nextindex = ni;
ni->previndex = li;
li = ni;
}
}
else {
/* sl->size++; */
}
sl->size++;
return ret;
}
APR_DECLARE(int) apr_skiplist_remove(apr_skiplist *sl, void *data, apr_skiplist_freefunc myfree)
{
if (!sl->compare) {
return 0;
}
return apr_skiplist_remove_compare(sl, data, myfree, sl->comparek);
}
#if 0
void skiplist_print_struct(apr_skiplist * sl, char *prefix)
{
apr_skiplistnode *p, *q;
fprintf(stderr, "Skiplist Structure (height: %d)\n", sl->height);
p = sl->bottom;
while (p) {
q = p;
fprintf(stderr, prefix);
while (q) {
fprintf(stderr, "%p ", q->data);
q = q->up;
}
fprintf(stderr, "\n");
p = p->next;
}
}
#endif
static int skiplisti_remove(apr_skiplist *sl, apr_skiplistnode *m, apr_skiplist_freefunc myfree)
{
apr_skiplistnode *p;
if (!m) {
return 0;
}
if (m->nextindex) {
skiplisti_remove(m->nextindex->sl, m->nextindex, NULL);
}
while (m->up) {
m = m->up;
}
while (m) {
p = m;
p->prev->next = p->next;/* take me out of the list */
if (p->next) {
p->next->prev = p->prev; /* take me out of the list */
}
m = m->down;
/* This only frees the actual data in the bottom one */
if (!m && myfree && p->data) {
myfree(p->data);
}
apr_skiplist_free(sl, p);
}
sl->size--;
while (sl->top && sl->top->next == NULL) {
/* While the row is empty and we are not on the bottom row */
p = sl->top;
sl->top = sl->top->down;/* Move top down one */
if (sl->top) {
sl->top->up = NULL; /* Make it think its the top */
}
apr_skiplist_free(sl, p);
sl->height--;
}
if (!sl->top) {
sl->bottom = NULL;
}
return sl->height; /* return 1; ?? */
}
APR_DECLARE(int) apr_skiplist_remove_compare(apr_skiplist *sli,
void *data,
apr_skiplist_freefunc myfree, apr_skiplist_compare comp)
{
apr_skiplistnode *m;
apr_skiplist *sl;
if (comp == sli->comparek || !sli->index) {
sl = sli;
}
else {
apr_skiplist_find(sli->index, (void *)comp, &m);
sl = (apr_skiplist *) m->data;
}
skiplisti_find_compare(sl, data, &m, comp);
if (!m) {
return 0;
}
while (m->previndex) {
m = m->previndex;
}
return skiplisti_remove(sl, m, myfree);
}
APR_DECLARE(void) apr_skiplist_remove_all(apr_skiplist *sl, apr_skiplist_freefunc myfree)
{
/*
* This must remove even the place holder nodes (bottom though top)
* because we specify in the API that one can free the Skiplist after
* making this call without memory leaks
*/
apr_skiplistnode *m, *p, *u;
m = sl->bottom;
while (m) {
p = m->next;
if (p && myfree && p->data)
myfree(p->data);
while (m) {
u = m->up;
apr_skiplist_free(sl, p);
m = u;
}
m = p;
}
sl->top = sl->bottom = NULL;
sl->height = 0;
sl->size = 0;
}
APR_DECLARE(void *) apr_skiplist_pop(apr_skiplist *a, apr_skiplist_freefunc myfree)
{
apr_skiplistnode *sln;
void *data = NULL;
sln = apr_skiplist_getlist(a);
if (sln) {
data = sln->data;
skiplisti_remove(a, sln, myfree);
}
return data;
}
APR_DECLARE(void *) apr_skiplist_peek(apr_skiplist *a)
{
apr_skiplistnode *sln;
sln = apr_skiplist_getlist(a);
if (sln) {
return sln->data;
}
return NULL;
}
static void skiplisti_destroy(void *vsl)
{
apr_skiplist_destroy((apr_skiplist *) vsl, NULL);
apr_skiplist_free((apr_skiplist *) vsl, vsl);
}
APR_DECLARE(void) apr_skiplist_destroy(apr_skiplist *sl, apr_skiplist_freefunc myfree)
{
while (apr_skiplist_pop(sl->index, skiplisti_destroy) != NULL)
;
apr_skiplist_remove_all(sl, myfree);
}
APR_DECLARE(apr_skiplist *) apr_skiplist_merge(apr_skiplist *sl1, apr_skiplist *sl2)
{
/* Check integrity! */
apr_skiplist temp;
struct apr_skiplistnode *b2;
if (sl1->bottomend == NULL || sl1->bottomend->prev == NULL) {
apr_skiplist_remove_all(sl1, NULL);
temp = *sl1;
*sl1 = *sl2;
*sl2 = temp;
/* swap them so that sl2 can be freed normally upon return. */
return sl1;
}
if(sl2->bottom == NULL || sl2->bottom->next == NULL) {
apr_skiplist_remove_all(sl2, NULL);
return sl1;
}
/* This is what makes it brute force... Just insert :/ */
b2 = apr_skiplist_getlist(sl2);
while (b2) {
apr_skiplist_insert(sl1, b2->data);
apr_skiplist_next(sl2, &b2);
}
apr_skiplist_remove_all(sl2, NULL);
return sl1;
}

View File

@ -357,6 +357,14 @@ struct apr_table_t {
int index_last[TABLE_HASH_SIZE];
};
/* keep state for apr_table_getm() */
typedef struct
{
apr_pool_t *p;
const char *first;
apr_array_header_t *merged;
} table_getm_t;
/*
* NOTICE: if you tweak this you should look at is_empty_table()
* and table_elts() in alloc.h
@ -736,12 +744,14 @@ APR_DECLARE(void) apr_table_mergen(apr_table_t *t, const char *key,
{
apr_pool_t *pool;
pool = apr_pool_find(key);
if ((pool != key) && (!apr_pool_is_ancestor(pool, t->a.pool))) {
if ((pool != (apr_pool_t *)key)
&& (!apr_pool_is_ancestor(pool, t->a.pool))) {
fprintf(stderr, "apr_table_mergen: key not in ancestor pool of t\n");
abort();
}
pool = apr_pool_find(val);
if ((pool != val) && (!apr_pool_is_ancestor(pool, t->a.pool))) {
if ((pool != (apr_pool_t *)val)
&& (!apr_pool_is_ancestor(pool, t->a.pool))) {
fprintf(stderr, "apr_table_mergen: val not in ancestor pool of t\n");
abort();
}
@ -1236,3 +1246,51 @@ APR_DECLARE(void) apr_table_overlap(apr_table_t *a, const apr_table_t *b,
apr_table_compress(a, flags);
}
static int table_getm_do(void *v, const char *key, const char *val)
{
table_getm_t *state = (table_getm_t *) v;
if (!state->first) {
/**
* The most common case is a single header, and this is covered by
* a fast path that doesn't allocate any memory. On the second and
* subsequent header, an array is created and the array concatenated
* together to form the final value.
*/
state->first = val;
}
else {
const char **elt;
if (!state->merged) {
state->merged = apr_array_make(state->p, 10, sizeof(const char *));
elt = apr_array_push(state->merged);
*elt = state->first;
}
elt = apr_array_push(state->merged);
*elt = val;
}
return 1;
}
APR_DECLARE(const char *) apr_table_getm(apr_pool_t *p, const apr_table_t *t,
const char *key)
{
table_getm_t state;
state.p = p;
state.first = NULL;
state.merged = NULL;
apr_table_do(table_getm_do, &state, t, key, NULL);
if (!state.first) {
return NULL;
}
else if (!state.merged) {
return state.first;
}
else {
return apr_array_pstrcat(p, state.merged, ',');
}
}

115
tools/gen_test_char.c Normal file
View File

@ -0,0 +1,115 @@
/* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#if defined(WIN32) || defined(OS2)
#define NEED_ENHANCED_ESCAPES
#endif
#include <stdio.h>
#include <string.h>
#include <stdio.h>
#include <ctype.h>
/* A bunch of functions in util.c scan strings looking for certain characters.
* To make that more efficient we encode a lookup table.
*/
#define T_ESCAPE_SHELL_CMD (0x01)
#define T_ESCAPE_PATH_SEGMENT (0x02)
#define T_OS_ESCAPE_PATH (0x04)
#define T_ESCAPE_ECHO (0x08)
#define T_ESCAPE_URLENCODED (0x10)
#define T_ESCAPE_XML (0x20)
int main(int argc, char *argv[])
{
unsigned c;
unsigned char flags;
printf("/* this file is automatically generated by gen_test_char, "
"do not edit. \"make include/private/apr_escape_test_char.h\" to regenerate. */\n"
"#define T_ESCAPE_SHELL_CMD (%u)\n"
"#define T_ESCAPE_PATH_SEGMENT (%u)\n"
"#define T_OS_ESCAPE_PATH (%u)\n"
"#define T_ESCAPE_ECHO (%u)\n"
"#define T_ESCAPE_URLENCODED (%u)\n"
"#define T_ESCAPE_XML (%u)\n"
"\n"
"static const unsigned char test_char_table[256] = {",
T_ESCAPE_SHELL_CMD,
T_ESCAPE_PATH_SEGMENT,
T_OS_ESCAPE_PATH,
T_ESCAPE_ECHO,
T_ESCAPE_URLENCODED,
T_ESCAPE_XML);
for (c = 0; c < 256; ++c) {
flags = 0;
if (c % 20 == 0)
printf("\n ");
/* escape_shell_cmd */
#ifdef NEED_ENHANCED_ESCAPES
/* Win32/OS2 have many of the same vulnerable characters
* as Unix sh, plus the carriage return and percent char.
* The proper escaping of these characters varies from unix
* since Win32/OS2 use carets or doubled-double quotes,
* and neither lf nor cr can be escaped. We escape unix
* specific as well, to assure that cross-compiled unix
* applications behave similiarly when invoked on win32/os2.
*
* Rem please keep in-sync with apr's list in win32/filesys.c
*/
if (c && strchr("&;`'\"|*?~<>^()[]{}$\\\n\r%", c)) {
flags |= T_ESCAPE_SHELL_CMD;
}
#else
if (c && strchr("&;`'\"|*?~<>^()[]{}$\\\n", c)) {
flags |= T_ESCAPE_SHELL_CMD;
}
#endif
if (!isalnum(c) && !strchr("$-_.+!*'(),:@&=~", c)) {
flags |= T_ESCAPE_PATH_SEGMENT;
}
if (!isalnum(c) && !strchr("$-_.+!*'(),:@&=/~", c)) {
flags |= T_OS_ESCAPE_PATH;
}
if (!isalnum(c) && !strchr(".-*_ ", c)) {
flags |= T_ESCAPE_URLENCODED;
}
/* For logging, escape all control characters,
* double quotes (because they delimit the request in the log file)
* backslashes (because we use backslash for escaping)
* and 8-bit chars with the high bit set
*/
if (c && (!isprint(c) || c == '"' || c == '\\' || iscntrl(c))) {
flags |= T_ESCAPE_ECHO;
}
if (strchr("<>&\"", c)) {
flags |= T_ESCAPE_XML;
}
printf("%u%c", flags, (c < 255) ? ',' : ' ');
}
printf("\n};\n");
return 0;
}