Compare commits
38 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
1c3aa01846 | ||
|
|
191ff137f1 | ||
|
|
156945c458 | ||
|
|
31fcb77412 | ||
|
|
631f514c7c | ||
|
|
6e496e80d1 | ||
|
|
2256c979b0 | ||
|
|
7529577e3b | ||
|
|
1c96fd1cb4 | ||
|
|
8d078a0c7d | ||
|
|
8a4051964f | ||
|
|
5ef537684e | ||
|
|
c1dcd728d7 | ||
|
|
78684e0e57 | ||
|
|
f57acd2c10 | ||
|
|
ba5ade1852 | ||
|
|
8a0fc0373b | ||
|
|
4340e76445 | ||
|
|
ce910f52c3 | ||
|
|
219ab33625 | ||
|
|
e9e576f4bb | ||
|
|
5bb1138b87 | ||
|
|
955dcfc7b5 | ||
|
|
07a371703f | ||
|
|
1950a8240c | ||
|
|
a662cae239 | ||
|
|
2b3c6f2e26 | ||
|
|
b1d9c57101 | ||
|
|
446e0d4af8 | ||
|
|
2f51653a9e | ||
|
|
b9899213d4 | ||
|
|
0c12b02d4f | ||
|
|
ac12ccad38 | ||
|
|
8fdaa13c97 | ||
|
|
29fa0621d7 | ||
|
|
465920fcf1 | ||
|
|
b9e9537376 | ||
|
|
fb46786ccb |
4
.github/workflows/ci-scripts-build.yml
vendored
4
.github/workflows/ci-scripts-build.yml
vendored
@@ -85,7 +85,6 @@ jobs:
|
||||
configuration: default
|
||||
rtems: "5"
|
||||
rtems_target: RTEMS-pc686-qemu
|
||||
test: NO
|
||||
name: "Ub-20 gcc-9 + RT-5.1 pc686"
|
||||
|
||||
- os: ubuntu-20.04
|
||||
@@ -137,6 +136,7 @@ jobs:
|
||||
rtems: "4.10"
|
||||
name: "Ub-20 gcc-9 + RT-4.10"
|
||||
rtems_target: RTEMS-pc386-qemu
|
||||
test: NO
|
||||
|
||||
- os: ubuntu-20.04
|
||||
cmp: gcc
|
||||
@@ -186,7 +186,7 @@ jobs:
|
||||
- name: Build main module
|
||||
run: python .ci/cue.py build
|
||||
- name: Run main module tests
|
||||
run: python .ci/cue.py -T 20M test
|
||||
run: python .ci/cue.py -T 60M test
|
||||
- name: Upload tapfiles Artifact
|
||||
if: ${{ always() }}
|
||||
uses: actions/upload-artifact@v2
|
||||
|
||||
@@ -52,11 +52,11 @@ EPICS_MODIFICATION = 6
|
||||
|
||||
# EPICS_PATCH_LEVEL must be a number (win32 resource file requirement)
|
||||
# Not included in the official EPICS version number if zero
|
||||
EPICS_PATCH_LEVEL = 1
|
||||
EPICS_PATCH_LEVEL = 2
|
||||
|
||||
# Immediately after an official release the EPICS_PATCH_LEVEL is incremented
|
||||
# and the -DEV suffix is added (similar to the Maven -SNAPSHOT versions)
|
||||
EPICS_DEV_SNAPSHOT=
|
||||
EPICS_DEV_SNAPSHOT=-DEV
|
||||
|
||||
# No changes should be needed below here
|
||||
|
||||
|
||||
@@ -2,11 +2,11 @@
|
||||
|
||||
EPICS_CA_MAJOR_VERSION = 4
|
||||
EPICS_CA_MINOR_VERSION = 14
|
||||
EPICS_CA_MAINTENANCE_VERSION = 1
|
||||
EPICS_CA_MAINTENANCE_VERSION = 2
|
||||
|
||||
# Development flag, set to zero for release versions
|
||||
|
||||
EPICS_CA_DEVELOPMENT_FLAG = 0
|
||||
EPICS_CA_DEVELOPMENT_FLAG = 1
|
||||
|
||||
# Immediately after a release the MAINTENANCE_VERSION
|
||||
# will be incremented and the DEVELOPMENT_FLAG set to 1
|
||||
|
||||
@@ -56,6 +56,7 @@ GNU_DIR = /usr
|
||||
# Directories
|
||||
|
||||
INSTALL_LOCATION = $(TOP)
|
||||
INSTALL_ABSOLUTE = $(abspath $(INSTALL_LOCATION))
|
||||
|
||||
INSTALL_LOCATION_LIB = $(INSTALL_LOCATION)/lib
|
||||
INSTALL_LOCATION_BIN = $(INSTALL_LOCATION)/bin
|
||||
@@ -71,13 +72,14 @@ INSTALL_DBD = $(INSTALL_LOCATION)/dbd
|
||||
INSTALL_DB = $(INSTALL_LOCATION)/db
|
||||
INSTALL_CONFIG = $(INSTALL_LOCATION)/configure
|
||||
|
||||
FINAL_LOCATION = $(shell $(PERL) $(TOOLS)/fullPathName.pl $(INSTALL_LOCATION))
|
||||
#-------------------------------------------------------
|
||||
# These are default settings that may be overridden later
|
||||
|
||||
# Directory for OS independant build created files
|
||||
COMMON_DIR = ../O.Common
|
||||
# Eventual install path (to be compiled into binaries)
|
||||
FINAL_LOCATION = $(INSTALL_ABSOLUTE)
|
||||
|
||||
# IOC's absolute path to $(TOP), may be overridden inside the application
|
||||
IOCS_APPL_TOP = $(shell $(FULLPATHNAME) $(INSTALL_LOCATION))
|
||||
# IOC's view of install path
|
||||
IOCS_APPL_TOP = $(INSTALL_ABSOLUTE)
|
||||
|
||||
#-------------------------------------------------------
|
||||
# Silencing the build - suppress messages during 'make -s'
|
||||
@@ -133,6 +135,8 @@ LIB_SUFFIX =
|
||||
SHRLIB_PREFIX = $(LIB_PREFIX)
|
||||
DLLSTUB_PREFIX = $(LIB_PREFIX)
|
||||
DLLSTUB_SUFFIX = $(LIB_SUFFIX)
|
||||
LOADABLE_SHRLIB_PREFIX = $(SHRLIB_PREFIX)
|
||||
LOADABLE_SHRLIB_SUFFIX = $(SHRLIB_SUFFIX)
|
||||
|
||||
BUILDLIB_PREFIX_YES = $(DLLSTUB_PREFIX)
|
||||
BUILDLIB_PREFIX_NO = $(LIB_PREFIX)
|
||||
@@ -153,12 +157,14 @@ CMPLR_SRC_DIRS += . $(foreach dir, .. $(SRC_DIRS), \
|
||||
ALL_SRC_DIRS = $(CMPLR_SRC_DIRS) $(OS_SRC_DIRS) $(GENERIC_SRC_DIRS)
|
||||
|
||||
#--------------------------------------------------
|
||||
# Directory for OS independant build created files
|
||||
COMMON_DIR = ../O.Common
|
||||
|
||||
# compile line include directories
|
||||
INSTALL_INCLUDES += \
|
||||
-I$(INSTALL_INCLUDE)/compiler/$(CMPLR_CLASS) \
|
||||
-I$(INSTALL_INCLUDE)/os/$(OS_CLASS) \
|
||||
-I$(INSTALL_INCLUDE)
|
||||
SRC_INCLUDES = -I$(COMMON_DIR) $(addprefix -I, $(wildcard $(ALL_SRC_DIRS)))
|
||||
INSTALL_INCLUDE_DIRS = $(INSTALL_INCLUDE)/compiler/$(CMPLR_CLASS) \
|
||||
$(INSTALL_INCLUDE)/os/$(OS_CLASS) $(INSTALL_INCLUDE)
|
||||
INSTALL_INCLUDES += $(addprefix -I, $(INSTALL_INCLUDE_DIRS))
|
||||
SRC_INCLUDES = $(addprefix -I, $(COMMON_DIR) $(wildcard $(ALL_SRC_DIRS)))
|
||||
|
||||
#--------------------------------------------------
|
||||
# Target filename definitions
|
||||
@@ -172,23 +178,27 @@ TESTSHRLIBNAME = $(TESTSHRLIBNAME_$(SHARED_LIBRARIES))
|
||||
#--------------------------------------------------
|
||||
# obj files
|
||||
|
||||
TARGET_OBJS = $($*_LDOBJS) $(addsuffix $(OBJ),$(basename $($*_OBJS) $($*_SRCS)))
|
||||
TARGET_OBJS = $($*_LDOBJS) $(addsuffix $(OBJ), \
|
||||
$(basename $($*_OBJS) $($*_SRCS)))
|
||||
|
||||
PRODUCT_OBJS = $(addsuffix $(OBJ),$(basename $(SRCS) $(USR_SRCS) $(PROD_SRCS) $(USR_OBJS) $(PROD_OBJS)))
|
||||
PRODUCT_OBJS = $(addsuffix $(OBJ), \
|
||||
$(basename $(SRCS) $(USR_SRCS) $(PROD_SRCS) $(USR_OBJS) $(PROD_OBJS)))
|
||||
PROD_LD_OBJS = $(TARGET_OBJS) $(PRODUCT_OBJS)
|
||||
|
||||
LIBRARY_OBJS = $(addsuffix $(OBJ),$(basename $(SRCS) $(USR_SRCS) $(LIB_SRCS) $(LIBSRCS) $(USR_OBJS) $(LIB_OBJS)))
|
||||
LIBRARY_OBJS = $(addsuffix $(OBJ), \
|
||||
$(basename $(SRCS) $(USR_SRCS) $(LIB_SRCS) $(LIBSRCS) $(USR_OBJS) $(LIB_OBJS)))
|
||||
LIBRARY_LD_OBJS = $(TARGET_OBJS) $(LIBRARY_OBJS)
|
||||
|
||||
#--------------------------------------------------
|
||||
# Windows resource files
|
||||
|
||||
TARGET_RESS = $(if $(RES),$(addsuffix $(RES),$(basename $($*_RCS))),)
|
||||
TARGET_RESS = $(if $(RES), $(addsuffix $(RES), $(basename $($*_RCS))))
|
||||
|
||||
PROD_RESS = $(if $(RES),$(addsuffix $(RES),$(basename $(RCS) $(PROD_RCS))),)
|
||||
PROD_RESS = $(if $(RES), $(addsuffix $(RES), $(basename $(RCS) $(PROD_RCS))))
|
||||
PROD_LD_RESS = $(TARGET_RESS) $(PROD_RESS)
|
||||
|
||||
LIBRARY_RESS = $(if $(RES),$(addsuffix $(RES),$(basename $(RCS) $(LIB_RCS) $(LIBRARY_RCS))),)
|
||||
LIBRARY_RESS = $(if $(RES), $(addsuffix $(RES), \
|
||||
$(basename $(RCS) $(LIB_RCS) $(LIBRARY_RCS))))
|
||||
LIBRARY_LD_RESS = $(TARGET_RESS) $(LIBRARY_RESS)
|
||||
|
||||
#--------------------------------------------------
|
||||
@@ -265,15 +275,16 @@ STATIC_LDFLAGS = $(STATIC_LDFLAGS_$(STATIC_BUILD))
|
||||
STATIC_LDLIBS = $(STATIC_LDLIBS_$(STATIC_BUILD))
|
||||
|
||||
#--------------------------------------------------
|
||||
# cflags for shared library src files (from SHRLIB_CFLAGS)
|
||||
LIBRARY_SRCS=$(basename $(foreach lib,$(LIBRARY) $(TESTLIBRARY) $(LOADABLE_LIBRARY),$($(lib)_OBJSNAME) $(LIBRARY_OBJS)))
|
||||
LIBRARY_SRC_CFLAGS=$($(patsubst $*,SHRLIB,$(findstring $*,$(LIBRARY_SRCS)))_CFLAGS)
|
||||
# cflags for shared library src files
|
||||
LIBRARY_SRCS = $(basename $(foreach lib, \
|
||||
$(LIBRARY) $(TESTLIBRARY) $(LOADABLE_LIBRARY), \
|
||||
$($(lib)_OBJSNAME) $(LIBRARY_OBJS)))
|
||||
LIBRARY_SRC_CFLAGS = $(if $(findstring $*, $(LIBRARY_SRCS)), $(SHRLIB_CFLAGS))
|
||||
|
||||
#--------------------------------------------------
|
||||
# prefix, suffix, and ldflags for loadable shared libraries
|
||||
TARGET_LIB_LDFLAGS=$($(patsubst $*,LOADABLE_,$(findstring $*,$(LOADABLE_LIBRARY)))SHRLIB_LDFLAGS)
|
||||
LOADABLE_SHRLIB_PREFIX=$(SHRLIB_PREFIX)
|
||||
LOADABLE_SHRLIB_SUFFIX=$(SHRLIB_SUFFIX)
|
||||
# ldflags for loadable and shared libraries
|
||||
TARGET_LIB_LDFLAGS = $(if $(findstring $*, $(LOADABLE_LIBRARY)), \
|
||||
$(LOADABLE_SHRLIB_LDFLAGS), $(SHRLIB_LDFLAGS))
|
||||
|
||||
#--------------------------------------------------
|
||||
# Command-line input support default
|
||||
@@ -285,31 +296,31 @@ RUNTIME_LDFLAGS += $(RUNTIME_LDFLAGS_$(COMMANDLINE_LIBRARY))
|
||||
#--------------------------------------------------
|
||||
# Flags
|
||||
|
||||
INCLUDES = -I. $(SRC_INCLUDES) $(INSTALL_INCLUDES) $(RELEASE_INCLUDES)\
|
||||
$(TARGET_INCLUDES) $(USR_INCLUDES) $(CMD_INCLUDES) $(OP_SYS_INCLUDES)\
|
||||
$($(BUILD_CLASS)_INCLUDES)
|
||||
INCLUDES = -I. $(SRC_INCLUDES) $(INSTALL_INCLUDES) $(RELEASE_INCLUDES) \
|
||||
$(TARGET_INCLUDES) $(USR_INCLUDES) $(CMD_INCLUDES) $(OP_SYS_INCLUDES) \
|
||||
$($(BUILD_CLASS)_INCLUDES)
|
||||
|
||||
CFLAGS = $($(BUILD_CLASS)_CFLAGS) $(POSIX_CFLAGS) $(OPT_CFLAGS)\
|
||||
$(DEBUG_CFLAGS) $(PIPE_CFLAGS) $(WARN_CFLAGS) $(TARGET_CFLAGS)\
|
||||
$(USR_CFLAGS) $(CMD_CFLAGS) $(ARCH_DEP_CFLAGS) $(CODE_CFLAGS)\
|
||||
$(STATIC_CFLAGS) $(OP_SYS_CFLAGS) $(LIBRARY_SRC_CFLAGS)
|
||||
CFLAGS = $($(BUILD_CLASS)_CFLAGS) $(POSIX_CFLAGS) $(OPT_CFLAGS) \
|
||||
$(DEBUG_CFLAGS) $(PIPE_CFLAGS) $(WARN_CFLAGS) $(TARGET_CFLAGS) \
|
||||
$(USR_CFLAGS) $(CMD_CFLAGS) $(ARCH_DEP_CFLAGS) $(CODE_CFLAGS) \
|
||||
$(STATIC_CFLAGS) $(OP_SYS_CFLAGS) $(LIBRARY_SRC_CFLAGS)
|
||||
|
||||
CXXFLAGS = $($(BUILD_CLASS)_CXXFLAGS) $(POSIX_CXXFLAGS) $(OPT_CXXFLAGS)\
|
||||
$(DEBUG_CXXFLAGS) $(PIPE_CFLAGS) $(WARN_CXXFLAGS) $(TARGET_CXXFLAGS)\
|
||||
$(USR_CXXFLAGS) $(CMD_CXXFLAGS) $(ARCH_DEP_CXXFLAGS) $(CODE_CXXFLAGS)\
|
||||
$(STATIC_CXXFLAGS) $(OP_SYS_CXXFLAGS) $(LIBRARY_SRC_CFLAGS)
|
||||
CXXFLAGS = $($(BUILD_CLASS)_CXXFLAGS) $(POSIX_CXXFLAGS) $(OPT_CXXFLAGS) \
|
||||
$(DEBUG_CXXFLAGS) $(PIPE_CFLAGS) $(WARN_CXXFLAGS) $(TARGET_CXXFLAGS) \
|
||||
$(USR_CXXFLAGS) $(CMD_CXXFLAGS) $(ARCH_DEP_CXXFLAGS) $(CODE_CXXFLAGS) \
|
||||
$(STATIC_CXXFLAGS) $(OP_SYS_CXXFLAGS) $(LIBRARY_SRC_CFLAGS)
|
||||
|
||||
LDFLAGS = $(OPT_LDFLAGS) $(TARGET_LDFLAGS) $(USR_LDFLAGS) $(CMD_LDFLAGS)\
|
||||
$(POSIX_LDFLAGS) $(ARCH_DEP_LDFLAGS) $(DEBUG_LDFLAGS) $(OP_SYS_LDFLAGS)\
|
||||
$($(BUILD_CLASS)_LDFLAGS) $(RUNTIME_LDFLAGS) $(CODE_LDFLAGS)
|
||||
LDFLAGS = $(OPT_LDFLAGS) $(TARGET_LDFLAGS) $(USR_LDFLAGS) $(CMD_LDFLAGS) \
|
||||
$(POSIX_LDFLAGS) $(ARCH_DEP_LDFLAGS) $(DEBUG_LDFLAGS) $(OP_SYS_LDFLAGS) \
|
||||
$($(BUILD_CLASS)_LDFLAGS) $(RUNTIME_LDFLAGS) $(CODE_LDFLAGS)
|
||||
|
||||
LDLIBS = $(POSIX_LDLIBS) $(ARCH_DEP_LDLIBS) $(DEBUG_LDLIBS) $(OP_SYS_LDLIBS)\
|
||||
$(GNU_LDLIBS_$(GNU))
|
||||
LDLIBS = $(POSIX_LDLIBS) $(ARCH_DEP_LDLIBS) $(DEBUG_LDLIBS) $(OP_SYS_LDLIBS) \
|
||||
$(GNU_LDLIBS_$(GNU))
|
||||
|
||||
CPPFLAGS = $($(BUILD_CLASS)_CPPFLAGS) $(POSIX_CPPFLAGS) $(OPT_CPPFLAGS)\
|
||||
$(DEBUG_CPPFLAGS) $(WARN_CPPFLAGS) $(BASE_CPPFLAGS) $(TARGET_CPPFLAGS)\
|
||||
$(USR_CPPFLAGS) $(CMD_CPPFLAGS) $(ARCH_DEP_CPPFLAGS) $(OP_SYS_CPPFLAGS)\
|
||||
$(OP_SYS_INCLUDE_CPPFLAGS) $(CODE_CPPFLAGS) $(API_CPPFLAGS)
|
||||
CPPFLAGS = $($(BUILD_CLASS)_CPPFLAGS) $(POSIX_CPPFLAGS) $(OPT_CPPFLAGS) \
|
||||
$(DEBUG_CPPFLAGS) $(WARN_CPPFLAGS) $(BASE_CPPFLAGS) $(TARGET_CPPFLAGS) \
|
||||
$(USR_CPPFLAGS) $(CMD_CPPFLAGS) $(ARCH_DEP_CPPFLAGS) $(OP_SYS_CPPFLAGS) \
|
||||
$(OP_SYS_INCLUDE_CPPFLAGS) $(CODE_CPPFLAGS) $(API_CPPFLAGS)
|
||||
|
||||
#--------------------------------------------------
|
||||
# ar definition default
|
||||
@@ -396,7 +407,7 @@ INSTALL_DOCS = $(DOCS:%= $(INSTALL_DOC)/%)
|
||||
INSTALL_HTMLS = $(HTMLS:%= $(INSTALL_HTML)/$(HTMLS_DIR)/%)
|
||||
|
||||
INSTALL_TEMPLATE = $(addprefix $(INSTALL_TEMPLATES_SUBDIR)/, \
|
||||
$(subst $(CONFIG),top/configure,$(TEMPLATES)))
|
||||
$(subst $(CONFIG),top/configure,$(TEMPLATES)))
|
||||
INSTALL_CONFIGS = $(CONFIGS:%= $(INSTALL_CONFIG)/%)
|
||||
|
||||
INSTALL_BIN_INSTALLS = $(addprefix $(INSTALL_BIN)/,$(notdir $(BIN_INSTALLS)))
|
||||
@@ -431,42 +442,41 @@ INSTALL_INC += $(foreach inc, $(INC), \
|
||||
$(CMPLR_INSTALL_INC) \
|
||||
$(OS_INSTALL_INC) \
|
||||
$(GENERIC_INSTALL_INC) \
|
||||
$(GENERATED_INSTALL_INC) ) )
|
||||
INSTALL_INC += $(addprefix $(INSTALL_INCLUDE)/os/$(OS_CLASS)/, $(INC_$(OS_CLASS)) )
|
||||
$(GENERATED_INSTALL_INC)))
|
||||
INSTALL_INC += $(addprefix $(INSTALL_INCLUDE)/os/$(OS_CLASS)/, $(INC_$(OS_CLASS)))
|
||||
|
||||
#
|
||||
# Rule 0
|
||||
#
|
||||
CMPLR_INSTALL_INC = $(addprefix $(INSTALL_INCLUDE)/compiler/$(CMPLR_CLASS)/, $(INSTALL_INC_jjj) )
|
||||
INSTALL_INC_jjj = $(foreach dir, $(CMPLR_SRC_DIRS), $(INSTALL_INC_iii) )
|
||||
INSTALL_INC_iii = $(subst $(dir)/, , $(INSTALL_INC_hhh) )
|
||||
INSTALL_INC_hhh = $(wildcard $(addsuffix /$(inc), $(dir)) )
|
||||
CMPLR_INSTALL_INC = $(addprefix $(INSTALL_INCLUDE)/compiler/$(CMPLR_CLASS)/, \
|
||||
$(foreach dir, $(CMPLR_SRC_DIRS), \
|
||||
$(subst $(dir)/,, $(wildcard $(addsuffix /$(inc), $(dir))))))
|
||||
|
||||
#
|
||||
# Rule 1
|
||||
#
|
||||
OS_INSTALL_INC = $(addprefix $(INSTALL_INCLUDE)/os/$(OS_CLASS)/, $(INSTALL_INC_ggg) )
|
||||
INSTALL_INC_ggg = $(foreach dir, $(OS_SRC_DIRS), $(INSTALL_INC_fff) )
|
||||
INSTALL_INC_fff = $(subst $(dir)/, , $(INSTALL_INC_eee) )
|
||||
INSTALL_INC_eee = $(wildcard $(addsuffix /$(inc), $(dir)) )
|
||||
OS_INSTALL_INC = $(addprefix $(INSTALL_INCLUDE)/os/$(OS_CLASS)/, \
|
||||
$(foreach dir, $(OS_SRC_DIRS), \
|
||||
$(subst $(dir)/,, $(wildcard $(addsuffix /$(inc), $(dir))))))
|
||||
|
||||
#
|
||||
# Rule 2
|
||||
#
|
||||
GENERIC_INSTALL_INC = $(addprefix $(INSTALL_INCLUDE)/, $(INSTALL_INC_ccc) )
|
||||
INSTALL_INC_ccc = $(foreach dir, .. $(SRC_DIRS), $(INSTALL_INC_bbb) )
|
||||
INSTALL_INC_bbb = $(subst $(dir)/, , $(INSTALL_INC_aaa) )
|
||||
INSTALL_INC_aaa = $(wildcard $(addsuffix /$(inc), $(dir)) )
|
||||
GENERIC_INSTALL_INC = $(addprefix $(INSTALL_INCLUDE)/, \
|
||||
$(foreach dir, .. $(SRC_DIRS), \
|
||||
$(subst $(dir)/,, $(wildcard $(addsuffix /$(inc), $(dir))))))
|
||||
|
||||
#
|
||||
# Rule 3
|
||||
#
|
||||
GENERATED_INSTALL_INC = $(INSTALL_INCLUDE)/$(inc)
|
||||
|
||||
COMMON_INC += $(filter $(COMMON_DIR)/%, $(foreach file, $(INC), \
|
||||
$(firstword $(SOURCE_INC) $(COMMON_DIR)/$(file) ) ) )
|
||||
SOURCE_INC = $(wildcard $(file) $(SOURCE_INC_bbb) )
|
||||
SOURCE_INC_bbb = $(foreach dir, $(ALL_SRC_DIRS), $(SOURCE_INC_aaa) )
|
||||
SOURCE_INC_aaa = $(addsuffix /$(file), $(dir) )
|
||||
#---------------------------------------------------------------
|
||||
# Files listed in INC that must first be created in O.Common
|
||||
COMMON_INC += $(filter $(COMMON_DIR)/%, \
|
||||
$(foreach file, $(INC), \
|
||||
$(firstword $(wildcard $(file) \
|
||||
$(foreach dir, $(ALL_SRC_DIRS), \
|
||||
$(addsuffix /$(file), $(dir)))) $(COMMON_DIR)/$(file))))
|
||||
|
||||
endif
|
||||
|
||||
@@ -2,11 +2,11 @@
|
||||
|
||||
EPICS_DATABASE_MAJOR_VERSION = 3
|
||||
EPICS_DATABASE_MINOR_VERSION = 21
|
||||
EPICS_DATABASE_MAINTENANCE_VERSION = 0
|
||||
EPICS_DATABASE_MAINTENANCE_VERSION = 1
|
||||
|
||||
# Development flag, set to zero for release versions
|
||||
|
||||
EPICS_DATABASE_DEVELOPMENT_FLAG = 0
|
||||
EPICS_DATABASE_DEVELOPMENT_FLAG = 1
|
||||
|
||||
# Immediately after a release the MAINTENANCE_VERSION
|
||||
# will be incremented and the DEVELOPMENT_FLAG set to 1
|
||||
|
||||
@@ -2,11 +2,11 @@
|
||||
|
||||
EPICS_LIBCOM_MAJOR_VERSION = 3
|
||||
EPICS_LIBCOM_MINOR_VERSION = 21
|
||||
EPICS_LIBCOM_MAINTENANCE_VERSION = 0
|
||||
EPICS_LIBCOM_MAINTENANCE_VERSION = 1
|
||||
|
||||
# Development flag, set to zero for release versions
|
||||
|
||||
EPICS_LIBCOM_DEVELOPMENT_FLAG = 0
|
||||
EPICS_LIBCOM_DEVELOPMENT_FLAG = 1
|
||||
|
||||
# Immediately after a release the MAINTENANCE_VERSION
|
||||
# will be incremented and the DEVELOPMENT_FLAG set to 1
|
||||
|
||||
@@ -28,7 +28,6 @@ DIRS += $(LIVE_SUBMODULES)
|
||||
|
||||
include $(CONFIG)/RULES_DIRS
|
||||
|
||||
INSTALL_LOCATION_ABS := $(abspath $(INSTALL_LOCATION))
|
||||
RELEASE_LOCAL := RELEASE.$(EPICS_HOST_ARCH).local
|
||||
|
||||
# Ensure that RELEASE.<host>.local exists before doing anything else
|
||||
@@ -40,8 +39,8 @@ RELEASE.host: $(RELEASE_LOCAL)
|
||||
|
||||
$(RELEASE_LOCAL): Makefile CONFIG_SITE.local
|
||||
$(ECHO) Creating $@ with
|
||||
$(ECHO) " $(PARENT_MODULE) = $(INSTALL_LOCATION_ABS)"
|
||||
@echo $(PARENT_MODULE) = $(INSTALL_LOCATION_ABS)> $@
|
||||
$(ECHO) " $(PARENT_MODULE) = $(INSTALL_ABSOLUTE)"
|
||||
@echo $(PARENT_MODULE) = $(INSTALL_ABSOLUTE)> $@
|
||||
realclean:
|
||||
$(RM) $(wildcard RELEASE.*.local)
|
||||
|
||||
|
||||
@@ -56,7 +56,7 @@ SHRLIB_LDLIBS = $(addprefix -l, $($*_LDLIBS) $(LIB_LIBS) $(USR_LIBS)) \
|
||||
|
||||
SHRLIB_DEPLIB_DIRS = $(foreach word, \
|
||||
$(sort $(INSTALL_LIB)/ $(dir $($*_DEPLIBS) $(SHRLIB_DEPLIBS))), \
|
||||
$(shell $(FULLPATHNAME) $(word)))
|
||||
$(abspath $(word)))
|
||||
|
||||
SHRLIBDIR_LDFLAGS += $(SHRLIB_DEPLIB_DIRS:%=-L%)
|
||||
|
||||
@@ -85,7 +85,7 @@ PROD_LDLIBS += $($(firstword $(LDLIBS_STATIC_$(STATIC_BUILD)) \
|
||||
|
||||
PROD_DEPLIB_DIRS = $(foreach word, \
|
||||
$(sort $(INSTALL_LIB)/ $(dir $($*_DEPLIBS) $(PROD_DEPLIBS))), \
|
||||
$(shell $(FULLPATHNAME) $(word)))
|
||||
$(abspath $(word)))
|
||||
|
||||
PRODDIR_LDFLAGS += $(PROD_DEPLIB_DIRS:%=-L%)
|
||||
|
||||
|
||||
@@ -77,7 +77,7 @@ OP_SYS_LDFLAGS += -dynamic -Z -L$(SDK_DIR)/usr/lib -L$(SDK_DIR)/usr/lib/system
|
||||
# Shared libraries
|
||||
SHRLIB_VERSION = $(EPICS_VERSION).$(EPICS_REVISION).$(EPICS_MODIFICATION)
|
||||
SHRLIB_LDFLAGS = -dynamiclib -flat_namespace -undefined suppress \
|
||||
-install_name $(shell $(FULLPATHNAME) $(INSTALL_LIB))/$@ \
|
||||
-install_name $(abspath $(INSTALL_LIB))/$@ \
|
||||
-compatibility_version $(EPICS_VERSION).$(EPICS_REVISION) \
|
||||
-current_version $(SHRLIB_VERSION)
|
||||
SHRLIB_SUFFIX_BASE = .dylib
|
||||
|
||||
@@ -67,7 +67,7 @@ GNU = NO
|
||||
# Darwin shared libraries
|
||||
#
|
||||
SHRLIB_LDFLAGS = -dynamiclib -flat_namespace -undefined dynamic_lookup \
|
||||
-install_name $(shell $(FULLPATHNAME) $(INSTALL_LIB))/$@ \
|
||||
-install_name $(abspath $(INSTALL_LIB))/$@ \
|
||||
$(addprefix -compatibility_version , $(SHRLIB_VERSION)) \
|
||||
$(addprefix -current_version , $(SHRLIB_VERSION))
|
||||
SHRLIB_SUFFIX_BASE = .dylib
|
||||
|
||||
@@ -10,6 +10,46 @@ everything that has changed in each release.
|
||||
The PVA submodules each have their own individual sets of release notes which
|
||||
should also be read to understand what has changed since earlier releases.
|
||||
|
||||
**This version of EPICS has not been released yet.**
|
||||
|
||||
## Changes made on the 7.0 branch since 7.0.6.1
|
||||
|
||||
<!-- Insert new items immediately below here ... -->
|
||||
|
||||
### Fix for `undefined` in configure/RELEASE files
|
||||
|
||||
Prevents `Use of uninitialized value` warnings from convertRelease.pl.
|
||||
|
||||
### Colorized Messages for errlog
|
||||
|
||||
Many internal error messages now emit ANSI escape sequences to highlight the
|
||||
words "ERROR" and "WARNING" in an attempt to make occurrences more noticeable
|
||||
during IOC startup.
|
||||
|
||||
The macros `ERL_ERROR` and `ERL_WARNING` are defined for external usage,
|
||||
and expand as string constants. eg.
|
||||
|
||||
```c
|
||||
#include <errlog.h>
|
||||
#ifndef ERL_ERROR
|
||||
# define ERL_ERROR "ERROR"
|
||||
#endif
|
||||
void fn() {
|
||||
...
|
||||
errlogPrintf(ERL_ERROR ": something bad happens :(\n");
|
||||
```
|
||||
|
||||
ANSI escapes are automatically removed from errlog output not destined
|
||||
for a terminal. For example, for logClient, if stderr is redirected,
|
||||
or if unsupported (`$TERM` not set, or Windows < 10).
|
||||
|
||||
### `dbnd` filter pass through `DBE_ALARM|DBE_PROPERTY`
|
||||
|
||||
The `dbnd` server side filter now passes through alarm and property
|
||||
change events, even when not exceeding the deadband.
|
||||
|
||||
-----
|
||||
|
||||
## EPICS Release 7.0.6.1
|
||||
|
||||
### `mbboDirectRecord` enhancements
|
||||
|
||||
@@ -188,7 +188,7 @@ int main ( int argc, char ** argv )
|
||||
epicsSocketConvertErrnoToString (
|
||||
sockErrBuf, sizeof ( sockErrBuf ) );
|
||||
epicsSocketDestroy ( sock );
|
||||
errlogPrintf ("casw: error from recv was = \"%s\"\n",
|
||||
errlogPrintf ("casw: " ERL_ERROR " from recv was = \"%s\"\n",
|
||||
sockErrBuf );
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -178,7 +178,7 @@ void tcpSendThread::run ()
|
||||
char sockErrBuf[64];
|
||||
epicsSocketConvertErrnoToString (
|
||||
sockErrBuf, sizeof ( sockErrBuf ) );
|
||||
errlogPrintf ("CAC TCP clean socket shutdown error was %s\n",
|
||||
errlogPrintf ("CAC TCP clean socket shutdown " ERL_ERROR " was %s\n",
|
||||
sockErrBuf );
|
||||
}
|
||||
}
|
||||
@@ -194,7 +194,7 @@ void tcpSendThread::run ()
|
||||
char sockErrBuf[64];
|
||||
epicsSocketConvertErrnoToString (
|
||||
sockErrBuf, sizeof ( sockErrBuf ) );
|
||||
errlogPrintf ("CAC TCP clean socket shutdown error was %s\n",
|
||||
errlogPrintf ("CAC TCP clean socket shutdown " ERL_ERROR " was %s\n",
|
||||
sockErrBuf );
|
||||
}
|
||||
}
|
||||
@@ -283,7 +283,7 @@ unsigned tcpiiu::sendBytes ( const void *pBuf,
|
||||
char sockErrBuf[64];
|
||||
epicsSocketConvertErrnoToString (
|
||||
sockErrBuf, sizeof ( sockErrBuf ) );
|
||||
errlogPrintf ( "CAC: unexpected TCP send error: %s\n",
|
||||
errlogPrintf ( "CAC: unexpected TCP send " ERL_ERROR ": %s\n",
|
||||
sockErrBuf );
|
||||
}
|
||||
|
||||
@@ -957,7 +957,7 @@ void tcpiiu::initiateAbortShutdown (
|
||||
char sockErrBuf[64];
|
||||
epicsSocketConvertErrnoToString (
|
||||
sockErrBuf, sizeof ( sockErrBuf ) );
|
||||
errlogPrintf ( "CAC TCP socket linger set error was %s\n",
|
||||
errlogPrintf ( "CAC TCP socket linger set " ERL_ERROR " was %s\n",
|
||||
sockErrBuf );
|
||||
}
|
||||
this->discardingPendingData = true;
|
||||
@@ -988,7 +988,7 @@ void tcpiiu::initiateAbortShutdown (
|
||||
char sockErrBuf[64];
|
||||
epicsSocketConvertErrnoToString (
|
||||
sockErrBuf, sizeof ( sockErrBuf ) );
|
||||
errlogPrintf ("CAC TCP socket shutdown error was %s\n",
|
||||
errlogPrintf ("CAC TCP socket shutdown " ERL_ERROR " was %s\n",
|
||||
sockErrBuf );
|
||||
}
|
||||
}
|
||||
@@ -1058,7 +1058,7 @@ void tcpiiu::show ( unsigned level ) const
|
||||
this->_receiveThreadIsBusy );
|
||||
}
|
||||
if ( level > 2u ) {
|
||||
::printf ( "\tvirtual circuit socket identifier %d\n", this->sock );
|
||||
::printf ( "\tvirtual circuit socket identifier %d\n", (int)this->sock );
|
||||
::printf ( "\tsend thread flush signal:\n" );
|
||||
this->sendThreadFlushEvent.show ( level-2u );
|
||||
::printf ( "\tsend thread:\n" );
|
||||
|
||||
@@ -266,7 +266,7 @@ udpiiu::udpiiu (
|
||||
epicsSocketConvertErrnoToString (
|
||||
sockErrBuf, sizeof ( sockErrBuf ) );
|
||||
epicsSocketDestroy ( this->sock );
|
||||
errlogPrintf ( "CAC: getsockname () error was \"%s\"\n", sockErrBuf );
|
||||
errlogPrintf ( "CAC: getsockname () " ERL_ERROR " was \"%s\"\n", sockErrBuf );
|
||||
throwWithLocation ( noSocket () );
|
||||
}
|
||||
if ( tmpAddr.sa.sa_family != AF_INET) {
|
||||
@@ -428,7 +428,7 @@ void udpRecvThread::run ()
|
||||
char sockErrBuf[64];
|
||||
epicsSocketConvertErrnoToString (
|
||||
sockErrBuf, sizeof ( sockErrBuf ) );
|
||||
errlogPrintf ( "CAC: UDP recv error was \"%s\"\n",
|
||||
errlogPrintf ( "CAC: UDP recv " ERL_ERROR " was \"%s\"\n",
|
||||
sockErrBuf );
|
||||
}
|
||||
}
|
||||
|
||||
@@ -85,7 +85,7 @@ static epicsEventId startStopEvent;
|
||||
static char *threadNamePrefix[NUM_CALLBACK_PRIORITIES] = {
|
||||
"cbLow", "cbMedium", "cbHigh"
|
||||
};
|
||||
#define FULL_MSG(name) "callbackRequest: " name " ring buffer full\n"
|
||||
#define FULL_MSG(name) "callbackRequest: " ERL_ERROR " " name " ring buffer full\n"
|
||||
static char *fullMessage[NUM_CALLBACK_PRIORITIES] = {
|
||||
FULL_MSG("cbLow"), FULL_MSG("cbMedium"), FULL_MSG("cbHigh")
|
||||
};
|
||||
@@ -326,17 +326,17 @@ int callbackRequest(epicsCallback *pcallback)
|
||||
cbQueueSet *mySet;
|
||||
|
||||
if (!pcallback) {
|
||||
epicsInterruptContextMessage("callbackRequest: pcallback was NULL\n");
|
||||
epicsInterruptContextMessage("callbackRequest: " ERL_ERROR " pcallback was NULL\n");
|
||||
return S_db_notInit;
|
||||
}
|
||||
priority = pcallback->priority;
|
||||
if (priority < 0 || priority >= NUM_CALLBACK_PRIORITIES) {
|
||||
epicsInterruptContextMessage("callbackRequest: Bad priority\n");
|
||||
epicsInterruptContextMessage("callbackRequest: " ERL_ERROR " Bad priority\n");
|
||||
return S_db_badChoice;
|
||||
}
|
||||
mySet = &callbackQueue[priority];
|
||||
if (!mySet->queue) {
|
||||
epicsInterruptContextMessage("callbackRequest: Callbacks not initialized\n");
|
||||
epicsInterruptContextMessage("callbackRequest: " ERL_ERROR " Callbacks not initialized\n");
|
||||
return S_db_notInit;
|
||||
}
|
||||
if (mySet->queueOverflow) return S_db_bufFull;
|
||||
|
||||
@@ -1104,9 +1104,9 @@ static long dbPutFieldLink(DBADDR *paddr,
|
||||
if (link_info.ltype == PV_LINK &&
|
||||
(link_info.modifiers & (pvlOptCA | pvlOptCP | pvlOptCPP)) == 0) {
|
||||
chan = dbChannelCreate(link_info.target);
|
||||
if (chan && dbChannelOpen(chan) != 0) {
|
||||
errlogPrintf("ERROR: dbPutFieldLink %s.%s=%s: dbChannelOpen() failed\n",
|
||||
precord->name, pfldDes->name, link_info.target);
|
||||
if (chan && (status = dbChannelOpen(chan)) != 0) {
|
||||
errlogPrintf(ERL_ERROR ": dbPutFieldLink %s.%s=%s: dbChannelOpen() failed w/ 0x%lx\n",
|
||||
precord->name, pfldDes->name, link_info.target, status);
|
||||
goto cleanup;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -196,6 +196,73 @@ static void caLinkDec(caLink *pca)
|
||||
if (callback) callback(userPvt);
|
||||
}
|
||||
|
||||
struct waitPvt {
|
||||
caLink *pca;
|
||||
epicsEventId evt;
|
||||
};
|
||||
enum testEvent {
|
||||
testEventConnect,
|
||||
testEventCount,
|
||||
};
|
||||
|
||||
static
|
||||
void testdbCaWaitForEventCB(void *raw)
|
||||
{
|
||||
struct waitPvt *pvt = raw;
|
||||
|
||||
epicsMutexMustLock(pvt->pca->lock);
|
||||
epicsEventMustTrigger(pvt->evt);
|
||||
epicsMutexUnlock(pvt->pca->lock);
|
||||
}
|
||||
|
||||
static
|
||||
void testdbCaWaitForEvent(DBLINK *plink, unsigned long cnt, enum testEvent event)
|
||||
{
|
||||
caLink *pca;
|
||||
epicsEventId evt = epicsEventMustCreate(epicsEventEmpty);
|
||||
|
||||
dbScanLock(plink->precord);
|
||||
|
||||
assert(plink->type==CA_LINK);
|
||||
pca = (caLink *)plink->value.pv_link.pvt;
|
||||
|
||||
epicsMutexMustLock(pca->lock);
|
||||
assert(!pca->monitor && !pca->connect && !pca->userPvt);
|
||||
|
||||
while(!pca->isConnected || (event==testEventCount && pca->nUpdate < cnt)) {
|
||||
struct waitPvt pvt = {pca, evt};
|
||||
pca->connect = &testdbCaWaitForEventCB;
|
||||
pca->monitor = &testdbCaWaitForEventCB;
|
||||
pca->userPvt = &pvt;
|
||||
|
||||
epicsMutexUnlock(pca->lock);
|
||||
dbScanUnlock(plink->precord);
|
||||
|
||||
epicsEventMustWait(evt);
|
||||
|
||||
dbScanLock(plink->precord);
|
||||
epicsMutexMustLock(pca->lock);
|
||||
|
||||
pca->connect = NULL;
|
||||
pca->monitor = NULL;
|
||||
pca->userPvt = NULL;
|
||||
}
|
||||
|
||||
epicsEventDestroy(evt);
|
||||
epicsMutexUnlock(pca->lock);
|
||||
dbScanUnlock(plink->precord);
|
||||
}
|
||||
|
||||
void testdbCaWaitForConnect(DBLINK *plink)
|
||||
{
|
||||
testdbCaWaitForEvent(plink, 0, testEventConnect);
|
||||
}
|
||||
|
||||
void testdbCaWaitForUpdateCount(DBLINK *plink, unsigned long cnt)
|
||||
{
|
||||
testdbCaWaitForEvent(plink, cnt, testEventCount);
|
||||
}
|
||||
|
||||
/* Block until worker thread has processed all previously queued actions.
|
||||
* Does not prevent additional actions from being queued.
|
||||
*/
|
||||
@@ -232,22 +299,6 @@ void dbCaSync(void)
|
||||
epicsEventDestroy(wake);
|
||||
}
|
||||
|
||||
DBCORE_API unsigned long dbCaGetUpdateCount(struct link *plink)
|
||||
{
|
||||
caLink *pca = (caLink *)plink->value.pv_link.pvt;
|
||||
unsigned long ret;
|
||||
|
||||
if (!pca) return (unsigned long)-1;
|
||||
|
||||
epicsMutexMustLock(pca->lock);
|
||||
|
||||
ret = pca->nUpdate;
|
||||
|
||||
epicsMutexUnlock(pca->lock);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
void dbCaCallbackProcess(void *userPvt)
|
||||
{
|
||||
struct link *plink = (struct link *)userPvt;
|
||||
@@ -785,6 +836,8 @@ static void connectionCallback(struct connection_handler_args arg)
|
||||
caLink *pca;
|
||||
short link_action = 0;
|
||||
struct link *plink;
|
||||
dbCaCallback connect = 0;
|
||||
void *userPvt = 0;
|
||||
|
||||
pca = ca_puser(arg.chid);
|
||||
assert(pca);
|
||||
@@ -851,11 +904,16 @@ static void connectionCallback(struct connection_handler_args arg)
|
||||
}
|
||||
pca->gotAttributes = 0;
|
||||
if (pca->dbrType != DBR_STRING) {
|
||||
/* will run connect() callback later */
|
||||
link_action |= CA_GET_ATTRIBUTES;
|
||||
} else {
|
||||
connect = pca->connect;
|
||||
userPvt = pca->userPvt;
|
||||
}
|
||||
done:
|
||||
if (link_action) addAction(pca, link_action);
|
||||
epicsMutexUnlock(pca->lock);
|
||||
if (connect) connect(userPvt);
|
||||
}
|
||||
|
||||
static void eventCallback(struct event_handler_args arg)
|
||||
@@ -881,10 +939,10 @@ static void eventCallback(struct event_handler_args arg)
|
||||
if (precord) {
|
||||
if (arg.status != ECA_NORDACCESS &&
|
||||
arg.status != ECA_GETFAIL)
|
||||
errlogPrintf("dbCa: eventCallback record %s error %s\n",
|
||||
errlogPrintf("dbCa: eventCallback record %s " ERL_ERROR " %s\n",
|
||||
precord->name, ca_message(arg.status));
|
||||
} else {
|
||||
errlogPrintf("dbCa: eventCallback error %s\n",
|
||||
errlogPrintf("dbCa: eventCallback " ERL_ERROR " %s\n",
|
||||
ca_message(arg.status));
|
||||
}
|
||||
goto done;
|
||||
@@ -1029,10 +1087,10 @@ static void getAttribEventCallback(struct event_handler_args arg)
|
||||
if (arg.status != ECA_NORMAL) {
|
||||
dbCommon *precord = plink->precord;
|
||||
if (precord) {
|
||||
errlogPrintf("dbCa: getAttribEventCallback record %s error %s\n",
|
||||
errlogPrintf("dbCa: getAttribEventCallback record %s " ERL_ERROR " %s\n",
|
||||
precord->name, ca_message(arg.status));
|
||||
} else {
|
||||
errlogPrintf("dbCa: getAttribEventCallback error %s\n",
|
||||
errlogPrintf("dbCa: getAttribEventCallback " ERL_ERROR " %s\n",
|
||||
ca_message(arg.status));
|
||||
}
|
||||
epicsMutexUnlock(pca->lock);
|
||||
@@ -1058,6 +1116,7 @@ static void getAttribEventCallback(struct event_handler_args arg)
|
||||
|
||||
static void dbCaTask(void *arg)
|
||||
{
|
||||
epicsEventId requestSync = NULL;
|
||||
taskwdInsert(0, NULL, NULL);
|
||||
SEVCHK(ca_context_create(ca_enable_preemptive_callback),
|
||||
"dbCaTask calling ca_context_create");
|
||||
@@ -1078,13 +1137,20 @@ static void dbCaTask(void *arg)
|
||||
|
||||
epicsMutexMustLock(workListLock);
|
||||
if (!(pca = (caLink *)ellGet(&workList))){ /* Take off list head */
|
||||
if(requestSync) {
|
||||
/* dbCaSync() requires workListLock to be held here */
|
||||
epicsEventMustTrigger(requestSync);
|
||||
requestSync = NULL;
|
||||
}
|
||||
epicsMutexUnlock(workListLock);
|
||||
if (dbCaCtl == ctlExit) goto shutdown;
|
||||
break; /* workList is empty */
|
||||
}
|
||||
link_action = pca->link_action;
|
||||
if (link_action&CA_SYNC)
|
||||
epicsEventMustTrigger((epicsEventId)pca->userPvt); /* dbCaSync() requires workListLock to be held here */
|
||||
if (link_action&CA_SYNC) {
|
||||
assert(!requestSync);
|
||||
requestSync = pca->userPvt;
|
||||
}
|
||||
pca->link_action = 0;
|
||||
if (link_action & CA_CLEAR_CHANNEL) --removesOutstanding;
|
||||
epicsMutexUnlock(workListLock); /* Give back immediately */
|
||||
|
||||
@@ -48,8 +48,12 @@ DBCORE_API long dbCaPutLink(struct link *plink,short dbrType,
|
||||
extern struct ca_client_context * dbCaClientContext;
|
||||
|
||||
#ifdef EPICS_DBCA_PRIVATE_API
|
||||
/* Wait CA link work queue to become empty. eg. after from dbPut() to OUT */
|
||||
DBCORE_API void dbCaSync(void);
|
||||
DBCORE_API unsigned long dbCaGetUpdateCount(struct link *plink);
|
||||
/* Wait for the data update counter to reach the specified value. */
|
||||
DBCORE_API void testdbCaWaitForUpdateCount(DBLINK *plink, unsigned long cnt);
|
||||
/* Wait for CA link to become connected */
|
||||
DBCORE_API void testdbCaWaitForConnect(DBLINK *plink);
|
||||
#endif
|
||||
|
||||
/* These macros are for backwards compatibility */
|
||||
|
||||
@@ -98,7 +98,7 @@ static int dblsj_string(void *ctx, const unsigned char *val, size_t len) {
|
||||
char *pdest = parser->pdest;
|
||||
|
||||
if (parser->dbrType != DBF_STRING) {
|
||||
errlogPrintf("dbConvertJSON: dblsj_string dbrType error\n");
|
||||
errlogPrintf("dbConvertJSON: dblsj_string dbrType " ERL_ERROR "\n");
|
||||
return 0; /* Illegal */
|
||||
}
|
||||
|
||||
|
||||
@@ -886,6 +886,8 @@ unsigned int caEventMask
|
||||
if ( (dbChannelField(pevent->chan) == (void *)pField || pField==NULL) &&
|
||||
(caEventMask & pevent->select)) {
|
||||
db_field_log *pLog = db_create_event_log(pevent);
|
||||
if(pLog)
|
||||
pLog->mask = caEventMask & pevent->select;
|
||||
pLog = dbChannelRunPreChain(pevent->chan, pLog);
|
||||
if (pLog) db_queue_event_log(pevent, pLog);
|
||||
}
|
||||
|
||||
@@ -817,7 +817,7 @@ static void periodicTask(void *arg)
|
||||
epicsTimeAddSeconds(&next, delay);
|
||||
if (++overruns >= 10 &&
|
||||
epicsTimeDiffInSeconds(&now, &reported) > report_delay) {
|
||||
errlogPrintf("\ndbScan warning from '%s' scan thread:\n"
|
||||
errlogPrintf("\ndbScan " ERL_WARNING " from '%s' scan thread:\n"
|
||||
"\tScan processing averages %.3f seconds (%.3f .. %.3f).\n"
|
||||
"\tOver-runs have now happened %u times in a row.\n"
|
||||
"\tTo fix this, move some records to a slower scan rate.\n",
|
||||
|
||||
@@ -58,7 +58,7 @@ void camsgtask ( void *pParm )
|
||||
|
||||
epicsSocketConvertErrnoToString (
|
||||
sockErrBuf, sizeof ( sockErrBuf ) );
|
||||
errlogPrintf("CAS: FIONREAD error: %s\n",
|
||||
errlogPrintf("CAS: FIONREAD " ERL_ERROR ": %s\n",
|
||||
sockErrBuf);
|
||||
cas_send_bs_msg(client, TRUE);
|
||||
}
|
||||
|
||||
@@ -139,7 +139,7 @@ void cas_send_bs_msg ( struct client *pclient, int lock_needed )
|
||||
char sockErrBuf[64];
|
||||
epicsSocketConvertErrnoToString (
|
||||
sockErrBuf, sizeof ( sockErrBuf ) );
|
||||
errlogPrintf ("CAS: Socket shutdown error: %s\n",
|
||||
errlogPrintf ("CAS: Socket shutdown " ERL_ERROR ": %s\n",
|
||||
sockErrBuf );
|
||||
}
|
||||
}
|
||||
|
||||
@@ -86,7 +86,7 @@ static void req_server (void *pParm)
|
||||
char sockErrBuf[64];
|
||||
epicsSocketConvertErrnoToString (
|
||||
sockErrBuf, sizeof ( sockErrBuf ) );
|
||||
errlogPrintf("CAS: Client accept error: %s (%d)\n",
|
||||
errlogPrintf("CAS: Client accept " ERL_ERROR ": %s (%d)\n",
|
||||
sockErrBuf, (int)addLen );
|
||||
epicsThreadSleep(15.0);
|
||||
continue;
|
||||
@@ -131,7 +131,7 @@ int tryBind(SOCKET sock, const osiSockAddr* addr, const char *name)
|
||||
{
|
||||
epicsSocketConvertErrnoToString (
|
||||
sockErrBuf, sizeof ( sockErrBuf ) );
|
||||
errlogPrintf ( "CAS: %s bind error: %s\n",
|
||||
errlogPrintf ( "CAS: %s bind " ERL_ERROR ": %s\n",
|
||||
name, sockErrBuf );
|
||||
epicsThreadSuspendSelf ();
|
||||
}
|
||||
@@ -196,7 +196,7 @@ SOCKET* rsrv_grab_tcp(unsigned short *port)
|
||||
char sockErrBuf[64];
|
||||
epicsSocketConvertErrnoToString (
|
||||
sockErrBuf, sizeof ( sockErrBuf ) );
|
||||
errlogPrintf ( "CAS: getsockname error: %s\n",
|
||||
errlogPrintf ( "CAS: getsockname " ERL_ERROR ": %s\n",
|
||||
sockErrBuf );
|
||||
epicsThreadSuspendSelf ();
|
||||
ok = 0;
|
||||
@@ -576,12 +576,12 @@ void rsrv_init (void)
|
||||
|
||||
if ( sport != ca_server_port ) {
|
||||
ca_server_port = sport;
|
||||
errlogPrintf ( "cas warning: Configured TCP port was unavailable.\n");
|
||||
errlogPrintf ( "cas warning: Using dynamically assigned TCP port %hu,\n",
|
||||
errlogPrintf ( "cas " ERL_WARNING ": Configured TCP port was unavailable.\n");
|
||||
errlogPrintf ( "cas " ERL_WARNING ": Using dynamically assigned TCP port %hu,\n",
|
||||
ca_server_port );
|
||||
errlogPrintf ( "cas warning: but now two or more servers share the same UDP port.\n");
|
||||
errlogPrintf ( "cas warning: Depending on your IP kernel this server may not be\n" );
|
||||
errlogPrintf ( "cas warning: reachable with UDP unicast (a host's IP in EPICS_CA_ADDR_LIST)\n" );
|
||||
errlogPrintf ( "cas " ERL_WARNING ": but now two or more servers share the same UDP port.\n");
|
||||
errlogPrintf ( "cas " ERL_WARNING ": Depending on your IP kernel this server may not be\n" );
|
||||
errlogPrintf ( "cas " ERL_WARNING ": reachable with UDP unicast (a host's IP in EPICS_CA_ADDR_LIST)\n" );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -94,7 +94,7 @@ void rsrv_online_notify_task(void *pParm)
|
||||
|
||||
epicsSocketConvertErrorToString(sockErrBuf, sizeof(sockErrBuf), err);
|
||||
ipAddrToDottedIP(&pAddr->addr.ia, sockDipBuf, sizeof(sockDipBuf));
|
||||
errlogPrintf ( "CAS: CA beacon send to %s error: %s\n",
|
||||
errlogPrintf ( "CAS: CA beacon send to %s " ERL_ERROR ": %s\n",
|
||||
sockDipBuf, sockErrBuf);
|
||||
|
||||
lastError[i] = err;
|
||||
|
||||
@@ -20,7 +20,7 @@
|
||||
#include <chfPlugin.h>
|
||||
#include <recGbl.h>
|
||||
#include <epicsExit.h>
|
||||
#include <db_field_log.h>
|
||||
#include <dbAccess.h>
|
||||
#include <epicsExport.h>
|
||||
|
||||
typedef struct myStruct {
|
||||
@@ -81,8 +81,8 @@ static db_field_log* filter(void* pvt, dbChannel *chan, db_field_log *pfl) {
|
||||
status = dbFastGetConvertRoutine[pfl->field_type][DBR_DOUBLE]
|
||||
(localAddr.pfield, (void*) &val, &localAddr);
|
||||
if (!status) {
|
||||
send = 0;
|
||||
recGblCheckDeadband(&my->last, val, my->hyst, &send, 1);
|
||||
send = pfl->mask & ~(DBE_VALUE|DBE_LOG);
|
||||
recGblCheckDeadband(&my->last, val, my->hyst, &send, pfl->mask & (DBE_VALUE|DBE_LOG));
|
||||
if (send && my->mode == 1) {
|
||||
my->hyst = val * my->cval/100.;
|
||||
}
|
||||
|
||||
@@ -50,13 +50,6 @@ void dbTestIoc_registerRecordDeviceDriver(struct dbBase *);
|
||||
static epicsEventId waitEvent;
|
||||
static unsigned waitCounter;
|
||||
|
||||
static
|
||||
void waitForUpdateN(DBLINK *plink, unsigned long n)
|
||||
{
|
||||
while(dbCaGetUpdateCount(plink)<n)
|
||||
epicsThreadSleep(0.01);
|
||||
}
|
||||
|
||||
static
|
||||
void putLink(DBLINK *plink, short dbr, const void*buf, long nReq)
|
||||
{
|
||||
@@ -133,14 +126,14 @@ static void testNativeLink(void)
|
||||
|
||||
testOk1(psrclnk->type==CA_LINK);
|
||||
|
||||
waitForUpdateN(psrclnk, 1);
|
||||
testdbCaWaitForUpdateCount(psrclnk, 1);
|
||||
|
||||
dbScanLock((dbCommon*)ptarg);
|
||||
ptarg->val = 42;
|
||||
db_post_events(ptarg, &ptarg->val, DBE_VALUE|DBE_ALARM|DBE_ARCHIVE);
|
||||
dbScanUnlock((dbCommon*)ptarg);
|
||||
|
||||
waitForUpdateN(psrclnk, 2);
|
||||
testdbCaWaitForUpdateCount(psrclnk, 2);
|
||||
|
||||
dbScanLock((dbCommon*)psrc);
|
||||
/* local CA_LINK connects immediately */
|
||||
@@ -218,14 +211,14 @@ static void testStringLink(void)
|
||||
|
||||
testOk1(psrclnk->type==CA_LINK);
|
||||
|
||||
waitForUpdateN(psrclnk, 1);
|
||||
testdbCaWaitForUpdateCount(psrclnk, 1);
|
||||
|
||||
dbScanLock((dbCommon*)ptarg);
|
||||
strcpy(ptarg->desc, "hello");
|
||||
db_post_events(ptarg, &ptarg->desc, DBE_VALUE|DBE_ALARM|DBE_ARCHIVE);
|
||||
dbScanUnlock((dbCommon*)ptarg);
|
||||
|
||||
waitForUpdateN(psrclnk, 2);
|
||||
testdbCaWaitForUpdateCount(psrclnk, 2);
|
||||
|
||||
dbScanLock((dbCommon*)psrc);
|
||||
/* local CA_LINK connects immediately */
|
||||
@@ -400,7 +393,7 @@ static void testArrayLink(unsigned nsrc, unsigned ntarg)
|
||||
testIocInitOk();
|
||||
eltc(1);
|
||||
|
||||
waitForUpdateN(psrclnk, 1);
|
||||
testdbCaWaitForUpdateCount(psrclnk, 1);
|
||||
|
||||
bufsrc = psrc->bptr;
|
||||
buftarg= ptarg->bptr;
|
||||
@@ -421,7 +414,7 @@ static void testArrayLink(unsigned nsrc, unsigned ntarg)
|
||||
db_post_events(ptarg, &ptarg->val, DBE_VALUE|DBE_ALARM|DBE_ARCHIVE);
|
||||
dbScanUnlock((dbCommon*)ptarg);
|
||||
|
||||
waitForUpdateN(psrclnk, 2);
|
||||
testdbCaWaitForUpdateCount(psrclnk, 2);
|
||||
|
||||
dbScanLock((dbCommon*)psrc);
|
||||
testDiag("fetch source.INP into source.BPTR");
|
||||
|
||||
@@ -13,6 +13,7 @@
|
||||
|
||||
#include <string.h>
|
||||
|
||||
#include "dbAccess.h"
|
||||
#include "dbStaticLib.h"
|
||||
#include "dbAccessDefs.h"
|
||||
#include "db_field_log.h"
|
||||
@@ -46,6 +47,7 @@ static void fl_setup(dbChannel *chan, db_field_log *pfl) {
|
||||
pfl->stat = prec->stat;
|
||||
pfl->sevr = prec->sevr;
|
||||
pfl->time = prec->time;
|
||||
pfl->mask = DBE_VALUE;
|
||||
pfl->field_type = dbChannelFieldType(chan);
|
||||
pfl->field_size = dbChannelFieldSize(chan);
|
||||
pfl->no_elements = dbChannelElements(chan);
|
||||
|
||||
@@ -8,6 +8,8 @@
|
||||
|
||||
#include <string.h>
|
||||
|
||||
#define EPICS_DBCA_PRIVATE_API
|
||||
|
||||
#include "dbAccess.h"
|
||||
#include "dbStaticLib.h"
|
||||
#include "dbTest.h"
|
||||
@@ -116,6 +118,8 @@ void checkAsyncOutput(const char *rec, dbCommon *async)
|
||||
strcpy(proc, rec);
|
||||
strcat(proc, ".PROC");
|
||||
|
||||
testdbCaWaitForConnect(dbGetDevLink(testdbRecordPtr(rec)));
|
||||
|
||||
testdbPutFieldOk(proc, DBF_CHAR, 1);
|
||||
|
||||
epicsEventWait(asyncEvent);
|
||||
|
||||
@@ -33,15 +33,16 @@
|
||||
#include "epicsExport.h"
|
||||
|
||||
static
|
||||
void testmbbioFields(const char* rec, unsigned int value)
|
||||
void testmbbioFields(char dir, unsigned n, unsigned int value)
|
||||
{
|
||||
char field[40];
|
||||
unsigned int i;
|
||||
|
||||
testdbGetFieldEqual(rec, DBF_ULONG, value);
|
||||
sprintf(field,"d%c%d", dir, n);
|
||||
testdbGetFieldEqual(field, DBF_ULONG, value);
|
||||
for (i=0; i < 32; i++)
|
||||
{
|
||||
sprintf(field,"%s.B%X", rec, i);
|
||||
sprintf(field,"d%c%d.B%X", dir, n, i);
|
||||
testdbGetFieldEqual(field, DBF_ULONG, (value>>i)&1);
|
||||
}
|
||||
}
|
||||
@@ -49,16 +50,14 @@ void testmbbioFields(const char* rec, unsigned int value)
|
||||
static
|
||||
void testmbbioRecords(unsigned int count, unsigned int value)
|
||||
{
|
||||
char rec[40];
|
||||
unsigned int i;
|
||||
|
||||
for (i = 1; i <= count; i++)
|
||||
{
|
||||
sprintf(rec, "do%d", i);
|
||||
testDiag(" ### %s ###", rec);
|
||||
testmbbioFields(rec, value);
|
||||
sprintf(rec, "di%d", i);
|
||||
testmbbioFields(rec, value);
|
||||
testDiag(" ### do%d ###", i);
|
||||
testmbbioFields('o', i, value);
|
||||
testDiag(" ### di%d ###", i);
|
||||
testmbbioFields('i', i, value);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -172,9 +172,12 @@ static
|
||||
void testLinkSevr(void)
|
||||
{
|
||||
dbChannel *chan;
|
||||
|
||||
startRegressTestIoc("regressLinkSevr.db");
|
||||
dbCaSync(); /* wait for CA links to connect */
|
||||
dbCaSync(); /* wait for initial update */
|
||||
|
||||
/* wait for CA links to connect and receive an initial update */
|
||||
testdbCaWaitForUpdateCount(dbGetDevLink(testdbRecordPtr("si2")), 1);
|
||||
testdbCaWaitForUpdateCount(dbGetDevLink(testdbRecordPtr("li2")), 1);
|
||||
|
||||
chan = dbChannelCreate("ai.SEVR");
|
||||
if(!chan)
|
||||
|
||||
@@ -8,8 +8,11 @@
|
||||
|
||||
#include <string.h>
|
||||
|
||||
#define EPICS_DBCA_PRIVATE_API
|
||||
|
||||
#include "dbAccess.h"
|
||||
#include "dbStaticLib.h"
|
||||
#include "dbCa.h"
|
||||
#include "dbTest.h"
|
||||
#include "dbUnitTest.h"
|
||||
#include "epicsThread.h"
|
||||
@@ -60,14 +63,17 @@ void testGroup0(void)
|
||||
|
||||
testDiag("============ Starting %s ============", EPICS_FUNCTION);
|
||||
|
||||
testdbPutFieldOk("source", DBR_LONG, 1);
|
||||
/* The above put sends CA monitors to all of the CA links, but
|
||||
* doesn't trigger record processing (the links are not CP/CPP).
|
||||
* How could we wait until all of those monitors have arrived,
|
||||
* instead of just waiting for an arbitrary time period?
|
||||
*/
|
||||
epicsThreadSleep(1.0); /* FIXME: Wait here? */
|
||||
for (rec = records; *rec; rec++) {
|
||||
DBLINK* plink = dbGetDevLink(testdbRecordPtr(*rec));
|
||||
if(plink->type==CA_LINK)
|
||||
testdbCaWaitForUpdateCount(plink, 1);
|
||||
}
|
||||
|
||||
testdbPutFieldOk("source", DBR_LONG, 1);
|
||||
for (rec = records; *rec; rec++) {
|
||||
DBLINK* plink = dbGetDevLink(testdbRecordPtr(*rec));
|
||||
if(plink->type==CA_LINK)
|
||||
testdbCaWaitForUpdateCount(plink, 2);
|
||||
if (strncmp(*rec, "lsi0", 4) != 0)
|
||||
testdbGetFieldEqual(*rec, DBR_LONG, 0);
|
||||
checkDtyp(*rec);
|
||||
@@ -76,8 +82,10 @@ void testGroup0(void)
|
||||
}
|
||||
|
||||
testdbPutFieldOk("source", DBR_LONG, 0);
|
||||
epicsThreadSleep(1.0); /* FIXME: Wait here as above */
|
||||
for (rec = records; *rec; rec++) {
|
||||
DBLINK* plink = dbGetDevLink(testdbRecordPtr(*rec));
|
||||
if(plink->type==CA_LINK)
|
||||
testdbCaWaitForUpdateCount(plink, 3);
|
||||
doProcess(*rec);
|
||||
testdbGetFieldEqual(*rec, DBR_LONG, 0);
|
||||
}
|
||||
|
||||
@@ -18,6 +18,9 @@
|
||||
* Extensive tests so far only with qemu.
|
||||
*/
|
||||
|
||||
/* trigger sys/syslog.h to emit prioritynames[] */
|
||||
#define SYSLOG_NAMES
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
@@ -30,6 +33,7 @@
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/syslog.h>
|
||||
#include <netinet/in.h>
|
||||
#include <arpa/inet.h>
|
||||
#include <assert.h>
|
||||
@@ -93,7 +97,7 @@ epicsEventId dhcpDone;
|
||||
* may provide by dhcp/bootp
|
||||
* or environments from the "BIOS" like u-boot, motboot etc.
|
||||
*/
|
||||
char rtemsInit_NTP_server_ip[16] = "10.0.5.1";
|
||||
char rtemsInit_NTP_server_ip[16] = "";
|
||||
char bootp_server_name_init[128] = "1001.1001@10.0.5.1:/epics";
|
||||
char bootp_boot_file_name_init[128] = "/epics/myExample/bin/RTEMS-beatnik/myExample.boot";
|
||||
char bootp_cmdline_init[128] = "/epics/myExample/iocBoot/iocmyExample/st.cmd";
|
||||
@@ -633,6 +637,42 @@ static void zonesetCallFunc(const iocshArgBuf *args)
|
||||
zoneset(args[0].sval);
|
||||
}
|
||||
|
||||
#ifndef RTEMS_LEGACY_STACK
|
||||
static int bsd_log_to_erl(int level, const char *fmt, va_list ap)
|
||||
{
|
||||
return errlogVprintf(fmt, ap);
|
||||
}
|
||||
#endif // RTEMS_LEGACY_STACK
|
||||
|
||||
static void setlogmaskCallFunc(const iocshArgBuf *args)
|
||||
{
|
||||
const char* name = args[0].sval;
|
||||
const CODE* cur;
|
||||
if(!name) {
|
||||
printf("Usage: setlogmask <level>\n"
|
||||
"\n"
|
||||
" Level names:\n");
|
||||
for(cur = prioritynames; cur->c_name; cur++) {
|
||||
printf(" %s\n", cur->c_name);
|
||||
}
|
||||
} else {
|
||||
for(cur = prioritynames; cur->c_name; cur++) {
|
||||
if(strcmp(name, cur->c_name)!=0)
|
||||
continue;
|
||||
|
||||
(void)setlogmask(LOG_MASK(cur->c_val));
|
||||
#ifndef RTEMS_LEGACY_STACK
|
||||
rtems_bsd_setlogpriority(name);
|
||||
#endif
|
||||
return;
|
||||
}
|
||||
printf("Error: unknown log level.\n");
|
||||
}
|
||||
}
|
||||
static const iocshArg setlogmaskArg0 = {"level name", iocshArgString};
|
||||
static const iocshArg * const setlogmaskArgs[1] = {&setlogmaskArg0};
|
||||
static const iocshFuncDef setlogmaskFuncDef = {"setlogmask",1,setlogmaskArgs,
|
||||
"Set syslog() threshold level"};
|
||||
|
||||
/*
|
||||
* Register RTEMS-specific commands
|
||||
@@ -646,6 +686,7 @@ static void iocshRegisterRTEMS (void)
|
||||
#endif
|
||||
iocshRegister(&zonesetFuncDef, &zonesetCallFunc);
|
||||
iocshRegister(&rtshellFuncDef, &rtshellCallFunc);
|
||||
iocshRegister(&setlogmaskFuncDef, &setlogmaskCallFunc);
|
||||
#if __RTEMS_MAJOR__ > 4
|
||||
rtems_shell_init_environment();
|
||||
#endif
|
||||
@@ -685,89 +726,76 @@ exitHandler(void)
|
||||
}
|
||||
|
||||
#ifndef RTEMS_LEGACY_STACK
|
||||
static char* getPrimaryNetworkInterface(void)
|
||||
{
|
||||
// lookup available network interfaces
|
||||
char ifnamebuf[IF_NAMESIZE];
|
||||
char *ifname;
|
||||
// get primary network interface
|
||||
ifname = if_indextoname(1, &ifnamebuf[0]);
|
||||
if (ifname == NULL) return (NULL);
|
||||
printf("\n***** Primary Network interface : %s *****\n", ifname);
|
||||
return (ifname);
|
||||
}
|
||||
|
||||
static void
|
||||
dhcpcd_hook_handler(rtems_dhcpcd_hook *hook, char *const *env)
|
||||
{
|
||||
int bound = 0;
|
||||
char iName[16];
|
||||
char *name;
|
||||
char *value;
|
||||
char * env_position;
|
||||
|
||||
(void)hook;
|
||||
char interface[16] = "?";
|
||||
char reason[16] = "?";
|
||||
char new_host_name[32] = "RTEMShost";
|
||||
struct dhcp_vars_t {
|
||||
const char * const name;
|
||||
char* var;
|
||||
size_t varsize;
|
||||
} dhcp_vars[] = {
|
||||
#define DEFVAR(N) { #N, N, sizeof(N) }
|
||||
DEFVAR(interface),
|
||||
DEFVAR(reason),
|
||||
DEFVAR(new_host_name),
|
||||
#undef DEFVAR
|
||||
#define DEFVAR(N, V) { N, V, sizeof(V) }
|
||||
DEFVAR("new_ntp_servers", rtemsInit_NTP_server_ip),
|
||||
DEFVAR("new_tftp_server_name", bootp_server_name_init),
|
||||
DEFVAR("new_bootfile_name", bootp_boot_file_name_init),
|
||||
DEFVAR("new_rtems_cmdline", bootp_cmdline_init),
|
||||
#undef DEFVAR
|
||||
{NULL}
|
||||
};
|
||||
(void)hook;
|
||||
|
||||
char ifnamebuf[IF_NAMESIZE];
|
||||
sprintf(ifnamebuf, "%s", getPrimaryNetworkInterface());
|
||||
|
||||
while (*env != NULL) {
|
||||
char const * interface = "interface";
|
||||
char const * reason = "reason";
|
||||
char const * bound_str = "BOUND";
|
||||
printf("\n");
|
||||
for (;NULL != *env;++env) {
|
||||
printf("dhcpcd ---> '%s'\n", *env);
|
||||
|
||||
name = strtok_r(*env,"=", &env_position);
|
||||
value = strtok_r(NULL,"=", &env_position);
|
||||
printf("all out ---> %s = %s\n", name, value);
|
||||
for(const struct dhcp_vars_t* var = dhcp_vars; var->name; var++) {
|
||||
size_t namelen = strlen(var->name);
|
||||
|
||||
if (!strncmp(name, interface, strlen(interface)) &&
|
||||
!strcmp(value, ifnamebuf)) {
|
||||
snprintf(iName, sizeof(iName), "%s", value);
|
||||
}
|
||||
// assume "KEY=value" with no whitespace around '='
|
||||
if(strncmp(*env, var->name, namelen)!=0 || (*env)[namelen]!='=')
|
||||
continue;
|
||||
|
||||
if (!strncmp(name, reason, strlen(reason)) &&
|
||||
!strncmp(value, bound_str, strlen(bound_str))) {
|
||||
printf ("Interface %s bounded\n", iName);
|
||||
bound = 1;
|
||||
const char* value = *env + namelen+1;
|
||||
size_t valuelen = strlen(value);
|
||||
|
||||
// require ordering of keys:
|
||||
// interface=
|
||||
// reason=
|
||||
// all others...
|
||||
if(var->var!=reason && var->var!=interface && !bound) {
|
||||
// ignore others if !BOUND
|
||||
|
||||
} else if(valuelen >= var->varsize) {
|
||||
printf(" Not enough space for value string. Expand buffer and recompile.\n");
|
||||
|
||||
} else {
|
||||
memcpy(var->var, value, valuelen);
|
||||
var->var[valuelen] = '\0';
|
||||
printf(" '%s' = '%s'\n", var->name, var->var);
|
||||
|
||||
if(var->var==reason && strcmp(reason, "BOUND")==0) {
|
||||
printf(" is BOUND\n");
|
||||
bound = 1;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
if (bound) {
|
||||
// as there is no ntp-support in rtems-libbsd, we call our own client
|
||||
char const * new_ntp_servers = "new_ntp_servers";
|
||||
char const * new_host_name = "new_host_name";
|
||||
char const * new_tftp_server_name = "new_tftp_server_name";
|
||||
|
||||
if (!strncmp(name, new_ntp_servers, strlen(new_ntp_servers)))
|
||||
snprintf(rtemsInit_NTP_server_ip,
|
||||
sizeof(rtemsInit_NTP_server_ip),
|
||||
"%s", value);
|
||||
|
||||
if (!strncmp(name, new_host_name, strlen(new_host_name)))
|
||||
sethostname (value, strlen (value));
|
||||
|
||||
if (!strncmp(name, new_tftp_server_name, strlen(new_tftp_server_name))){
|
||||
snprintf(rtems_bsdnet_bootp_server_name,
|
||||
sizeof(bootp_server_name_init),
|
||||
"%s", value);
|
||||
printf(" rtems_bsdnet_bootp_server_name : %s\n", rtems_bsdnet_bootp_server_name);
|
||||
}
|
||||
if(!strncmp(name, "new_bootfile_name", 20)){
|
||||
snprintf(rtems_bsdnet_bootp_boot_file_name,
|
||||
sizeof(bootp_boot_file_name_init),
|
||||
"%s", value);
|
||||
printf(" rtems_bsdnet_bootp_boot_file_name : %s\n", rtems_bsdnet_bootp_boot_file_name);
|
||||
}
|
||||
if(!strncmp(name, "new_rtems_cmdline", 20)){
|
||||
snprintf(rtems_bsdnet_bootp_cmdline,
|
||||
sizeof(bootp_cmdline_init),
|
||||
"%s", value);
|
||||
printf(" rtems_bsdnet_bootp_cmdline : %s\n", rtems_bsdnet_bootp_cmdline);
|
||||
}
|
||||
}
|
||||
++env;
|
||||
}
|
||||
if (bound)
|
||||
|
||||
if(bound) {
|
||||
sethostname (new_host_name, strlen (new_host_name));
|
||||
epicsEventSignal(dhcpDone);
|
||||
printf("dhcpd BOUND\n");
|
||||
}
|
||||
}
|
||||
|
||||
static rtems_dhcpcd_hook dhcpcd_hook = {
|
||||
@@ -816,10 +844,10 @@ default_network_dhcpcd(void)
|
||||
static const char fhi_cfg[] =
|
||||
"nodhcp6\n"
|
||||
"ipv4only\n"
|
||||
"option ntp_servers\n"
|
||||
"option ntp-servers\n"
|
||||
"option rtems_cmdline\n"
|
||||
"option tftp_server_name\n"
|
||||
"option bootfile_name\n"
|
||||
"option tftp-server-name\n"
|
||||
"option bootfile-name\n"
|
||||
"define 129 string rtems_cmdline\n"
|
||||
"timeout 0";
|
||||
|
||||
@@ -975,12 +1003,19 @@ POSIX_Init ( void *argument __attribute__((unused)))
|
||||
rtems_get_version_string());
|
||||
|
||||
#ifndef RTEMS_LEGACY_STACK
|
||||
#if defined(QEMU_FIXUPS) && defined(__i386__)
|
||||
// glorious hack to stub out useless EEPROM check
|
||||
// which takes sooooo longggg w/ QEMU
|
||||
// Writes a 'ret' instruction to immediatly return to the caller
|
||||
extern void _bsd_e1000_validate_nvm_checksum(void);
|
||||
*(char*)&_bsd_e1000_validate_nvm_checksum = 0xc3;
|
||||
#endif
|
||||
/*
|
||||
* Start network (libbsd)
|
||||
*
|
||||
* start qemu like this
|
||||
* qemu-system-i386 -m 64 -no-reboot -serial stdio -display none \
|
||||
* -net nic,model=rtl8139,macaddr=0e:b0:ba:5e:ba:11 -net user,restrict=yes \
|
||||
* -net nic,model=e1000 -net user,restrict=yes \
|
||||
* -append "--video=off --console=/dev/com1" -kernel libComTestHarness
|
||||
*/
|
||||
printf("\n***** Initializing network (libbsd, dhcpcd) *****\n");
|
||||
@@ -990,9 +1025,6 @@ POSIX_Init ( void *argument __attribute__((unused)))
|
||||
/* Let other tasks run to complete background work */
|
||||
default_network_set_self_prio(RTEMS_MAXIMUM_PRIORITY - 1U);
|
||||
|
||||
/* suppress all output from bsd network initialization */
|
||||
rtems_bsd_set_vprintf_handler(rtems_bsd_vprintf_handler_mute);
|
||||
|
||||
sc = rtems_bsd_initialize();
|
||||
assert(sc == RTEMS_SUCCESSFUL);
|
||||
|
||||
@@ -1042,7 +1074,9 @@ POSIX_Init ( void *argument __attribute__((unused)))
|
||||
/* until now there is no NTP support in libbsd -> Sebastian Huber ... */
|
||||
printf("\n***** Until now no NTP support in RTEMS 5 with rtems-libbsd *****\n");
|
||||
printf("\n***** Ask ntp server once... *****\n");
|
||||
if (epicsNtpGetTime(rtemsInit_NTP_server_ip, &now) < 0) {
|
||||
if (rtemsInit_NTP_server_ip[0]=='\0') {
|
||||
printf ("***** No NTP server ...\n");
|
||||
} else if (epicsNtpGetTime(rtemsInit_NTP_server_ip, &now) < 0) {
|
||||
printf ("***** Can't get time from ntp ...\n");
|
||||
} else {
|
||||
if (clock_settime(CLOCK_REALTIME, &now) < 0){
|
||||
@@ -1077,9 +1111,6 @@ POSIX_Init ( void *argument __attribute__((unused)))
|
||||
rtems_bsdnet_synchronize_ntp (0, 0);
|
||||
#endif // not RTEMS_LEGACY_STACK
|
||||
|
||||
/* show messages from network after initialization ? good idea? */
|
||||
//rtems_bsd_set_vprintf_handler(bsd_vprintf_handler_old);
|
||||
|
||||
printf("\n***** Setting up file system *****\n");
|
||||
initialize_remote_filesystem(argv, initialize_local_filesystem(argv));
|
||||
fixup_hosts();
|
||||
@@ -1124,6 +1155,12 @@ POSIX_Init ( void *argument __attribute__((unused)))
|
||||
errlogFlush();
|
||||
printf ("***** Starting EPICS application *****\n");
|
||||
|
||||
|
||||
#ifndef RTEMS_LEGACY_STACK
|
||||
// switch OS to async logging
|
||||
rtems_bsd_set_vprintf_handler(bsd_log_to_erl);
|
||||
#endif
|
||||
|
||||
#if 0
|
||||
// Start an rtems shell before main, for debugging RTEMS system issues
|
||||
rtems_shell_init("SHLL", RTEMS_MINIMUM_STACK_SIZE * 4,
|
||||
|
||||
@@ -32,7 +32,7 @@
|
||||
* Ticket URL: <http://devel.rtems.org/ticket/2375#comment:23>
|
||||
*/
|
||||
|
||||
#if RTEMS_VERSION_INT<=VERSION_INT(4,10,0,0)
|
||||
#if RTEMS_VERSION_INT<VERSION_INT(4,11,0,0)
|
||||
extern void rtems_bsdnet_loopattach();
|
||||
static struct rtems_bsdnet_ifconfig loopback_config = {
|
||||
"lo0", /* name */
|
||||
@@ -58,7 +58,7 @@ rtems_ne2kpci_driver_attach (struct rtems_bsdnet_ifconfig *config, int attach);
|
||||
static struct rtems_bsdnet_ifconfig ne2k_driver_config = {
|
||||
"ne2", /* name */
|
||||
rtems_ne2kpci_driver_attach, /* attach function */
|
||||
#if RTEMS_VERSION_INT<=VERSION_INT(4,10,0,0)
|
||||
#if RTEMS_VERSION_INT<VERSION_INT(4,11,0,0)
|
||||
&loopback_config, /* link to next interface */
|
||||
#else
|
||||
NULL,
|
||||
@@ -96,7 +96,7 @@ static struct rtems_bsdnet_ifconfig e3c509_driver_config = {
|
||||
static struct rtems_bsdnet_ifconfig netdriver_config = {
|
||||
RTEMS_BSP_NETWORK_DRIVER_NAME, /* name */
|
||||
RTEMS_BSP_NETWORK_DRIVER_ATTACH, /* attach function */
|
||||
#if RTEMS_VERSION_INT<=VERSION_INT(4,10,0,0)
|
||||
#if RTEMS_VERSION_INT<VERSION_INT(4,11,0,0)
|
||||
&loopback_config, /* link to next interface */
|
||||
#endif
|
||||
};
|
||||
|
||||
@@ -21,15 +21,27 @@
|
||||
#include "libComAPI.h"
|
||||
#include "epicsAssert.h"
|
||||
|
||||
class LIBCOM_API SingletonUntyped {
|
||||
class SingletonUntyped {
|
||||
public:
|
||||
SingletonUntyped ();
|
||||
~SingletonUntyped ();
|
||||
SingletonUntyped () :_pInstance ( 0 ), _refCount ( 0 ) {}
|
||||
# if 0
|
||||
~SingletonUntyped () {
|
||||
// we don't assert fail on non-zero _refCount
|
||||
// and or non nill _pInstance here because this
|
||||
// is designed to tolerate situations where
|
||||
// file scope epicsSingleton objects (which
|
||||
// theoretically don't have storage lifespan
|
||||
// issues) are deleted in a non-deterministic
|
||||
// order
|
||||
assert ( _refCount == 0 );
|
||||
assert ( _pInstance == 0 );
|
||||
}
|
||||
# endif
|
||||
typedef void * ( * PBuild ) ();
|
||||
void incrRefCount ( PBuild );
|
||||
LIBCOM_API void incrRefCount ( PBuild );
|
||||
typedef void ( * PDestroy ) ( void * );
|
||||
void decrRefCount ( PDestroy );
|
||||
void * pInstance () const;
|
||||
LIBCOM_API void decrRefCount ( PDestroy );
|
||||
inline void * pInstance () const { return _pInstance; }
|
||||
private:
|
||||
void * _pInstance;
|
||||
std :: size_t _refCount;
|
||||
@@ -46,18 +58,56 @@ class epicsSingleton {
|
||||
public:
|
||||
class reference {
|
||||
public:
|
||||
reference ( epicsSingleton & );
|
||||
reference ( const reference & );
|
||||
~reference ();
|
||||
reference ( epicsSingleton & es)
|
||||
:_pSingleton ( & es )
|
||||
{
|
||||
es._singletonUntyped.
|
||||
incrRefCount ( & epicsSingleton < TYPE > :: _build );
|
||||
}
|
||||
reference ( const reference & ref)
|
||||
:_pSingleton ( ref._pSingleton )
|
||||
{
|
||||
assert ( _pSingleton );
|
||||
_pSingleton->_singletonUntyped.
|
||||
incrRefCount ( & epicsSingleton < TYPE > :: _build );
|
||||
}
|
||||
~reference () {
|
||||
assert ( _pSingleton );
|
||||
_pSingleton->_singletonUntyped.
|
||||
decrRefCount ( & epicsSingleton < TYPE > :: _destroy );
|
||||
}
|
||||
// this somewhat convoluted reference of the return
|
||||
// type ref through the epicsSingleton template is
|
||||
// required for the archaic Tornado gnu compiler
|
||||
typename epicsSingleton < TYPE > :: reference &
|
||||
operator = ( const reference & );
|
||||
TYPE * operator -> ();
|
||||
const TYPE * operator -> () const;
|
||||
TYPE & operator * ();
|
||||
const TYPE & operator * () const;
|
||||
operator = ( const reference & ref) {
|
||||
if ( _pSingleton != ref._pSingleton ) {
|
||||
assert ( _pSingleton );
|
||||
_pSingleton->_singletonUntyped.
|
||||
decrRefCount ( epicsSingleton < TYPE > :: _destroy );
|
||||
_pSingleton = ref._pSingleton;
|
||||
assert ( _pSingleton );
|
||||
_pSingleton->_singletonUntyped.
|
||||
incrRefCount ( & epicsSingleton < TYPE > :: _build );
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
TYPE * operator -> () {
|
||||
assert ( _pSingleton );
|
||||
return reinterpret_cast < TYPE * >
|
||||
( _pSingleton->_singletonUntyped.pInstance () );
|
||||
}
|
||||
const TYPE * operator -> () const {
|
||||
assert ( _pSingleton );
|
||||
return reinterpret_cast < const TYPE * >
|
||||
( _pSingleton->_singletonUntyped.pInstance () );
|
||||
}
|
||||
TYPE & operator * () {
|
||||
return * this->operator -> ();
|
||||
}
|
||||
const TYPE & operator * () const {
|
||||
return * this->operator -> ();
|
||||
}
|
||||
private:
|
||||
epicsSingleton * _pSingleton;
|
||||
};
|
||||
@@ -65,152 +115,25 @@ public:
|
||||
epicsSingleton () {}
|
||||
// mutex lock/unlock pair overhead incurred
|
||||
// when either of these are called
|
||||
reference getReference ();
|
||||
const reference getReference () const;
|
||||
reference getReference () {
|
||||
return reference ( * this );
|
||||
}
|
||||
const reference getReference () const {
|
||||
epicsSingleton < TYPE > * pConstCastAway =
|
||||
const_cast < epicsSingleton < TYPE > * > ( this );
|
||||
return pConstCastAway->getReference ();
|
||||
}
|
||||
private:
|
||||
SingletonUntyped _singletonUntyped;
|
||||
static void * _build ();
|
||||
static void _destroy ( void * );
|
||||
static void * _build () { return new TYPE (); }
|
||||
static void _destroy ( void * pDestroyTypeless) {
|
||||
TYPE * pDestroy =
|
||||
reinterpret_cast < TYPE * > ( pDestroyTypeless );
|
||||
delete pDestroy;
|
||||
}
|
||||
epicsSingleton ( const epicsSingleton & );
|
||||
epicsSingleton & operator = ( const epicsSingleton & );
|
||||
};
|
||||
|
||||
template < class TYPE >
|
||||
inline epicsSingleton < TYPE > :: reference ::
|
||||
reference ( epicsSingleton & es ):
|
||||
_pSingleton ( & es )
|
||||
{
|
||||
es._singletonUntyped.
|
||||
incrRefCount ( & epicsSingleton < TYPE > :: _build );
|
||||
}
|
||||
|
||||
template < class TYPE >
|
||||
inline epicsSingleton < TYPE > :: reference ::
|
||||
reference ( const reference & ref ) :
|
||||
_pSingleton ( ref._pSingleton )
|
||||
{
|
||||
assert ( _pSingleton );
|
||||
_pSingleton->_singletonUntyped.
|
||||
incrRefCount ( & epicsSingleton < TYPE > :: _build );
|
||||
}
|
||||
|
||||
template < class TYPE >
|
||||
inline epicsSingleton < TYPE > :: reference ::
|
||||
~reference ()
|
||||
{
|
||||
assert ( _pSingleton );
|
||||
_pSingleton->_singletonUntyped.
|
||||
decrRefCount ( & epicsSingleton < TYPE > :: _destroy );
|
||||
}
|
||||
|
||||
template < class TYPE >
|
||||
typename epicsSingleton < TYPE > :: reference &
|
||||
epicsSingleton < TYPE > :: reference ::
|
||||
operator = ( const reference & ref )
|
||||
{
|
||||
if ( _pSingleton != ref._pSingleton ) {
|
||||
assert ( _pSingleton );
|
||||
_pSingleton->_singletonUntyped.
|
||||
decrRefCount ( epicsSingleton < TYPE > :: _destroy );
|
||||
_pSingleton = ref._pSingleton;
|
||||
assert ( _pSingleton );
|
||||
_pSingleton->_singletonUntyped.
|
||||
incrRefCount ( & epicsSingleton < TYPE > :: _build );
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
|
||||
template < class TYPE >
|
||||
inline TYPE *
|
||||
epicsSingleton < TYPE > :: reference ::
|
||||
operator -> ()
|
||||
{
|
||||
assert ( _pSingleton );
|
||||
return reinterpret_cast < TYPE * >
|
||||
( _pSingleton->_singletonUntyped.pInstance () );
|
||||
}
|
||||
|
||||
template < class TYPE >
|
||||
inline const TYPE *
|
||||
epicsSingleton < TYPE > :: reference ::
|
||||
operator -> () const
|
||||
{
|
||||
assert ( _pSingleton );
|
||||
return reinterpret_cast < const TYPE * >
|
||||
( _pSingleton->_singletonUntyped.pInstance () );
|
||||
}
|
||||
|
||||
template < class TYPE >
|
||||
inline TYPE &
|
||||
epicsSingleton < TYPE > :: reference ::
|
||||
operator * ()
|
||||
{
|
||||
return * this->operator -> ();
|
||||
}
|
||||
|
||||
template < class TYPE >
|
||||
inline const TYPE &
|
||||
epicsSingleton < TYPE > :: reference ::
|
||||
operator * () const
|
||||
{
|
||||
return * this->operator -> ();
|
||||
}
|
||||
|
||||
inline SingletonUntyped :: SingletonUntyped () :
|
||||
_pInstance ( 0 ), _refCount ( 0 )
|
||||
{
|
||||
}
|
||||
|
||||
inline void * SingletonUntyped :: pInstance () const
|
||||
{
|
||||
return _pInstance;
|
||||
}
|
||||
|
||||
inline SingletonUntyped :: ~SingletonUntyped ()
|
||||
{
|
||||
// we don't assert fail on non-zero _refCount
|
||||
// and or non nill _pInstance here because this
|
||||
// is designed to tolerate situations where
|
||||
// file scope epicsSingleton objects (which
|
||||
// theoretically don't have storage lifespan
|
||||
// issues) are deleted in a non-deterministic
|
||||
// order
|
||||
# if 0
|
||||
assert ( _refCount == 0 );
|
||||
assert ( _pInstance == 0 );
|
||||
# endif
|
||||
}
|
||||
|
||||
template < class TYPE >
|
||||
void * epicsSingleton < TYPE > :: _build ()
|
||||
{
|
||||
return new TYPE ();
|
||||
}
|
||||
|
||||
template < class TYPE >
|
||||
void epicsSingleton < TYPE > ::
|
||||
_destroy ( void * pDestroyTypeless )
|
||||
{
|
||||
TYPE * pDestroy =
|
||||
reinterpret_cast < TYPE * > ( pDestroyTypeless );
|
||||
delete pDestroy;
|
||||
}
|
||||
|
||||
template < class TYPE >
|
||||
inline typename epicsSingleton < TYPE > :: reference
|
||||
epicsSingleton < TYPE > :: getReference ()
|
||||
{
|
||||
return reference ( * this );
|
||||
}
|
||||
|
||||
template < class TYPE >
|
||||
inline const typename epicsSingleton < TYPE > :: reference
|
||||
epicsSingleton < TYPE > :: getReference () const
|
||||
{
|
||||
epicsSingleton < TYPE > * pConstCastAway =
|
||||
const_cast < epicsSingleton < TYPE > * > ( this );
|
||||
return pConstCastAway->getReference ();
|
||||
}
|
||||
|
||||
#endif // epicsSingleton_h
|
||||
|
||||
|
||||
@@ -23,6 +23,8 @@
|
||||
# define SIZE_MAX UINT_MAX
|
||||
#endif
|
||||
|
||||
namespace {
|
||||
|
||||
static epicsThreadOnceId epicsSigletonOnceFlag ( EPICS_THREAD_ONCE_INIT );
|
||||
static epicsMutex * pEPICSSigletonMutex = 0;
|
||||
|
||||
@@ -34,6 +36,8 @@ extern "C" void SingletonMutexOnce ( void * /* pParm */ )
|
||||
pEPICSSigletonMutex = newEpicsMutex;
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
void SingletonUntyped :: incrRefCount ( PBuild pBuild )
|
||||
{
|
||||
epicsThreadOnce ( & epicsSigletonOnceFlag, SingletonMutexOnce, 0 );
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -250,6 +250,42 @@ LIBCOM_API int errlogVprintfNoConsole(const char *pformat,va_list pvar);
|
||||
*/
|
||||
LIBCOM_API void errSymLookup(long status, char *pBuf, size_t bufLength);
|
||||
|
||||
/** @defgroup colormacros Color macros
|
||||
*
|
||||
* @brief Colorize string constants with ANSI terminal escapes.
|
||||
*
|
||||
* The ANSI_ESC_\* family of macros expand to individual escape sequences.
|
||||
* The ANSI_\* family expand around a string constant to prepend a color, and append a RESET.
|
||||
*
|
||||
* @code
|
||||
* // equivalent
|
||||
* errlogPrintf(ERL_ERROR ": something is amiss\n");
|
||||
* errlogPrintf(ANSI_RED("ERROR") ": something is amiss\n");
|
||||
* errlogPrintf(ANSI_ESC_RED "ERROR" ANSI_ESC_RESET ": something is amiss\n");
|
||||
* @endcode
|
||||
*
|
||||
* @since UNRELEASED
|
||||
*
|
||||
* @see errlogPrintf()
|
||||
* @{
|
||||
*/
|
||||
#define ANSI_ESC_RED "\033[31;1m"
|
||||
#define ANSI_ESC_GREEN "\033[32;1m"
|
||||
#define ANSI_ESC_YELLOW "\033[33;1m"
|
||||
#define ANSI_ESC_BLUE "\033[34;1m"
|
||||
#define ANSI_ESC_MAGENTA "\033[35;1m"
|
||||
#define ANSI_ESC_CYAN "\033[36;1m"
|
||||
#define ANSI_ESC_RESET "\033[0m"
|
||||
#define ANSI_RED(STR) ANSI_ESC_RED STR ANSI_ESC_RESET
|
||||
#define ANSI_GREEN(STR) ANSI_ESC_GREEN STR ANSI_ESC_RESET
|
||||
#define ANSI_YELLOW(STR) ANSI_ESC_YELLOW STR ANSI_ESC_RESET
|
||||
#define ANSI_BLUE(STR) ANSI_ESC_BLUE STR ANSI_ESC_RESET
|
||||
#define ANSI_MAGENTA(STR) ANSI_ESC_MAGENTA STR ANSI_ESC_RESET
|
||||
#define ANSI_CYAN(STR) ANSI_ESC_CYAN STR ANSI_ESC_RESET
|
||||
#define ERL_ERROR ANSI_RED("ERROR")
|
||||
#define ERL_WARNING ANSI_MAGENTA("WARNING")
|
||||
/** @} */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -588,7 +588,7 @@ static MAC_ENTRY *lookup( MAC_HANDLE *handle, const char *name, int special )
|
||||
}
|
||||
if ( (special == FALSE) && (entry == NULL) &&
|
||||
(handle->flags & FLAG_USE_ENVIRONMENT) ) {
|
||||
char *value = getenv(name);
|
||||
char *value = name && *name ? getenv(name) : NULL;
|
||||
if (value) {
|
||||
entry = create( handle, name, FALSE );
|
||||
if ( entry ) {
|
||||
|
||||
@@ -28,6 +28,13 @@
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#ifdef __rtems__
|
||||
# include <syslog.h>
|
||||
# ifndef RTEMS_LEGACY_STACK
|
||||
# include <rtems/bsd/bsd.h>
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#include "epicsThread.h"
|
||||
#include "epicsMutex.h"
|
||||
#include "epicsUnitTest.h"
|
||||
@@ -95,6 +102,18 @@ static int testReportHook(int reportType, char *message, int *returnValue)
|
||||
static void testOnce(void *dummy) {
|
||||
testLock = epicsMutexMustCreate();
|
||||
perlHarness = (getenv("HARNESS_ACTIVE") != NULL);
|
||||
#ifdef __rtems__
|
||||
// syslog() on RTEMS prints to stdout, which will interfere with test output.
|
||||
// setlogmask() ignores empty mask, so must allow at least one level.
|
||||
(void)setlogmask(LOG_MASK(LOG_CRIT));
|
||||
printf("# mask syslog() output\n");
|
||||
#ifndef RTEMS_LEGACY_STACK
|
||||
// with libbsd setlogmask() is a no-op :(
|
||||
// name strings in sys/syslog.h
|
||||
rtems_bsd_setlogpriority("crit");
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifdef _WIN32
|
||||
#ifdef HAVE_SETERROMODE
|
||||
/* SEM_FAILCRITICALERRORS - Don't display modal dialog
|
||||
|
||||
@@ -118,6 +118,11 @@ int epicsStdCall epicsStdoutPrintf(const char *pFormat, ...)
|
||||
return nchar;
|
||||
}
|
||||
|
||||
int epicsStdCall epicsStdoutVPrintf(const char *pformat, va_list ap)
|
||||
{
|
||||
return vfprintf(epicsGetStdout(), pformat, ap);
|
||||
}
|
||||
|
||||
int epicsStdCall epicsStdoutPuts(const char *str)
|
||||
{
|
||||
return fprintf(epicsGetStdout(), "%s\n", str);
|
||||
|
||||
@@ -36,6 +36,7 @@
|
||||
* - `printf` becomes epicsStdoutPrintf()
|
||||
* - `puts` becomes epicsStdoutPuts()
|
||||
* - `putchar` becomes epicsStdoutPutchar()
|
||||
* - `vprintf` becomes epicsStdoutVPrintf()
|
||||
*
|
||||
* The epicsSetThreadStdin(), epicsSetThreadStdout() and epicsSetThreadStderr()
|
||||
* routines allow the standard file streams to be redirected on a per thread
|
||||
@@ -75,6 +76,11 @@ extern "C" {
|
||||
# endif
|
||||
# define printf epicsStdoutPrintf
|
||||
|
||||
# ifdef vprintf
|
||||
# undef vprintf
|
||||
# endif
|
||||
# define vprintf epicsStdoutVPrintf
|
||||
|
||||
# ifdef puts
|
||||
# undef puts
|
||||
# endif
|
||||
@@ -172,6 +178,8 @@ LIBCOM_API void epicsStdCall epicsSetThreadStderr(FILE *);
|
||||
|
||||
LIBCOM_API int epicsStdCall epicsStdoutPrintf(
|
||||
const char *pformat, ...) EPICS_PRINTF_STYLE(1,2);
|
||||
LIBCOM_API int epicsStdCall epicsStdoutVPrintf(
|
||||
const char *pformat, va_list ap);
|
||||
LIBCOM_API int epicsStdCall epicsStdoutPuts(const char *str);
|
||||
LIBCOM_API int epicsStdCall epicsStdoutPutchar(int c);
|
||||
|
||||
@@ -185,6 +193,7 @@ using ::epicsGetStdin;
|
||||
using ::epicsGetStdout;
|
||||
using ::epicsGetStderr;
|
||||
using ::epicsStdoutPrintf;
|
||||
using ::epicsStdoutVPrintf;
|
||||
using ::epicsStdoutPuts;
|
||||
using ::epicsStdoutPutchar;
|
||||
}
|
||||
|
||||
@@ -36,12 +36,12 @@
|
||||
|
||||
#define checkStatus(status,message) \
|
||||
if((status)) { \
|
||||
errlogPrintf("epicsMutex %s failed: error %s\n", \
|
||||
errlogPrintf("epicsMutex %s failed: " ERL_ERROR " %s\n", \
|
||||
(message), strerror((status))); \
|
||||
}
|
||||
#define checkStatusQuit(status,message,method) \
|
||||
if(status) { \
|
||||
errlogPrintf("epicsMutex %s failed: error %s\n", \
|
||||
errlogPrintf("epicsMutex %s failed: " ERL_ERROR " %s\n", \
|
||||
(message), strerror((status))); \
|
||||
cantProceed((method)); \
|
||||
}
|
||||
|
||||
@@ -34,7 +34,7 @@
|
||||
|
||||
#define checkStatus(status,message) \
|
||||
if ((status)) { \
|
||||
errlogPrintf("epicsSpin %s failed: error %s\n", \
|
||||
errlogPrintf("epicsSpin %s failed: " ERL_ERROR " %s\n", \
|
||||
(message), strerror((status))); \
|
||||
}
|
||||
|
||||
|
||||
@@ -94,12 +94,12 @@ static epicsThreadOSD *createImplicit(void);
|
||||
|
||||
#define checkStatus(status,message) \
|
||||
if((status)) {\
|
||||
errlogPrintf("%s error %s\n",(message),strerror((status))); \
|
||||
errlogPrintf("%s " ERL_ERROR " %s\n",(message),strerror((status))); \
|
||||
}
|
||||
|
||||
#define checkStatusQuit(status,message,method) \
|
||||
if(status) { \
|
||||
errlogPrintf("%s error %s\n",(message),strerror((status))); \
|
||||
errlogPrintf("%s " ERL_ERROR " %s\n",(message),strerror((status))); \
|
||||
cantProceed((method)); \
|
||||
}
|
||||
|
||||
|
||||
@@ -157,10 +157,9 @@ void yajl_string_decode(yajl_buf buf, const unsigned char * str,
|
||||
end+=3;
|
||||
/* check if this is a surrogate */
|
||||
if ((codepoint & 0xFC00) == 0xD800) {
|
||||
end++;
|
||||
if (str[end] == '\\' && str[end + 1] == 'u') {
|
||||
if (str[end + 1] == '\\' && str[end + 2] == 'u') {
|
||||
unsigned int surrogate = 0;
|
||||
hexToDigit(&surrogate, 4, str + end + 2);
|
||||
hexToDigit(&surrogate, 4, str + ++end + 2);
|
||||
codepoint =
|
||||
(((codepoint & 0x3F) << 10) |
|
||||
((((codepoint >> 6) & 0xF) + 1) << 16) |
|
||||
|
||||
@@ -28,6 +28,11 @@
|
||||
#include "envDefs.h"
|
||||
#include "osiSock.h"
|
||||
#include "fdmgr.h"
|
||||
#include "epicsString.h"
|
||||
|
||||
/* private between errlog.c and this test */
|
||||
LIBCOM_API
|
||||
void errlogStripANSI(char *msg);
|
||||
|
||||
#define LOGBUFSIZE 2048
|
||||
|
||||
@@ -167,13 +172,40 @@ void logClient(void* raw, const char* msg)
|
||||
epicsEventSignal(pvt->done);
|
||||
}
|
||||
|
||||
static
|
||||
void testANSIStrip(void)
|
||||
{
|
||||
char scratch[64];
|
||||
char actual[128];
|
||||
char input[128];
|
||||
#define testEscape(INP, EXPECT) \
|
||||
strcpy(scratch, INP); \
|
||||
epicsStrnEscapedFromRaw(input, sizeof(input), INP, sizeof(INP)); \
|
||||
errlogStripANSI(scratch); \
|
||||
epicsStrnEscapedFromRaw(actual, sizeof(actual), scratch, epicsStrnLen(scratch, sizeof(scratch))); \
|
||||
testOk(strcmp(scratch, EXPECT)==0, "input \"%s\" expect \"%s\" actual \"%s\"", input, EXPECT, actual)
|
||||
|
||||
testEscape("", "");
|
||||
testEscape("hello", "hello");
|
||||
testEscape("he\033[31;1mllo", "hello");
|
||||
testEscape("\033[31;1mhello", "hello");
|
||||
testEscape("hello\033[31;1m", "hello");
|
||||
testEscape("hello\033[31;1", "hello");
|
||||
testEscape("hello\033[", "hello");
|
||||
testEscape("hello\033", "hello");
|
||||
|
||||
#undef testEscape
|
||||
}
|
||||
|
||||
MAIN(epicsErrlogTest)
|
||||
{
|
||||
size_t mlen, i, N;
|
||||
char msg[256];
|
||||
clientPvt pvt, pvt2;
|
||||
|
||||
testPlan(40);
|
||||
testPlan(48);
|
||||
|
||||
testANSIStrip();
|
||||
|
||||
strcpy(msg, truncmsg);
|
||||
|
||||
@@ -211,10 +243,11 @@ MAIN(epicsErrlogTest)
|
||||
|
||||
errlogAddListener(&logClient, &pvt2);
|
||||
|
||||
/* logClient will not see ANSI escape sequences */
|
||||
pvt2.expect = pvt.expect = "Testing2";
|
||||
pvt2.checkLen = pvt.checkLen = strlen(pvt.expect);
|
||||
|
||||
errlogPrintfNoConsole("%s", pvt.expect);
|
||||
errlogPrintfNoConsole("%s", ANSI_RED("Testing2"));
|
||||
errlogFlush();
|
||||
|
||||
epicsEventMustWait(pvt.done);
|
||||
@@ -370,7 +403,8 @@ MAIN(epicsErrlogTest)
|
||||
|
||||
testDiag("Logged %u messages", pvt.count);
|
||||
epicsEventMustWait(pvt.done);
|
||||
testEqInt(pvt.count, N+1);
|
||||
/* Expect N+1 messages +- 1 depending on impl */
|
||||
testOk(pvt.count >= N && pvt.count<=N+2, "Logged %u messages, expected %zu", pvt.count, N+1);
|
||||
|
||||
/* Clean up */
|
||||
testOk(1 == errlogRemoveListeners(&logClient, &pvt),
|
||||
|
||||
@@ -64,6 +64,15 @@ static void testEpicsSnprintf(void) {
|
||||
}
|
||||
}
|
||||
|
||||
void checkVPrintf(const char *pFormat, ...)
|
||||
{
|
||||
va_list pvar;
|
||||
|
||||
va_start(pvar, pFormat);
|
||||
vprintf(pFormat, pvar);
|
||||
va_end(pvar);
|
||||
}
|
||||
|
||||
void testStdoutRedir (const char *report)
|
||||
{
|
||||
FILE *realStdout = stdout;
|
||||
@@ -85,7 +94,8 @@ void testStdoutRedir (const char *report)
|
||||
testOk1(stdout == stream);
|
||||
|
||||
printf(LINE_1);
|
||||
printf(LINE_2);
|
||||
putchar('\n');
|
||||
checkVPrintf(LINE_2);
|
||||
|
||||
epicsSetThreadStdout(0);
|
||||
testOk1(epicsGetStdout() == realStdout);
|
||||
@@ -113,15 +123,21 @@ void testStdoutRedir (const char *report)
|
||||
fclose(stream);
|
||||
return;
|
||||
}
|
||||
testOk(strcmp(linebuf, LINE_1) == 0, "First line correct");
|
||||
testOk(strcmp(linebuf, LINE_1) == 0, "printf() line correct");
|
||||
|
||||
if (!testOk1(fgets(linebuf, buflen, stream) != NULL)) {
|
||||
testDiag("File read error: %s", strerror(errno));
|
||||
testSkip(1, "No line to compare.");
|
||||
testSkip(1, "Nothing to compare.");
|
||||
} else
|
||||
testOk(strcmp(linebuf, LINE_2) == 0, "Second line");
|
||||
testOk(strcmp(linebuf, "\n") == 0, "putchar() line correct");
|
||||
|
||||
testOk(!fgets(linebuf, buflen, stream), "File ends");
|
||||
if (!testOk1(fgets(linebuf, buflen, stream) != NULL)) {
|
||||
testDiag("File read error: %s", strerror(errno));
|
||||
testSkip(1, "Nothing to compare.");
|
||||
} else
|
||||
testOk(strcmp(linebuf, LINE_2) == 0, "vprintf() line correct");
|
||||
|
||||
testOk(!fgets(linebuf, buflen, stream) && feof(stream), "End of file");
|
||||
|
||||
if (!testOk1(!fclose(stream)))
|
||||
testDiag("fclose error: %s\n", strerror(errno));
|
||||
@@ -129,7 +145,7 @@ void testStdoutRedir (const char *report)
|
||||
|
||||
MAIN(epicsStdioTest)
|
||||
{
|
||||
testPlan(163);
|
||||
testPlan(165);
|
||||
testEpicsSnprintf();
|
||||
#ifdef __rtems__
|
||||
/* ensure there is a writable area */
|
||||
|
||||
@@ -3354,6 +3354,18 @@ sub cases {
|
||||
"memory leaks:\t0"
|
||||
]
|
||||
},
|
||||
{
|
||||
name => "truncated_surrogate",
|
||||
opts => [],
|
||||
input => [
|
||||
"\"\\uDBFF\360\237\222\200\"",
|
||||
""
|
||||
],
|
||||
gives => [
|
||||
"string: '?\360\237\222\200'",
|
||||
"memory leaks:\t0"
|
||||
]
|
||||
},
|
||||
{
|
||||
name => "unescaped_bulgarian",
|
||||
opts => [],
|
||||
|
||||
Submodule modules/normativeTypes updated: 1250a3c236...7a2d264f2c
Submodule modules/pvAccess updated: de20a37b5e...284de4fb6b
Submodule modules/pvData updated: b1c8303870...d3b4976ea2
Submodule modules/pvDatabase updated: 8cac3975cc...0cf706511e
Submodule modules/pva2pva updated: 466d41ebb9...61ec0715be
Submodule modules/pvaClient updated: a34876e36a...8ed07fef96
@@ -67,6 +67,7 @@ sub readRelease {
|
||||
my ($uvar) = m/^ undefine \s+ ($MVAR)/x;
|
||||
if ($uvar ne '') {
|
||||
delete $Rmacros->{$uvar};
|
||||
@$Rapps = grep($_ ne $uvar, @$Rapps);
|
||||
next;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user