diff --git a/configure/CONFIG_COMMON b/configure/CONFIG_COMMON index 56e285017..f9b63e2d9 100644 --- a/configure/CONFIG_COMMON +++ b/configure/CONFIG_COMMON @@ -75,9 +75,12 @@ INSTALL_DBD = $(INSTALL_LOCATION)/dbd INSTALL_DB = $(INSTALL_LOCATION)/db INSTALL_CONFIG = $(INSTALL_LOCATION)/configure -#Directory for OS independant build created files +# Directory for OS independant build created files COMMON_DIR = ../O.Common +# The IOC's path to $(TOP), may be overridden inside the application +IOCS_APPL_TOP = $(INSTALL_LOCATION) + #------------------------------------------------------- # Make echo output - suppress echoing if make's '-s' flag is set NOP = : diff --git a/configure/RULES.Db b/configure/RULES.Db index 3271e3965..896e0b095 100644 --- a/configure/RULES.Db +++ b/configure/RULES.Db @@ -389,8 +389,7 @@ $(foreach file, $(DB_INSTALLS), $(eval $(call DB_INSTALLS_template, $(file)))) ##################################################### register record,device,driver support -IOC_INST_TOP := $(firstword $(IOCS_APPL_TOP) \ - $(shell $(PERL) $(TOOLS)/fullPathName.pl $(INSTALL_LOCATION) ) ) +IOC_INST_TOP := $(shell $(PERL) $(TOOLS)/fullPathName.pl $(IOCS_APPL_TOP) ) %_registerRecordDeviceDriver.cpp: $(COMMON_DIR)/%.dbd @$(RM) $@ diff --git a/configure/RULES.ioc b/configure/RULES.ioc index c661d54d5..cf74343b2 100644 --- a/configure/RULES.ioc +++ b/configure/RULES.ioc @@ -1,13 +1,13 @@ #************************************************************************* -# Copyright (c) 2002 The University of Chicago, as Operator of Argonne +# Copyright (c) 2013 UChicago Argonne LLC, as Operator of Argonne # National Laboratory. # Copyright (c) 2002 The Regents of the University of California, as # Operator of Los Alamos National Laboratory. -# EPICS BASE Versions 3.13.7 -# and higher are distributed subject to a Software License Agreement found -# in file LICENSE that is included with this distribution. +# EPICS BASE is distributed subject to a Software License Agreement found +# in file LICENSE that is included with this distribution. #************************************************************************* #RULES.ioc + include $(CONFIG)/RULES_DIRS build$(DIVIDER)$(ARCH) build: buildInstall @@ -15,23 +15,18 @@ install$(DIVIDER)$(ARCH) install: buildInstall $(ARCH): buildInstall ifeq ($(filter $(ARCH),$(BUILD_ARCHS)),$(ARCH)) -buildInstall$(DIVIDER)$(ARCH) buildInstall: $(TARGETS) + buildInstall$(DIVIDER)$(ARCH) buildInstall: $(TARGETS) -clean$(DIVIDER)$(ARCH) clean: + clean$(DIVIDER)$(ARCH) clean: $(RM) cdCommands envPaths dllPath.bat - -else -buildInstall$(DIVIDER)$(ARCH) buildInstall: -clean$(DIVIDER)$(ARCH) clean: +else + buildInstall$(DIVIDER)$(ARCH) buildInstall: + clean$(DIVIDER)$(ARCH) clean: endif cdCommands envPaths dllPath.bat: $(wildcard $(TOP)/configure/RELEASE*) \ - $(TOP)/configure/CONFIG $(INSTALL_BIN) -ifeq ($(IOCS_APPL_TOP),) - $(PERL) $(TOOLS)/convertRelease.pl -a $(ARCH) $@ -else + $(wildcard $(TOP)/configure/CONFIG_SITE*) $(INSTALL_BIN) $(PERL) $(TOOLS)/convertRelease.pl -a $(ARCH) -t $(IOCS_APPL_TOP) $@ -endif realclean: $(RM) cdCommands envPaths dllPath.bat diff --git a/configure/RULES_TOP b/configure/RULES_TOP index efcf14720..97949eca2 100644 --- a/configure/RULES_TOP +++ b/configure/RULES_TOP @@ -63,11 +63,11 @@ help: @echo " rebuild - Same as clean install" @echo " archclean - Removes O. dirs but not O.Common dir" @echo "\"Partial\" build targets supported by Makefiles:" - @echo " inc. - Installs only header files." - @echo " build. - Builds and installs only." - @echo " install. - Builds and installs only." - @echo " clean. - Cleans binaries in O. dirs only." - @echo " uninstall. - Remove bin & lib directories for only." + @echo " inc$(DIVIDER) - Installs only header files." + @echo " build$(DIVIDER) - Builds and installs only." + @echo " install$(DIVIDER) - Builds and installs only." + @echo " clean$(DIVIDER) - Cleans binaries in O. dirs only." + @echo " uninstall$(DIVIDER) - Remove bin & lib directories for only." @echo "Targets supported by top level Makefile:" @echo " archuninstall - Remove bin & lib directories created by this hostarch." @echo " uninstall - Remove install directories created by this hostarch." diff --git a/src/ca/client/CAref.html b/src/ca/client/CAref.html index 30e8127d4..94f43aed8 100644 --- a/src/ca/client/CAref.html +++ b/src/ca/client/CAref.html @@ -1938,8 +1938,8 @@ Termination Appear to be Ignored

Short lived CA client applications that issue a CA put request and then immediately exit the process (return from main or call exit) may find that there request isn't executed. To guarantee -that the request is sent call ca_flush followed by -ca_context_destroy prior to terminating the process.

+that the request is sent call ca_flush_io() followed by +ca_context_destroy() prior to terminating the process.

ENOBUFS Messages

@@ -2648,7 +2648,7 @@ get called in the correct order.

resources used by the client library such as sockets and allocated memory are automatically released by the system when the process exits and ca_context_destroy() hasn't been called, but on light weight systems such as -vxWorks or RTEMS no cleanup occurs unless the application call +vxWorks or RTEMS no cleanup occurs unless the application calls ca_context_destroy().

Returns

@@ -2661,16 +2661,10 @@ ca_context_destroy().

ca_create_channel()

#include <cadef.h>
-typedef void ( *pCallBack ) (
-         struct connection_handler_args );
-int ca_create_channel
-(
-        const char     *PROCESS_VARIABLE_NAME, 
-        caCh           *USERFUNC, 
-        void           *PUSER,
-        capri          priority,
-        chid           *PCHID
-);
+typedef void ( caCh ) (struct connection_handler_args); +int ca_create_channel (const char *PVNAME, + caCh *USERFUNC, void *PUSER, + capri PRIORITY, chid *PCHID );

Description

@@ -2719,7 +2713,7 @@ time.

Arguments

-
PROCESS_VARIABLE_NAME
+
PVNAME
A nil terminated process variable name string. EPICS process control function block database variable names are of the form "<record name>.<field name>". If the field name and the period separator @@ -2818,17 +2812,15 @@ subscriptions (monitors) registered with the channel.

#include <cadef.h>
 int ca_put ( chtype TYPE, 
         chid CHID, void *PVALUE ); 
-int ca_array_put ( chtype TYPE, 
-        unsigned long COUNT, 
+int ca_array_put ( chtype TYPE, unsigned long COUNT, 
         chid CHID, const void *PVALUE);
-typedef void ( *pCallBack ) (struct event_handler_args );
+typedef void ( caEventCallBackFunc ) (struct event_handler_args);
 int ca_put_callback ( chtype TYPE, 
         chid CHID, const void *PVALUE, 
-        pCallBack PFUNC, void *USERARG ); 
-int ca_array_put_callback ( chtype TYPE, 
-        unsigned long COUNT, 
+        caEventCallBackFunc PFUNC, void *USERARG ); 
+int ca_array_put_callback ( chtype TYPE, unsigned long COUNT, 
         chid CHID, const void *PVALUE, 
-        pCallBack PFUNC, void *USERARG );
+ caEventCallBackFunc PFUNC, void *USERARG );

Description

@@ -2948,12 +2940,13 @@ int ca_get ( chtype TYPE, chid CHID, void *PVALUE ); int ca_array_get ( chtype TYPE, unsigned long COUNT, chid CHID, void *PVALUE ); -typedef void ( *pCallBack ) (struct event_handler_args ); +typedef void ( caEventCallBackFunc ) (struct event_handler_args); int ca_get_callback ( chtype TYPE, - chid CHID, pCallBack USERFUNC, void *USERARG); + chid CHID, + caEventCallBackFunc USERFUNC, void *USERARG); int ca_array_get_callback ( chtype TYPE, unsigned long COUNT, chid CHID, - pCallBack USERFUNC, void *USERARG ); + caEventCallBackFunc USERFUNC, void *USERARG);

Description

@@ -3051,11 +3044,10 @@ when a CA get request is initiated.

ca_create_subscription()

#include <cadef.h>
-typedef void ( *pCallBack ) (
-        struct event_handler_args );
-int ca_create_subscription ( chtype TYPE, 
-        unsigned long COUNT, chid CHID, 
-        unsigned long MASK, pCallBack USERFUNC, void *USERARG, 
+typedef void ( caEventCallBackFunc ) (struct event_handler_args);
+int ca_create_subscription ( chtype TYPE, unsigned long COUNT,
+        chid CHID, unsigned long MASK,
+        caEventCallBackFunc USERFUNC, void *USERARG, 
         evid *PEVID );

Description

@@ -3540,7 +3532,7 @@ get the lowest latency response to the arrival of CA messages.

ca_replace_printf_handler ()

#include <cadef.h>
-typedef int caPrintfFunc ( const char *pFromat, va_list args );
+typedef int caPrintfFunc ( const char *pFormat, va_list args );
 int ca_replace_printf_handler ( caPrintfFunc *PFUNC );

Description

@@ -3571,8 +3563,9 @@ SEVCHK ( status, "failed to install my printf handler" );

ca_replace_access_rights_event()

#include <cadef.h>
-typedef void ( *pCallBack )( struct access_rights_handler_args );
-int ca_replace_access_rights_event ( chid CHAN, pCallBack PFUNC );
+typedef void ( caEventCallBackFunc )(struct access_rights_handler_args); +int ca_replace_access_rights_event ( chid CHAN, + caEventCallBackFunc PFUNC );

Description

@@ -4029,7 +4022,7 @@ SEVCHK ( status, Sync group delete failed );

ca_sg_block()

#include <cadef.h>
-int ca_sg_block ( CA_SYNC_GID GID, double timeout );
+int ca_sg_block ( CA_SYNC_GID GID, double TIMEOUT );

Description

@@ -4050,13 +4043,16 @@ access background activity while it is waiting.

Arguments

-
GID
+
GID
Identifier of the synchronous group.
+
TIMEOUT
+
The duration to block in this routine in seconds. A timeout of zero + seconds blocks forever.

Examples

CA_SYNC_GID gid;
-status = ca_sg_block(gid);
+status = ca_sg_block(gid, 0.0);
 SEVCHK(status, Sync group block failed);

Returns

@@ -4267,8 +4263,8 @@ reissued.

ca_client_status()

int ca_client_status ( unsigned level );
-int ca_context_status ( struct ca_client_context *, 
-       unsigned level );
+int ca_context_status ( struct ca_client_context *CONTEXT, + unsigned LEVEL );

Description

@@ -4279,7 +4275,7 @@ ca_client_status() prints information about the calling threads CA context.

Arguments

CONTEXT
-
A pointer to the CA context to join with.
+
A pointer to the CA context to examine.
LEVEL
The interest level. Increasing level produces increasing detail.
diff --git a/src/ca/client/ca_client_context.cpp b/src/ca/client/ca_client_context.cpp index 75ff80bb0..a390b6bcb 100644 --- a/src/ca/client/ca_client_context.cpp +++ b/src/ca/client/ca_client_context.cpp @@ -753,16 +753,16 @@ epicsShareFunc int epicsShareAPI ca_clear_subscription ( evid pMon ) ca_client_context & cac = chan.getClientCtx (); // !!!! the order in which we take the mutex here prevents deadlocks { - epicsGuard < epicsMutex > guard ( cac.mutex ); - try { - // if this stalls out on a live circuit then an exception - // can be forthcoming which we must ignore as the clear - // request must always be successful - chan.eliminateExcessiveSendBacklog ( guard ); - } - catch ( cacChannel::notConnected & ) { - // intentionally ignored - } + epicsGuard < epicsMutex > guard ( cac.mutex ); + try { + // if this stalls out on a live circuit then an exception + // can be forthcoming which we must ignore as the clear + // request must always be successful + chan.eliminateExcessiveSendBacklog ( guard ); + } + catch ( cacChannel::notConnected & ) { + // intentionally ignored + } } if ( cac.pCallbackGuard.get() && cac.createdByThread == epicsThreadGetIdSelf () ) { diff --git a/src/ca/client/oldAccess.h b/src/ca/client/oldAccess.h index ee5020513..19074e27f 100644 --- a/src/ca/client/oldAccess.h +++ b/src/ca/client/oldAccess.h @@ -348,7 +348,7 @@ public: template < class T > void whenThereIsAnExceptionDestroySyncGroupIO ( epicsGuard < epicsMutex > &, T & ); - + // legacy C API friend int epicsShareAPI ca_create_channel ( const char * name_str, caCh * conn_func, void * puser, diff --git a/src/ca/client/syncgrp.cpp b/src/ca/client/syncgrp.cpp index f11ce3551..9727ae8df 100644 --- a/src/ca/client/syncgrp.cpp +++ b/src/ca/client/syncgrp.cpp @@ -134,15 +134,15 @@ extern "C" int epicsShareAPI ca_sg_block ( if ( status == ECA_NORMAL ) { CASG * pcasg; { - epicsGuard < epicsMutex > guard ( pcac->mutex ); - pcasg = pcac->lookupCASG ( guard, gid ); - if ( pcasg ) { - status = pcasg->block ( - pcac->pCallbackGuard.get (), guard, timeout ); - } - else { - status = ECA_BADSYNCGRP; - } + epicsGuard < epicsMutex > guard ( pcac->mutex ); + pcasg = pcac->lookupCASG ( guard, gid ); + if ( pcasg ) { + status = pcasg->block ( + pcac->pCallbackGuard.get (), guard, timeout ); + } + else { + status = ECA_BADSYNCGRP; + } } if ( pcasg ) { sync_group_reset ( *pcac, *pcasg ); diff --git a/src/ioc/db/dbCAC.h b/src/ioc/db/dbCAC.h index 1a4086b4e..ad3d0287b 100644 --- a/src/ioc/db/dbCAC.h +++ b/src/ioc/db/dbCAC.h @@ -183,7 +183,7 @@ public: void show ( unsigned level ) const; void showAllIO ( const dbChannelIO & chan, unsigned level ) const; void destroyAllIO ( CallbackGuard & cbGuard, - epicsGuard < epicsMutex > &, dbChannelIO & chan ); + epicsGuard < epicsMutex > &, dbChannelIO & chan ); void ioCancel ( CallbackGuard &, epicsGuard < epicsMutex > &, dbChannelIO & chan, const cacChannel::ioid &id ); void ioShow ( epicsGuard < epicsMutex > &, diff --git a/src/ioc/db/dbChannelIO.h b/src/ioc/db/dbChannelIO.h index 372f809a3..e1b63d760 100644 --- a/src/ioc/db/dbChannelIO.h +++ b/src/ioc/db/dbChannelIO.h @@ -111,8 +111,8 @@ private: epicsGuard < epicsMutex > & ) const; unsigned long nativeElementCount ( epicsGuard < epicsMutex > & ) const; - dbChannelIO ( const dbChannelIO & ); - dbChannelIO & operator = ( const dbChannelIO & ); + dbChannelIO ( const dbChannelIO & ); + dbChannelIO & operator = ( const dbChannelIO & ); void operator delete ( void * ); }; diff --git a/src/ioc/db/dbSubscriptionIO.cpp b/src/ioc/db/dbSubscriptionIO.cpp index 02b2b0105..70864b2dd 100644 --- a/src/ioc/db/dbSubscriptionIO.cpp +++ b/src/ioc/db/dbSubscriptionIO.cpp @@ -74,7 +74,7 @@ void dbSubscriptionIO::destructor ( CallbackGuard & cbGuard, } void dbSubscriptionIO::unsubscribe ( CallbackGuard & cbGuard, - epicsGuard < epicsMutex > & guard ) + epicsGuard < epicsMutex > & guard ) { guard.assertIdenticalMutex ( this->mutex ); if ( this->es ) { diff --git a/src/ioc/dbStatic/dbStaticLib.c b/src/ioc/dbStatic/dbStaticLib.c index ed983f9f0..b76333f7c 100644 --- a/src/ioc/dbStatic/dbStaticLib.c +++ b/src/ioc/dbStatic/dbStaticLib.c @@ -755,6 +755,11 @@ long dbWriteRecordFP( dctonly = ((level>1) ? FALSE : TRUE); dbInitEntry(pdbbase,pdbentry); + if (precordTypename) { + if (*precordTypename == 0 || *precordTypename == '*') + precordTypename = 0; + } + if(!precordTypename) { status = dbFirstRecordType(pdbentry); if(status) { @@ -851,6 +856,10 @@ long dbWriteMenuFP(DBBASE *pdbbase,FILE *fp,const char *menuName) fprintf(stderr,"pdbbase not specified\n"); return(-1); } + if (menuName) { + if (*menuName == 0 || *menuName == '*') + menuName = 0; + } pdbMenu = (dbMenu *)ellFirst(&pdbbase->menuList); while(pdbMenu) { if(menuName) { @@ -896,6 +905,11 @@ long dbWriteRecordTypeFP( fprintf(stderr,"pdbbase not specified\n"); return(-1); } + if (recordTypeName) { + if (*recordTypeName == 0 || *recordTypeName == '*') + recordTypeName = 0; + } + for(pdbRecordType = (dbRecordType *)ellFirst(&pdbbase->recordTypeList); pdbRecordType; pdbRecordType = (dbRecordType *)ellNext(&pdbRecordType->node)) { if(recordTypeName) { @@ -3172,8 +3186,9 @@ void dbDumpDevice(DBBASE *pdbbase,const char *recordTypeName) devSup *pdevSup; int gotMatch; - if(recordTypeName) { - if(recordTypeName[0]==0 || recordTypeName[0] == '*') recordTypeName = 0; + if (recordTypeName) { + if (*recordTypeName == 0 || *recordTypeName == '*') + recordTypeName = 0; } if(!pdbbase) { fprintf(stderr,"pdbbase not specified\n"); diff --git a/src/ioc/dbStatic/dbYacc.y b/src/ioc/dbStatic/dbYacc.y index b61ab26ea..b8cc9b4cf 100644 --- a/src/ioc/dbStatic/dbYacc.y +++ b/src/ioc/dbStatic/dbYacc.y @@ -31,7 +31,13 @@ static int yyAbort = 0; %% -database: database database_item | database_item; +database: /* empty */ + | database_item_list + ; + +database_item_list: database_item_list database_item + | database_item + ; database_item: include | path diff --git a/src/libCom/misc/epicsConvert.h b/src/libCom/misc/epicsConvert.h index 9674db0ef..1c38bc30a 100644 --- a/src/libCom/misc/epicsConvert.h +++ b/src/libCom/misc/epicsConvert.h @@ -3,12 +3,14 @@ * National Laboratory. * Copyright (c) 2002 The Regents of the University of California, as * Operator of Los Alamos National Laboratory. -* EPICS BASE Versions 3.13.7 -* and higher are distributed subject to a Software License Agreement found -* in file LICENSE that is included with this distribution. +* EPICS BASE is distributed subject to a Software License Agreement found +* in file LICENSE that is included with this distribution. \*************************************************************************/ /*epicsConvert.h*/ +#ifndef INC_epicsConvert_H +#define INC_epicsConvert_H + #include #ifdef __cplusplus @@ -21,3 +23,4 @@ epicsShareFunc float epicsConvertDoubleToFloat(double value); } #endif +#endif /* INC_epicsConvert_H */ diff --git a/src/libCom/misc/epicsStdlib.h b/src/libCom/misc/epicsStdlib.h index fbdfec3f0..03dace5b4 100644 --- a/src/libCom/misc/epicsStdlib.h +++ b/src/libCom/misc/epicsStdlib.h @@ -4,11 +4,14 @@ * Copyright (c) 2002 The Regents of the University of California, as * Operator of Los Alamos National Laboratory. * EPICS BASE is distributed subject to a Software License Agreement found -* in file LICENSE that is included with this distribution. +* in file LICENSE that is included with this distribution. \*************************************************************************/ /* epicsStdlib.h */ /* Author: Eric Norum */ +#ifndef INC_epicsStdlib_H +#define INC_epicsStdlib_H + #include #include @@ -67,3 +70,4 @@ epicsShareFunc int } #endif +#endif /* INC_epicsStdlib_H */ diff --git a/src/libCom/osi/devLibVME.h b/src/libCom/osi/devLibVME.h index 6d7476098..8e526a139 100644 --- a/src/libCom/osi/devLibVME.h +++ b/src/libCom/osi/devLibVME.h @@ -300,11 +300,6 @@ epicsShareFunc long locationProbe (epicsAddressType addrType, char *pLocation); #endif /* NO_DEVLIB_OLD_INTERFACE */ -/* - * Some vxWorks convenience routines - */ -void bcopyLongs(char *source, char *destination, int nlongs); - #ifdef __cplusplus } #endif diff --git a/src/libCom/osi/epicsSignal.h b/src/libCom/osi/epicsSignal.h index 2fd0e5839..79adf71d1 100644 --- a/src/libCom/osi/epicsSignal.h +++ b/src/libCom/osi/epicsSignal.h @@ -3,11 +3,13 @@ * National Laboratory. * Copyright (c) 2002 The Regents of the University of California, as * Operator of Los Alamos National Laboratory. - * EPICS BASE Versions 3.13.7 - * and higher are distributed subject to a Software License Agreement found - * in file LICENSE that is included with this distribution. + * EPICS BASE is distributed subject to a Software License Agreement found + * in file LICENSE that is included with this distribution. \*************************************************************************/ +#ifndef INC_epicsSignal_H +#define INC_epicsSignal_H + #ifdef __cplusplus extern "C" { #endif @@ -44,3 +46,4 @@ epicsShareFunc void epicsShareAPI epicsSignalRaiseSigAlarm ( struct epicsThreadO } #endif +#endif /* INC_epicsSignal_H */ diff --git a/src/libCom/osi/os/RTEMS/osdVME.h b/src/libCom/osi/os/RTEMS/osdVME.h index 470f64866..5e8c5f984 100644 --- a/src/libCom/osi/os/RTEMS/osdVME.h +++ b/src/libCom/osi/os/RTEMS/osdVME.h @@ -19,3 +19,5 @@ #endif #endif #endif + +void bcopyLongs(char *source, char *destination, int nlongs); diff --git a/src/libCom/osi/os/WIN32/osdFindSymbol.c b/src/libCom/osi/os/WIN32/osdFindSymbol.c new file mode 100644 index 000000000..ed2b79c95 --- /dev/null +++ b/src/libCom/osi/os/WIN32/osdFindSymbol.c @@ -0,0 +1,46 @@ +/*************************************************************************\ +* Copyright (c) 2013 Dirk Zimoch, PSI +* EPICS BASE is distributed subject to a Software License Agreement found +* in file LICENSE that is included with this distribution. +\*************************************************************************/ +/* osi/os/WIN32/epicsFindSymbol.c */ + + +#include + +#define epicsExportSharedSymbols +#include "epicsFindSymbol.h" + +static int epicsLoadErrorCode = 0; + +epicsShareFunc void * epicsLoadLibrary(const char *name) +{ + HMODULE lib; + + epicsLoadErrorCode = 0; + lib = LoadLibrary(name); + if (lib == NULL) + { + epicsLoadErrorCode = GetLastError(); + } + return lib; +} + +epicsShareFunc const char *epicsLoadError(void) +{ + static char buffer[100]; + + FormatMessage( + FORMAT_MESSAGE_FROM_SYSTEM, + NULL, + epicsLoadErrorCode, + 0, + buffer, + sizeof(buffer)-1, NULL ); + return buffer; +} + +epicsShareFunc void * epicsShareAPI epicsFindSymbol(const char *name) +{ + return GetProcAddress(0, name); +} diff --git a/src/libCom/osi/os/WIN32/osdThread.c b/src/libCom/osi/os/WIN32/osdThread.c index 6588b2e3f..6246c7736 100644 --- a/src/libCom/osi/os/WIN32/osdThread.c +++ b/src/libCom/osi/os/WIN32/osdThread.c @@ -3,9 +3,8 @@ * National Laboratory. * Copyright (c) 2002 The Regents of the University of California, as * Operator of Los Alamos National Laboratory. -* EPICS BASE Versions 3.13.7 -* and higher are distributed subject to a Software License Agreement found -* in file LICENSE that is included with this distribution. +* EPICS BASE is distributed subject to a Software License Agreement found +* in file LICENSE that is included with this distribution. \*************************************************************************/ /* @@ -248,10 +247,7 @@ static void epicsParmCleanupWIN32 ( win32ThreadParam * pParm ) ellDelete ( & pGbl->threadList, & pParm->node ); LeaveCriticalSection ( & pGbl->mutex ); - /* close the handle if its an implicit thread id */ - if ( ! pParm->funptr ) { - CloseHandle ( pParm->handle ); - } + CloseHandle ( pParm->handle ); free ( pParm ); TlsSetValue ( pGbl->tlsIndexThreadLibraryEPICS, 0 ); } diff --git a/src/libCom/osi/os/vxWorks/atReboot.cpp b/src/libCom/osi/os/vxWorks/atReboot.cpp index cb4bff5cc..9a35286ef 100644 --- a/src/libCom/osi/os/vxWorks/atReboot.cpp +++ b/src/libCom/osi/os/vxWorks/atReboot.cpp @@ -1,10 +1,9 @@ /*************************************************************************\ -* Copyright (c) 2002 The University of Chicago, as Operator of Argonne +* Copyright (c) 2013 UChicago Argonne LLC, as Operator of Argonne * National Laboratory. * Copyright (c) 2002 The Regents of the University of California, as * Operator of Los Alamos National Laboratory. -* EPICS BASE Versions 3.13.7 -* and higher are distributed subject to a Software License Agreement found +* EPICS BASE is distributed subject to a Software License Agreement found * in file LICENSE that is included with this distribution. \*************************************************************************/ /* atReboot.cpp */ @@ -16,34 +15,28 @@ #include "epicsDynLink.h" #include "epicsExit.h" -/* osdThread references atRebootExtern just to make this module load*/ -int atRebootExtern; +extern "C" { typedef int (*sysAtReboot_t)(void(func)(void)); -class atRebootRegister { -public: - atRebootRegister(); -}; - -atRebootRegister::atRebootRegister() +void atRebootRegister(void) { STATUS status; sysAtReboot_t sysAtReboot; SYM_TYPE type; status = symFindByNameEPICS(sysSymTbl, "_sysAtReboot", - (char **)&sysAtReboot, &type); + (char **)&sysAtReboot, &type); if (status == OK) { status = sysAtReboot(epicsExitCallAtExits); if (status != OK) { printf("atReboot: sysAtReboot returned error %d\n", status); } } else { - printf("BSP routine sysAtReboot() not found, epicsExit() will not be\n" - "called by reboot. For reduced functionality, call\n" - " rebootHookAdd(epicsExitCallAtExits)\n"); + printf("BSP routine sysAtReboot() not found, epicsExit() will not be\n" + "called by reboot. For reduced functionality, call\n" + " rebootHookAdd(epicsExitCallAtExits)\n"); } } -static atRebootRegister atRebootRegisterObj; +} diff --git a/src/libCom/osi/os/vxWorks/osdThread.c b/src/libCom/osi/os/vxWorks/osdThread.c index c38918d8d..b2998663f 100644 --- a/src/libCom/osi/os/vxWorks/osdThread.c +++ b/src/libCom/osi/os/vxWorks/osdThread.c @@ -52,12 +52,8 @@ static int *taskIdList = 0; int taskIdListSize = 0; static SEM_ID epicsThreadListMutex = 0; -/*The following forces atReboot to be loaded*/ -extern int atRebootExtern; -static struct pext { - int *pExtern; - struct pext *pext; -} pext = {&atRebootExtern, &pext}; +/* This routine is found in atReboot.cpp */ +extern void atRebootRegister(void); /* definitions for implementation of epicsThreadPrivate */ static void **papTSD = 0; @@ -93,6 +89,7 @@ static int getOssPriorityValue(unsigned int osiPriority) } } +#define THREAD_SEM_FLAGS (SEM_DELETE_SAFE|SEM_INVERSION_SAFE|SEM_Q_PRIORITY) static void epicsThreadInit(void) { static int lock = 0; @@ -104,13 +101,14 @@ static void epicsThreadInit(void) taskDelay(1); if (!done) { - epicsThreadOnceMutex = semMCreate(SEM_DELETE_SAFE|SEM_INVERSION_SAFE|SEM_Q_PRIORITY); - assert(epicsThreadOnceMutex); - epicsThreadListMutex = semMCreate(SEM_DELETE_SAFE|SEM_INVERSION_SAFE|SEM_Q_PRIORITY); - assert(epicsThreadListMutex); + epicsThreadOnceMutex = semMCreate(THREAD_SEM_FLAGS); + assert(epicsThreadOnceMutex); + epicsThreadListMutex = semMCreate(THREAD_SEM_FLAGS); + assert(epicsThreadListMutex); taskIdList = calloc(ID_LIST_CHUNK, sizeof(int)); assert(taskIdList); taskIdListSize = ID_LIST_CHUNK; + atRebootRegister(); done = 1; } lock = 0; diff --git a/src/libCom/osi/os/vxWorks/osdTime.cpp b/src/libCom/osi/os/vxWorks/osdTime.cpp index a0e2422e9..eed1ad078 100644 --- a/src/libCom/osi/os/vxWorks/osdTime.cpp +++ b/src/libCom/osi/os/vxWorks/osdTime.cpp @@ -67,14 +67,18 @@ void osdNTPReport(void) } -// vxWorks localtime_r interface does not match POSIX standards +// vxWorks localtime_r returns different things in different versions. +// It can't fail though, so we just ignore the return value. int epicsTime_localtime(const time_t *clock, struct tm *result) { - return localtime_r(clock, result) == OK ? epicsTimeOK : epicsTimeERROR; + localtime_r(clock, result); + return epicsTimeOK; } -// vxWorks gmtime_r interface does not match POSIX standards +// vxWorks gmtime_r returns different things in different versions. +// It can't fail though, so we just ignore the return value. int epicsTime_gmtime ( const time_t *pAnsiTime, struct tm *pTM ) { - return gmtime_r(pAnsiTime, pTM) == OK ? epicsTimeOK : epicsTimeERROR; + gmtime_r(pAnsiTime, pTM); + return epicsTimeOK; } diff --git a/src/libCom/osi/osiPoolStatus.h b/src/libCom/osi/osiPoolStatus.h index c80612a37..20f1b7339 100644 --- a/src/libCom/osi/osiPoolStatus.h +++ b/src/libCom/osi/osiPoolStatus.h @@ -3,11 +3,13 @@ * National Laboratory. * Copyright (c) 2002 The Regents of the University of California, as * Operator of Los Alamos National Laboratory. -* EPICS BASE Versions 3.13.7 -* and higher are distributed subject to a Software License Agreement found -* in file LICENSE that is included with this distribution. +* EPICS BASE is distributed subject to a Software License Agreement found +* in file LICENSE that is included with this distribution. \*************************************************************************/ +#ifndef INC_osiPoolStatus_H +#define INC_osiPoolStatus_H + /* * $Revision-Id$ * @@ -39,3 +41,4 @@ epicsShareFunc int epicsShareAPI osiSufficentSpaceInPool ( size_t contiguousBloc #include "osdPoolStatus.h" +#endif /* INC_osiPoolStatus_H */ diff --git a/src/libCom/osi/osiProcess.h b/src/libCom/osi/osiProcess.h index bd3cb5b31..b954c4019 100644 --- a/src/libCom/osi/osiProcess.h +++ b/src/libCom/osi/osiProcess.h @@ -3,11 +3,13 @@ * National Laboratory. * Copyright (c) 2002 The Regents of the University of California, as * Operator of Los Alamos National Laboratory. -* EPICS BASE Versions 3.13.7 -* and higher are distributed subject to a Software License Agreement found -* in file LICENSE that is included with this distribution. +* EPICS BASE is distributed subject to a Software License Agreement found +* in file LICENSE that is included with this distribution. \*************************************************************************/ +#ifndef INC_osiProcess_H +#define INC_osiProcess_H + /* * $Revision-Id$ * @@ -44,3 +46,4 @@ epicsShareFunc osiSpawnDetachedProcessReturn epicsShareAPI osiSpawnDetachedProce } #endif +#endif /* INC_osiProcess_H */ diff --git a/src/libCom/test/epicsTimeTest.cpp b/src/libCom/test/epicsTimeTest.cpp index c89d13a5c..c108eca7f 100644 --- a/src/libCom/test/epicsTimeTest.cpp +++ b/src/libCom/test/epicsTimeTest.cpp @@ -48,17 +48,23 @@ MAIN(epicsTimeTest) const int wasteTime = 100000; const int nTimes = 10; - testPlan(16 + nTimes * 18); + testPlan(12 + nTimes * 18); - { + try { const epicsTimeStamp epochTS = {0, 0}; epicsTime epochET = epochTS; struct gm_tm_nano_sec epicsEpoch = epochET; - testOk1(epicsEpoch.ansi_tm.tm_sec == 0); - testOk1(epicsEpoch.ansi_tm.tm_min == 0); - testOk1(epicsEpoch.ansi_tm.tm_hour == 0); - testOk1(epicsEpoch.ansi_tm.tm_yday == 0); - testOk1(epicsEpoch.ansi_tm.tm_year == 90); + + testOk(epicsEpoch.ansi_tm.tm_sec == 0 && + epicsEpoch.ansi_tm.tm_min == 0 && + epicsEpoch.ansi_tm.tm_hour == 0 && + epicsEpoch.ansi_tm.tm_yday == 0 && + epicsEpoch.ansi_tm.tm_year == 90, + "epicsTime_gmtime() for EPICS epoch"); + } + catch ( ... ) { + testFail("epicsTime_gmtime() failed"); + testAbort("Can't continue, check your OS!"); } { // badNanosecTest diff --git a/src/tools/munch.pl b/src/tools/munch.pl index 2ed6567fb..f6c0d6e08 100644 --- a/src/tools/munch.pl +++ b/src/tools/munch.pl @@ -1,6 +1,6 @@ #!/usr/bin/env perl #************************************************************************* -# Copyright (c) 2010 UChicago Argonne LLC, as Operator of Argonne +# Copyright (c) 2013 UChicago Argonne LLC, as Operator of Argonne # National Laboratory. # Copyright (c) 2002 The Regents of the University of California, as # Operator of Los Alamos National Laboratory. @@ -24,6 +24,9 @@ $Getopt::Std::OUTPUT_HELP_VERSION = 1; # Is exception handler frame info required? my $need_eh_frame = 0; +# Is module destructor needed? +my $need_mod_dtor = 0; + # Constructor and destructor names: # Array contains names from input file. # Hash is used to skip duplicate names. @@ -34,6 +37,7 @@ while (<>) { chomp; $need_eh_frame++ if m/__? gxx_personality_v [0-9]/x; + $need_mod_dtor++ if m/__? cxa_atexit $/x; next if m/__? GLOBAL_. (F | I._GLOBAL_.D) .+/x; if (m/__? GLOBAL_ . D .+/x) { my ($addr, $type, $name) = split ' ', $_, 3; @@ -55,8 +59,11 @@ push my @out, '', '/* Declarations */', (map {cDecl($_)} @ctors, @dtors), + '', + 'char __dso_handle = 0;', ''; +moduleDestructor() if $need_mod_dtor; exceptionHandlerFrame() if $need_eh_frame; push @out, @@ -81,6 +88,19 @@ if ($opt_o) { print join "\n", @out; } +# Outputs the C code for registering a module destructor +sub moduleDestructor { + my $mod_dtor = 'mod_dtor'; + push @dtors, $mod_dtor; + push @out, + '/* Module destructor */', + "static void $mod_dtor(void) {", + ' extern void __cxa_finalize(void *);', + '', + ' __cxa_finalize(&__dso_handle);', + '}', + ''; +} # Outputs the C code for registering exception handler frame info sub exceptionHandlerFrame { @@ -97,7 +117,11 @@ sub exceptionHandlerFrame { '', "static void $eh_ctor(void) {", ' extern void __register_frame_info (const void *, void *);', - ' static struct { unsigned pad[8]; } object;', + ' static struct {', + ' void *a, *b, *c, *d;', + ' unsigned long e;', + ' void *f, *g;', + ' } object;', '', ' __register_frame_info(__EH_FRAME_BEGIN__, &object);', '}', @@ -108,7 +132,6 @@ sub exceptionHandlerFrame { ' __deregister_frame_info(__EH_FRAME_BEGIN__);', '}', ''; - return; } sub cName {