[Ace-users] [ace-users] ACE_Process_Mutex has different lifetime on Windows and GNU/Linux

Lars Hagström lars at update.uu.se
Mon Nov 19 08:47:15 CST 2007


    ACE VERSION: 5.6.1

    HOST MACHINE and OPERATING SYSTEM:
	Gentoo Linux, kernel 2.6.22 (glibc 2.6.1)
	Windows XP service pack 3

    THE $ACE_ROOT/ace/config.h FILE
	This is the output of the ./configure script, I have done no modifications.
      (apart from removing all non-code from the file to make it terser
for this email) #ifndef ACE_CONFIG_H #define ACE_CONFIG_H #define
ACE_DEFAULT_BASE_ADDR ((char *) 0x80000000) #define
ACE_DEFAULT_MAX_SOCKET_BUFSIZ 65535 #define
ACE_EXPLICIT_TEMPLATE_DESTRUCTOR_TAKES_ARGS 1 #define
ACE_HAS_2_PARAM_ASCTIME_R_AND_CTIME_R 1 #define
ACE_HAS_3_PARAM_READDIR_R 1 #define ACE_HAS_3_PARAM_WCSTOK 1 #define
ACE_HAS_4_4BSD_SENDMSG_RECVMSG 1 #define ACE_HAS_AIO_CALLS 1 #define
ACE_HAS_ALT_CUSERID 1 #define ACE_HAS_AUTOMATIC_INIT_FINI 1 #define
ACE_HAS_BIG_FD_SET 1 #define ACE_HAS_BYTESWAP_H 1 #define
ACE_HAS_CLOCK_GETTIME 1 #define ACE_HAS_CLOCK_SETTIME 1 #define
ACE_HAS_CONSISTENT_SIGNAL_PROTOTYPES 1 #define ACE_HAS_CPLUSPLUS_HEADERS
1 #define ACE_HAS_CPU_SET_T 1 #define ACE_HAS_DIRENT 1 #define
ACE_HAS_EVENT_POLL 1 #define ACE_HAS_EXCEPTIONS 1 #define
ACE_HAS_GETIFADDRS 1 #define ACE_HAS_GETPAGESIZE 1 #define
ACE_HAS_GETRUSAGE 1 #define ACE_HAS_GETRUSAGE_PROTOTYPE 1 #define
ACE_HAS_GNU_CSTRING_H 1 #define ACE_HAS_GPERF 1 #define
ACE_HAS_HANDLE_SET_OPTIMIZED_FOR_SELECT 1 #define ACE_HAS_ICMP_SUPPORT 1
#define ACE_HAS_INT16_T 1 #define ACE_HAS_INT32_T 1 #define
ACE_HAS_INT64_T 1 #define ACE_HAS_INT8_T 1 #define ACE_HAS_IPV6 1
#define ACE_HAS_IP_MULTICAST 1 #define ACE_HAS_ISASTREAM_PROTOTYPE 1
#define ACE_HAS_LSEEK64 1 #define ACE_HAS_MEMCHR 1 #define ACE_HAS_MKDIR
1 #define ACE_HAS_MSG 1 #define ACE_HAS_MUTEX_TIMEOUTS 1 #define
ACE_HAS_NANOSLEEP 1 #define ACE_HAS_NEW_NOTHROW 1 #define
ACE_HAS_NEW_NO_H 1 #define ACE_HAS_NONCONST_SELECT_TIMEVAL 1 #define
ACE_HAS_NONCONST_SWAB 1 #define ACE_HAS_PENTIUM 1 #define ACE_HAS_POLL 1
#define ACE_HAS_POSITION_INDEPENDENT_POINTERS 1 #define
ACE_HAS_POSIX_GETPWNAM_R 1 #define ACE_HAS_POSIX_NONBLOCK 1 #define
ACE_HAS_POSIX_REALTIME_SIGNALS 1 #define ACE_HAS_POSIX_SEM 1 #define
ACE_HAS_POSIX_TIME 1 #define ACE_HAS_PROC_FS 1 #define ACE_HAS_PTHREADS
1 #define ACE_HAS_PTHREADS_STD 1 #define ACE_HAS_PTHREADS_UNIX98_EXT 1
#define ACE_HAS_PTHREAD_GETAFFINITY_NP 1 #define
ACE_HAS_PTHREAD_GETCONCURRENCY 1 #define
ACE_HAS_PTHREAD_MUTEXATTR_SETKIND_NP 1 #define
ACE_HAS_PTHREAD_PROCESS_ENUM 1 #define ACE_HAS_PTHREAD_SETAFFINITY_NP 1
#define ACE_HAS_PTHREAD_SETCONCURRENCY 1 #define
ACE_HAS_PTHREAD_SIGMASK_PROTOTYPE 1 #define ACE_HAS_P_READ_WRITE 1
#define ACE_HAS_RECURSIVE_THR_EXIT_SEMANTICS 1 #define
ACE_HAS_REENTRANT_FUNCTIONS 1 #define ACE_HAS_SCHED_GETAFFINITY 1
#define ACE_HAS_SCHED_SETAFFINITY 1 #define ACE_HAS_SHM_OPEN 1 #define
ACE_HAS_SIGACTION_CONSTP2 1 #define ACE_HAS_SIGINFO_T 1 #define
ACE_HAS_SIGSUSPEND 1 #define ACE_HAS_SIGTIMEDWAIT 1 #define
ACE_HAS_SIGWAIT 1 #define ACE_HAS_SIG_ATOMIC_T 1 #define
ACE_HAS_SIG_C_FUNC 1 #define ACE_HAS_SNPRINTF 1 #define
ACE_HAS_SOCKADDR_MSG_NAME 1 #define ACE_HAS_SOCKLEN_T 1 #define
ACE_HAS_SSIZE_T 1 #define ACE_HAS_STANDARD_CPP_LIBRARY 1 #define
ACE_HAS_STDCPP_STL_INCLUDES 1 #define
ACE_HAS_STD_TEMPLATE_CLASS_MEMBER_SPECIALIZATION 1 #define
ACE_HAS_STD_TEMPLATE_SPECIALIZATION 1 #define ACE_HAS_STRBUF_T 1 #define
ACE_HAS_STREAMS 1 #define ACE_HAS_STRERROR 1 #define ACE_HAS_STRINGS 1
#define ACE_HAS_STRING_CLASS 1 #define ACE_HAS_STRNLEN 1 #define
ACE_HAS_SVR4_DYNAMIC_LINKING 1 #define ACE_HAS_SYSCTL 1 #define
ACE_HAS_SYSV_IPC 1 #define ACE_HAS_SYS_ERRLIST 1 #define
ACE_HAS_SYS_SIGLIST 1 #define ACE_HAS_SYS_SYSCALL_H 1 #define
ACE_HAS_TEMPLATE_TYPEDEFS 1 #define ACE_HAS_TERMIO 1 #define
ACE_HAS_TERMIOS 1 #define ACE_HAS_THREADS 1 #define
ACE_HAS_THREAD_SPECIFIC_STORAGE 1 #define ACE_HAS_TIMEZONE 1 #define
ACE_HAS_TIMEZONE_GETTIMEOFDAY 1 #define ACE_HAS_TYPENAME_KEYWORD 1
#define ACE_HAS_UALARM 1 #define ACE_HAS_UCONTEXT_T 1 #define
ACE_HAS_UINT16_T 1 #define ACE_HAS_UINT32_T 1 #define ACE_HAS_UINT64_T 1
#define ACE_HAS_UINT8_T 1 #define ACE_HAS_VFWPRINTF 1 #define
ACE_HAS_VOIDPTR_MMAP 1 #define ACE_HAS_VOIDPTR_SOCKOPT 1 #define
ACE_HAS_VSWPRINTF 1 #define ACE_HAS_WCHAR 1 #define
ACE_HAS_WORKING_EXPLICIT_TEMPLATE_DESTRUCTOR 1 #define
ACE_HAS_XPG4_MULTIBYTE_CHAR 1 #define ACE_INT64_TYPE signed long long
#define ACE_IOCTL_TYPE_ARG2 int #define ACE_LACKS_GETIPNODEBYADDR 1
#define ACE_LACKS_GETIPNODEBYNAME 1 #define ACE_LACKS_IOSTREAM_FX 1
#define ACE_LACKS_ITOW 1 #define ACE_LACKS_LINEBUFFERED_STREAMBUF 1
#define ACE_LACKS_MSG_ACCRIGHTS 1 #define
ACE_LACKS_NETDB_REENTRANT_FUNCTIONS 1 #define ACE_LACKS_PRAGMA_ONCE 1
#define ACE_LACKS_PRI_T 1 #define ACE_LACKS_PTHREAD_THR_SIGSETMASK 1
#define ACE_LACKS_RWLOCK_T 1 #define ACE_LACKS_SIGINFO_H 1 #define
ACE_LACKS_TIMEDWAIT_PROTOTYPES 1 #define ACE_LACKS_TIMESPEC_T 1 #define
ACE_LACKS_UNBUFFERED_STREAMBUF 1 #define ACE_LACKS_U_LONGLONG_T 1
#define ACE_LACKS_WCSNICMP 1 #define ACE_MT_SAFE 1 #define
ACE_NEW_THROWS_EXCEPTIONS 1 #define ACE_SIZEOF_DOUBLE 8 #define
ACE_SIZEOF_FLOAT 4 #define ACE_SIZEOF_INT 4 #define ACE_SIZEOF_LONG 4
#define ACE_SIZEOF_LONG_DOUBLE 12 #define ACE_SIZEOF_LONG_LONG 8 #define
ACE_SIZEOF_SHORT 2 #define ACE_SIZEOF_VOID_P 4 #define ACE_SIZEOF_WCHAR
4 #define ACE_TEMPLATES_REQUIRE_SOURCE 1 #define ACE_TIMER_SKEW (1000 *
10) #define ACE_UINT64_TYPE unsigned long long #define
ACE_USES_STD_NAMESPACE_FOR_STDCPP_LIB 1 #define HAVE_DIRENT_H 1 #define
HAVE_DLFCN_H 1 #define HAVE_FSTREAM 1 #define HAVE_INTTYPES_H 1 #define
HAVE_IOMANIP 1 #define HAVE_IOS 1 #define HAVE_IOSTREAM 1 #define
HAVE_ISTREAM 1 #define HAVE_MEMORY_H 1 #define HAVE_OSTREAM 1 #define
HAVE_STDINT_H 1 #define HAVE_STDLIB_H 1 #define HAVE_STREAMBUF 1 #define
HAVE_STRFTIME 1 #define HAVE_STRINGS_H 1 #define HAVE_STRING_H 1 #define
HAVE_SYS_STAT_H 1 #define HAVE_SYS_TYPES_H 1 #define HAVE_SYS_WAIT_H 1
#define HAVE_UNISTD_H 1 #define PACKAGE_BUGREPORT "ace-bugs at cs.wustl.edu"
#define PACKAGE_NAME "ACE"
#define PACKAGE_STRING "ACE 5.6.1"
#define PACKAGE_TARNAME "ace"
#define PACKAGE_VERSION "5.6.1"
#define SIZEOF_DOUBLE 8
#define SIZEOF_FLOAT 4
#define SIZEOF_INT 4
#define SIZEOF_LONG 4
#define SIZEOF_LONG_DOUBLE 12
#define SIZEOF_LONG_LONG 8
#define SIZEOF_SHORT 2
#define SIZEOF_SIGNED_CHAR 1
#define SIZEOF_VOID_P 4
#define SIZEOF_WCHAR_T 4
#define STDC_HEADERS 1
#define __ACE_INLINE__ 1
#endif  /* ACE_CONFIG_H */

    AREA/CLASS/EXAMPLE AFFECTED:
	ACE_Process_Semaphore lifetime semantics

    DOES THE PROBLEM AFFECT:
        EXECUTION of applications that use the ACE_Process_Semaphore

    SYNOPSIS:
	The lifetime of ACE_Process_Semaphores is different on
	Windows and Linux.

    DESCRIPTION:
I'm using the ACE_Process_Semaphore for synchronization between some
processes. The code is meant to work without modification on both
windows and linux.
My problem is that, on Linux, once one process that uses the
semaphore exits no process launched after this can open the same
semaphore. This is due to the fact that the POSIX function sem_unlink
gets called in the ACE_Process_Semaphore destructor (implicitly called
through ACE_Semaphore destructor).
On Windows the behaviour is different, since any process that opens
the semaphore after the first one exits still gets the same semaphore.

The behaviour of the Linux semaphores is obviously due to the way that
sem_unlink behaves.

If I remove ACE_HAS_POSIX_SEM from config.h the ACE_Process_Semaphore
will start using SysV semaphores, which work correctly.	My question is
really if this is a conscious decision on part of the ACE team, or if it
is an oversight.
Shouldn't the ACE_Process_Semaphore always use SysV semaphores to ensure
that the lifetime is correct?

I also notice that if I, rather than doing ./configure, just use
ace/config-linux.h for my config.h-file I will not get the
ACE_HAS_POSIX_SEM macro defined, so I get the portable semantics.

    REPEAT BY:
#include <ace/Process_Semaphore.h>
#include <iostream>
#include <ace/OS_NS_unistd.h>

int main(int argc, char * argv[]) {
    ACE_Process_Semaphore * sem;

    sem = new ACE_Process_Semaphore(1,"my_semaphore_name");
    if (sem->tryacquire() == 0) {
        ACE_OS::sleep(1);
        sem->release();
        delete sem;
    }
    else {
        ACE_OS::sleep(2);
        if (sem->tryacquire() == 0) {
            ACE_OS::sleep(1);
            delete sem;
        }
        else {
            sem = new ACE_Process_Semaphore(1,"my_semaphore_name");
            if (sem->tryacquire() == 0) {
                std::wcout << "ACE_Process_Semaphore destructor destroys
lock!" << std::endl;
            }
            else {
                std::wcout << "ACE_Process_Semaphore destructor does not
remove lock!" << std::endl;
            }
            std::cin.get();
            delete sem;
        }
    }
    return 0;
}

Run like this on windows (from command prompt): start synctest.exe &
start synctest.exe & start synctest.exe Run like this on Linux:
./synctest & ./synctest & ./synctest

Output on Windows is: ACE_Process_Semaphore destructor does not remove lock!
Output on Linux is: ACE_Process_Semaphore destructor destroys lock!

    SAMPLE FIX/WORKAROUND:
Dont define ACE_HAS_POSIX_SEM in config.h Not really satisfactory, since
Linux does indeed have posix semaphores.


-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 368 bytes
Desc: OpenPGP digital signature
Url : http://list.isis.vanderbilt.edu/pipermail/ace-users/attachments/20071119/2cd6f850/attachment.bin 


More information about the Ace-users mailing list