Compare commits
238 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
95fd1a7623 | ||
|
|
5be53b39a8 | ||
|
|
8c364aa636 | ||
|
|
7366f7359c | ||
|
|
894936cc5e | ||
|
|
b760fbdf95 | ||
|
|
1c594c2522 | ||
|
|
0897e71ca0 | ||
|
|
2cdb8d2cbb | ||
|
|
ae5c8365d2 | ||
|
|
4853de114b | ||
|
|
5a2a33f3e0 | ||
|
|
36809d6d20 | ||
|
|
5ecb0738c5 | ||
|
|
d625b13899 | ||
|
|
987f598804 | ||
|
|
5ecac228c6 | ||
|
|
51a1d5991d | ||
|
|
50f58c9974 | ||
|
|
33a5dd714e | ||
|
|
b5ee956916 | ||
|
|
720f6ba418 | ||
|
|
329172afc7 | ||
|
|
41aeb709e5 | ||
|
|
dc31948da1 | ||
|
|
2c05bf61ce | ||
|
|
8b9a59d072 | ||
|
|
4a8aa93f1e | ||
|
|
57d488b7a0 | ||
|
|
5fc1e3217b | ||
|
|
164449f0d6 | ||
|
|
5bf2821512 | ||
|
|
4818d705a5 | ||
|
|
ecd7d5a9ce | ||
|
|
2bef3a2d08 | ||
|
|
668ecc9b94 | ||
|
|
267e352bb5 | ||
|
|
36d3033de4 | ||
|
|
23e17b664c | ||
|
|
4a7100cbf0 | ||
|
|
8ee9595026 | ||
|
|
22df40f776 | ||
|
|
2344a4b0e3 | ||
|
|
1e9826e1f7 | ||
|
|
272940d50e | ||
|
|
dc3f271ea2 | ||
|
|
32d48f7dcd | ||
|
|
de99791d82 | ||
|
|
df6f19a611 | ||
|
|
82b2a0be6e | ||
|
|
3dff2767c7 | ||
|
|
cbcc94ba9e | ||
|
|
c91c7b32f0 | ||
|
|
a4c47660f3 | ||
|
|
800d614eed | ||
|
|
0381f13e3f | ||
|
|
22bc683370 | ||
|
|
87b4d8db21 | ||
|
|
37958418e4 | ||
|
|
965a511c47 | ||
|
|
ce29419d3d | ||
|
|
8992b2c956 | ||
|
|
53ce107e5f | ||
|
|
810e60fc98 | ||
|
|
0189d48d73 | ||
|
|
afd785354a | ||
|
|
6ef89dd871 | ||
|
|
7a920f831d | ||
|
|
cab998f40d | ||
|
|
563733cf3c | ||
|
|
7e80920164 | ||
|
|
21e72e7f13 | ||
|
|
fae1b240f6 | ||
|
|
ee99561235 | ||
|
|
14aa5b47b0 | ||
|
|
eb78bf867f | ||
|
|
81ad1fe161 | ||
|
|
5ed18e6e6f | ||
|
|
b76257a0d6 | ||
|
|
d844c2dd61 | ||
|
|
eb40c4e79b | ||
|
|
068613e447 | ||
|
|
4c606f43e7 | ||
|
|
c6a0e60989 | ||
|
|
cb4604a157 | ||
|
|
0b52634e38 | ||
|
|
ff3329b0f9 | ||
|
|
76f1fdf92d | ||
|
|
09ef609f43 | ||
|
|
5e5346e6b3 | ||
|
|
a011b98f62 | ||
|
|
72a1539a86 | ||
|
|
f169cd57f9 | ||
|
|
429c47eb11 | ||
|
|
cac8ee7b0e | ||
|
|
27f39ec664 | ||
|
|
42489a84d4 | ||
|
|
8996ab2b5c | ||
|
|
b3872bf14a | ||
|
|
1ab4c344aa | ||
|
|
30efff9cd0 | ||
|
|
c93585e950 | ||
|
|
07fd7b3588 | ||
|
|
3f290c6c9e | ||
|
|
3068262901 | ||
|
|
5453865724 | ||
|
|
c3c1c6c980 | ||
|
|
4599f5540a | ||
|
|
e8c5ab29fa | ||
|
|
68556e0534 | ||
|
|
5ea6509553 | ||
|
|
ef50d04061 | ||
|
|
07e0bce2d3 | ||
|
|
6b0f70a734 | ||
|
|
93b46f62a5 | ||
|
|
5b30180c3f | ||
|
|
2e21360559 | ||
|
|
d212f0428b | ||
|
|
5f08b2170a | ||
|
|
31c88f6044 | ||
|
|
8c4e8dd35f | ||
|
|
9be94797d5 | ||
|
|
52f10d9b47 | ||
|
|
1165285c6f | ||
|
|
6d8753602e | ||
|
|
65130ee6bd | ||
|
|
1e0ecdb3fe | ||
|
|
da35bba798 | ||
|
|
4a03176538 | ||
|
|
ff08561ba0 | ||
|
|
610eb4ea87 | ||
|
|
6ff5355e3e | ||
|
|
a0e0cd7ef5 | ||
|
|
2074838a12 | ||
|
|
b4137fe9df | ||
|
|
1d6a7f59f4 | ||
|
|
7e606dafac | ||
|
|
672d4a6dbb | ||
|
|
e3ad8f867e | ||
|
|
40e79bace4 | ||
|
|
ea297a6078 | ||
|
|
bfb3de64ce | ||
|
|
af97e702d1 | ||
|
|
ff54104aa0 | ||
|
|
8da4eb3b46 | ||
|
|
35d8565e41 | ||
|
|
a473612084 | ||
|
|
2f827fc92d | ||
|
|
5201304c10 | ||
|
|
26b6974cfa | ||
|
|
d80664f33f | ||
|
|
6a71ba0026 | ||
|
|
b25c2e9d4c | ||
|
|
11e5c14c7f | ||
|
|
5bf1789650 | ||
|
|
b984a302c6 | ||
|
|
b389342440 | ||
|
|
ad89f422ce | ||
|
|
6af0cdeb50 | ||
|
|
d900b9fd63 | ||
|
|
c5db766b33 | ||
|
|
36f9090897 | ||
|
|
58d4f27307 | ||
|
|
ea35450f45 | ||
|
|
3bc6a48ade | ||
|
|
a170d40be2 | ||
|
|
7c34b847e0 | ||
|
|
c07e6af98c | ||
|
|
7e0b996c72 | ||
|
|
2369ade2fa | ||
|
|
7c99669444 | ||
|
|
16e182a89c | ||
|
|
ebfded8107 | ||
|
|
d7df37414c | ||
|
|
48d48343ae | ||
|
|
c49db18285 | ||
|
|
41f7f4ef81 | ||
|
|
8ea67657bc | ||
|
|
bbd1080208 | ||
|
|
3fc3300e54 | ||
|
|
11da58cc5b | ||
|
|
2cdbee7d32 | ||
|
|
9a48a5c906 | ||
|
|
e46c04d514 | ||
|
|
d192351f77 | ||
|
|
454bd2b0a5 | ||
|
|
5b1d6ac38f | ||
|
|
0d071c9f0c | ||
|
|
bfd0826f03 | ||
|
|
72db656797 | ||
|
|
0e3f04824e | ||
|
|
509ff37ec4 | ||
|
|
4a1612e133 | ||
|
|
e80aa34d00 | ||
|
|
4d3fcd56bf | ||
|
|
16832b9f07 | ||
|
|
323e378fc5 | ||
|
|
82f5d588db | ||
|
|
08e0d5a5bc | ||
|
|
6bf437cf28 | ||
|
|
2ef8d4b21a | ||
|
|
f32d647482 | ||
|
|
5f712bde67 | ||
|
|
6f58f32c96 | ||
|
|
9e9d2c91f6 | ||
|
|
318a0b6d1d | ||
|
|
b66388ea9d | ||
|
|
2bfe077968 | ||
|
|
6cda511ed8 | ||
|
|
79b47c4f54 | ||
|
|
d6c0e9dcc5 | ||
|
|
13a779ca81 | ||
|
|
7517890d03 | ||
|
|
8d043dfe6e | ||
|
|
c282a107eb | ||
|
|
113878e491 | ||
|
|
c02246e7cc | ||
|
|
74af851746 | ||
|
|
bc81744d8f | ||
|
|
29335e7672 | ||
|
|
7282989961 | ||
|
|
c4e42b4bdc | ||
|
|
4410805493 | ||
|
|
b607b062ba | ||
|
|
13eb94b6be | ||
|
|
8799d3c6ba | ||
|
|
d6b34a9732 | ||
|
|
08cb4a265a | ||
|
|
f8829aed21 | ||
|
|
4bf312df58 | ||
|
|
2c68ac3a10 | ||
|
|
1fa297d34f | ||
|
|
452a040183 | ||
|
|
0b51e1f972 | ||
|
|
410623730b | ||
|
|
35f9e3dcbb | ||
|
|
0a93c81e2c | ||
|
|
a5fd9c839e |
2
Makefile
2
Makefile
@@ -14,7 +14,9 @@
|
||||
TOP = .
|
||||
include $(TOP)/configure/CONFIG
|
||||
|
||||
ifeq ($(findstring YES,$(COMPAT_313) $(COMPAT_TOOLS_313)),YES)
|
||||
DIRS += config config/tools
|
||||
endif
|
||||
DIRS += configure src
|
||||
|
||||
include $(TOP)/configure/RULES_TOP
|
||||
|
||||
@@ -1,65 +0,0 @@
|
||||
#*************************************************************************
|
||||
# Copyright (c) 2002 The University of Chicago, 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.
|
||||
#*************************************************************************
|
||||
# CONFIG.Host.LynxOS
|
||||
#
|
||||
# This file is maintained by the EPICS community.
|
||||
# Sites may override these definitions in CONFIG_SITE.Host.LynxOS
|
||||
|
||||
ARCH_CLASS = LynxOS
|
||||
|
||||
# Include definitions common to all Unix archs
|
||||
include $(EPICS_BASE)/config/CONFIG.Host.UnixCommon
|
||||
|
||||
AR = ar -rc
|
||||
ARCMD = $(AR) $@
|
||||
RANLIB = ranlib -t
|
||||
|
||||
|
||||
|
||||
# Configure OS vendor C compiler
|
||||
ACC_ANSI = $(ACC) -ansi
|
||||
ACC_STRICT = $(ACC) -ansi -pedantic
|
||||
ACC_TRAD = $(ACC)
|
||||
ACC_WARN_YES = -Wall
|
||||
ACC_WARN_NO = -w
|
||||
ACC_OPT_YES = -O
|
||||
ACC_OPT_NO = -g
|
||||
ACC_SFLAGS_YES = -Bstatic
|
||||
ACC_SFLAGS_NO=
|
||||
ACC_SLIBS_YES =
|
||||
ACC_SLIBS_NO=
|
||||
ACC_SHRLIB_CFLAGS_YES =
|
||||
ACC_SHRLIB_LDFLAGS_YES =
|
||||
|
||||
|
||||
|
||||
# Configure OS vendor C++ compiler
|
||||
CCC_NORMAL = $(CCC)
|
||||
CCC_STRICT = $(CCC)
|
||||
CCC_TEMPL_INST_FLAG = -pedantic -DEXPL_TEMP
|
||||
CCC_WARN_YES = -Wall
|
||||
CCC_WARN_NO = -w
|
||||
CCC_OPT_YES = -O
|
||||
CCC_OPT_NO = -g
|
||||
CCC_SFLAGS_YES = -Bstatic
|
||||
CCC_SFLAGS_NO=
|
||||
CCC_SLIBS_YES =
|
||||
CCC_SLIBS_NO=
|
||||
CCC_DEPENDS_FLAG = -pedantic
|
||||
|
||||
|
||||
# added smh 6/5/98 : when building fdmgr - seems to use this not ACC
|
||||
# in effect this overides orig def in CONFIG_COMMON :
|
||||
# which is GCC_STRICT = $(GCC) -ansi -pedantic
|
||||
GCC_STRICT = $(GCC)
|
||||
G++_STRICT = $(G++) -Wtraditional -DEXPL_TEMP
|
||||
|
||||
ARCH_DEP_CFLAGS = -DLynxOS -mposix -D_X86_ -DLYNXOS_RELEASE_2_4_0
|
||||
ARCH_DEP_LDLIBS = -lc -lbsd -lnsl -lm -lposix4d9 -llynx
|
||||
@@ -67,7 +67,9 @@ CCC_SHRLIB_LDFLAGS_YES = -G -h $@
|
||||
|
||||
SOLARIS_VERSION = $(subst 5.,,$(shell uname -r))
|
||||
ARCH_DEP_CPPFLAGS += -DSOLARIS=$(SOLARIS_VERSION)
|
||||
POSIX_CPPFLAGS_YES += -D__EXTENSIONS__
|
||||
POSIX_CPPFLAGS_YES += -D__EXTENSIONS__ -mt
|
||||
|
||||
ARCH_DEP_LDFLAGS += -mt
|
||||
|
||||
# socket and nsl needed by libca.a
|
||||
ARCH_DEP_LDLIBS += -lsocket -lnsl
|
||||
|
||||
@@ -37,6 +37,8 @@ SOLARIS_VERSION = $(subst 5.,,$(shell uname -r))
|
||||
ARCH_DEP_CPPFLAGS += -DSOLARIS=$(SOLARIS_VERSION)
|
||||
POSIX_CPPFLAGS_YES += -D__EXTENSIONS__
|
||||
|
||||
ARCH_DEP_LDFLAGS += -mt
|
||||
|
||||
# socket and nsl needed by libca.a
|
||||
ARCH_DEP_LDLIBS += -lsocket -lnsl
|
||||
ARCH_DEP_LDLIBS += -lposix4 -lpthread
|
||||
|
||||
@@ -1,142 +0,0 @@
|
||||
#*************************************************************************
|
||||
# Copyright (c) 2002 The University of Chicago, 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.
|
||||
#*************************************************************************
|
||||
# $Id$
|
||||
#
|
||||
# This file contains definitions for Vx builds
|
||||
|
||||
#--------------------------------------------------
|
||||
# operating system class (include/os/<os_class>)
|
||||
OS_CLASS = LynxOS
|
||||
|
||||
lynx_pc486 =YES
|
||||
|
||||
CC = gcc
|
||||
CXX = g++
|
||||
|
||||
#--------------------------------------------------
|
||||
# vxWorks directory definitions
|
||||
|
||||
# The definitions VX_DIR, VX_GNU, GNU_DIR and GNU_LIB
|
||||
# can be overridden for specific host architectures
|
||||
# by creating a CONFIG_SITE.Vx.<host_arch> file with
|
||||
# the override definitions.
|
||||
|
||||
# Tornado directory definitions
|
||||
VX_INCLUDE_YES =
|
||||
VX_GNU_YES =
|
||||
VX_GNU_BIN_YES =
|
||||
VX_GNU_LIB_YES =
|
||||
|
||||
|
||||
# pre Torando directory definitions
|
||||
VX_INCLUDE_NO =
|
||||
VX_GNU_NO =
|
||||
VX_GNU_BIN_NO =
|
||||
|
||||
# directory definitions
|
||||
VX_DIR =
|
||||
VX_INCLUDE =
|
||||
VX_GNU =
|
||||
|
||||
GNU_BIN = /usr/local/bin
|
||||
GNU_LIB = /usr/local/lib
|
||||
|
||||
#--------------------------------------------------
|
||||
# VxWorks command definitions
|
||||
|
||||
#GCC = $(GNU_BIN)/cc$(CMPLR_SUFFIX) -B$(GNU_LIB)/gcc-lib/ -nostdinc
|
||||
#AR = $(GNU_BIN)/ar$(CMPLR_SUFFIX)
|
||||
#CPP = $(GNU_BIN)/cpp$(CMPLR_SUFFIX) -nostdinc
|
||||
#RANLIB = $(GNU_BIN)/ranlib$(CMPLR_SUFFIX)
|
||||
#LD = $(GNU_BIN)/ld$(CMPLR_SUFFIX) -r
|
||||
|
||||
AR = ar -rc
|
||||
ARCMD = $(AR) $@
|
||||
RANLIB = ranlib -t
|
||||
GCC = gcc
|
||||
CPP = cpp
|
||||
LD = ld -r
|
||||
|
||||
|
||||
#--------------------------------------------------
|
||||
# Tornado C++ crosscompiler definitions
|
||||
|
||||
#CPLUSPLUS_YES = G++
|
||||
#G++ = $(GNU_BIN)/cc$(CMPLR_SUFFIX) -B$(GNU_LIB)/gcc-lib/ -nostdinc
|
||||
#LD_G++ = $(GNU_BIN)/ld$(CMPLR_SUFFIX) -r
|
||||
#NM = $(GNU_BIN)/nm$(CMPLR_SUFFIX)
|
||||
#MUNCH = $(GNU_BIN)/munch
|
||||
|
||||
CPLUSPLUS_YES = g++ -DLynxOS -DLynxOS_pc486 -mposix -D_X86_ -DEXPL_TEMP
|
||||
G++ = g++ -DLynxOS -DLynxOS_pc486 -mposix -D_X86_ -DEXPL_TEMP
|
||||
LD_G++ = ld -r
|
||||
NM = nm
|
||||
|
||||
#--------------------------------------------------
|
||||
# Pre Tornado C++ crosscompiler definitions
|
||||
# These are pre tornado definitions for Hideos builds (defined for 68k only)
|
||||
|
||||
#CPLUSPLUS_NO = CCC
|
||||
#CCC = $(GNU_DIR)/bin/sun3-g++ -B$(GNU_DIR)/lib/gcc-lib/ -nostdinc -DEXPL_TEMPL
|
||||
#LD_CCC = $(GNU_DIR)/bin/sun3-ld $(OLD_ARCH_DEP_LDFLAGS) -r
|
||||
|
||||
CPLUSPLUS_NO = g++ -DLynxOS -DLynxOS_pc486 -mposix -D_X86_ -DEXPL_TEMP
|
||||
CCC = g++ -DLynxOS -DLynxOS_pc486 -mposix -D_X86_ -DEXPL_TEMP
|
||||
LD_CCC = ld -r
|
||||
|
||||
CCC_NORMAL = $(CCC) $(OLD_ARCH_DEP_CFLAGS)
|
||||
CCC_STRICT = $(CCC) -ansi -pedantic -Wall -traditional $(OLD_ARCH_DEP_CFLAGS)
|
||||
CCC_TRAD = $(CCC) -traditional $(OLD_ARCH_DEP_CFLAGS)
|
||||
CCC_TEMPL_INST_FLAG = -DEXPL_TEMP
|
||||
CCC_WARN_YES = -Wall
|
||||
CCC_WARN_NO = -w
|
||||
CCC_OPT_YES = -O
|
||||
CCC_OPT_NO = -g
|
||||
CCC_DEPENDS_FLAG = -pedantic -DLynxOS -DLynxOS_pc486 -mposix -D_X86_
|
||||
CPU = i486
|
||||
OS = lynxos
|
||||
OLD_ARCH_DEP_CFLAGS = -DLynxOS -DLynxOS_pc486 -mposix -D_X86_
|
||||
# --no-builtin -Wa,"-m68040" -DOS_EQ_$(OS) \
|
||||
# -DBOARD_EQ_$(BOARD) -DCPU_EQ_$(CPU) -DBOARD=$(BOARD)
|
||||
OLD_ARCH_DEP_LDFLAGS = -mposix -lc -lbsd -lnsl -lm -lposix4d9 -llynx
|
||||
# -Ur -N -T$(EPICS_BASE_BIN)/vxldscript.MRI
|
||||
|
||||
#--------------------------------------------------
|
||||
# C compiler definitions
|
||||
ANSI = gcc -ansi
|
||||
|
||||
#--------------------------------------------------
|
||||
# Command definitions
|
||||
CPLUSPLUS = g++
|
||||
# $(CPLUSPLUS_$(TORNADO))
|
||||
LD_CXX = ld -r
|
||||
# $(LD_$(CPLUSPLUS))
|
||||
|
||||
#--------------------------------------------------
|
||||
# Operating system flags
|
||||
OP_SYS_INCLUDES =
|
||||
# -I$(VX_INCLUDE)
|
||||
OP_SYS_CFLAGS = -DLynxOS -DLynxOS_pc486 -mposix -D_X86_
|
||||
# -DvxWorks -DV5_vxWorks -fno-builtin
|
||||
OP_SYS_LDFLAGS = -DLynxOS -DLynxOS_pc486 -mposix -D_X86_
|
||||
OP_SYS_LDLIBS = -lc -lbsd -lnsl -lm -lposix4d9 -llynx
|
||||
|
||||
#--------------------------------------------------
|
||||
# Optimization flag overrides
|
||||
GCC_OPT_YES = -O
|
||||
# 2 -fstrength-reduce
|
||||
G++_OPT_YES = -O
|
||||
# 2 -fstrength-reduce
|
||||
|
||||
#--------------------------------------------------
|
||||
# Link definitions
|
||||
LINK.c = $(LD) $(LDFLAGS) -o
|
||||
LINK.cc = $(LD_CXX) $(LDFLAGS) -o
|
||||
|
||||
@@ -20,7 +20,7 @@ OS_CLASS = vxWorks
|
||||
|
||||
# The definitions VX_DIR, VX_GNU, GNU_DIR and GNU_LIB
|
||||
# can be overridden for specific host architectures
|
||||
# by creating a CONFIG_SITE.Vx.<host_archfile with
|
||||
# by creating a CONFIG_SITE.Vx.<host_arch> file with
|
||||
# the override definitions.
|
||||
|
||||
# Tornado directory definitions
|
||||
@@ -41,7 +41,6 @@ VX_GNU = $(VX_GNU_$(TORNADO))
|
||||
GNU_BIN = $(VX_GNU_BIN_$(TORNADO))
|
||||
GNU_LIB = $(VX_GNU_LIB_$(TORNADO))
|
||||
export GCC_EXEC_PREFIX = $(GNU_LIB)/gcc-lib/
|
||||
export WIND_BASE = $(VX_DIR)
|
||||
|
||||
#--------------------------------------------------
|
||||
# VxWorks command definitions
|
||||
@@ -148,4 +147,3 @@ MUNCHNAME = $(LIBNAME:%=%$(MUNCH_SUFFIX))
|
||||
export WIND_BASE = $(VX_DIR)
|
||||
export WIND_HOST_TYPE
|
||||
|
||||
|
||||
|
||||
@@ -18,7 +18,7 @@
|
||||
|
||||
EPICS_VERSION=3
|
||||
EPICS_REVISION=14
|
||||
EPICS_MODIFICATION=5
|
||||
EPICS_MODIFICATION=6
|
||||
EPICS_UPDATE_NAME=
|
||||
EPICS_UPDATE_LEVEL=0
|
||||
|
||||
|
||||
@@ -42,6 +42,7 @@ INSTALL_CONFIG = $(INSTALL_LOCATION)/config
|
||||
INSTALL_JAVA = $(INSTALL_LOCATION)/javalib
|
||||
|
||||
EPICS_BASE_INCLUDE = $(EPICS_BASE)/include
|
||||
EPICS_BASE_TOOLS = $(EPICS_BASE)/config/tools
|
||||
|
||||
DIVIDER = .
|
||||
OBJ = .
|
||||
@@ -63,7 +64,7 @@ LEX = $(ELEX)
|
||||
PERL=perl
|
||||
|
||||
# install from EPICS
|
||||
INSTALL = $(PERL) $(EPICS_BASE_HOST_BIN)/installEpics.pl
|
||||
INSTALL = $(PERL) $(EPICS_BASE_TOOLS)/installEpics.pl
|
||||
INSTALL_PRODUCT = $(INSTALL)
|
||||
INSTALL_LIBRARY = $(INSTALL)
|
||||
|
||||
|
||||
@@ -24,7 +24,7 @@ ARCH_WIN32 = win32-x86
|
||||
ARCH_hp700 = hpux-m68k
|
||||
ARCH_alpha = osf-alpha
|
||||
ARCH_Borland = win32-x86-borland
|
||||
ARCH_cygwin32 = win32-x86-cygwin
|
||||
ARCH_cygwin32 = cygwin-x86
|
||||
|
||||
ifndef EPICS_HOST_ARCH
|
||||
ifdef HOST_ARCH
|
||||
|
||||
@@ -13,12 +13,12 @@
|
||||
EXE=.exe
|
||||
HOSTEXE=.exe
|
||||
|
||||
CP =$(PERL) $(EPICS_BASE_HOST_BIN)/cp.pl
|
||||
MV =$(PERL) $(EPICS_BASE_HOST_BIN)/mv.pl
|
||||
RM =$(PERL) $(EPICS_BASE_HOST_BIN)/rm.pl -f
|
||||
MKDIR=$(PERL) $(EPICS_BASE_HOST_BIN)/mkdir.pl
|
||||
RMDIR=$(PERL) $(EPICS_BASE_HOST_BIN)/rm.pl -rf
|
||||
FN =$(PERL) $(EPICS_BASE_HOST_BIN)/fullName.pl
|
||||
CP =$(PERL) $(EPICS_BASE_TOOLS)/cp.pl
|
||||
MV =$(PERL) $(EPICS_BASE_TOOLS)/mv.pl
|
||||
RM =$(PERL) $(EPICS_BASE_TOOLS)/rm.pl -f
|
||||
MKDIR=$(PERL) $(EPICS_BASE_TOOLS)/mkdir.pl
|
||||
RMDIR=$(PERL) $(EPICS_BASE_TOOLS)/rm.pl -rf
|
||||
FN =$(PERL) $(EPICS_BASE_TOOLS)/fullName.pl
|
||||
CHMOD=echo
|
||||
ECHO=echo
|
||||
|
||||
|
||||
@@ -1,18 +0,0 @@
|
||||
#*************************************************************************
|
||||
# Copyright (c) 2002 The University of Chicago, 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.
|
||||
#*************************************************************************
|
||||
# CONFIG_HOST_ARCH.LynxOS
|
||||
#
|
||||
# Override values in CONFIG.LynxOS
|
||||
|
||||
# Include definitions common to all Unix archs
|
||||
include $(EPICS_BASE)/config/CONFIG_HOST_ARCH.UnixCommon
|
||||
|
||||
WIND_HOST_TYPE = LynxOS
|
||||
|
||||
@@ -13,11 +13,11 @@
|
||||
EXE=.exe
|
||||
HOSTEXE=.exe
|
||||
|
||||
CP =$(PERL) $(EPICS_BASE_HOST_BIN)/cp.pl
|
||||
MV =$(PERL) $(EPICS_BASE_HOST_BIN)/mv.pl
|
||||
RM =$(PERL) $(EPICS_BASE_HOST_BIN)/rm.pl -f
|
||||
MKDIR=$(PERL) $(EPICS_BASE_HOST_BIN)/mkdir.pl
|
||||
RMDIR=$(PERL) $(EPICS_BASE_HOST_BIN)/rm.pl -rf
|
||||
CP =$(PERL) $(EPICS_BASE_TOOLS)/cp.pl
|
||||
MV =$(PERL) $(EPICS_BASE_TOOLS)/mv.pl
|
||||
RM =$(PERL) $(EPICS_BASE_TOOLS)/rm.pl -f
|
||||
MKDIR=$(PERL) $(EPICS_BASE_TOOLS)/mkdir.pl
|
||||
RMDIR=$(PERL) $(EPICS_BASE_TOOLS)/rm.pl -rf
|
||||
CHMOD=echo
|
||||
ECHO=echo
|
||||
|
||||
|
||||
@@ -1,15 +0,0 @@
|
||||
#
|
||||
# $Id$
|
||||
#
|
||||
# Site Specific Configuration Information
|
||||
# Only the local epics system manager should modify this file
|
||||
|
||||
# APS overrides of definitions
|
||||
|
||||
GCC = gcc
|
||||
G++ = g++
|
||||
CC = gcc
|
||||
CCC = g++
|
||||
ACC = gcc
|
||||
PLUSPLUS = g++
|
||||
CXX = g++
|
||||
@@ -15,7 +15,7 @@ TOP=..
|
||||
|
||||
include $(TOP)/configure/CONFIG
|
||||
|
||||
ifeq ($(strip $(COMPAT_313)),YES)
|
||||
ifeq ($(findstring YES,$(COMPAT_313) $(COMPAT_TOOLS_313)),YES)
|
||||
INSTALL_CONFIG = $(INSTALL_LOCATION)/config
|
||||
|
||||
CONFIGS += $(subst ../,,$(wildcard ../CONFIG*))
|
||||
|
||||
@@ -149,7 +149,7 @@ $(TARGETS) $(PROD): $(DEPLIBS)
|
||||
$(SNC) $(TARGET_SNCFLAGS) $(SNCFLAGS) $*.i
|
||||
|
||||
%.c: ../%.stt
|
||||
@echo "converting $<
|
||||
@echo "converting $<"
|
||||
@$(RM) $@
|
||||
$(SNC) $(TARGET_SNCFLAGS) $(SNCFLAGS) $<
|
||||
|
||||
|
||||
@@ -129,7 +129,7 @@ endif
|
||||
%.out : %.o
|
||||
@ $(RM) ctct.o ctdt.c nm.out
|
||||
$(NM) $< > nm.out
|
||||
$(PERL) $(EPICS_BASE)/bin/$(HOST_ARCH)/munch.pl < nm.out > ctdt.c
|
||||
$(PERL) $(EPICS_BASE_TOOLS)/munch.pl < nm.out > ctdt.c
|
||||
$(COMPILE.c) -traditional ctdt.c
|
||||
$(LINK.cc) $@ $< ctdt.o
|
||||
|
||||
@@ -137,7 +137,7 @@ endif
|
||||
$(MUNCHNAME):%.munch : %
|
||||
@ $(RM) ctct.o ctdt.c nm.out
|
||||
$(NM) $< > nm.out
|
||||
$(PERL) $(EPICS_BASE)/bin/$(HOST_ARCH)/munch.pl < nm.out > ctdt.c
|
||||
$(PERL) $(EPICS_BASE_TOOLS)/munch.pl < nm.out > ctdt.c
|
||||
$(COMPILE.c) -traditional ctdt.c
|
||||
$(LINK.cc) $@ $(LDFLAGS) $< ctdt.o
|
||||
|
||||
|
||||
@@ -60,11 +60,11 @@ $(crossActionArchTargets) :
|
||||
$(crossArchs) :
|
||||
endif
|
||||
|
||||
$(hostDirs) :
|
||||
$(PERL) $(EPICS_BASE_HOST_BIN)/makeMakefile.pl $@ Host
|
||||
$(hostDirs) : $(EPICS_BASE_TOOLS)/makeMakefile.pl
|
||||
$(PERL) $(EPICS_BASE_TOOLS)/makeMakefile.pl $@ Host
|
||||
|
||||
$(crossDirs) :
|
||||
$(PERL) $(EPICS_BASE_HOST_BIN)/makeMakefile.pl $@ Vx
|
||||
$(crossDirs) : $(EPICS_BASE_TOOLS)/makeMakefile.pl
|
||||
$(PERL) $(EPICS_BASE_TOOLS)/makeMakefile.pl $@ Vx
|
||||
|
||||
#
|
||||
# host/cross action targets
|
||||
|
||||
@@ -23,8 +23,10 @@ CONFIG ?= $(TOP)/configure
|
||||
|
||||
-include $(CONFIG)/RELEASE
|
||||
-include $(CONFIG)/RELEASE.$(EPICS_HOST_ARCH)
|
||||
ifdef T_A
|
||||
-include $(CONFIG)/RELEASE.Common.$(T_A)
|
||||
-include $(CONFIG)/RELEASE.$(EPICS_HOST_ARCH).$(T_A)
|
||||
endif
|
||||
|
||||
include $(CONFIG)/CONFIG_COMMON
|
||||
|
||||
@@ -68,21 +70,11 @@ endif
|
||||
|
||||
# User specific definitions
|
||||
#
|
||||
-include $(HOME)/configure/CONFIG
|
||||
-include $(HOME)/os/configure/CONFIG.Host.$(HOST_ARCH)
|
||||
-include $(HOME)/os/configure/CONFIG.Host.$(EPICS_HOST_ARCH)
|
||||
-include $(HOME)/os/configure/CONFIG.$(HOST_ARCH).Common
|
||||
-include $(HOME)/os/configure/CONFIG.$(EPICS_HOST_ARCH).Common
|
||||
-include $(HOME)/configure/CONFIG_USER
|
||||
-include $(HOME)/configure/CONFIG_USER.$(EPICS_HOST_ARCH)
|
||||
ifdef T_A
|
||||
-include $(HOME)/configure/CONFIG.$(OS_CLASS)
|
||||
-include $(HOME)/configure/CONFIG.Target.$(T_A)
|
||||
-include $(HOME)/configure/CONFIG.Common.$(T_A)
|
||||
-include $(HOME)/configure/CONFIG.$(HOST_ARCH).$(T_A)
|
||||
-include $(HOME)/configure/CONFIG.$(EPICS_HOST_ARCH).$(T_A)
|
||||
-include $(HOME)/configure/os/CONFIG.Target.$(T_A)
|
||||
-include $(HOME)/configure/os/CONFIG.Common.$(T_A)
|
||||
-include $(HOME)/configure/os/CONFIG.$(HOST_ARCH).$(T_A)
|
||||
-include $(HOME)/configure/os/CONFIG.$(EPICS_HOST_ARCH).$(T_A)
|
||||
-include $(HOME)/configure/CONFIG_USER.Common.$(T_A)
|
||||
-include $(HOME)/configure/CONFIG_USER.$(EPICS_HOST_ARCH).$(T_A)
|
||||
endif
|
||||
|
||||
# All options
|
||||
|
||||
@@ -24,7 +24,7 @@ endif
|
||||
#---------------------------------------------------------------
|
||||
# Epics base Ioc libraries
|
||||
|
||||
EPICS_BASE_IOC_LIBS += recIoc softDevIoc testDevIoc iocsh
|
||||
EPICS_BASE_IOC_LIBS += recIoc softDevIoc iocsh
|
||||
EPICS_BASE_IOC_LIBS += miscIoc rsrvIoc dbtoolsIoc asIoc
|
||||
EPICS_BASE_IOC_LIBS += dbIoc registryIoc dbStaticIoc ca Com
|
||||
|
||||
|
||||
@@ -18,7 +18,7 @@
|
||||
|
||||
EPICS_VERSION=3
|
||||
EPICS_REVISION=14
|
||||
EPICS_MODIFICATION=5
|
||||
EPICS_MODIFICATION=6
|
||||
EPICS_UPDATE_NAME=
|
||||
EPICS_UPDATE_LEVEL=0
|
||||
|
||||
|
||||
@@ -15,16 +15,14 @@
|
||||
#
|
||||
# CONFIG_ENV - EPICS Environment Parameter configuration file
|
||||
#
|
||||
# This file is interpreted by the Bourne Shell, so spaces are
|
||||
# not allowed around the '=' signs or in unquoted values.
|
||||
# Makefile variables are not defined here.
|
||||
# This file is read by the script base/src/libCom/env/bldEnvdata.pl
|
||||
# Variable definitions must take the form
|
||||
# VAR = VALUE
|
||||
# or
|
||||
# VAR = "Value containing spaces"
|
||||
# with each one on its own line.
|
||||
# Enclosing spaces and "" will be trimmed.
|
||||
#
|
||||
# Note: This file is read by base/src/libCom/env/bldEnvdata.pl,
|
||||
# so the variable definitions in here should be kept 'simple':
|
||||
# VAR=VALUE
|
||||
# each one on a single line.
|
||||
#
|
||||
|
||||
|
||||
# Default environment settings
|
||||
|
||||
|
||||
@@ -15,34 +15,42 @@
|
||||
#
|
||||
# CONFIG_SITE_ENV - EPICS Environment Parameter Site configuration file
|
||||
#
|
||||
# This file is interpreted by the Bourne Shell, so spaces are
|
||||
# not allowed around the '=' signs or in unquoted values.
|
||||
# Makefile variables are not defined here.
|
||||
#
|
||||
# Note: This file is read by base/src/libCom/env/bldEnvdata.pl,
|
||||
# so the variable definitions in here should be kept 'simple':
|
||||
# VAR=VALUE
|
||||
# each one on a single line.
|
||||
# This file is read by the script base/src/libCom/env/bldEnvdata.pl
|
||||
# Variable definitions must take the form
|
||||
# VAR = VALUE
|
||||
# or
|
||||
# VAR = "Value containing spaces"
|
||||
# with each one on its own line.
|
||||
# Enclosing spaces and "" will be trimmed.
|
||||
#
|
||||
|
||||
# Site-specific environment settings
|
||||
|
||||
# Time service:
|
||||
# EPICS_TIMEZONE needed for vxWorks
|
||||
# EPICS_TIMEZONE=<name>::<minutesWest>:<start daylight>:<end daylight>
|
||||
#NOTE: start and end are mmddhh that bis mounth,day,hour
|
||||
# eg EPICS_TIMEZONE=CUS::360:033102:102802
|
||||
# EPICS_TIMEZONE
|
||||
# local timezone info for vxWorks IOCs. The format required is
|
||||
# <name>::<minutesWest>:<start daylight>:<end daylight>
|
||||
# where the start and end are mmddhh - that is month,day,hour
|
||||
# eg EPICS_TIMEZONE=CUS::360:033102:102802
|
||||
#
|
||||
# DST for 2004 US: Apr 4 - Oct 31
|
||||
# EU: Mar 28 - Oct 31
|
||||
# (see: http://www.worldtimezone.org/daylight.html)
|
||||
# DST for 2004 US: Apr 4 - Oct 31
|
||||
# EU: Mar 28 - Oct 31
|
||||
# (see: http://www.worldtimezone.org/daylight.html)
|
||||
#
|
||||
# EPICS_TS_NTP_INET ntp or Unix time server ip addr.
|
||||
# EPICS_TS_NTP_INET
|
||||
# NTP or Unix time server ip address. Uses boot host if not set.
|
||||
|
||||
EPICS_TIMEZONE=CUS::360:040402:103102
|
||||
#EPICS_TIMEZONE=MET::-60:032802:103102
|
||||
EPICS_TS_NTP_INET=
|
||||
|
||||
# IOC Shell:
|
||||
# IOCSH_PS1
|
||||
# Prompt string
|
||||
# IOCSH_HISTSIZE
|
||||
# Number of lines of command history to keep.
|
||||
IOCSH_PS1="epics> "
|
||||
IOCSH_HISTSIZE=50
|
||||
|
||||
# Log Server:
|
||||
# EPICS_IOC_LOG_INET
|
||||
@@ -52,7 +60,7 @@ EPICS_TS_NTP_INET=
|
||||
# EPICS_IOC_LOG_FILE_LIMIT
|
||||
# maximum log file size.
|
||||
# EPICS_IOC_LOG_FILE_COMMAND
|
||||
# A shell command string used to obtain a new
|
||||
# A shell command string used to obtain a new
|
||||
# path name in response to SIGHUP - the new path name will
|
||||
# replace any path name supplied in EPICS_IOC_LOG_FILE_NAME
|
||||
|
||||
|
||||
@@ -11,9 +11,9 @@
|
||||
|
||||
##################################################### vpath
|
||||
|
||||
vpath %.dbd $(USR_VPATH) $(GENERIC_SRC_DIRS) $(dir $(DBD)) $(COMMON_DIR)
|
||||
vpath %.db $(USR_VPATH) $(GENERIC_SRC_DIRS) $(dir $(DB)) $(COMMON_DIR)
|
||||
vpath %.vdb $(USR_VPATH) $(GENERIC_SRC_DIRS) $(dir $(DB)) $(COMMON_DIR)
|
||||
vpath %.dbd $(USR_VPATH) $(GENERIC_SRC_DIRS) $(dir $(DBD))
|
||||
vpath %.db $(USR_VPATH) $(GENERIC_SRC_DIRS) $(dir $(DB))
|
||||
vpath %.vdb $(USR_VPATH) $(GENERIC_SRC_DIRS) $(dir $(DB))
|
||||
vpath %.substitutions $(USR_VPATH) $(GENERIC_SRC_DIRS) $(COMMON_DIR)
|
||||
vpath %.template $(USR_VPATH) $(GENERIC_SRC_DIRS) $(COMMON_DIR)
|
||||
vpath bpt%.data $(USR_VPATH) $(GENERIC_SRC_DIRS) $(COMMON_DIR)
|
||||
@@ -23,6 +23,7 @@ vpath bpt%.data $(USR_VPATH) $(GENERIC_SRC_DIRS) $(COMMON_DIR)
|
||||
# dbExpand
|
||||
INSTALL_DBDFLAGS += -I $(INSTALL_LOCATION)/dbd
|
||||
DBDFLAGS = $(USR_DBDFLAGS) -I . -I .. $(INSTALL_DBDFLAGS) $(RELEASE_DBDFLAGS)
|
||||
DBFLAGS = $($*_DBFLAGS) $(USR_DBFLAGS) -I. $(GENERIC_SRC_INCLUDES)
|
||||
|
||||
##################################################### Targets
|
||||
|
||||
@@ -192,10 +193,18 @@ $(INSTALL_DB)/%.template: %.template
|
||||
|
||||
##################################################### INC files
|
||||
|
||||
$(COMMON_DIR)/%Record.h: $(COMMON_DIR)/%Record.dbd
|
||||
@$(RM) $@
|
||||
$(DBTORECORDTYPEH) $(DBDFLAGS) $< $@
|
||||
|
||||
$(COMMON_DIR)/%Record.h: %Record.dbd
|
||||
@$(RM) $@
|
||||
$(DBTORECORDTYPEH) $(DBDFLAGS) $< $@
|
||||
|
||||
$(COMMON_DIR)/menu%.h: $(COMMON_DIR)/menu%.dbd
|
||||
@$(RM) $@
|
||||
$(DBTOMENUH) $< $@
|
||||
|
||||
$(COMMON_DIR)/menu%.h: menu%.dbd
|
||||
@$(RM) $@
|
||||
$(DBTOMENUH) $< $@
|
||||
@@ -206,6 +215,13 @@ $(COMMON_DIR)/bpt%.dbd: bpt%.data
|
||||
@$(RM) $@
|
||||
$(MAKEBPT) $< $@
|
||||
|
||||
$(COMMON_DIR)/%.dbd: $(COMMON_DIR)/%Include.dbd
|
||||
@$(RM) $@$(DEP)
|
||||
@$(DBDDEPENDS_CMD)
|
||||
@echo "Expanding dbd"
|
||||
@$(RM) $@
|
||||
$(DBEXPAND) $(DBDFLAGS) -o $@ $<
|
||||
|
||||
$(COMMON_DIR)/%.dbd: %Include.dbd
|
||||
@$(RM) $@$(DEP)
|
||||
@$(DBDDEPENDS_CMD)
|
||||
@@ -213,6 +229,14 @@ $(COMMON_DIR)/%.dbd: %Include.dbd
|
||||
@$(RM) $@
|
||||
$(DBEXPAND) $(DBDFLAGS) -o $@ $<
|
||||
|
||||
$(COMMON_DIR)/%Include.dbd:
|
||||
@$(RM) $@
|
||||
$(PERL) $(TOOLS)/makeIncludeDbd.pl $($*_DBD) $@
|
||||
|
||||
$(INSTALL_DBD)/%: $(COMMON_DIR)/%
|
||||
@echo "Installing dbd file $@"
|
||||
@$(INSTALL) -d -m 644 $< $(@D)
|
||||
|
||||
$(INSTALL_DBD)/%: %
|
||||
@echo "Installing dbd file $@"
|
||||
@$(INSTALL) -d -m 644 $< $(@D)
|
||||
@@ -221,7 +245,7 @@ dbdInstalls: $(DBD_INSTALLS)
|
||||
@echo "Installing $(^F)"
|
||||
@$(INSTALL) -d -m 555 $^ $(INSTALL_DBD)
|
||||
|
||||
.PRECIOUS: $(COMMON_DBDS)
|
||||
.PRECIOUS: $(COMMON_DBDS) $(COMMON_DIR)/%Include.dbd
|
||||
|
||||
##################################################### DB files
|
||||
|
||||
@@ -237,7 +261,15 @@ $(COMMON_DIR)/%.db$(RAW): %.substitutions
|
||||
@echo "$@:$(TEMPLATE_FILENAME)" >> $@$(DEP)
|
||||
@echo "Inflating database from $<"
|
||||
@$(RM) $@
|
||||
$(MSI) -S$< $(TEMPLATE_FILENAME) > msi.tmp
|
||||
$(MSI) $(DBFLAGS) -S$< $(TEMPLATE_FILENAME) > msi.tmp
|
||||
$(MV) msi.tmp $@
|
||||
|
||||
$(COMMON_DIR)/%.db$(RAW): %.template
|
||||
@$(RM) $@$(DEP)
|
||||
@$(DBDDEPENDS_CMD)
|
||||
@echo "Inflating database from $<"
|
||||
@$(RM) $@
|
||||
$(MSI) $(DBFLAGS) $< > msi.tmp
|
||||
$(MV) msi.tmp $@
|
||||
|
||||
# dbst based database optimization
|
||||
@@ -252,10 +284,6 @@ $(COMMON_DIR)/%.db: $(COMMON_DIR)/%.db$(RAW)
|
||||
@$(RM) $@
|
||||
$(DBST) . $< -d > $@
|
||||
|
||||
$(INSTALL_DB)/%.db: $(COMMON_DIR)/%.db
|
||||
@echo "Installing db file $@"
|
||||
@$(INSTALL) -d -m 644 $< $(@D)
|
||||
|
||||
.PRECIOUS: $(COMMON_DIR)/%.db
|
||||
.PRECIOUS: $(DB:%=$(COMMON_DIR)/%$(RAW))
|
||||
else
|
||||
@@ -265,6 +293,10 @@ $(INSTALL_DB)/%: %
|
||||
@$(INSTALL) -d -m 644 $< $(@D)
|
||||
endif
|
||||
|
||||
$(INSTALL_DB)/%.db: $(COMMON_DIR)/%.db
|
||||
@echo "Installing db file $@"
|
||||
@$(INSTALL) -d -m 644 $< $(@D)
|
||||
|
||||
dbInstalls: $(DB_INSTALLS)
|
||||
@echo "Installing $(^F)"
|
||||
@$(INSTALL) -d -m 555 $^ $(INSTALL_DB)
|
||||
@@ -274,6 +306,11 @@ dbInstalls: $(DB_INSTALLS)
|
||||
|
||||
##################################################### register record,device,driver support
|
||||
|
||||
%_registerRecordDeviceDriver.cpp: $(COMMON_DIR)/%.dbd
|
||||
@$(RM) $@ temp.cpp
|
||||
$(REGISTERRECORDDEVICEDRIVER) $< $(basename $@) > temp.cpp
|
||||
$(MV) temp.cpp $@
|
||||
|
||||
%_registerRecordDeviceDriver.cpp: %.dbd
|
||||
@$(RM) $@ temp.cpp
|
||||
$(REGISTERRECORDDEVICEDRIVER) $< $(basename $@) > temp.cpp
|
||||
|
||||
@@ -16,7 +16,7 @@ install: buildInstall
|
||||
buildInstall: $(TARGETS)
|
||||
|
||||
envPaths cdCommands: $(wildcard $(TOP)/configure/RELEASE*) \
|
||||
$(TOP)/configure/CONFIG $(TOP)/bin
|
||||
$(TOP)/configure/CONFIG $(INSTALL_BIN)
|
||||
@$(RM) $@
|
||||
ifeq ($(IOCS_APPL_TOP),)
|
||||
$(PERL) $(TOOLS)/convertRelease.pl -a $(ARCH) $@
|
||||
|
||||
@@ -68,6 +68,9 @@ $(checkReleaseTargets):checkRelease.%:
|
||||
clean ::
|
||||
$(RMDIR) $(addprefix O.,$(BUILD_ARCHS)) O.Common
|
||||
|
||||
archclean ::
|
||||
$(RMDIR) $(addprefix O.,$(BUILD_ARCHS))
|
||||
|
||||
$(cleanArchTargets) ::
|
||||
$(RMDIR) O.$(archPart)
|
||||
|
||||
@@ -77,6 +80,6 @@ realclean ::
|
||||
.PHONY : $(actionArchTargets)
|
||||
.PHONY : $(cleanArchTargets)
|
||||
.PHONY : $(BUILD_ARCHS)
|
||||
.PHONY : $(ACTIONS) clean realclean all
|
||||
.PHONY : $(ACTIONS) clean realclean archclean all
|
||||
.PHONY : checkRelease $(checkReleaseTargets)
|
||||
|
||||
|
||||
@@ -77,7 +77,7 @@ endif
|
||||
|
||||
ifneq (,$(strip $(PROD) $(TESTPROD) $(LIBRARY) $(LOADABLE_LIBRARY)))
|
||||
|
||||
MakefileInclude: ../Makefile
|
||||
MakefileInclude: ../Makefile $(wildcard $(TOP)/configure/RELEASE*)
|
||||
@$(RM) $@
|
||||
@$(PERL) $(TOOLS)/makeMakefileInclude.pl $(PROD) $(TESTPROD) $(LIBRARY) $(LOADABLE_LIBRARY) $@
|
||||
|
||||
|
||||
@@ -13,7 +13,7 @@
|
||||
|
||||
|
||||
ARCHS += $(BUILD_ARCHS)
|
||||
ACTIONS += inc build install buildInstall clean realclean
|
||||
ACTIONS += inc build install buildInstall clean realclean archclean
|
||||
|
||||
dirPart = $(word 1, $(subst $(DIVIDER), ,$@))
|
||||
actionArchPart = $(join $(word 2, $(subst $(DIVIDER), ,$@)), \
|
||||
|
||||
@@ -16,7 +16,6 @@
|
||||
|
||||
JAVA_INC = $(JAVA_DIR)/include
|
||||
JAVA_BIN = $(JAVA_DIR)/bin
|
||||
JAVA_INCLUDES += -I$(JAVA_INC) -I$(JAVA_INC)/$(OS_CLASS) -I$(COMMON_DIR)
|
||||
JAVA_INCLUDES += -I$(JAVA_INC) -I$(JAVA_INC)/$(word 1, $(subst -, ,$(T_A))) -I$(COMMON_DIR)
|
||||
|
||||
JAVACCMD = $(subst \,/,$(JAVA_BIN)/javac$(EXE) $(CLASSPATH) $(SOURCEPATH) $(JAVACFLAGS))
|
||||
|
||||
@@ -20,16 +20,20 @@ $(uninstallArchTargets): uninstallDirs
|
||||
@$(RMDIR) $(INSTALL_LOCATION_BIN)/$(archPart) $(INSTALL_LOCATION_LIB)/$(archPart)
|
||||
|
||||
cleandirs:
|
||||
@echo " " #stops "nothing to be done for cleandirs" message
|
||||
ifeq ($(wildcard $(INSTALL_LOCATION_BIN)/*),)
|
||||
@$(RMDIR) $(INSTALL_LOCATION_BIN)
|
||||
endif
|
||||
ifeq ($(wildcard $(INSTALL_LOCATION_LIB)/*),)
|
||||
@$(RMDIR) $(INSTALL_LOCATION_LIB)
|
||||
endif
|
||||
@echo
|
||||
# The echo above stops a "nothing to be done for cleandirs" message
|
||||
|
||||
distclean: realclean realuninstall
|
||||
|
||||
cvsclean:
|
||||
@$(PERL) $(TOOLS)/cvsclean.pl
|
||||
|
||||
realuninstall:
|
||||
@$(RMDIR) $(INSTALL_LOCATION_BIN) $(INSTALL_LOCATION_LIB)
|
||||
@$(RMDIR) $(INSTALL_DBD) $(INSTALL_INCLUDE) $(INSTALL_DOC)\
|
||||
@@ -57,6 +61,7 @@ help:
|
||||
@echo " rebuild - Same as clean install"
|
||||
@echo " inc - Installs header files"
|
||||
@echo " build - Builds all targets"
|
||||
@echo " archclean - Removes O.<arch> dirs but not O.Common dir"
|
||||
@echo "\"Partial\" build targets supported by Makefiles:"
|
||||
@echo " inc.<arch> - Installs <arch> only header files."
|
||||
@echo " install.<arch> - Builds and installs <arch> only."
|
||||
@@ -66,10 +71,12 @@ help:
|
||||
@echo " uninstall - Cleans directories created by the install."
|
||||
@echo " realuninstall - Removes ALL install dirs"
|
||||
@echo " distclean - Same as realclean realuninstall."
|
||||
@echo " cvsclean - Removes cvs .#* files in all dirs of directory tree"
|
||||
@echo " help - Prints this list of valid make targets "
|
||||
@echo "Indiv. object targets are supported by O.<arch> level Makefile .e.g"
|
||||
@echo " xxxRecord.o"
|
||||
|
||||
.PHONY : $(uninstallArchTargets)
|
||||
.PHONY : uninstall help cleandirs distclean uninstallDirs realuninstall
|
||||
.PHONY : cvsclean
|
||||
|
||||
|
||||
@@ -72,7 +72,7 @@ INC = file.h
|
||||
# defining a library
|
||||
# --------------------------------------------------------------------
|
||||
#
|
||||
# Contents of a library are specified via SRCS, LIBSRCS, or .._SRCS.
|
||||
# Contents of a library are specified via SRCS, LIB_SRCS, or .._SRCS.
|
||||
# From this the platform specific object names (.o, .obj, ...)
|
||||
# are derived automatically.
|
||||
#
|
||||
@@ -86,7 +86,7 @@ INC = file.h
|
||||
# ./os/OS_CLASS
|
||||
# ./os/generic
|
||||
# .
|
||||
# So usually only LIBSRCS should be sufficient!
|
||||
# So usually only LIB_SRCS should be sufficient!
|
||||
|
||||
# SRCS files will be used for both LIBRARY and PROD
|
||||
SRCS = file_for_lib.c another_file.cpp
|
||||
|
||||
@@ -98,8 +98,8 @@ CONFORM_CXXFLAGS_STRICT = -ansi
|
||||
|
||||
#--------------------------------------------------
|
||||
# Command-line input support
|
||||
COMMANDLINE_LIBRARY = LIBTECLA
|
||||
LDLIBS_LIBTECLA = -ltecla_r -lncurses
|
||||
LDLIBS_READLINE = -lreadline -lncurses
|
||||
|
||||
#--------------------------------------------------
|
||||
# Allow site overrides
|
||||
|
||||
@@ -16,6 +16,14 @@ VALID_BUILDS = Host Ioc
|
||||
# Gnu directory
|
||||
GNU_DIR = /usr/local
|
||||
|
||||
#-------------------------------------------------------
|
||||
FULLPATHTOP= $(shell perl $(TOOLS)/fullPathName.pl $(TOP))
|
||||
# Get fullpathname of modules relative to TOP
|
||||
SHRLIB_SEARCH_FULLPATHTOP = $(SHRLIB_SEARCH_DIRS:$(TOP)/%=$(FULLPATHTOP)/%)
|
||||
# Get fullpathname of other relative dirs
|
||||
SHRLIB_SEARCH_FULLPATHDIRS = $(SHRLIB_SEARCH_FULLPATHTOP:.%= \
|
||||
$(shell perl $(TOOLS)/fullPathName.pl .%)
|
||||
|
||||
#-------------------------------------------------------
|
||||
# Unix prefix and suffix definitions
|
||||
EXE =
|
||||
|
||||
@@ -1,10 +1,10 @@
|
||||
# CONFIG.Common.win32-x86-cygwin
|
||||
# CONFIG.Common.cygwin-x86
|
||||
#
|
||||
# $Id$
|
||||
# This file is maintained by the build community.
|
||||
#
|
||||
# Definitions for win32-x86-cygwin target builds
|
||||
# Sites may override these definitions in CONFIG_SITE.Common.win32-x86-cygwin
|
||||
# Definitions for cygwin-x86 target builds
|
||||
# Sites may override these definitions in CONFIG_SITE.Common.cygwin-x86
|
||||
#-------------------------------------------------------
|
||||
|
||||
# Include definitions common to all Unix targets
|
||||
@@ -15,11 +15,20 @@ ARCH_CLASS = x86
|
||||
|
||||
EXE=.exe
|
||||
|
||||
COMPILER_CPPFLAGS = -D_REENTRANT
|
||||
|
||||
#POSIX_CPPFLAGS_YES = -D_POSIX_SOURCE=199506L -D_POSIX_THREADS -D_POSIX_TIMERS
|
||||
# _POSIX_SOURCE eliminates select()
|
||||
POSIX_CPPFLAGS_YES = -D_POSIX_THREADS -D_POSIX_TIMERS
|
||||
#POSIX_LDLIBS_YES += -lpthread
|
||||
POSIX_LDLIBS_YES += -lpthread
|
||||
|
||||
ARCH_DEP_CPPFLAGS += -D_X86_
|
||||
|
||||
OP_SYS_CPPFLAGS += -DCYGWIN32 -U_WIN32
|
||||
|
||||
# Set runtime path for shared libraries
|
||||
RUNTIME_LDFLAGS = $(SHRLIB_SEARCH_DIRS:%=-Wl,-rpath,%)
|
||||
|
||||
LDLIBS_READLINE = -lcygreadline5 -lcygcurses7
|
||||
|
||||
@@ -26,7 +26,7 @@ LOADABLE_SHRLIB_SUFFIX = .sl
|
||||
# Set runtime path for shared libraries
|
||||
empty:= # trick from the make docs...
|
||||
space:= $(empty) $(empty)
|
||||
RUNTIME_LDFLAGS = -Wl,+b$(subst $(space),:,$(sort $(SHRLIB_SEARCH_DIRS))),+s
|
||||
RUNTIME_LDFLAGS = -Wl,+b$(subst $(space),:,$(sort $(SHRLIB_SEARCH_FULLPATHDIRS))),+s
|
||||
|
||||
ifeq ($(BUILD_CLASS),CROSS)
|
||||
GNU_TARGET=parisc-hp-unix
|
||||
|
||||
@@ -27,7 +27,7 @@ OP_SYS_LDLIBS += -lrt
|
||||
ARCH_DEP_CPPFLAGS += -D_X86_
|
||||
|
||||
# Set runtime path for shared libraries
|
||||
RUNTIME_LDFLAGS = $(SHRLIB_SEARCH_DIRS:%=-Wl,-rpath,%)
|
||||
RUNTIME_LDFLAGS = $(SHRLIB_SEARCH_FULLPATHDIRS:%=-Wl,-rpath,%)
|
||||
|
||||
ifeq ($(BUILD_CLASS),CROSS)
|
||||
ifeq ($(EPICS_HOST_ARCH),linux-x86)
|
||||
|
||||
@@ -13,22 +13,22 @@ include $(CONFIG)/os/CONFIG.Common.UnixCommon
|
||||
OS_CLASS = solaris
|
||||
ARCH_CLASS = sparc
|
||||
|
||||
CODE_CPPFLAGS = -D__EXTENSIONS__
|
||||
CODE_CPPFLAGS = -D__EXTENSIONS__
|
||||
|
||||
COMPILER_CPPFLAGS += -mt
|
||||
COMPILER_LDFLAGS += -mt
|
||||
|
||||
SOLARIS_VERSION = $(subst 5.,,$(shell uname -r))
|
||||
|
||||
# Flags for solaris 6
|
||||
POSIX_CPPFLAGS_YES_6 += -D_REENTRANT
|
||||
|
||||
POSIX_CPPFLAGS_YES += -D_POSIX_C_SOURCE=199506L $(POSIX_CPPFLAGS_YES_$(SOLARIS_VERSION))
|
||||
POSIX_CPPFLAGS_YES += -D_XOPEN_SOURCE=500
|
||||
POSIX_LDLIBS_YES_6 += -lthread
|
||||
POSIX_LDLIBS_YES += -lposix4 -lpthread $(POSIX_LDLIBS_YES_$(SOLARIS_VERSION))
|
||||
|
||||
OP_SYS_CPPFLAGS += -DSOLARIS=$(SOLARIS_VERSION)
|
||||
OP_SYS_CPPFLAGS += -DSOLARIS=$(SOLARIS_VERSION) $(COMPILER_CPPFLAGS)
|
||||
OP_SYS_LDFLAGS += $(COMPILER_LDFLAGS)
|
||||
|
||||
# Set runtime path for shared libraries
|
||||
RUNTIME_LDFLAGS = $(SHRLIB_SEARCH_DIRS:%=-R%)
|
||||
RUNTIME_LDFLAGS = $(SHRLIB_SEARCH_FULLPATHDIRS:%=-R%)
|
||||
|
||||
ifeq ($(BUILD_CLASS),CROSS)
|
||||
GNU_TARGET=sparc-sun-solaris2
|
||||
|
||||
@@ -11,7 +11,10 @@
|
||||
include $(CONFIG)/os/CONFIG.Common.solaris-sparc
|
||||
# CONFIG.Common.solaris-sparc
|
||||
|
||||
COMPILER_CPPFLAGS = -D_REENTRANT
|
||||
|
||||
OP_SYS_LDLIBS_8 = -lc
|
||||
OP_SYS_LDLIBS_9 = -lc
|
||||
|
||||
OP_SYS_LDFLAGS += -R$(GNU_LIB) -L$(GNU_LIB)
|
||||
|
||||
|
||||
@@ -15,21 +15,21 @@ ARCH_CLASS = x86
|
||||
|
||||
CODE_CPPFLAGS = -D__EXTENSIONS__
|
||||
|
||||
SOLARIS_VERSION = $(subst 5.,,$(shell uname -r))
|
||||
COMPILER_CPPFLAGS += -mt
|
||||
COMPILER_LDFLAGS += -mt
|
||||
|
||||
# Flags for solaris 6
|
||||
POSIX_CPPFLAGS_YES_6 += -D_REENTRANT
|
||||
SOLARIS_VERSION = $(subst 5.,,$(shell uname -r))
|
||||
|
||||
POSIX_CPPFLAGS_YES += -D_POSIX_C_SOURCE=199506L $(POSIX_CPPFLAGS_YES_$(SOLARIS_VERSION))
|
||||
POSIX_CPPFLAGS_YES += -D_XOPEN_SOURCE=500
|
||||
POSIX_LDLIBS_YES_6 += -lthread
|
||||
POSIX_LDLIBS_YES += -lposix4 -lpthread $(POSIX_LDLIBS_YES_$(SOLARIS_VERSION))
|
||||
|
||||
OP_SYS_CPPFLAGS += -DSOLARIS=$(SOLARIS_VERSION)
|
||||
OP_SYS_CPPFLAGS += -DSOLARIS=$(SOLARIS_VERSION) $(COMPILER_CPPFLAGS)
|
||||
OP_SYS_LDFLAGS += $(COMPILER_LDFLAGS)
|
||||
ARCH_DEP_CPPFLAGS = -D_X86_
|
||||
|
||||
# Set runtime path for shared libraries
|
||||
RUNTIME_LDFLAGS = $(SHRLIB_SEARCH_DIRS:%=-R%)
|
||||
RUNTIME_LDFLAGS = $(SHRLIB_SEARCH_FULLPATHDIRS:%=-R%)
|
||||
|
||||
ifeq ($(BUILD_CLASS),CROSS)
|
||||
GNU_TARGET=x86-sun-solaris2
|
||||
@@ -41,3 +41,13 @@ OP_SYS_LDLIBS += -lsocket -lnsl
|
||||
OP_SYS_LDLIBS_8 += -lCrun -lc -lCstd
|
||||
OP_SYS_LDLIBS_9 += -lCrun -lc -lCstd
|
||||
OP_SYS_LDLIBS += $(OP_SYS_LDLIBS_$(SOLARIS_VERSION))
|
||||
|
||||
# Definitions used when COMMANDLINE_LIBRARY is READLINE
|
||||
GNU_DIR = /opt/gnu
|
||||
INCLUDES_READLINE = -I$(GNU_DIR)/include
|
||||
LDFLAGS_READLINE += -R$(GNU_DIR)/lib
|
||||
LDFLAGS_READLINE += -L$(GNU_DIR)/lib
|
||||
LDLIBS_READLINE = -lreadline -lcurses
|
||||
# Use archive if there is a problem with the readline shared library
|
||||
#LDLIBS_READLINE = -Bstatic -lreadline -Bdynamic -lcurses
|
||||
|
||||
|
||||
@@ -10,3 +10,10 @@
|
||||
# Include definitions common to all solaris-x86 target archs
|
||||
include $(CONFIG)/os/CONFIG.Common.solaris-x86
|
||||
|
||||
COMPILER_CPPFLAGS = -D_REENTRANT
|
||||
|
||||
OP_SYS_LDLIBS_8 = -lc
|
||||
OP_SYS_LDLIBS_9 = -lc
|
||||
|
||||
OP_SYS_LDFLAGS += -R$(GNU_LIB) -L$(GNU_LIB)
|
||||
|
||||
|
||||
@@ -19,3 +19,4 @@ ARCH_CLASS = 68k
|
||||
ARCH_DEP_CPPFLAGS = -DCPU=MC68040
|
||||
ARCH_DEP_CFLAGS = -m68040
|
||||
|
||||
GNU_TARGET = m68k-wrs-vxworks
|
||||
|
||||
@@ -18,3 +18,5 @@ ARCH_CLASS = 68k
|
||||
# Architecture specific build flags
|
||||
ARCH_DEP_CPPFLAGS = -DCPU=MC68LC040
|
||||
ARCH_DEP_CFLAGS = -m68040 -msoft-float
|
||||
|
||||
GNU_TARGET = m68k-wrs-vxworks
|
||||
|
||||
@@ -19,3 +19,4 @@ ARCH_CLASS = 68k
|
||||
ARCH_DEP_CPPFLAGS = -DCPU=MC68060
|
||||
ARCH_DEP_CFLAGS = -m68040
|
||||
|
||||
GNU_TARGET = m68k-wrs-vxworks
|
||||
|
||||
@@ -19,3 +19,4 @@ ARCH_CLASS = ppc
|
||||
ARCH_DEP_CPPFLAGS = -DCPU=PPC603
|
||||
ARCH_DEP_CFLAGS = -mcpu=603 -mstrict-align
|
||||
|
||||
GNU_TARGET = powerpc-wrs-vxworks
|
||||
|
||||
@@ -19,3 +19,4 @@ ARCH_CLASS = ppc
|
||||
ARCH_DEP_CPPFLAGS = -DCPU=PPC603
|
||||
ARCH_DEP_CFLAGS = -mcpu=603 -mstrict-align -mlongcall
|
||||
|
||||
GNU_TARGET = powerpc-wrs-vxworks
|
||||
|
||||
@@ -19,3 +19,4 @@ ARCH_CLASS = ppc
|
||||
ARCH_DEP_CPPFLAGS = -DCPU=PPC604
|
||||
ARCH_DEP_CFLAGS = -mcpu=604 -mstrict-align
|
||||
|
||||
GNU_TARGET = powerpc-wrs-vxworks
|
||||
|
||||
@@ -19,3 +19,4 @@ ARCH_CLASS = ppc
|
||||
ARCH_DEP_CPPFLAGS = -DCPU=PPC604
|
||||
ARCH_DEP_CFLAGS = -mcpu=604 -mstrict-align -mlongcall
|
||||
|
||||
GNU_TARGET = powerpc-wrs-vxworks
|
||||
|
||||
@@ -1,10 +1,10 @@
|
||||
# CONFIG.win32-x86-cygwin.Common
|
||||
# CONFIG.cygwin-x86.Common
|
||||
#
|
||||
# $Id$
|
||||
# This file is maintained by the build community.
|
||||
#
|
||||
# Definitions for win32-x86-cygwin host archs
|
||||
# Sites may override these definitions in CONFIG_SITE.win32-x86-cygwin.Common
|
||||
# Definitions for cygwin-x86 host archs
|
||||
# Sites may override these definitions in CONFIG_SITE.cygwin-x86.Common
|
||||
#-------------------------------------------------------
|
||||
|
||||
#Include definitions common to unix hosts
|
||||
@@ -1,9 +1,9 @@
|
||||
# CONFIG.win32-x86-cygwin.win32-x86-cygwin
|
||||
# CONFIG.cygwin-x86.cygwin-x86
|
||||
#
|
||||
# $Id$
|
||||
#
|
||||
# Definitions for win32-x86-cygwin host - win32-x86-cygwin target builds
|
||||
# Sites may override these definitions in CONFIG_SITE.win32-x86-cygwin.win32-x86-cygwin
|
||||
# Definitions for cygwin-x86 host - cygwin-x86 target builds
|
||||
# Sites may override these definitions in CONFIG_SITE.cygwin-x86.cygwin-x86
|
||||
#-------------------------------------------------------
|
||||
|
||||
# Include common gnu compiler definitions
|
||||
@@ -21,5 +21,5 @@ LD = ld -r
|
||||
SHRLIB_LDFLAGS = -z defs -G -h $@
|
||||
LOADABLE_SHRLIB_LDFLAGS += -G -h $@
|
||||
|
||||
OP_SYS_LDFLAGS = -z ignore -z combreloc -z lazyload
|
||||
OP_SYS_LDFLAGS += -z ignore -z combreloc -z lazyload
|
||||
|
||||
|
||||
@@ -54,5 +54,5 @@ STATIC_LDLIBS_NO=
|
||||
SHRLIB_LDFLAGS = -z defs -KPIC -G -h $@
|
||||
LOADABLE_SHRLIB_LDFLAGS = -KPIC -G -h $@
|
||||
|
||||
OP_SYS_LDFLAGS = -z ignore -z combreloc -z lazyload
|
||||
OP_SYS_LDFLAGS += -z ignore -z combreloc -z lazyload
|
||||
|
||||
|
||||
@@ -91,9 +91,9 @@ STATIC_CFLAGS_YES= /MT$(VISC_STATIC_CFLAGS_DEBUG) $(VISC_DLL)
|
||||
STATIC_CFLAGS_NO= /MD$(VISC_STATIC_CFLAGS_DEBUG) $(VISC_DLL)
|
||||
|
||||
# OS vendor c preprocessor
|
||||
#CPP = cl /E
|
||||
CPP = cl /C /E
|
||||
#GNU c preprocessor
|
||||
CPP = gcc -x c -E
|
||||
#CPP = gcc -x c -E
|
||||
|
||||
# Configure OS vendor C++ compiler
|
||||
#
|
||||
|
||||
@@ -16,7 +16,7 @@ ARCH_Darwin = darwin-ppc
|
||||
ARCH_WIN32 = win32-x86
|
||||
ARCH_hp700 = hpux-parisc
|
||||
ARCH_alpha = osf-alpha
|
||||
ARCH_cygwin32 = win32-x86-cygwin
|
||||
ARCH_cygwin32 = cygwin-x86
|
||||
ARCH_Borland = win32-x86-borland
|
||||
|
||||
ifndef EPICS_HOST_ARCH
|
||||
|
||||
@@ -1,9 +1,9 @@
|
||||
# CONFIG_SITE.win32-x86-cygwin.Common
|
||||
# CONFIG_SITE.cygwin-x86.Common
|
||||
#
|
||||
# $Id$
|
||||
# This file is maintained by the build community.
|
||||
#
|
||||
# Site override definitions for win32-x86-cygwin host builds
|
||||
# Site override definitions for cygwin-x86 host builds
|
||||
#-------------------------------------------------------
|
||||
|
||||
CROSS_COMPILER_TARGET_ARCHS =
|
||||
@@ -1,9 +1,9 @@
|
||||
# CONFIG_SITE.win32-x86-cygwin.win32-x86-cygwin
|
||||
# CONFIG_SITE.cygwin-x86.cygwin-x86
|
||||
#
|
||||
# $Id$
|
||||
# This file is maintained by the build community.
|
||||
#
|
||||
# Site override definitions for win32-x86-cygwin host - win32-x86-cygwin target builds
|
||||
# Site override definitions for cygwin-x86 host - cygwin-x86 target builds
|
||||
#-------------------------------------------------------
|
||||
|
||||
##GNU_DIR=C:/cygwin
|
||||
@@ -15,7 +15,7 @@ eval 'exec perl -S $0 ${1+"$@"}' # -*- Mode: perl -*-
|
||||
# Parse configure/RELEASE file(s) and generate a derived output file.
|
||||
#
|
||||
|
||||
use Cwd;
|
||||
use Cwd qw(cwd abs_path);
|
||||
use Getopt::Std;
|
||||
|
||||
$cwd = cwd();
|
||||
@@ -72,7 +72,7 @@ $outfile = $ARGV[0];
|
||||
|
||||
# Read the RELEASE file(s)
|
||||
$relfile = "$top/configure/RELEASE";
|
||||
die "Can't find configure/RELEASE file" unless (-r $relfile);
|
||||
die "Can't find $relfile" unless (-f $relfile);
|
||||
&readReleaseFiles($relfile, \%macros, \@apps);
|
||||
&expandRelease(\%macros, \@apps);
|
||||
|
||||
@@ -302,7 +302,8 @@ sub checkRelease {
|
||||
delete $check{TOP};
|
||||
|
||||
while (($parent, $ppath) = each %check) {
|
||||
if (exists $macros{$parent} && ($macros{$parent} ne $ppath)) {
|
||||
if (exists $macros{$parent} &&
|
||||
abs_path($macros{$parent}) ne abs_path($ppath)) {
|
||||
print "\n" unless ($status);
|
||||
print "Definition of $parent conflicts with $app support.\n";
|
||||
print "In this application configure/RELEASE defines\n";
|
||||
|
||||
21
configure/tools/cvsclean.pl
Executable file
21
configure/tools/cvsclean.pl
Executable file
@@ -0,0 +1,21 @@
|
||||
eval 'exec perl -S $0 ${1+"$@"}' # -*- Mode: perl -*-
|
||||
if $running_under_some_shell; # cvsclean.pl
|
||||
#*************************************************************************
|
||||
# Copyright (c) 2002 The University of Chicago, as Operator of Argonne
|
||||
# National Laboratory.
|
||||
# Copyright (c) 2002 The Regents of the University of California, as
|
||||
# Operator of Los Alamos National Laboratory.
|
||||
# This file is distributed subject to a Software License Agreement found
|
||||
# in the file LICENSE that is included with this distribution.
|
||||
#*************************************************************************
|
||||
|
||||
# $Id$
|
||||
#
|
||||
# Find and delete cvs .#* files in all dirs of directory tree
|
||||
|
||||
use File::Find;
|
||||
|
||||
@ARGV = ('.') unless @ARGV;
|
||||
|
||||
find sub { unlink if -f && m/^\.\#/ }, @ARGV;
|
||||
|
||||
@@ -20,10 +20,14 @@ foreach( @files ) {
|
||||
open(INPUT, "<$_");
|
||||
$backup = "$_.bak";
|
||||
rename( $_, $backup) || die "Unable to rename $_\n$!\n";
|
||||
# Make the output be binary so it won't convert /n back to /r/n
|
||||
binmode OUTPUT, ":raw";
|
||||
open(OUTPUT, ">$_");
|
||||
binmode OUTPUT, ":raw";
|
||||
while(<INPUT>) {
|
||||
s/\r\n/\n/;
|
||||
print OUTPUT;
|
||||
# Remove CR-LF sequences
|
||||
s/\r\n/\n/;
|
||||
print OUTPUT;
|
||||
}
|
||||
close INPUT;
|
||||
close OUTPUT;
|
||||
|
||||
8
configure/tools/fullPathName.pl
Executable file
8
configure/tools/fullPathName.pl
Executable file
@@ -0,0 +1,8 @@
|
||||
eval 'exec perl -S -w $0 ${1+"$@"}' # -*- Mode: perl -*-
|
||||
if 0;
|
||||
|
||||
use Cwd 'abs_path';
|
||||
my $dir;
|
||||
$dir = abs_path("$ARGV[0]");
|
||||
print "$dir\n";
|
||||
|
||||
43
configure/tools/makeIncludeDbd.pl
Normal file
43
configure/tools/makeIncludeDbd.pl
Normal file
@@ -0,0 +1,43 @@
|
||||
#!/usr/bin/perl
|
||||
#*************************************************************************
|
||||
# Copyright (c) 2002 The University of Chicago, 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.
|
||||
#*************************************************************************
|
||||
#
|
||||
# $Id$
|
||||
|
||||
use File::Basename;
|
||||
|
||||
sub Usage
|
||||
{
|
||||
my ($txt) = @_;
|
||||
|
||||
print "Usage:\n";
|
||||
print "\tmakeIncludeDbd.pl infile1 [ infile2 infile3 ...] outfile\n";
|
||||
print "\nError: $txt\n" if $txt;
|
||||
|
||||
exit 2;
|
||||
}
|
||||
|
||||
# need at least two args: ARGV[0] and ARGV[1]
|
||||
Usage("\"makeIncludeDbd.pl @ARGV\": No input files specified") if $#ARGV < 1;
|
||||
|
||||
$target=$ARGV[$#ARGV];
|
||||
@sources=@ARGV[0..$#ARGV-1];
|
||||
|
||||
open(OUT, "> $target") or die "Cannot create $target\n";;
|
||||
foreach $file ( @sources )
|
||||
{
|
||||
$base=basename($file);
|
||||
print OUT "include \"$base\"\n";
|
||||
}
|
||||
|
||||
close OUT;
|
||||
|
||||
# EOF makeIncludeDbd.pl
|
||||
|
||||
@@ -28,6 +28,12 @@ applications subject to the following restrictions:</p>
|
||||
Ultimately applications should be converted to use the new configure rules so
|
||||
that the OSI features are available.
|
||||
|
||||
<h3>Prerequisite for building R3.13 applications</h3>
|
||||
<p>The macro COMPAT_313 must be set to YES in base/configure/CONFIG_SITE
|
||||
before the base build. This will install vxWorks object files and perl
|
||||
scripts needed for building R3.13 ioc applications.
|
||||
</p>
|
||||
|
||||
<h3><b>Gnumake clean uninstall</b></h3>
|
||||
|
||||
<p>At the top of the application execute:</p>
|
||||
|
||||
@@ -17,12 +17,28 @@ EPICS R3.13 extensions have both a Makefile and a Makefile.Host in the build
|
||||
directories and the EPICS R3.13 extension tree has an extensions/config
|
||||
directory.</p>
|
||||
|
||||
<h3>Prerequisite for building R3.13 extensions</h3>
|
||||
|
||||
<blockquote>
|
||||
<ul>
|
||||
<li>The macro COMPAT_TOOLS_313 must be set to YES in base/configure/CONFIG_SITE
|
||||
before the base build. If it was not set, set it to YES and then do a gmake
|
||||
in the base/config/tools directory. This will install some perl scripts needed
|
||||
for building R3.13 extensions.
|
||||
</li>
|
||||
</ul>
|
||||
</blockquote>
|
||||
|
||||
<h3>Preliminary steps for all extensions</h3>
|
||||
|
||||
<blockquote>
|
||||
<ul>
|
||||
<li>Download the latest version of the extensions/config files,
|
||||
extensionsConfig.tar.gz, from the APS EPICS www page.</li>
|
||||
The extensions directory can have both the base/config (for extensions with
|
||||
R3.13 makefiles) and base/configure (for extensions with R3.14 makefiles)
|
||||
directories.
|
||||
</li>
|
||||
<li>Make certain that you have set the HOST_ARCH environment
|
||||
variable.</li>
|
||||
<li>Set EPICS_BASE in extensions/config/RELEASE to the full path location
|
||||
|
||||
@@ -4,23 +4,14 @@
|
||||
<html xmlns="http://www.w3.org/1999/xhtml">
|
||||
<head>
|
||||
<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1" />
|
||||
<title>No title</title>
|
||||
<title>Known Problems R3.14.x</title>
|
||||
<meta name="GENERATOR" content="amaya 5.1" />
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<h1 style="text-align: center">EPICS base R3.14.4: Known Problems</h1>
|
||||
<h1 style="text-align: center">EPICS Base R3.14.6: Known Problems</h1>
|
||||
|
||||
<h3>Known Bugs R3.14.4</h3>
|
||||
|
||||
<h4>exampleApp sequencer</h4>
|
||||
<p>The following must be added to exampleInclude.dbd</p>
|
||||
</pre>registrar(sncExampleRegistrar)</pre>
|
||||
<h4>mbboRecord</h4>
|
||||
<p>
|
||||
If a database link is made to an mbbo record with a request type of DBR_STRING then the DBR_STRING value is the numeric value of the VAL field converted to a string. It should be the appropriate choice string indexed by the VAL field.
|
||||
An example is the DOL link of a stringout record linked to an mbbo record.
|
||||
This bug has been in all releases since 3.13.6<p>
|
||||
<p>None yet.</p>
|
||||
|
||||
</body>
|
||||
</html>
|
||||
|
||||
@@ -17,7 +17,10 @@ EPICS base</h2></center>
|
||||
|
||||
<center>
|
||||
<h2>
|
||||
Release 3.14.4</h2></center>
|
||||
Release 3.14.6</h2></center>
|
||||
|
||||
<p>
|
||||
<em>NOTE:</em> Parts of this document are likely to be out of date.</p>
|
||||
|
||||
<h3>
|
||||
What is EPICS base?</h3>
|
||||
@@ -60,18 +63,17 @@ directory and then make changes for your new platforms.</blockquote>
|
||||
c++ compiler>)</b>
|
||||
<blockquote>
|
||||
|
||||
<br><tt>aix-ppc</tt>
|
||||
<br><tt>cygwin-x86</tt>
|
||||
<br><tt>darwin-ppc (Mac OS X)</tt>
|
||||
<br><tt>hpux-parisc</tt>
|
||||
<br><tt>hpux-parisc-gnu</tt>
|
||||
<br><tt>linux-mpc82xx</tt>
|
||||
<br><tt>linux-x86</tt>
|
||||
<br><tt>lynxos-x86</tt>
|
||||
<br><tt>osf-alpha</tt>
|
||||
<br><tt>linux-x86-borland</tt>
|
||||
<br><tt>solaris-sparc</tt>
|
||||
<br><tt>solaris-sparc-gnu</tt>
|
||||
<br><tt>solaris-x86</tt>
|
||||
<br><tt>solaris-x86-gnu</tt>
|
||||
<br><tt>sun4-x86</tt>
|
||||
<br><tt>win32-x86</tt>
|
||||
<br><tt>win32-x86-borland</tt>
|
||||
|
||||
|
||||
@@ -7,11 +7,262 @@
|
||||
</head>
|
||||
|
||||
<body lang="en">
|
||||
<h1 align="center">EPICS Base Release 3.14.6<br>
|
||||
28 May 2004</h1>
|
||||
|
||||
<h1 align='center'>EPICS Base Release 3.14.5<br>
|
||||
4 February 2004</h1>
|
||||
<h2 align="center">Changes since 3.14.5</h2>
|
||||
|
||||
<h2 align='center'>Changes since 3.14.4</h2>
|
||||
<h4>CA command line tools complete</h4>
|
||||
|
||||
<p>The complete set of Channel Access command line tools (caget, caput,
|
||||
camonitor, cainfo) is available as announced during the May 2004
|
||||
Collab. meeting. Documentation is part of the CA Reference Manual. Be
|
||||
aware of possible name conflicts with existing local tools.</p>
|
||||
|
||||
<h4>IOC template file configure/RULES.iocBoot removed</h4>
|
||||
|
||||
<p>The directory name wildcards that were defined here have been moved to
|
||||
iocBoot/Makefile, which as a result is no longer unique in having its own
|
||||
configure/RULES file.</p>
|
||||
|
||||
<h4>APS Virtual Linac template removed</h4>
|
||||
|
||||
<p>This is really a demo and a complete EPICS IOC application, not a
|
||||
template. It will be made available separately.</p>
|
||||
|
||||
<h4>EPICS_HOST_ARCH win32-x86-cygwin renamed to cygwin-x86</h4>
|
||||
|
||||
<p>The EPICS_HOST_ARCH win32-x86-cygwin was renamed cygwin-x86 to avoid
|
||||
confusion about what OS interfaces are used on Windows: native win32 or
|
||||
cygwin's emulation of POSIX. Now we have</p>
|
||||
<ul>
|
||||
<li>win32-x86 Uses native win32 interfaces with MS compiler.</li>
|
||||
<li>win32-x86-borland Uses native win32 interfaces with borland
|
||||
compiler.</li>
|
||||
<li>win32-x86-gnu Uses native win32 interfaces with cygwin gnu compiler.
|
||||
(Not implemented yet.)</li>
|
||||
<li>cygwin-x86 Uses cygwin POSIX interfaces with cygwin gnu compiler.</li>
|
||||
</ul>
|
||||
|
||||
<h4>EPICS_TS_NTP_INET</h4>
|
||||
|
||||
<p>The time server's IP address used by the vxWorks clock routines was not
|
||||
reading the default value from the generated envData.c file but going
|
||||
straight to the boot host if no environment variable by that name was set.</p>
|
||||
|
||||
<h4>CONFIG_ENV and CONFIG_SITE_ENV</h4>
|
||||
|
||||
<p>These files are now parsed by a program that recognizes and ignores
|
||||
comment lines. Previous versions of this parser would extract settings from
|
||||
these files even if they appear on a line starting with a '#' character, so
|
||||
the last line containing a setting for any variable would give the value used
|
||||
as the default. This was first noticed in R3.14.5 where a commented-out
|
||||
setting for the <code>EPICS_TIMEZONE</code> parameter was added
|
||||
<em>after</em> the uncommented version.</p>
|
||||
|
||||
<h4>db test shell commands</h4>
|
||||
|
||||
<p>Many of the commands crashed if given no arguments. They are now more
|
||||
crash proof.</p>
|
||||
|
||||
<h4>db_access - conversion of double to float</h4>
|
||||
|
||||
<p>When a CA user asked for display or control limits as a float a 0 value
|
||||
was returned as -1.17549435E-38. This is now fixed.</p>
|
||||
|
||||
<h4>New DBD rule</h4>
|
||||
|
||||
<p>A new dbd rule will create a <name>Include.dbd from files specified
|
||||
in a <name>_DBD macro definition. An include line will be placed in the
|
||||
<name>Include.dbd for each file specified in the <name>_DBD
|
||||
definition. If a Makefile contains</p>
|
||||
<pre> DBD=xxx.dbd
|
||||
xxx_DBD = f1.dbd f2.dbd f3.dbd </pre>
|
||||
|
||||
<p>an xxxInclude.dbd file will be created containing the lines</p>
|
||||
<pre> include "f1.dbd"
|
||||
include "f2.dbd"
|
||||
include "f1.dbd"</pre>
|
||||
|
||||
<p>and dbExpand will be invoked to create the xxx.dbd file from the
|
||||
xxxInclude.dbd.</p>
|
||||
|
||||
<h4>Solaris Builds</h4>
|
||||
|
||||
<p>Old solaris 6 specific compiler options have been removed.</p>
|
||||
|
||||
<h4>New make targets cvsclean and archclean</h4>
|
||||
|
||||
<p>The new top level Makefile only target, cvsclean, removes cvs .#* files in
|
||||
all dirs of the top directory tree.</p>
|
||||
|
||||
<p>The new archclean target is like the clean target except that O.Common
|
||||
directories are not removed.</p>
|
||||
|
||||
<h4>epicsString</h4>
|
||||
|
||||
<p>Add epicsSnStrPrintEscaped.</p>
|
||||
|
||||
<h4>epicsExport</h4>
|
||||
|
||||
<p>epicsExportAddress(typ,obj) now generates an extern named pvar_typ_obj and
|
||||
epicsExportRegistrar(func) an extern named pvar_func_obj. Previously both
|
||||
just named the variable pobj.</p>
|
||||
|
||||
<p>epicsRegisterFunction(name) in conjunction with the dbd 'function' keyword
|
||||
can be used to register functions referred to by record subroutine name
|
||||
fields.</p>
|
||||
|
||||
<h4>Access Security</h4>
|
||||
|
||||
<p>The access security configuration rules now accept quoted strings where
|
||||
just names were allowed previously.</p>
|
||||
|
||||
<p>All dump routines now have FP version.</p>
|
||||
|
||||
<p>A new shell command "ascar(int level)" is now available. It produces a
|
||||
report of the INP channel access connections. Level (0,1,2) produces (a
|
||||
summary report, summary plus unconnected channels, summary plus report of all
|
||||
channels)</p>
|
||||
|
||||
<h4>Channel Access Client Library</h4>
|
||||
<ul>
|
||||
<li>Fixed "subscription updates intermittently do not resume when
|
||||
unresponsive circuit reconnects" bug
|
||||
<ul>
|
||||
<li>Scope:
|
||||
<p>This bug was introduced in R3.14.5 and does not exist in any other
|
||||
release.</p>
|
||||
</li>
|
||||
<li>Symptom:
|
||||
<p>Subscription updates intermittently do not resume depending on
|
||||
circumstances when unresponsive circuit reconnects</p>
|
||||
</li>
|
||||
<li>Additional Information:
|
||||
<p>A decision was made to add a change to EPICS R3.14.5 so that when
|
||||
a TCP circuit is temporarily unresponsive the channel, but not the
|
||||
circuit, is immediately disconnected. This change was determined to
|
||||
be necessary to improve overall system robustness in the face of IOC
|
||||
or network overload. Unfortunately, an error was made when installing
|
||||
these changes. I am sorry about any inconvenience that this has
|
||||
caused. Thanks to Ken Evans at the APS for discovering this
|
||||
problem.</p>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
<li>Fixed "ca_replace_access_rights_event() fails if passed a nill function
|
||||
pointer" bug
|
||||
<ul>
|
||||
<li>Scope:
|
||||
<p>This bug probably exists in all R3.14 releases.</p>
|
||||
</li>
|
||||
<li>Symptom:
|
||||
<p>Passing a nill function pointer to
|
||||
ca_replace_access_rights_event() should install a noop handler, but
|
||||
this currently causes a failure.</p>
|
||||
</li>
|
||||
<li>Additional information:
|
||||
<p>Regression tests have been installed to detect this mistake.</p>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
<li>Fixed "CA client library crash when clear channel request occurs in get
|
||||
callback handler" bug
|
||||
<ul>
|
||||
<li>Scope:
|
||||
<p>This bug was introduced in R3.14.5 and does not exist in any other
|
||||
release.</p>
|
||||
</li>
|
||||
<li>Symptom:
|
||||
<p>CA client library crash when clear channel request occurs in get
|
||||
callback handler</p>
|
||||
</li>
|
||||
<li>Additional information:
|
||||
<p>When testing the striptool application, Ken Evans, discovered a
|
||||
bug in the CA client library occurring when a clear channel request
|
||||
occurs in get callback handler. Regression tests have been updated so
|
||||
that this mistake will not slip through testing undetected in a
|
||||
future release.</p>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
<li>Fixed "Double server subscription install when subscription request
|
||||
occurs in connection callback handler" bug
|
||||
<ul>
|
||||
<li>Scope:
|
||||
<p>This bug was introduced in R3.14.5 and does not exist in any other
|
||||
release. Subscription request must be made from within connection
|
||||
callback handler</p>
|
||||
</li>
|
||||
<li>Symptom:
|
||||
<p>It has been discovered (by Ken Evans while testing the gateway)
|
||||
that certain subscription requests were persisting in the gateway
|
||||
after clients had deleted them. This bug causes additional resources
|
||||
to be consumed, but does not result in a crash.</p>
|
||||
</li>
|
||||
<li>Additional information
|
||||
<p>Additional debugging has revealed that the CA client library in
|
||||
this situation inadvertently made the subscription request twice:
|
||||
once at the users’ request, and later on again when the
|
||||
library auto installed subscriptions for disconnected channels.</p>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
<li>Fixed "failure when deleting channel in get callback handler" bug
|
||||
<ul>
|
||||
<li>Scope:
|
||||
<p>Probably introduced in a previous R3.14 release.</p>
|
||||
</li>
|
||||
<li>Symptom:
|
||||
<p>An intermittent C++ exceptions during regression testing.</p>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
</ul>
|
||||
<ul>
|
||||
<li>Behavior Changes
|
||||
<ul>
|
||||
<li>Process blocks attempting to exit if the application does not call
|
||||
ca_context_destroy()
|
||||
<p>In EPICS release R3.14 the CA client library is implemented using
|
||||
axillary threads. If the application does not call
|
||||
ca_context_destroy() these threads will still be running, and
|
||||
depending on operating system conventions the process may
|
||||
<em>not</em> exit if the main thread exits, but axillary threads are
|
||||
still running. Note that ca_context_destroy() is functionally
|
||||
equivalent to the deprecated call ca_task_exit().</p>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
</ul>
|
||||
|
||||
<h4>Channel Access Portable Server (used by the CA gateway and others)</h4>
|
||||
<ul>
|
||||
<li>Fixed "assert fail when writing string through Portable CA Server" bug
|
||||
<ul>
|
||||
<li>Scope:
|
||||
<p>This bug is only present in the portable CA server and so it does
|
||||
<em>not</em> impact IOC based applications. The bug is present in the
|
||||
CA gateway and any portable CA server based application. This problem
|
||||
may have been recently introduced when GDD was patched to properly
|
||||
handle fixed sized strings.</p>
|
||||
</li>
|
||||
<li>Symptom:
|
||||
<p>Failure, when writing large string through the portable CA server.
|
||||
There appears to be a possibility of the wrong string being written
|
||||
when a smaller string is used. You may see the following message.</p>
|
||||
<p>A call to "assert (! this->pValue->unreference ())" failed
|
||||
in ..\..\..\..\include\smartGDDPointer.h line 88.</p>
|
||||
</li>
|
||||
<li>Additional Information:
|
||||
<p>Thanks to Stephanie Alison at SLAC for discovering the bug and to
|
||||
Ken Evans at the APS for reminding me to fix it.</p>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
</ul>
|
||||
|
||||
<h2 align="center">Changes since 3.14.4</h2>
|
||||
|
||||
<h4>dbtr</h4>
|
||||
|
||||
@@ -71,7 +322,7 @@ to experiment with other CA client tools.</p>
|
||||
<h4>Stringin record time-stamp soft device support</h4>
|
||||
Add simple device support for converting time to nicely-formatted string
|
||||
using INP field as epicsTimeToStrftime format string:
|
||||
<pre>record(stringin, "$(user):now")
|
||||
<pre>record(stringin, "$(user)now")
|
||||
{
|
||||
field(DESC, "Current time and date")
|
||||
field(DTYP, "Soft Timestamp")
|
||||
@@ -88,7 +339,7 @@ using INP field as epicsTimeToStrftime format string:
|
||||
production CA gateway at the APS.</li>
|
||||
</ul>
|
||||
|
||||
<h4>Channel Access Original Server (used in IOC) </h4>
|
||||
<h4>Channel Access Original Server (used in IOC)</h4>
|
||||
<ul>
|
||||
<li>A bug causing the server threads to become stuck in a state where they
|
||||
process requests, but no longer send responses, if in the past the system
|
||||
@@ -133,6 +384,10 @@ using INP field as epicsTimeToStrftime format string:
|
||||
channels in these situations at 2 seconds but due to the above bug the
|
||||
delay was more like 64mS. This bug appears only in earlier versions of
|
||||
EPICS R3.14.</li>
|
||||
<li>A bug has been found in the CA repeater supplied with EPICS R3.14.2
|
||||
through R3.14.4 (inclusive). The symptom will be clients running for more
|
||||
than a few minuites do not connect to a newly introduced server. Fixed in
|
||||
R3.14.5.</li>
|
||||
</ul>
|
||||
|
||||
<h4>dbCa</h4>
|
||||
|
||||
@@ -41,7 +41,7 @@ have been responsible for specific tasks in the past:</p>
|
||||
</tr>
|
||||
<tr>
|
||||
<td> </td>
|
||||
<td>Marty Kraimer</td>
|
||||
<td>Release Manager</td>
|
||||
<td>Email all developers about the upcoming release and ask for a list
|
||||
of remaining jobs that must be finished.</td>
|
||||
</tr>
|
||||
@@ -54,7 +54,7 @@ have been responsible for specific tasks in the past:</p>
|
||||
</tr>
|
||||
<tr>
|
||||
<td> </td>
|
||||
<td>Marty Kraimer</td>
|
||||
<td>Release Manager</td>
|
||||
<td>Set a date by which all CVS commits must be done, after which
|
||||
commits should only be to fix problems that show up during Final
|
||||
Testing.</td>
|
||||
@@ -104,6 +104,18 @@ have been responsible for specific tasks in the past:</p>
|
||||
<td>Run the CA client side regression tests on all available host
|
||||
platforms.</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td> </td>
|
||||
<td>Release Manager</td>
|
||||
<td>Check that the documentation has been updated:
|
||||
<ul>
|
||||
<li>Application Developers Guide</li>
|
||||
<li>Release Notes</li>
|
||||
<li>Known Problems (hopefully empty)</li>
|
||||
<li>Other documents (converting...)</li>
|
||||
</ul>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td> </td>
|
||||
<td>?</td>
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
/*asCa.c*/
|
||||
/*************************************************************************\
|
||||
* Copyright (c) 2002 The University of Chicago, as Operator of Argonne
|
||||
* National Laboratory.
|
||||
@@ -7,8 +8,6 @@
|
||||
* and higher are distributed subject to a Software License Agreement found
|
||||
* in file LICENSE that is included with this distribution.
|
||||
\*************************************************************************/
|
||||
/* share/src/as/asCa.c */
|
||||
/* share/src/as $Id$ */
|
||||
/* Author: Marty Kraimer Date: 10-15-93 */
|
||||
|
||||
/*This module is separate from asDbLib because CA uses old database access*/
|
||||
@@ -32,12 +31,13 @@
|
||||
#include "caeventmask.h"
|
||||
#include "alarm.h"
|
||||
|
||||
#define epicsExportSharedSymbols
|
||||
#include "epicsExport.h"
|
||||
#include "asLib.h"
|
||||
#include "asDbLib.h"
|
||||
#include "asCa.h"
|
||||
|
||||
epicsShareDef int asCaDebug = 0;
|
||||
int asCaDebug = 0;
|
||||
epicsExportAddress(int,asCaDebug);
|
||||
LOCAL int firstTime = TRUE;
|
||||
LOCAL epicsThreadId threadid=0;
|
||||
LOCAL int caInitializing=FALSE;
|
||||
@@ -259,3 +259,46 @@ void epicsShareAPI asCaStop(void)
|
||||
if(asCaDebug) printf("asCaStop done\n");
|
||||
epicsMutexUnlock(asCaTaskLock);
|
||||
}
|
||||
|
||||
int epicsShareAPI ascar(int level) {return ascarFP(stdout,level);}
|
||||
|
||||
int epicsShareAPI ascarFP(FILE *fp,int level)
|
||||
{
|
||||
ASG *pasg;
|
||||
int n=0,nbad=0;
|
||||
enum channel_state state;
|
||||
|
||||
if(!pasbase) {
|
||||
fprintf(fp,"access security not started\n");
|
||||
return(0);
|
||||
}
|
||||
pasg = (ASG *)ellFirst(&pasbase->asgList);
|
||||
while(pasg) {
|
||||
ASGINP *pasginp;
|
||||
pasginp = (ASGINP *)ellFirst(&pasg->inpList);
|
||||
while(pasginp) {
|
||||
CAPVT *pcapvt = (CAPVT *)pasginp->capvt;
|
||||
chid chid = pcapvt->chid;
|
||||
pcapvt = pasginp->capvt;
|
||||
++n;
|
||||
state = ca_state(chid);
|
||||
if(state!=cs_conn) ++nbad;
|
||||
if(level>1 || (level==1 && state!=cs_conn)) {
|
||||
fprintf(fp,"connected:");
|
||||
if(state==cs_never_conn) fprintf(fp,"never ");
|
||||
else if(state==cs_prev_conn) fprintf(fp,"prev ");
|
||||
else if(state==cs_conn) fprintf(fp,"yes ");
|
||||
else if(state==cs_closed) fprintf(fp,"closed");
|
||||
else fprintf(fp,"unknown");
|
||||
fprintf(fp," read:%s write:%s",
|
||||
(ca_read_access(chid) ? "yes" : "no "),
|
||||
(ca_write_access(chid) ? "yes" : "no "));
|
||||
fprintf(fp," %s %s\n", ca_name(chid),ca_host_name(chid));
|
||||
}
|
||||
pasginp = (ASGINP *)ellNext((ELLNODE *)pasginp);
|
||||
}
|
||||
pasg = (ASG *)ellNext((ELLNODE *)pasg);
|
||||
}
|
||||
fprintf(fp,"%d channels %d not connected\n",n,nbad);
|
||||
return(0);
|
||||
}
|
||||
|
||||
@@ -20,7 +20,8 @@ extern "C" {
|
||||
|
||||
epicsShareFunc void epicsShareAPI asCaStart(void);
|
||||
epicsShareFunc void epicsShareAPI asCaStop(void);
|
||||
epicsShareExtern int asCaDebug;
|
||||
epicsShareFunc int epicsShareAPI ascar(int level);
|
||||
epicsShareFunc int epicsShareAPI ascarFP(FILE *fp, int level);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
/* share/src/as/asDbLib.c */
|
||||
/*************************************************************************\
|
||||
* Copyright (c) 2002 The University of Chicago, as Operator of Argonne
|
||||
* National Laboratory.
|
||||
@@ -7,8 +8,6 @@
|
||||
* and higher are distributed subject to a Software License Agreement found
|
||||
* in file LICENSE that is included with this distribution.
|
||||
\*************************************************************************/
|
||||
/* share/src/as/asDbLib.c */
|
||||
/* share/src/as $Id$ */
|
||||
/* Author: Marty Kraimer Date: 02-11-94*/
|
||||
|
||||
#include <stdlib.h>
|
||||
@@ -259,41 +258,72 @@ int epicsShareAPI astac(char *pname,char *user,char *location)
|
||||
return(0);
|
||||
}
|
||||
|
||||
static void myMemberCallback(ASMEMBERPVT memPvt)
|
||||
static void myMemberCallback(ASMEMBERPVT memPvt,FILE *fp)
|
||||
{
|
||||
dbCommon *precord;
|
||||
|
||||
precord = asGetMemberPvt(memPvt);
|
||||
if(precord) printf(" Record:%s",precord->name);
|
||||
if(precord) fprintf(fp," Record:%s",precord->name);
|
||||
}
|
||||
|
||||
int epicsShareAPI asdbdump(void)
|
||||
{
|
||||
asDump(myMemberCallback,NULL,1);
|
||||
asDumpFP(stdout,myMemberCallback,NULL,1);
|
||||
return(0);
|
||||
}
|
||||
|
||||
int epicsShareAPI asdbdumpFP(FILE *fp)
|
||||
{
|
||||
asDumpFP(fp,myMemberCallback,NULL,1);
|
||||
return(0);
|
||||
}
|
||||
|
||||
int epicsShareAPI aspuag(char *uagname)
|
||||
{
|
||||
|
||||
asDumpUag(uagname);
|
||||
asDumpUagFP(stdout,uagname);
|
||||
return(0);
|
||||
}
|
||||
|
||||
int epicsShareAPI aspuagFP(FILE *fp,char *uagname)
|
||||
{
|
||||
|
||||
asDumpUagFP(fp,uagname);
|
||||
return(0);
|
||||
}
|
||||
|
||||
int epicsShareAPI asphag(char *hagname)
|
||||
{
|
||||
asDumpHag(hagname);
|
||||
asDumpHagFP(stdout,hagname);
|
||||
return(0);
|
||||
}
|
||||
|
||||
int epicsShareAPI asphagFP(FILE *fp,char *hagname)
|
||||
{
|
||||
asDumpHagFP(fp,hagname);
|
||||
return(0);
|
||||
}
|
||||
|
||||
int epicsShareAPI asprules(char *asgname)
|
||||
{
|
||||
asDumpRules(asgname);
|
||||
asDumpRulesFP(stdout,asgname);
|
||||
return(0);
|
||||
}
|
||||
|
||||
int epicsShareAPI asprulesFP(FILE *fp,char *asgname)
|
||||
{
|
||||
asDumpRulesFP(fp,asgname);
|
||||
return(0);
|
||||
}
|
||||
|
||||
int epicsShareAPI aspmem(char *asgname,int clients)
|
||||
{
|
||||
asDumpMem(asgname,myMemberCallback,clients);
|
||||
asDumpMemFP(stdout,asgname,myMemberCallback,clients);
|
||||
return(0);
|
||||
}
|
||||
|
||||
int epicsShareAPI aspmemFP(FILE *fp,char *asgname,int clients)
|
||||
{
|
||||
asDumpMemFP(fp,asgname,myMemberCallback,clients);
|
||||
return(0);
|
||||
}
|
||||
|
||||
@@ -32,11 +32,16 @@ epicsShareFunc int epicsShareAPI asInit(void);
|
||||
epicsShareFunc int epicsShareAPI asInitAsyn(ASDBCALLBACK *pcallback);
|
||||
epicsShareFunc int epicsShareAPI asDbGetAsl( void *paddr);
|
||||
epicsShareFunc void * epicsShareAPI asDbGetMemberPvt( void *paddr);
|
||||
epicsShareFunc int epicsShareAPI asdbdump( void);
|
||||
epicsShareFunc int epicsShareAPI asdbdump(void);
|
||||
epicsShareFunc int epicsShareAPI asdbdumpFP(FILE *fp);
|
||||
epicsShareFunc int epicsShareAPI aspuag(char *uagname);
|
||||
epicsShareFunc int epicsShareAPI aspuagFP(FILE *fp,char *uagname);
|
||||
epicsShareFunc int epicsShareAPI asphag(char *hagname);
|
||||
epicsShareFunc int epicsShareAPI asphagFP(FILE *fp,char *hagname);
|
||||
epicsShareFunc int epicsShareAPI asprules(char *asgname);
|
||||
epicsShareFunc int epicsShareAPI asprulesFP(FILE *fp,char *asgname);
|
||||
epicsShareFunc int epicsShareAPI aspmem(char *asgname,int clients);
|
||||
epicsShareFunc int epicsShareAPI aspmemFP(FILE *fp,char *asgname,int clients);
|
||||
epicsShareFunc int epicsShareAPI astac(
|
||||
char *recordname,char *user,char *location);
|
||||
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
/* asLib.h */
|
||||
/*************************************************************************\
|
||||
* Copyright (c) 2002 The University of Chicago, as Operator of Argonne
|
||||
* National Laboratory.
|
||||
@@ -7,7 +8,6 @@
|
||||
* and higher are distributed subject to a Software License Agreement found
|
||||
* in file LICENSE that is included with this distribution.
|
||||
\*************************************************************************/
|
||||
/* $Id$ */
|
||||
/* Author: Marty Kraimer Date: 09-27-93*/
|
||||
|
||||
#ifndef INCasLibh
|
||||
@@ -72,13 +72,24 @@ epicsShareFunc long epicsShareAPI asComputeAllAsg(void);
|
||||
epicsShareFunc long epicsShareAPI asComputeAsg(ASG *pasg);
|
||||
*/
|
||||
epicsShareFunc long epicsShareAPI asCompute(ASCLIENTPVT asClientPvt);
|
||||
epicsShareFunc int epicsShareAPI asDump(void (*memcallback)(ASMEMBERPVT),
|
||||
void (*clientcallback)(ASCLIENTPVT),int verbose);
|
||||
epicsShareFunc int epicsShareAPI asDump(
|
||||
void (*memcallback)(ASMEMBERPVT,FILE *),
|
||||
void (*clientcallback)(ASCLIENTPVT,FILE *),int verbose);
|
||||
epicsShareFunc int epicsShareAPI asDumpFP(FILE *fp,
|
||||
void (*memcallback)(ASMEMBERPVT,FILE *),
|
||||
void (*clientcallback)(ASCLIENTPVT,FILE *),int verbose);
|
||||
epicsShareFunc int epicsShareAPI asDumpUag(char *uagname);
|
||||
epicsShareFunc int epicsShareAPI asDumpUagFP(FILE *fp,char *uagname);
|
||||
epicsShareFunc int epicsShareAPI asDumpHag(char *hagname);
|
||||
epicsShareFunc int epicsShareAPI asDumpHagFP(FILE *fp,char *hagname);
|
||||
epicsShareFunc int epicsShareAPI asDumpRules(char *asgname);
|
||||
epicsShareFunc int epicsShareAPI asDumpMem(char *asgname,void (*memcallback)(ASMEMBERPVT),int clients);
|
||||
epicsShareFunc int epicsShareAPI asDumpRulesFP(FILE *fp,char *asgname);
|
||||
epicsShareFunc int epicsShareAPI asDumpMem(char *asgname,
|
||||
void (*memcallback)(ASMEMBERPVT,FILE *),int clients);
|
||||
epicsShareFunc int epicsShareAPI asDumpMemFP(FILE *fp,char *asgname,
|
||||
void (*memcallback)(ASMEMBERPVT,FILE *),int clients);
|
||||
epicsShareFunc int epicsShareAPI asDumpHash(void);
|
||||
epicsShareFunc int epicsShareAPI asDumpHashFP(FILE *fp);
|
||||
|
||||
epicsShareFunc void * epicsShareAPI asTrapWriteBeforeWrite(
|
||||
const char *userid,const char *hostid,void *addr);
|
||||
|
||||
@@ -1,3 +1,12 @@
|
||||
/*************************************************************************\
|
||||
* Copyright (c) 2002 The University of Chicago, 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.
|
||||
\*************************************************************************/
|
||||
%{
|
||||
static int yyerror();
|
||||
static int yy_start;
|
||||
@@ -16,7 +25,7 @@ static ASGRULE *yyAsgRule=NULL;
|
||||
%token tokenUAG tokenHAG tokenASG tokenRULE tokenCALC
|
||||
%token <Str> tokenINP
|
||||
%token <Int> tokenINTEGER
|
||||
%token <Str> tokenNAME tokenSTRING
|
||||
%token <Str> tokenSTRING
|
||||
|
||||
%union
|
||||
{
|
||||
@@ -39,7 +48,7 @@ asconfig_item: tokenUAG uag_head uag_body
|
||||
| tokenASG asg_head
|
||||
;
|
||||
|
||||
uag_head: '(' tokenNAME ')'
|
||||
uag_head: '(' tokenSTRING ')'
|
||||
{
|
||||
yyUag = asUagAdd($2);
|
||||
if(!yyUag) yyerror("");
|
||||
@@ -57,19 +66,15 @@ uag_user_list: uag_user_list ',' uag_user_list_name
|
||||
| uag_user_list_name
|
||||
;
|
||||
|
||||
uag_user_list_name: tokenNAME
|
||||
uag_user_list_name: tokenSTRING
|
||||
{
|
||||
long status;
|
||||
|
||||
status = asUagAddUser(yyUag,$1);
|
||||
if(status) {
|
||||
if (asUagAddUser(yyUag,$1))
|
||||
yyerror($1);
|
||||
}
|
||||
free((void *)$1);
|
||||
}
|
||||
;
|
||||
|
||||
hag_head: '(' tokenNAME ')'
|
||||
hag_head: '(' tokenSTRING ')'
|
||||
{
|
||||
yyHag = asHagAdd($2);
|
||||
if(!yyHag) yyerror("");
|
||||
@@ -84,19 +89,15 @@ hag_user_list: hag_user_list ',' hag_user_list_name
|
||||
| hag_user_list_name
|
||||
;
|
||||
|
||||
hag_user_list_name: tokenNAME
|
||||
hag_user_list_name: tokenSTRING
|
||||
{
|
||||
long status;
|
||||
|
||||
status = asHagAddHost(yyHag,$1);
|
||||
if(status) {
|
||||
if (asHagAddHost(yyHag,$1))
|
||||
yyerror("");
|
||||
}
|
||||
free((void *)$1);
|
||||
}
|
||||
;
|
||||
|
||||
asg_head: '(' tokenNAME ')'
|
||||
asg_head: '(' tokenSTRING ')'
|
||||
{
|
||||
yyAsg = asAsgAdd($2);
|
||||
if(!yyAsg) yyerror("");
|
||||
@@ -116,17 +117,13 @@ asg_body_item: inp_config | rule_config
|
||||
|
||||
inp_config: tokenINP '(' inp_body ')'
|
||||
{
|
||||
long status;
|
||||
|
||||
status = asAsgAddInp(yyAsg,$<Str>3,$<Int>1);
|
||||
if(status) {
|
||||
if (asAsgAddInp(yyAsg,$<Str>3,$<Int>1))
|
||||
yyerror("");
|
||||
}
|
||||
free((void *)$<Str>3);
|
||||
}
|
||||
;
|
||||
|
||||
inp_body: tokenNAME
|
||||
inp_body: tokenSTRING
|
||||
;
|
||||
|
||||
rule_config: tokenRULE rule_head rule_body
|
||||
@@ -134,7 +131,7 @@ rule_config: tokenRULE rule_head rule_body
|
||||
|
||||
rule_head: rule_head_manditory rule_head_options
|
||||
|
||||
rule_head_manditory: '(' tokenINTEGER ',' tokenNAME
|
||||
rule_head_manditory: '(' tokenINTEGER ',' tokenSTRING
|
||||
{
|
||||
asAccessRights rights;
|
||||
|
||||
@@ -156,7 +153,7 @@ rule_head_manditory: '(' tokenINTEGER ',' tokenNAME
|
||||
rule_head_options: ')'
|
||||
| rule_log_options
|
||||
|
||||
rule_log_options: ',' tokenNAME ')'
|
||||
rule_log_options: ',' tokenSTRING ')'
|
||||
{
|
||||
if((strcmp($2,"TRAPWRITE")==0)) {
|
||||
long status;
|
||||
@@ -180,12 +177,8 @@ rule_list_item: tokenUAG '(' rule_uag_list ')'
|
||||
| tokenHAG '(' rule_hag_list ')'
|
||||
| tokenCALC '(' tokenSTRING ')'
|
||||
{
|
||||
long status;
|
||||
|
||||
status = asAsgRuleCalc(yyAsgRule,$3);
|
||||
if(status){
|
||||
yyerror("access security CALC failure");
|
||||
}
|
||||
if (asAsgRuleCalc(yyAsgRule,$3))
|
||||
yyerror("access security CALC failure");
|
||||
free((void *)$3);
|
||||
}
|
||||
;
|
||||
@@ -194,14 +187,10 @@ rule_uag_list: rule_uag_list ',' rule_uag_list_name
|
||||
| rule_uag_list_name
|
||||
;
|
||||
|
||||
rule_uag_list_name: tokenNAME
|
||||
rule_uag_list_name: tokenSTRING
|
||||
{
|
||||
long status;
|
||||
|
||||
status = asAsgRuleUagAdd(yyAsgRule,$1);
|
||||
if(status) {
|
||||
yyerror("");
|
||||
}
|
||||
if (asAsgRuleUagAdd(yyAsgRule,$1))
|
||||
yyerror("");
|
||||
free((void *)$1);
|
||||
}
|
||||
;
|
||||
@@ -210,14 +199,10 @@ rule_hag_list: rule_hag_list ',' rule_hag_list_name
|
||||
| rule_hag_list_name
|
||||
;
|
||||
|
||||
rule_hag_list_name: tokenNAME
|
||||
rule_hag_list_name: tokenSTRING
|
||||
{
|
||||
long status;
|
||||
|
||||
status = asAsgRuleHagAdd(yyAsgRule,$1);
|
||||
if(status) {
|
||||
yyerror("");
|
||||
}
|
||||
if (asAsgRuleHagAdd(yyAsgRule,$1))
|
||||
yyerror("");
|
||||
free((void *)$1);
|
||||
}
|
||||
;
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
/* share/src/as/asLibRoutines.c */
|
||||
/*************************************************************************\
|
||||
* Copyright (c) 2002 The University of Chicago, as Operator of Argonne
|
||||
* National Laboratory.
|
||||
@@ -7,8 +8,6 @@
|
||||
* and higher are distributed subject to a Software License Agreement found
|
||||
* in file LICENSE that is included with this distribution.
|
||||
\*************************************************************************/
|
||||
/* share/src/as/asLibRoutines.c */
|
||||
/* share/src/as $Id$ */
|
||||
/* Author: Marty Kraimer Date: 10-15-93 */
|
||||
|
||||
#include <stdlib.h>
|
||||
@@ -466,8 +465,17 @@ static char *asAccessName[] = {"NONE","READ","WRITE"};
|
||||
static char *asTrapOption[] = {"NOTRAPWRITE","TRAPWRITE"};
|
||||
static char *asLevelName[] = {"ASL0","ASL1"};
|
||||
int epicsShareAPI asDump(
|
||||
void (*memcallback)(struct asgMember *),
|
||||
void (*clientcallback)(struct asgClient *),
|
||||
void (*memcallback)(struct asgMember *,FILE *),
|
||||
void (*clientcallback)(struct asgClient *,FILE *),
|
||||
int verbose)
|
||||
{
|
||||
return asDumpFP(stdout,memcallback,clientcallback,verbose);
|
||||
}
|
||||
|
||||
int epicsShareAPI asDumpFP(
|
||||
FILE *fp,
|
||||
void (*memcallback)(struct asgMember *,FILE *),
|
||||
void (*clientcallback)(struct asgClient *,FILE *),
|
||||
int verbose)
|
||||
{
|
||||
UAG *puag;
|
||||
@@ -484,151 +492,156 @@ int epicsShareAPI asDump(
|
||||
|
||||
if(!asActive) return(0);
|
||||
puag = (UAG *)ellFirst(&pasbase->uagList);
|
||||
if(!puag) printf("No UAGs\n");
|
||||
if(!puag) fprintf(fp,"No UAGs\n");
|
||||
while(puag) {
|
||||
printf("UAG(%s)",puag->name);
|
||||
fprintf(fp,"UAG(%s)",puag->name);
|
||||
puagname = (UAGNAME *)ellFirst(&puag->list);
|
||||
if(puagname) printf(" {"); else printf("\n");
|
||||
if(puagname) fprintf(fp," {"); else fprintf(fp,"\n");
|
||||
while(puagname) {
|
||||
printf("%s",puagname->user);
|
||||
fprintf(fp,"%s",puagname->user);
|
||||
puagname = (UAGNAME *)ellNext((ELLNODE *)puagname);
|
||||
if(puagname) printf(","); else printf("}\n");
|
||||
if(puagname) fprintf(fp,","); else fprintf(fp,"}\n");
|
||||
}
|
||||
puag = (UAG *)ellNext((ELLNODE *)puag);
|
||||
}
|
||||
phag = (HAG *)ellFirst(&pasbase->hagList);
|
||||
if(!phag) printf("No HAGs\n");
|
||||
if(!phag) fprintf(fp,"No HAGs\n");
|
||||
while(phag) {
|
||||
printf("HAG(%s)",phag->name);
|
||||
fprintf(fp,"HAG(%s)",phag->name);
|
||||
phagname = (HAGNAME *)ellFirst(&phag->list);
|
||||
if(phagname) printf(" {"); else printf("\n");
|
||||
if(phagname) fprintf(fp," {"); else fprintf(fp,"\n");
|
||||
while(phagname) {
|
||||
printf("%s",phagname->host);
|
||||
fprintf(fp,"%s",phagname->host);
|
||||
phagname = (HAGNAME *)ellNext((ELLNODE *)phagname);
|
||||
if(phagname) printf(","); else printf("}\n");
|
||||
if(phagname) fprintf(fp,","); else fprintf(fp,"}\n");
|
||||
}
|
||||
phag = (HAG *)ellNext((ELLNODE *)phag);
|
||||
}
|
||||
pasg = (ASG *)ellFirst(&pasbase->asgList);
|
||||
if(!pasg) printf("No ASGs\n");
|
||||
if(!pasg) fprintf(fp,"No ASGs\n");
|
||||
while(pasg) {
|
||||
int print_end_brace;
|
||||
|
||||
printf("ASG(%s)",pasg->name);
|
||||
fprintf(fp,"ASG(%s)",pasg->name);
|
||||
pasginp = (ASGINP *)ellFirst(&pasg->inpList);
|
||||
pasgrule = (ASGRULE *)ellFirst(&pasg->ruleList);
|
||||
if(pasginp || pasgrule) {
|
||||
printf(" {\n");
|
||||
fprintf(fp," {\n");
|
||||
print_end_brace = TRUE;
|
||||
} else {
|
||||
printf("\n");
|
||||
fprintf(fp,"\n");
|
||||
print_end_brace = FALSE;
|
||||
}
|
||||
while(pasginp) {
|
||||
|
||||
printf("\tINP%c(%s)",(pasginp->inpIndex + 'A'),pasginp->inp);
|
||||
fprintf(fp,"\tINP%c(%s)",(pasginp->inpIndex + 'A'),pasginp->inp);
|
||||
if(verbose) {
|
||||
if((pasg->inpBad & (1<<pasginp->inpIndex)))
|
||||
printf(" INVALID");
|
||||
fprintf(fp," INVALID");
|
||||
else
|
||||
printf(" VALID");
|
||||
printf(" value=%f",pasg->pavalue[pasginp->inpIndex]);
|
||||
fprintf(fp," VALID");
|
||||
fprintf(fp," value=%f",pasg->pavalue[pasginp->inpIndex]);
|
||||
}
|
||||
printf("\n");
|
||||
fprintf(fp,"\n");
|
||||
pasginp = (ASGINP *)ellNext((ELLNODE *)pasginp);
|
||||
}
|
||||
while(pasgrule) {
|
||||
int print_end_brace;
|
||||
|
||||
printf("\tRULE(%d,%s,%s)",
|
||||
fprintf(fp,"\tRULE(%d,%s,%s)",
|
||||
pasgrule->level,asAccessName[pasgrule->access],
|
||||
asTrapOption[pasgrule->trapMask]);
|
||||
pasguag = (ASGUAG *)ellFirst(&pasgrule->uagList);
|
||||
pasghag = (ASGHAG *)ellFirst(&pasgrule->hagList);
|
||||
if(pasguag || pasghag || pasgrule->calc) {
|
||||
printf(" {\n");
|
||||
fprintf(fp," {\n");
|
||||
print_end_brace = TRUE;
|
||||
} else {
|
||||
printf("\n");
|
||||
fprintf(fp,"\n");
|
||||
print_end_brace = FALSE;
|
||||
}
|
||||
if(pasguag) printf("\t\tUAG(");
|
||||
if(pasguag) fprintf(fp,"\t\tUAG(");
|
||||
while(pasguag) {
|
||||
printf("%s",pasguag->puag->name);
|
||||
fprintf(fp,"%s",pasguag->puag->name);
|
||||
pasguag = (ASGUAG *)ellNext((ELLNODE *)pasguag);
|
||||
if(pasguag) printf(","); else printf(")\n");
|
||||
if(pasguag) fprintf(fp,","); else fprintf(fp,")\n");
|
||||
}
|
||||
pasghag = (ASGHAG *)ellFirst(&pasgrule->hagList);
|
||||
if(pasghag) printf("\t\tHAG(");
|
||||
if(pasghag) fprintf(fp,"\t\tHAG(");
|
||||
while(pasghag) {
|
||||
printf("%s",pasghag->phag->name);
|
||||
fprintf(fp,"%s",pasghag->phag->name);
|
||||
pasghag = (ASGHAG *)ellNext((ELLNODE *)pasghag);
|
||||
if(pasghag) printf(","); else printf(")\n");
|
||||
if(pasghag) fprintf(fp,","); else fprintf(fp,")\n");
|
||||
}
|
||||
if(pasgrule->calc) {
|
||||
printf("\t\tCALC(\"%s\")",pasgrule->calc);
|
||||
fprintf(fp,"\t\tCALC(\"%s\")",pasgrule->calc);
|
||||
if(verbose)
|
||||
printf(" result=%s",(pasgrule->result ? "TRUE" : "FALSE"));
|
||||
printf("\n");
|
||||
fprintf(fp," result=%s",(pasgrule->result ? "TRUE" : "FALSE"));
|
||||
fprintf(fp,"\n");
|
||||
}
|
||||
if(print_end_brace) printf("\t}\n");
|
||||
if(print_end_brace) fprintf(fp,"\t}\n");
|
||||
pasgrule = (ASGRULE *)ellNext((ELLNODE *)pasgrule);
|
||||
}
|
||||
pasgmember = (ASGMEMBER *)ellFirst(&pasg->memberList);
|
||||
if(!verbose) pasgmember = NULL;
|
||||
if(pasgmember) printf("\tMEMBERLIST\n");
|
||||
if(pasgmember) fprintf(fp,"\tMEMBERLIST\n");
|
||||
while(pasgmember) {
|
||||
if(strlen(pasgmember->asgName)==0)
|
||||
printf("\t\t<null>");
|
||||
fprintf(fp,"\t\t<null>");
|
||||
else
|
||||
printf("\t\t%s",pasgmember->asgName);
|
||||
if(memcallback) memcallback(pasgmember);
|
||||
printf("\n");
|
||||
fprintf(fp,"\t\t%s",pasgmember->asgName);
|
||||
if(memcallback) memcallback(pasgmember,fp);
|
||||
fprintf(fp,"\n");
|
||||
pasgclient = (ASGCLIENT *)ellFirst(&pasgmember->clientList);
|
||||
while(pasgclient) {
|
||||
printf("\t\t\t %s %s",pasgclient->user,pasgclient->host);
|
||||
fprintf(fp,"\t\t\t %s %s",pasgclient->user,pasgclient->host);
|
||||
if(pasgclient->level>=0 && pasgclient->level<=1)
|
||||
printf(" %s",asLevelName[pasgclient->level]);
|
||||
fprintf(fp," %s",asLevelName[pasgclient->level]);
|
||||
else
|
||||
printf(" Illegal Level %d",pasgclient->level);
|
||||
fprintf(fp," Illegal Level %d",pasgclient->level);
|
||||
if(pasgclient->access>=0 && pasgclient->access<=2)
|
||||
printf(" %s %s",
|
||||
fprintf(fp," %s %s",
|
||||
asAccessName[pasgclient->access],
|
||||
asTrapOption[pasgclient->trapMask]);
|
||||
else
|
||||
printf(" Illegal Access %d",pasgclient->access);
|
||||
if(clientcallback) clientcallback(pasgclient);
|
||||
printf("\n");
|
||||
fprintf(fp," Illegal Access %d",pasgclient->access);
|
||||
if(clientcallback) clientcallback(pasgclient,fp);
|
||||
fprintf(fp,"\n");
|
||||
pasgclient = (ASGCLIENT *)ellNext((ELLNODE *)pasgclient);
|
||||
}
|
||||
pasgmember = (ASGMEMBER *)ellNext((ELLNODE *)pasgmember);
|
||||
}
|
||||
if(print_end_brace) printf("}\n");
|
||||
if(print_end_brace) fprintf(fp,"}\n");
|
||||
pasg = (ASG *)ellNext((ELLNODE *)pasg);
|
||||
}
|
||||
return(0);
|
||||
}
|
||||
|
||||
int epicsShareAPI asDumpUag(char *uagname)
|
||||
{
|
||||
return asDumpUagFP(stdout,uagname);
|
||||
}
|
||||
|
||||
int epicsShareAPI asDumpUagFP(FILE *fp,char *uagname)
|
||||
{
|
||||
UAG *puag;
|
||||
UAGNAME *puagname;
|
||||
|
||||
if(!asActive) return(0);
|
||||
puag = (UAG *)ellFirst(&pasbase->uagList);
|
||||
if(!puag) printf("No UAGs\n");
|
||||
if(!puag) fprintf(fp,"No UAGs\n");
|
||||
while(puag) {
|
||||
if(uagname && strcmp(uagname,puag->name)!=0) {
|
||||
puag = (UAG *)ellNext((ELLNODE *)puag);
|
||||
continue;
|
||||
}
|
||||
printf("UAG(%s)",puag->name);
|
||||
fprintf(fp,"UAG(%s)",puag->name);
|
||||
puagname = (UAGNAME *)ellFirst(&puag->list);
|
||||
if(puagname) printf(" {"); else printf("\n");
|
||||
if(puagname) fprintf(fp," {"); else fprintf(fp,"\n");
|
||||
while(puagname) {
|
||||
printf("%s",puagname->user);
|
||||
fprintf(fp,"%s",puagname->user);
|
||||
puagname = (UAGNAME *)ellNext((ELLNODE *)puagname);
|
||||
if(puagname) printf(","); else printf("}\n");
|
||||
if(puagname) fprintf(fp,","); else fprintf(fp,"}\n");
|
||||
}
|
||||
puag = (UAG *)ellNext((ELLNODE *)puag);
|
||||
}
|
||||
@@ -636,25 +649,30 @@ int epicsShareAPI asDumpUag(char *uagname)
|
||||
}
|
||||
|
||||
int epicsShareAPI asDumpHag(char *hagname)
|
||||
{
|
||||
return asDumpHagFP(stdout,hagname);
|
||||
}
|
||||
|
||||
int epicsShareAPI asDumpHagFP(FILE *fp,char *hagname)
|
||||
{
|
||||
HAG *phag;
|
||||
HAGNAME *phagname;
|
||||
|
||||
if(!asActive) return(0);
|
||||
phag = (HAG *)ellFirst(&pasbase->hagList);
|
||||
if(!phag) printf("No HAGs\n");
|
||||
if(!phag) fprintf(fp,"No HAGs\n");
|
||||
while(phag) {
|
||||
if(hagname && strcmp(hagname,phag->name)!=0) {
|
||||
phag = (HAG *)ellNext((ELLNODE *)phag);
|
||||
continue;
|
||||
}
|
||||
printf("HAG(%s)",phag->name);
|
||||
fprintf(fp,"HAG(%s)",phag->name);
|
||||
phagname = (HAGNAME *)ellFirst(&phag->list);
|
||||
if(phagname) printf(" {"); else printf("\n");
|
||||
if(phagname) fprintf(fp," {"); else fprintf(fp,"\n");
|
||||
while(phagname) {
|
||||
printf("%s",phagname->host);
|
||||
fprintf(fp,"%s",phagname->host);
|
||||
phagname = (HAGNAME *)ellNext((ELLNODE *)phagname);
|
||||
if(phagname) printf(","); else printf("}\n");
|
||||
if(phagname) fprintf(fp,","); else fprintf(fp,"}\n");
|
||||
}
|
||||
phag = (HAG *)ellNext((ELLNODE *)phag);
|
||||
}
|
||||
@@ -662,6 +680,11 @@ int epicsShareAPI asDumpHag(char *hagname)
|
||||
}
|
||||
|
||||
int epicsShareAPI asDumpRules(char *asgname)
|
||||
{
|
||||
return asDumpRulesFP(stdout,asgname);
|
||||
}
|
||||
|
||||
int epicsShareAPI asDumpRulesFP(FILE *fp,char *asgname)
|
||||
{
|
||||
ASG *pasg;
|
||||
ASGINP *pasginp;
|
||||
@@ -671,7 +694,7 @@ int epicsShareAPI asDumpRules(char *asgname)
|
||||
|
||||
if(!asActive) return(0);
|
||||
pasg = (ASG *)ellFirst(&pasbase->asgList);
|
||||
if(!pasg) printf("No ASGs\n");
|
||||
if(!pasg) fprintf(fp,"No ASGs\n");
|
||||
while(pasg) {
|
||||
int print_end_brace;
|
||||
|
||||
@@ -679,67 +702,74 @@ int epicsShareAPI asDumpRules(char *asgname)
|
||||
pasg = (ASG *)ellNext((ELLNODE *)pasg);
|
||||
continue;
|
||||
}
|
||||
printf("ASG(%s)",pasg->name);
|
||||
fprintf(fp,"ASG(%s)",pasg->name);
|
||||
pasginp = (ASGINP *)ellFirst(&pasg->inpList);
|
||||
pasgrule = (ASGRULE *)ellFirst(&pasg->ruleList);
|
||||
if(pasginp || pasgrule) {
|
||||
printf(" {\n");
|
||||
fprintf(fp," {\n");
|
||||
print_end_brace = TRUE;
|
||||
} else {
|
||||
printf("\n");
|
||||
fprintf(fp,"\n");
|
||||
print_end_brace = FALSE;
|
||||
}
|
||||
while(pasginp) {
|
||||
|
||||
printf("\tINP%c(%s)",(pasginp->inpIndex + 'A'),pasginp->inp);
|
||||
if((pasg->inpBad & (1<<pasginp->inpIndex))) printf(" INVALID");
|
||||
printf(" value=%f",pasg->pavalue[pasginp->inpIndex]);
|
||||
printf("\n");
|
||||
fprintf(fp,"\tINP%c(%s)",(pasginp->inpIndex + 'A'),pasginp->inp);
|
||||
if((pasg->inpBad & (1<<pasginp->inpIndex))) fprintf(fp," INVALID");
|
||||
fprintf(fp," value=%f",pasg->pavalue[pasginp->inpIndex]);
|
||||
fprintf(fp,"\n");
|
||||
pasginp = (ASGINP *)ellNext((ELLNODE *)pasginp);
|
||||
}
|
||||
while(pasgrule) {
|
||||
int print_end_brace;
|
||||
|
||||
printf("\tRULE(%d,%s,%s)",
|
||||
fprintf(fp,"\tRULE(%d,%s,%s)",
|
||||
pasgrule->level,asAccessName[pasgrule->access],
|
||||
asTrapOption[pasgrule->trapMask]);
|
||||
pasguag = (ASGUAG *)ellFirst(&pasgrule->uagList);
|
||||
pasghag = (ASGHAG *)ellFirst(&pasgrule->hagList);
|
||||
if(pasguag || pasghag || pasgrule->calc) {
|
||||
printf(" {\n");
|
||||
fprintf(fp," {\n");
|
||||
print_end_brace = TRUE;
|
||||
} else {
|
||||
printf("\n");
|
||||
fprintf(fp,"\n");
|
||||
print_end_brace = FALSE;
|
||||
}
|
||||
if(pasguag) printf("\t\tUAG(");
|
||||
if(pasguag) fprintf(fp,"\t\tUAG(");
|
||||
while(pasguag) {
|
||||
printf("%s",pasguag->puag->name);
|
||||
fprintf(fp,"%s",pasguag->puag->name);
|
||||
pasguag = (ASGUAG *)ellNext((ELLNODE *)pasguag);
|
||||
if(pasguag) printf(","); else printf(")\n");
|
||||
if(pasguag) fprintf(fp,","); else fprintf(fp,")\n");
|
||||
}
|
||||
pasghag = (ASGHAG *)ellFirst(&pasgrule->hagList);
|
||||
if(pasghag) printf("\t\tHAG(");
|
||||
if(pasghag) fprintf(fp,"\t\tHAG(");
|
||||
while(pasghag) {
|
||||
printf("%s",pasghag->phag->name);
|
||||
fprintf(fp,"%s",pasghag->phag->name);
|
||||
pasghag = (ASGHAG *)ellNext((ELLNODE *)pasghag);
|
||||
if(pasghag) printf(","); else printf(")\n");
|
||||
if(pasghag) fprintf(fp,","); else fprintf(fp,")\n");
|
||||
}
|
||||
if(pasgrule->calc) {
|
||||
printf("\t\tCALC(\"%s\")",pasgrule->calc);
|
||||
printf(" result=%s",(pasgrule->result ? "TRUE" : "FALSE"));
|
||||
printf("\n");
|
||||
fprintf(fp,"\t\tCALC(\"%s\")",pasgrule->calc);
|
||||
fprintf(fp," result=%s",(pasgrule->result ? "TRUE" : "FALSE"));
|
||||
fprintf(fp,"\n");
|
||||
}
|
||||
if(print_end_brace) printf("\t}\n");
|
||||
if(print_end_brace) fprintf(fp,"\t}\n");
|
||||
pasgrule = (ASGRULE *)ellNext((ELLNODE *)pasgrule);
|
||||
}
|
||||
if(print_end_brace) printf("}\n");
|
||||
if(print_end_brace) fprintf(fp,"}\n");
|
||||
pasg = (ASG *)ellNext((ELLNODE *)pasg);
|
||||
}
|
||||
return(0);
|
||||
}
|
||||
|
||||
int epicsShareAPI asDumpMem(char *asgname,void (*memcallback)(ASMEMBERPVT),int clients)
|
||||
int epicsShareAPI asDumpMem(char *asgname,void (*memcallback)(ASMEMBERPVT,FILE *),
|
||||
int clients)
|
||||
{
|
||||
return asDumpMemFP(stdout,asgname,memcallback,clients);
|
||||
}
|
||||
|
||||
int epicsShareAPI asDumpMemFP(FILE *fp,char *asgname,
|
||||
void (*memcallback)(ASMEMBERPVT,FILE *),int clients)
|
||||
{
|
||||
ASG *pasg;
|
||||
ASGMEMBER *pasgmember;
|
||||
@@ -747,39 +777,39 @@ int epicsShareAPI asDumpMem(char *asgname,void (*memcallback)(ASMEMBERPVT),int c
|
||||
|
||||
if(!asActive) return(0);
|
||||
pasg = (ASG *)ellFirst(&pasbase->asgList);
|
||||
if(!pasg) printf("No ASGs\n");
|
||||
if(!pasg) fprintf(fp,"No ASGs\n");
|
||||
while(pasg) {
|
||||
|
||||
if(asgname && strcmp(asgname,pasg->name)!=0) {
|
||||
pasg = (ASG *)ellNext((ELLNODE *)pasg);
|
||||
continue;
|
||||
}
|
||||
printf("ASG(%s)\n",pasg->name);
|
||||
fprintf(fp,"ASG(%s)\n",pasg->name);
|
||||
pasgmember = (ASGMEMBER *)ellFirst(&pasg->memberList);
|
||||
if(pasgmember) printf("\tMEMBERLIST\n");
|
||||
if(pasgmember) fprintf(fp,"\tMEMBERLIST\n");
|
||||
while(pasgmember) {
|
||||
if(strlen(pasgmember->asgName)==0)
|
||||
printf("\t\t<null>");
|
||||
fprintf(fp,"\t\t<null>");
|
||||
else
|
||||
printf("\t\t%s",pasgmember->asgName);
|
||||
if(memcallback) memcallback(pasgmember);
|
||||
printf("\n");
|
||||
fprintf(fp,"\t\t%s",pasgmember->asgName);
|
||||
if(memcallback) memcallback(pasgmember,fp);
|
||||
fprintf(fp,"\n");
|
||||
pasgclient = (ASGCLIENT *)ellFirst(&pasgmember->clientList);
|
||||
if(!clients) pasgclient = NULL;
|
||||
while(pasgclient) {
|
||||
printf("\t\t\t %s %s",
|
||||
fprintf(fp,"\t\t\t %s %s",
|
||||
pasgclient->user,pasgclient->host);
|
||||
if(pasgclient->level>=0 && pasgclient->level<=1)
|
||||
printf(" %s",asLevelName[pasgclient->level]);
|
||||
fprintf(fp," %s",asLevelName[pasgclient->level]);
|
||||
else
|
||||
printf(" Illegal Level %d",pasgclient->level);
|
||||
fprintf(fp," Illegal Level %d",pasgclient->level);
|
||||
if(pasgclient->access>=0 && pasgclient->access<=2)
|
||||
printf(" %s %s",
|
||||
fprintf(fp," %s %s",
|
||||
asAccessName[pasgclient->access],
|
||||
asTrapOption[pasgclient->trapMask]);
|
||||
else
|
||||
printf(" Illegal Access %d",pasgclient->access);
|
||||
printf("\n");
|
||||
fprintf(fp," Illegal Access %d",pasgclient->access);
|
||||
fprintf(fp,"\n");
|
||||
pasgclient = (ASGCLIENT *)ellNext((ELLNODE *)pasgclient);
|
||||
}
|
||||
pasgmember = (ASGMEMBER *)ellNext((ELLNODE *)pasgmember);
|
||||
@@ -790,9 +820,14 @@ int epicsShareAPI asDumpMem(char *asgname,void (*memcallback)(ASMEMBERPVT),int c
|
||||
}
|
||||
|
||||
epicsShareFunc int epicsShareAPI asDumpHash(void)
|
||||
{
|
||||
return asDumpHashFP(stdout);
|
||||
}
|
||||
|
||||
epicsShareFunc int epicsShareAPI asDumpHashFP(FILE *fp)
|
||||
{
|
||||
if(!asActive) return(0);
|
||||
gphDump(pasbase->phash);
|
||||
gphDumpFP(pasbase->phash,fp);
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
@@ -1,3 +1,12 @@
|
||||
/*************************************************************************\
|
||||
* Copyright (c) 2002 The University of Chicago, 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.
|
||||
\*************************************************************************/
|
||||
integer [0-9]
|
||||
name [a-zA-Z0-9_\-:\.\[\]<>;]
|
||||
notquote [^\"]
|
||||
@@ -39,7 +48,7 @@ INP[A-L] {/* If A-L is changed then ASMAXINP must also be changed*/
|
||||
{name}+ { /*unquoted string*/
|
||||
yylval.Str=(char *)asCalloc(1,strlen(yytext)+1);
|
||||
strcpy(yylval.Str,yytext);
|
||||
return(tokenNAME);
|
||||
return(tokenSTRING);
|
||||
}
|
||||
|
||||
\"{string}*\" { /*quoted string*/
|
||||
|
||||
@@ -72,18 +72,14 @@ height="31" width="88"></a></p>
|
||||
data type to the console</a></li>
|
||||
</ul>
|
||||
|
||||
<h3 style=""><a href="#CommandTools">Command Line Tools <span
|
||||
style="color: #FF5F00">(under development)</span></a></h3>
|
||||
<h3 style=""><a href="#CommandTools">Command Line Tools</a></h3>
|
||||
<ul style="">
|
||||
<li><a href="#caget">caget - Get and print value for PVs</a></li>
|
||||
<li><a href="#camonitor">camonitor - Set up monitor and continuously print
|
||||
incoming values for PVs <span style="color: #FF5F00">(not implemented
|
||||
yet)</span></a></li>
|
||||
<li><a href="#caput">caput - Put value to a PV <span
|
||||
style="color: #FF5F00">(not implemented yet)</span></a></li>
|
||||
incoming values for PVs</a></li>
|
||||
<li><a href="#caput">caput - Put value to a PV</a></li>
|
||||
<li><a href="#cainfo">cainfo - Print all available channel status and
|
||||
information for a PV <span style="color: #FF5F00">(not implemented
|
||||
yet)</span></a></li>
|
||||
information for a PV</a></li>
|
||||
</ul>
|
||||
|
||||
<h3><a href="#Troublesho">Troubleshooting</a></h3>
|
||||
@@ -101,6 +97,8 @@ style="color: #FF5F00">(under development)</span></a></h3>
|
||||
<li><a href="#Server1">A server's IP address was changed</a></li>
|
||||
</ul>
|
||||
</li>
|
||||
<li><a href="#Requests">Put Requests Just Prior to Process Termination
|
||||
Appear to be Ignored</a></li>
|
||||
<li><a href="#Problems">ENOBUFS Messages</a></li>
|
||||
</ul>
|
||||
|
||||
@@ -123,6 +121,8 @@ style="color: #FF5F00">(under development)</span></a></h3>
|
||||
Applications</a></li>
|
||||
<li><a href="#Avoid">Avoid Emulating Bad Practices that May Still be
|
||||
Common</a></li>
|
||||
<li><a href="#Calling">Calling CA Functions from the vxWorks Shell
|
||||
Thread</a></li>
|
||||
</ul>
|
||||
|
||||
<h3>Functionality Index </h3>
|
||||
@@ -153,8 +153,9 @@ style="color: #FF5F00">(under development)</span></a></h3>
|
||||
<li><a href="#ca_clear_channel">ca_clear_channel</a></li>
|
||||
<li><a href="#ca_clear_event">ca_clear_subscription</a></li>
|
||||
<li><a href="#ca_client_status">ca_client_status</a></li>
|
||||
<li><a href="#ca_client_status">ca_context_status</a></li>
|
||||
<li><a href="#ca_context_create">ca_context_create</a></li>
|
||||
<li><a href="#ca_context_destroy">ca_context_destroy</a></li>
|
||||
<li><a href="#ca_client_status">ca_context_status</a></li>
|
||||
<li><a href="#ca_create_channel">ca_create_channel</a></li>
|
||||
<li><a href="#ca_add_event">ca_create_subscription</a></li>
|
||||
<li><a href="#ca_current_context">ca_current_context</a></li>
|
||||
@@ -496,14 +497,29 @@ subnets. See "routeLib" in the vxWorks reference manual.</p>
|
||||
<p>If the CA client library does not see a beacon from a server that it is
|
||||
connected to for EPICS_CA_CONN_TMO seconds then an state-of-health message is
|
||||
sent to the server over TCP/IP. If this state-of-health message isn't
|
||||
promptly replied to then the client will assume that the server is no longer
|
||||
present on the network and disconnect. Disconnecting implies notification of
|
||||
client side application programs via function callbacks. The parameter
|
||||
promptly replied to then the client library will conclude that channels
|
||||
communicating with the server are no longer responsive and inform the CA
|
||||
client side application via function callbacks. The parameter
|
||||
EPICS_CA_CONN_TMO is specified in floating point seconds. The default is
|
||||
typically 30 seconds. For efficient operation it is recommended that
|
||||
EPICS_CA_CONN_TMO be set to no less than twice the value specified for
|
||||
EPICS_CA_BEACON_PERIOD.</p>
|
||||
|
||||
<p>Prior to EPICS R3.14.5 an unresponsive server implied an immediate TCP
|
||||
circuit disconnect, immediate resumption of UDP based search requests, and
|
||||
immediate attempts to reconnect. There was concern about excessive levels of
|
||||
additional activity when servers are operated close to the edge of resource
|
||||
limitations. Therefore with version R3.14.5 and greater the CA client library
|
||||
continues to inform client side applications when channels are unresponsive,
|
||||
but does not immediately disconnect the TCP circuit. Instead the CA client
|
||||
library postpones circuit shutdown until receiving indication of circuit
|
||||
disconnect from the IP kernel. This can occur either because a server is
|
||||
restarted or because the IP kernel's internal TCP circuit inactivity keep
|
||||
alive timer has expired after a typically long duration (as is appropriate
|
||||
for IP based systems that need to avoid thrashing during periods of excessive
|
||||
load). The net result is less search and TCP circuit setup and shutdown
|
||||
activity suring periods of excessive load.</p>
|
||||
|
||||
<h3><a name="Dynamic">Dynamic Changes in the CA Client Library Search
|
||||
Interval</a></h3>
|
||||
|
||||
@@ -565,15 +581,24 @@ sent to the UDP port specified in the EPICS_CA_REPEATER_PORT parameter and
|
||||
fans any beacons received out to any CA client program running on the same
|
||||
host that have registered themselves with the CA Repeater. If the CA Repeater
|
||||
is not already running on a workstation, then the "caRepeater" program must
|
||||
be in your path before using the CA client library for the first time. If a
|
||||
host based IOC is run on the same workstation with standalone CA client
|
||||
processes, then it is probably best to start the caRepeater process when the
|
||||
workstation is booted. Otherwise it is possible for the standalone CA client
|
||||
processes to become dependent on a CA repeater started within the confines of
|
||||
the host based IOC. As long as the host based IOC continues to run there is
|
||||
nothing wrong with this situation, but problems could arise if this host
|
||||
based IOC process exits before the standalone client processes which are
|
||||
relying on its CA repeater for services exit.</p>
|
||||
be in your path before using the CA client library for the first time.</p>
|
||||
|
||||
<p>If a host based IOC is run on the same workstation with standalone CA
|
||||
client processes, then it is probably best to start the caRepeater process
|
||||
when the workstation is booted. Otherwise it is possible for the standalone
|
||||
CA client processes to become dependent on a CA repeater started within the
|
||||
confines of the host based IOC. As long as the host based IOC continues to
|
||||
run there is nothing wrong with this situation, but problems could arise if
|
||||
this host based IOC process exits before the standalone client processes
|
||||
which are relying on its CA repeater for services exit.</p>
|
||||
|
||||
<p>Since the repeater is intended to be shared by multiple clients then it
|
||||
could be argued that it makes less sense to set up a CA repeater that listens
|
||||
for beacons on only a subset of available network interfaces. In the worst
|
||||
case situation the client library might see beacon anomalies from servers
|
||||
that it is not interested in. Modifications to the CA repeater forcing it to
|
||||
listen only on a subset of network interfaces might be considered for a
|
||||
future release if there appear to be situations that require it.</p>
|
||||
|
||||
<h3><a name="Configurin">Configuring the Time Zone</a></h3>
|
||||
|
||||
@@ -712,16 +737,21 @@ Interval</a>.</p>
|
||||
|
||||
<p>CA servers build a list of addresses to send beacons to during
|
||||
initialization. If EPICS_CAS_AUTO_BEACON_ADDR_LIST has the value "YES" then
|
||||
the beacon address list will contain at least the broadcast address of all
|
||||
LAN interfaces found in the host and the destination address of all
|
||||
point-to-point interfaces found in the host.</p>
|
||||
the beacon address list will be automatically configured to contain the
|
||||
broadcast addresses of all LAN interfaces found in the host and the
|
||||
destination address of all point-to-point interfaces found in the host.
|
||||
However, if the user also defines EPICS_CAS_INTF_ADDR_LIST then beacon
|
||||
address list automatic configuration is constrained to the network interfaces
|
||||
specified therein, and therefore only the broadcast addresses of the
|
||||
specified LAN interfaces, and the destination addresses of all specified
|
||||
point-to-point links, will be automatically configured.</p>
|
||||
|
||||
<p>If EPICS_CAS_BEACON_ADDR_LIST is defined then its contents will be used to
|
||||
augment this list. Individual entries in EPICS_CAS_BEACON_ADDR_LIST may
|
||||
override the destination port number if ":nnn" follows the host name or IP
|
||||
address there. Alternatively, if EPICS_CAS_BEACON_ADDR_LIST is not defined,
|
||||
EPICS_CA_ADDR_LIST is defined, and EPICS_CAS_INTF_ADDR_LIST is not defined,
|
||||
then the contents of EPICS_CA_ADDR_LIST will be used to augment the list.
|
||||
augment any automatic configuration of the beacon address list. Individual
|
||||
entries in EPICS_CAS_BEACON_ADDR_LIST may override the destination port
|
||||
number if ":nnn" follows the host name or IP address there. Alternatively,
|
||||
when both EPICS_CAS_BEACON_ADDR_LIST and EPICS_CAS_INTF_ADDR_LIST are not
|
||||
defined then the contents of EPICS_CA_ADDR_LIST is used to augment the list.
|
||||
Otherwise, the list is not augmented.</p>
|
||||
|
||||
<p>The EPICS_CAS_BEACON_PORT parameter specifies the destination port for
|
||||
@@ -809,7 +839,9 @@ network bandwidth and server CPU load when searching for unresolved
|
||||
channels.</p>
|
||||
|
||||
<p>If there are no new CA servers appearing on the network, and network
|
||||
connectivity remains constant, then casw should print no messages at all.</p>
|
||||
connectivity remains constant, then casw should print no messages at all. At
|
||||
higher interest levels the program prints a message for every beacon that is
|
||||
received, and anomalous entries are flagged with a star.</p>
|
||||
|
||||
<h3><a name="caEventRat">caEventRate</a></h3>
|
||||
<pre>caEventRate <PV name> [subscription count]</pre>
|
||||
@@ -831,16 +863,7 @@ of the PV is converted to each of the many external data type that can be
|
||||
specified at the CA client library interface, and each of these is formated
|
||||
and then output to the console.</p>
|
||||
|
||||
<h2><a name="CommandTools">Command Line Tools <span
|
||||
style="color: #FF5F00">(under development)</span></a></h2>
|
||||
|
||||
<p><span style="color: #FF5F00">Note: The CA Command Line Tools are currently
|
||||
under development. Thus only the first of the tools is included in EPICS Base
|
||||
R3.14.5, while the others are still being worked on. These tools have not yet
|
||||
proven to be stable and reliable. The user interface might still change, so
|
||||
please be careful relying on these early versions in scripts and other
|
||||
crucial places. Please report any bugs or unexpected behaviour to the author:
|
||||
Ralph.Lange@bessy.de</span></p>
|
||||
<h2><a name="CommandTools">Command Line Tools</a></h2>
|
||||
|
||||
<h3><a name="caget">caget</a></h3>
|
||||
<pre>caget [options] <PV name> ...</pre>
|
||||
@@ -854,6 +877,9 @@ DBR_... format in which the data is read, the output format, and a number of
|
||||
details of how integer and float values are represented can be controlled
|
||||
using command line options.</p>
|
||||
|
||||
<p>When getting multiple PVs, their order on the command line is retained in
|
||||
the output.</p>
|
||||
|
||||
<table border="1">
|
||||
<caption></caption>
|
||||
<thead>
|
||||
@@ -898,8 +924,7 @@ using command line options.</p>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-n</td>
|
||||
<td>Print DBF_ENUM values as number (default are enum string
|
||||
values)</td>
|
||||
<td>Print DBF_ENUM values as number (default are enum strings)</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-d <type></td>
|
||||
@@ -1048,13 +1073,17 @@ using command line options.</p>
|
||||
<td>Default:</td>
|
||||
<td>Use %g format</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-e <nr></td>
|
||||
<td>Use %e format, with <nr> digits after the decimal point</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-f <nr></td>
|
||||
<td>Use %f format, with <nr> digits after the decimal point</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-e <nr></td>
|
||||
<td>Use e format, with <nr> digits after the decimal point</td>
|
||||
<td>-g <nr></td>
|
||||
<td>Use %g format, with <nr> digits after the decimal point</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td></td>
|
||||
@@ -1086,18 +1115,199 @@ using command line options.</p>
|
||||
|
||||
<p>Subscribe to and print value updates for PV(s).</p>
|
||||
|
||||
<p><span style="color: #FF5F00">Not implemented yet. Under
|
||||
development.</span></p>
|
||||
<table border="1">
|
||||
<caption></caption>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>Option</th>
|
||||
<th>Description</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>-h</td>
|
||||
<td>Print usage information</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td></td>
|
||||
<td><strong>CA options:</strong></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-w <sec></td>
|
||||
<td>Wait time, specifies longer CA timeout, default is 1.0 second</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-m <mask></td>
|
||||
<td>Specify CA event mask to use, with <mask> being any
|
||||
combination of 'v' (value), 'a' (alarm), 'l' (log). Default: va</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td></td>
|
||||
<td><strong>Timestamps:</strong></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Default:</td>
|
||||
<td>Print absolute timestamps (as reported by CA)</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-r</td>
|
||||
<td>Relative timestamps (time elapsed since start of program)</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-i</td>
|
||||
<td>Incremental timestamps (time elapsed since last update)</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-I</td>
|
||||
<td>Incremental timestamps (time elapsed since last update for this
|
||||
channel)</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td></td>
|
||||
<td><strong>Enum Format:</strong></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-n</td>
|
||||
<td>Print DBF_ENUM values as number (default are enum strings)</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td></td>
|
||||
<td><strong>Arrays:</strong></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td></td>
|
||||
<td>Value format: Print number of requested values, then list of
|
||||
values</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Default:</td>
|
||||
<td>Print all values</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-# <count></td>
|
||||
<td>Print first <count> elements of an array</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td></td>
|
||||
<td><strong>Floating point type format:</strong></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Default:</td>
|
||||
<td>Use %g format</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-e <nr></td>
|
||||
<td>Use %e format, with <nr> digits after the decimal point</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-f <nr></td>
|
||||
<td>Use %f format, with <nr> digits after the decimal point</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-g <nr></td>
|
||||
<td>Use %g format, with <nr> digits after the decimal
|
||||
pointDefault:</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td></td>
|
||||
<td><strong>Integer number format:</strong></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Default:</td>
|
||||
<td>Print as decimal number</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-0x</td>
|
||||
<td>Print as hex number</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-0o</td>
|
||||
<td>Print as octal number</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-0b</td>
|
||||
<td>Print as binary number</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
|
||||
<h3><a name="caput">caput</a></h3>
|
||||
<pre>caput [options] <PV name> <value></pre>
|
||||
<pre>caput [options] <PV name> <value>
|
||||
caput -a [options] <PV name> <no of elements> <value> ...</pre>
|
||||
|
||||
<h4>Description</h4>
|
||||
|
||||
<p>Put value to a PV.</p>
|
||||
|
||||
<p><span style="color: #FF5F00">Not implemented yet. Under
|
||||
development.</span></p>
|
||||
<p>The specified value is written to the PV (as a string). The PV value is
|
||||
read before and after the write operation and printed as "Old" and "new"
|
||||
values on stdout.</p>
|
||||
|
||||
<p>The array variant writes an array to the specified PV. The first numeric
|
||||
argument specifying the number of array elements is kept for compatibility
|
||||
with the array data format of caget - the actual number of values specified
|
||||
on the command line is used.</p>
|
||||
|
||||
<table border="1">
|
||||
<caption></caption>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>Option</th>
|
||||
<th>Description</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>-h</td>
|
||||
<td>Print usage information</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td></td>
|
||||
<td><strong>CA options:</strong></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-w <sec></td>
|
||||
<td>Wait time, specifies longer CA timeout, default is 1.0 second</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td></td>
|
||||
<td><strong>Format options:</strong></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-t</td>
|
||||
<td>Terse mode - print only sucessfully written value, without name</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td></td>
|
||||
<td><strong>Enum Format:</strong></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td></td>
|
||||
<td>Auto - try value as ENUM string, then as index number</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-n</td>
|
||||
<td>Force interpretation of values as numbers</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-s</td>
|
||||
<td>Force interpretation of values as strings</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td></td>
|
||||
<td><strong>Arrays:</strong></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-a</td>
|
||||
<td>Put array data</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td></td>
|
||||
<td>Value format: Print number of requested values, then list of
|
||||
values</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
|
||||
<h3><a name="cainfo">cainfo</a></h3>
|
||||
<pre>cainfo [options] <PV name> ...</pre>
|
||||
@@ -1106,8 +1316,43 @@ development.</span></p>
|
||||
|
||||
<p>Get and print channel and connection information for PV(s).</p>
|
||||
|
||||
<p><span style="color: #FF5F00">Not implemented yet. Under
|
||||
development.</span></p>
|
||||
<p>All available Channel Access related information about PV(s) is printed to
|
||||
stdout.</p>
|
||||
|
||||
<p>The -s option allows to specify an interest level for calling Channel
|
||||
Access' internal report function ca_client_status(), that prints lots of
|
||||
internal informations on stdout, including environment settings, used CA
|
||||
ports etc.</p>
|
||||
|
||||
<table border="1">
|
||||
<caption></caption>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>Option</th>
|
||||
<th>Description</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>-h</td>
|
||||
<td>Print usage information</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td></td>
|
||||
<td><strong>CA options:</strong></td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-w <sec></td>
|
||||
<td>Wait time, specifies longer CA timeout, default is 1.0 second</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>-s <level></td>
|
||||
<td>Call ca_client_status with the specified interest level</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
|
||||
<p></p>
|
||||
|
||||
<h2><a name="Troublesho">Troubleshooting</a></h2>
|
||||
|
||||
@@ -1202,7 +1447,7 @@ immediately searched for, and after successful search responses arrived then
|
||||
attempts were made to build a new circuit. This behavior could result in
|
||||
undesirable resource consumption resulting from periodic circuit setup and
|
||||
teardown overhead (thrashing) during periods of CPU / network / IP kernel
|
||||
buffer congestion. </p>
|
||||
buffer congestion.</p>
|
||||
|
||||
<h3><a name="Problems">ENOBUFS Messages</a></h3>
|
||||
|
||||
@@ -1314,6 +1559,15 @@ if ( status != ECA_NORMAL ) {
|
||||
|
||||
<h3><a name="Channel">Channel Access Data Types</a></h3>
|
||||
|
||||
<p>CA channels form a virtual circuit between a process variable (PV) and a
|
||||
client side application program. It is possible to connect a wide variety of
|
||||
data sources into EPICS using the CA server library. When a CA channel
|
||||
communicates with an EPICS Input Output Controller (IOC) then a field is a
|
||||
specialization of a PV, and an EPICS record is a plug compatible function
|
||||
block that contains fields, and the meta data below frequently are mapped
|
||||
onto specific fields within the EPICS records by the EPICS record support
|
||||
(see the EPICS Application Developer Guide).</p>
|
||||
|
||||
<p>Arguments of type chtype specifying the data type you wish to transfer.
|
||||
They expect one of the set of DBR_XXXX data type codes defined in
|
||||
db_access.h. There are data types for all of the C primitive types, and there
|
||||
@@ -1492,7 +1746,9 @@ the IOC. If the status field isn't set to ECA_NORMAL or data isn't normally
|
||||
returned from the operation (i.e. put call back) then you should expect that
|
||||
the <code>dbr </code>field will be set to a nill pointer (zero). The fields
|
||||
<code>usr</code>, <code>chid</code>, and <code>type</code> are set to the
|
||||
values specified when the request was made by the application.</p>
|
||||
values specified when the request was made by the application. The "dbr"
|
||||
pointer, and any data that it points to, are valid only when executing within
|
||||
the user's callback function.</p>
|
||||
<pre><code>typedef struct event_handler_args {
|
||||
void *usr; /* user argument supplied with request */
|
||||
chanId chid; /* channel id */
|
||||
@@ -1549,41 +1805,36 @@ in the server.</p>
|
||||
|
||||
<h3><a name="Connection">Connection Management</a></h3>
|
||||
|
||||
<p>Application programs should assume that CA server may be restarted, and
|
||||
that network connectivity is transient. When you create a CA channel it's
|
||||
<p>Application programs should assume that CA servers may be restarted, and
|
||||
that network connectivity is transient. When you create a CA channel its
|
||||
initial connection state will most commonly be disconnected. If the Process
|
||||
Variable's server is available the library will immediately initiate the
|
||||
necessary actions to make a connection with it. Otherwise, the client library
|
||||
will monitor the state of servers on the network and immediately connect or
|
||||
reconnect with the process variable's server when it becomes available.</p>
|
||||
will monitor the state of servers on the network and connect or reconnect
|
||||
with the process variable's server as it becomes available. After the channel
|
||||
connects the application program can freely perform IO operations through the
|
||||
channel, but should expect that the channel might disconnect at any time due
|
||||
to network connectivity disruptions or server restarts.</p>
|
||||
|
||||
<p>Two methods may be used to determine if a channel has connected: the
|
||||
application program can block in <code><a
|
||||
href="#ca_pend_io">ca_pend_io</a></code>, or the application program can
|
||||
<p>Three methods can be used to determine if a channel is connected: the
|
||||
application program might call <a href="#ca_state"><code>ca_state</code></a>
|
||||
to obtain the current connection state, block in <code><a
|
||||
href="#ca_pend_io">ca_pend_io</a></code> until the channel connects, or
|
||||
install a connection callback handler when it calls <code><a
|
||||
href="#ca_create_channel">ca_create_channel</a></code>. The <code><a
|
||||
href="#ca_pend_io">ca_pend_io</a></code> approach is best suited to simple
|
||||
command line programs with a short runtime duration, and the connection
|
||||
callback method is best suited to toolkit components with a long runtime
|
||||
duration. If a connection state change call back function is <em>not</em>
|
||||
installed when <code>ca_create_channel </code>is called (if a nil function
|
||||
pointer is supplied) then the application program <em>must </em>wait for
|
||||
successful status from <code><a href="#ca_pend_io">ca_pend_io</a></code>
|
||||
prior to using the channel for the first time. Otherwise, if a connection
|
||||
state change call back function <em>is</em> supplied, then one of the
|
||||
arguments to this function distinguishes between connect and disconnect
|
||||
events, and <code><a href="#ca_pend_io">ca_pend_io</a></code> will <em>not
|
||||
</em>block for the channel to connect. The user's connection state change
|
||||
function will be run immediately from within <code><a
|
||||
command line programs with short runtime duration, and the connection
|
||||
callback method is best suited to toolkit components with long runtime
|
||||
duration. Use of <code><a href="#ca_state">ca_state</a> </code>is appropriate
|
||||
only in programs that prefer to poll for connection state changes instead of
|
||||
opting for asynchronous notification. The <code>ca_pend_io</code> function
|
||||
blocks only for channels created specifying a nill connection handler
|
||||
callback function. The user's connection state change function will be run
|
||||
immediately from within <code><a
|
||||
href="#ca_create_channel">ca_create_channel</a> </code>if the CA client and
|
||||
the server are both hosted within the same address space (within the same
|
||||
CA server are both hosted within the same address space (within the same
|
||||
process).</p>
|
||||
|
||||
<p>Once the channel connects the application program can freely perform IO
|
||||
operations through the channel, but it should expect that the channel might
|
||||
disconnect at any time due to network connectivity disruptions or server
|
||||
restarts.</p>
|
||||
|
||||
<h3><a name="Thread">Thread Safety and Preemptive Callback to User
|
||||
Code</a></h3>
|
||||
|
||||
@@ -1598,7 +1849,9 @@ Otherwise, the user's call back functions will be called only when the main
|
||||
initiating channel access thread is executing inside of the CA client
|
||||
library. When the CA client library invokes a user's call back function
|
||||
it will always wait for the current callback to complete prior to executing
|
||||
another call back function.</p>
|
||||
another call back function. Programmers enabling preemptive callback should
|
||||
be familiar with using mutex locks to create a reliable multi-threaded
|
||||
program.</p>
|
||||
|
||||
<p>To set up a traditional single threaded client you will need code like
|
||||
this (see <a href="#ca_context_create">ca_context_create</a> and <a
|
||||
@@ -1609,9 +1862,9 @@ Threads</a>) .</p>
|
||||
"application pdq calling ca_context_create" );</code></p>
|
||||
|
||||
<p>To set up a preemptive callback enabled CA client context you will need
|
||||
code like this (see <a href="#ca_context_create">ca_context_create</a>and <a
|
||||
code like this (see <a href="#ca_context_create">ca_context_create</a> and <a
|
||||
href="#Client2">CA Client Contexts and Application Specific Auxiliary
|
||||
Threads</a>) .</p>
|
||||
Threads</a>).</p>
|
||||
|
||||
<p><code>SEVCHK ( ca_context_create(ca_enable_preemptive_callback ),
|
||||
"application pdq calling ca_context_create" );</code></p>
|
||||
@@ -1619,26 +1872,39 @@ Threads</a>) .</p>
|
||||
<h3><a name="Client2">CA Client Contexts and Application Specific Auxiliary
|
||||
Threads</a></h3>
|
||||
|
||||
<p>It may be necessary for several CA client side tools running in the same
|
||||
<p>It is often necessary for several CA client side tools running in the same
|
||||
address space (process) to be independent of each other. For example, the
|
||||
database CA links and the sequencer are designed to not use the same CA
|
||||
client library threads, network circuits, and data structures. Each thread
|
||||
that calls <a href="#ca_context_create">ca_context_create()</a> for the first
|
||||
time either directly, or implicitly when calling a CA routine for the first
|
||||
time, creates a CA client library context. A CA client library context
|
||||
contains all of the threads, network circuits, and data structures required
|
||||
to connect and communicate with the channels that a CA client application has
|
||||
created. The priority of auxiliary threads spawned by the CA client library
|
||||
are at fixed offsets from the priority of the thread that called <a
|
||||
href="#ca_context_create">ca_context_create()</a>. An application specific
|
||||
auxiliary thread can join a CA context by calling <a
|
||||
time either directly, or implicitly when calling any CA library function for
|
||||
the first time, creates a CA client library context. A CA client library
|
||||
context contains all of the threads, network circuits, and data structures
|
||||
required to connect and communicate with the channels that a CA client
|
||||
application has created. The priority of auxiliary threads spawned by the CA
|
||||
client library are at fixed offsets from the priority of the thread that
|
||||
called <a href="#ca_context_create">ca_context_create()</a>. An application
|
||||
specific auxiliary thread can join a CA context by calling <a
|
||||
href="#ca_attach_context">ca_attach_context()</a> using the CA context
|
||||
identifier that was returned from <a
|
||||
href="#ca_current_context">ca_current_context()</a> when it was called by the
|
||||
thread that called <a href="#ca_context_create">ca_context_create()</a>. A CA
|
||||
client library context can be shut down and cleaned up, after destroying any
|
||||
channels or application specific threads that are attached to it, by calling
|
||||
<a href="#ca_context_destroy">ca_context_destroy()</a>.</p>
|
||||
href="#ca_current_context">ca_current_context()</a> when it is called by the
|
||||
thread that created the context which needs to be joined. A context which is
|
||||
to be joined must be created using <a
|
||||
href="#ca_context_create">ca_context_create(ca_enable_preemptive_callback)</a>.
|
||||
It is not possible to attach a thread to a CA context created explicitly
|
||||
<em>or implicitly</em> with
|
||||
ca_create_context(ca_disable_preemptive_callback). Once a thread has joined
|
||||
with a CA context it need only make ordinary ca_xxxx() library calls to use
|
||||
the context. There is no need to specify the context identifier when invoking
|
||||
the CA y calls because the context identifier is stored in a thread
|
||||
privatelibrary calls because the context identifier is stored in a thread
|
||||
private variable by ca_attach_context().</p>
|
||||
|
||||
<p>A CA client library context can be shut down and cleaned up, after
|
||||
destroying any channels or application specific threads that are attached to
|
||||
it, by calling <a href="#ca_context_destroy">ca_context_destroy()</a>. The
|
||||
context may be created and destroyed by different threads as long as they are
|
||||
both part of the same context.</p>
|
||||
|
||||
<h3><a name="Polling">Polling the CA Client Library From Single Threaded
|
||||
Applications</a></h3>
|
||||
@@ -1680,6 +1946,38 @@ Otherwise, you can also use <code>ca_set_puser(CHID,PUSER)</code>, but this
|
||||
function is available only after the first official (post beta) release of
|
||||
EPICS 3.13.</p>
|
||||
|
||||
<h3><a name="Calling">Calling CA Functions from the vxWorks Shell
|
||||
Thread</a></h3>
|
||||
|
||||
<p>Calling CA functions from the vxWorks shell thread is a somewhat
|
||||
questionable practice for the following reasons.</p>
|
||||
<ul>
|
||||
<li>The vxWorks shell thread runs at the very highest priority in the
|
||||
system and therefore socket calls are made at a priority that is above
|
||||
the priority of tNetTask − a practice that has caused the WRS IP
|
||||
kernel to get sick in the past. That symptom was observed some time ago,
|
||||
but we don’t know if WRS has fixed the problem.</li>
|
||||
</ul>
|
||||
<ul>
|
||||
<li>The vxWorks shell thread runs at the very highest priority in the
|
||||
system and therefore certain CA auxiliary threads will not get the
|
||||
priorities that are requested for them. This might cause problems only
|
||||
when in a CPU saturation situations.</li>
|
||||
</ul>
|
||||
<ul>
|
||||
<li>If the code does not call ca_context_destroy (ca_task_exit in past
|
||||
releases) then resources are left dangling.</li>
|
||||
</ul>
|
||||
<ul>
|
||||
<li>In EPICS R3.13 the CA client library installed vxWorks task exit
|
||||
handlers behaved strangely if CA functions were called from the vxWorks
|
||||
shell, ca_task_exit() wasn’t called, and the vxWorks shell
|
||||
restarted. In EPICS R3.14 vxWorks task exit handlers are not installed
|
||||
and therefore cleanup is solely the responsibility of the user. With
|
||||
EPICS R3.14 the user must call ca_context_destroy or ca_task_exit to
|
||||
clean up on vxWorks. This is the same behavior as on all other OS.</li>
|
||||
</ul>
|
||||
|
||||
<h2><a name="Function Call Reference"></a>Function Call Reference</h2>
|
||||
|
||||
<h3><code><a name="ca_context_create">ca_context_create()</a></code></h3>
|
||||
@@ -1729,8 +2027,14 @@ void ca_context_destroy();</pre>
|
||||
<h4>Description</h4>
|
||||
|
||||
<p>Shut down a channel access client context and free any resources
|
||||
allocated. On most operating systems this is performed automatically at
|
||||
process exit.</p>
|
||||
allocated. </p>
|
||||
|
||||
<p>On many OS that execute programs in a process based environment the
|
||||
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
|
||||
ca_context_destroy().</p>
|
||||
|
||||
<h4>Returns</h4>
|
||||
|
||||
@@ -2184,8 +2488,8 @@ least one update indicating the current state of the channel.</p>
|
||||
<dl>
|
||||
<dt><code>MASK</code></dt>
|
||||
<dd>A mask with bits set for each of the event trigger types requested.
|
||||
The event trigger mask must be a logical or of one or more of the
|
||||
following constants.
|
||||
The event trigger mask must be a <em>bitwise or</em> of one or more of
|
||||
the following constants.
|
||||
<ul>
|
||||
<li>DBE_VALUE - Trigger events when the channel value exceeds the
|
||||
monitor dead band</li>
|
||||
@@ -3399,7 +3703,7 @@ void * PDBR );</code></p>
|
||||
bytes</dd>
|
||||
</dl>
|
||||
|
||||
<p><small>$Id: CAref.html,v 1.58.2.1 2003/09/03 22:31:48 jhill Exp
|
||||
$</small></p>
|
||||
<p><small>$Id$
|
||||
.</small></p>
|
||||
</body>
|
||||
</html>
|
||||
|
||||
@@ -382,6 +382,8 @@ int epicsShareAPI ca_array_get ( chtype type,
|
||||
}
|
||||
unsigned tmpType = static_cast < unsigned > ( type );
|
||||
epicsGuard < epicsMutex > guard ( pChan->getClientCtx().mutex );
|
||||
pChan->eliminateExcessiveSendBacklog (
|
||||
pChan->getClientCtx().pCallbackGuard.get(), guard );
|
||||
autoPtrFreeList < getCopy, 0x400, epicsMutexNOOP > pNotify
|
||||
( pChan->getClientCtx().getCopyFreeList,
|
||||
new ( pChan->getClientCtx().getCopyFreeList )
|
||||
@@ -449,6 +451,8 @@ int epicsShareAPI ca_array_get_callback ( chtype type,
|
||||
unsigned tmpType = static_cast < unsigned > ( type );
|
||||
|
||||
epicsGuard < epicsMutex > guard ( pChan->getClientCtx().mutex );
|
||||
pChan->eliminateExcessiveSendBacklog (
|
||||
pChan->getClientCtx().pCallbackGuard.get(), guard );
|
||||
autoPtrFreeList < getCallback, 0x400, epicsMutexNOOP > pNotify
|
||||
( pChan->getClientCtx().getCallbackFreeList,
|
||||
new ( pChan->getClientCtx().getCallbackFreeList )
|
||||
@@ -512,6 +516,8 @@ int epicsShareAPI ca_array_put_callback ( chtype type, arrayElementCount count,
|
||||
return ECA_BADTYPE;
|
||||
}
|
||||
epicsGuard < epicsMutex > guard ( pChan->getClientCtx().mutex );
|
||||
pChan->eliminateExcessiveSendBacklog (
|
||||
pChan->getClientCtx().pCallbackGuard.get(), guard );
|
||||
unsigned tmpType = static_cast < unsigned > ( type );
|
||||
autoPtrFreeList < putCallback, 0x400, epicsMutexNOOP > pNotify
|
||||
( pChan->getClientCtx().putCallbackFreeList,
|
||||
@@ -575,6 +581,8 @@ int epicsShareAPI ca_array_put ( chtype type, arrayElementCount count,
|
||||
int caStatus;
|
||||
try {
|
||||
epicsGuard < epicsMutex > guard ( pChan->getClientCtx().mutex );
|
||||
pChan->eliminateExcessiveSendBacklog (
|
||||
pChan->getClientCtx().pCallbackGuard.get(), guard );
|
||||
pChan->write ( guard, tmpType, count, pValue );
|
||||
caStatus = ECA_NORMAL;
|
||||
}
|
||||
@@ -683,6 +691,8 @@ int epicsShareAPI ca_create_subscription (
|
||||
|
||||
try {
|
||||
epicsGuard < epicsMutex > guard ( pChan->getClientCtx().mutex );
|
||||
pChan->eliminateExcessiveSendBacklog (
|
||||
pChan->getClientCtx().pCallbackGuard.get(), guard );
|
||||
autoPtrFreeList < oldSubscription, 0x400, epicsMutexNOOP > pSubsr
|
||||
( pChan->getClientCtx().subscriptionFreeList,
|
||||
new ( pChan->getClientCtx().subscriptionFreeList )
|
||||
@@ -749,11 +759,15 @@ epicsShareFunc int epicsShareAPI ca_clear_subscription ( evid pMon )
|
||||
ca_client_context & cac = chan.getClientCtx ();
|
||||
if ( cac.pCallbackGuard.get() ) {
|
||||
epicsGuard < epicsMutex > guard ( cac.mutex );
|
||||
chan.eliminateExcessiveSendBacklog (
|
||||
cac.pCallbackGuard.get(), guard );
|
||||
pMon->ioCancel ( *cac.pCallbackGuard, guard );
|
||||
}
|
||||
else {
|
||||
epicsGuard < epicsMutex > cbGuard ( cac.cbMutex );
|
||||
epicsGuard < epicsMutex > guard ( cac.mutex );
|
||||
chan.eliminateExcessiveSendBacklog (
|
||||
&cbGuard, guard );
|
||||
pMon->ioCancel ( cbGuard, guard );
|
||||
}
|
||||
return ECA_NORMAL;
|
||||
|
||||
@@ -390,6 +390,8 @@ void noopSubscriptionStateChange ( struct event_handler_args args )
|
||||
* 5) verify subscription can be cleared before channel is cleared
|
||||
*
|
||||
* 6) verify subscription can be cleared by clearing the channel
|
||||
*
|
||||
* 7) verify that a nill access rights handler can be installed
|
||||
*/
|
||||
void verifyConnectionHandlerConnect ( appChan *pChans, unsigned chanCount,
|
||||
unsigned repetitionCount, unsigned interestLevel )
|
||||
@@ -466,6 +468,12 @@ void verifyConnectionHandlerConnect ( appChan *pChans, unsigned chanCount,
|
||||
ca_self_test ();
|
||||
|
||||
showProgress ( interestLevel );
|
||||
|
||||
for ( j = 0u; j < chanCount; j++ ) {
|
||||
status = ca_replace_access_rights_event (
|
||||
pChans[j].channel, 0 );
|
||||
SEVCHK ( status, NULL );
|
||||
}
|
||||
|
||||
for ( j = 0u; j < chanCount; j++ ) {
|
||||
status = ca_clear_channel ( pChans[j].channel );
|
||||
@@ -2060,6 +2068,81 @@ dbr_float_t monitorUpdateTestPattern ( unsigned iter )
|
||||
return ( (float) iter ) * 10.12345f + 10.7f;
|
||||
}
|
||||
|
||||
void getCallbackClearsChannel ( struct event_handler_args args )
|
||||
{
|
||||
int status;
|
||||
status = ca_clear_channel ( args.chid );
|
||||
SEVCHK ( status, "clearChannelInGetCallbackTest clear channel" );
|
||||
}
|
||||
|
||||
void clearChannelInGetCallbackTest ( const char *pName, unsigned level )
|
||||
{
|
||||
chid chan;
|
||||
int status;
|
||||
|
||||
showProgressBegin ( "clearChannelInGetCallbackTest", level );
|
||||
|
||||
status = ca_create_channel ( pName, 0, 0, 0, & chan );
|
||||
SEVCHK ( status, "clearChannelInGetCallbackTest create channel" );
|
||||
|
||||
status = ca_pend_io ( 10.0 );
|
||||
SEVCHK ( status, "clearChannelInGetCallbackTest connect channel" );
|
||||
|
||||
status = ca_get_callback ( DBR_DOUBLE, chan, getCallbackClearsChannel, 0 );
|
||||
SEVCHK ( status, "clearChannelInGetCallbackTest get callback" );
|
||||
|
||||
status = ca_flush_io ();
|
||||
SEVCHK ( status, "clearChannelInGetCallbackTest flush" );
|
||||
|
||||
showProgressEnd ( level );
|
||||
}
|
||||
|
||||
void monitorAddConnectionCallback ( struct connection_handler_args args )
|
||||
{
|
||||
int status;
|
||||
status = ca_create_subscription ( DBR_DOUBLE, 1,
|
||||
args.chid, DBE_VALUE, nUpdatesTester, ca_puser ( args.chid ), 0 );
|
||||
SEVCHK ( status, "monitorAddConnectionCallback create subscription" );
|
||||
}
|
||||
|
||||
/*
|
||||
* monitorAddConnectionCallbackTest
|
||||
* 1) subscription add from within connection callback needs to work
|
||||
* 2) check for problems where subscription is installed twice if
|
||||
* its installed within the connection callback handler
|
||||
*/
|
||||
void monitorAddConnectionCallbackTest ( const char *pName, unsigned interestLevel )
|
||||
{
|
||||
chid chan;
|
||||
int status;
|
||||
unsigned eventCount = 0u;
|
||||
unsigned getCallbackCount = 0u;
|
||||
|
||||
showProgressBegin ( "monitorAddConnectionCallbackTest", interestLevel );
|
||||
|
||||
status = ca_create_channel ( pName,
|
||||
monitorAddConnectionCallback, &eventCount, 0, & chan );
|
||||
SEVCHK ( status, "monitorAddConnectionCallbackTest create channel" );
|
||||
|
||||
while ( eventCount == 0 ) {
|
||||
ca_pend_event ( 0.1 );
|
||||
}
|
||||
assert ( eventCount == 1u );
|
||||
|
||||
status = ca_get_callback ( DBR_DOUBLE, chan, nUpdatesTester, &getCallbackCount );
|
||||
SEVCHK ( status, "monitorAddConnectionCallback get callback" );
|
||||
while ( getCallbackCount == 0 ) {
|
||||
ca_pend_event ( 0.1 );
|
||||
}
|
||||
assert ( eventCount == 1u );
|
||||
assert ( getCallbackCount == 1u );
|
||||
|
||||
status = ca_clear_channel ( chan );
|
||||
SEVCHK ( status, "monitorAddConnectionCallbackTest clear channel" );
|
||||
|
||||
showProgressEnd ( interestLevel );
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* monitorUpdateTest
|
||||
@@ -2665,6 +2748,8 @@ int acctst ( char *pName, unsigned interestLevel, unsigned channelCount,
|
||||
printf ( "testing with a local channel\n" );
|
||||
}
|
||||
|
||||
clearChannelInGetCallbackTest ( pName, interestLevel );
|
||||
monitorAddConnectionCallbackTest ( pName, interestLevel );
|
||||
verifyConnectWithDisconnectedChannels ( pName, interestLevel );
|
||||
grEnumTest ( chan, interestLevel );
|
||||
test_sync_groups ( chan, interestLevel );
|
||||
|
||||
@@ -189,12 +189,15 @@ void ca_client_context::destroyChannel ( oldChannelNotify & chan )
|
||||
{
|
||||
if ( this->pCallbackGuard.get() ) {
|
||||
epicsGuard < epicsMutex > guard ( this->mutex );
|
||||
chan.eliminateExcessiveSendBacklog (
|
||||
this->pCallbackGuard.get(), guard );
|
||||
chan.destructor ( *this->pCallbackGuard.get(), guard );
|
||||
this->oldChannelNotifyFreeList.release ( & chan );
|
||||
}
|
||||
else {
|
||||
epicsGuard < epicsMutex > cbGuard ( this->cbMutex );
|
||||
epicsGuard < epicsMutex > guard ( this->mutex );
|
||||
chan.eliminateExcessiveSendBacklog ( &cbGuard, guard );
|
||||
chan.destructor ( cbGuard, guard );
|
||||
this->oldChannelNotifyFreeList.release ( & chan );
|
||||
}
|
||||
@@ -686,7 +689,7 @@ void ca_client_context::installCASG (
|
||||
epicsGuard < epicsMutex > & guard, CASG & sg )
|
||||
{
|
||||
guard.assertIdenticalMutex ( this->mutex );
|
||||
this->sgTable.add ( sg );
|
||||
this->sgTable.idAssignAdd ( sg );
|
||||
}
|
||||
|
||||
void ca_client_context::uninstallCASG (
|
||||
|
||||
@@ -47,7 +47,7 @@
|
||||
|
||||
static const char *pVersionCAC =
|
||||
"@(#) " EPICS_VERSION_STRING
|
||||
", CA Portable Server Library " __DATE__;
|
||||
", CA Client Library " __DATE__;
|
||||
|
||||
// TCP response dispatch table
|
||||
const cac::pProtoStubTCP cac::tcpJumpTableCAC [] =
|
||||
@@ -243,7 +243,7 @@ cac::~cac ()
|
||||
tsDLIter < tcpiiu > iter = this->circuitList.firstIter ();
|
||||
while ( iter.valid() ) {
|
||||
// this causes a clean shutdown to occur
|
||||
iter->removeAllChannels ( cbGuard, guard, *this->pudpiiu );
|
||||
iter->removeAllChannels ( true, cbGuard, guard, *this->pudpiiu );
|
||||
iter++;
|
||||
}
|
||||
}
|
||||
@@ -460,7 +460,7 @@ cacChannel & cac::createChannel (
|
||||
|
||||
nciu * pNetChan = new ( this->channelFreeList )
|
||||
nciu ( *this, *this->pudpiiu, chan, pName, pri );
|
||||
this->chanTable.add ( *pNetChan );
|
||||
this->chanTable.idAssignAdd ( *pNetChan );
|
||||
return *pNetChan;
|
||||
}
|
||||
|
||||
@@ -573,11 +573,8 @@ void cac::destroyChannel (
|
||||
if ( this->chanTable.remove ( chan ) != & chan ) {
|
||||
throw std::logic_error ( "Invalid channel identifier" );
|
||||
}
|
||||
|
||||
chan.getPIIU(guard)->uninstallChan ( cbGuard, guard, chan );
|
||||
|
||||
chan.destructor ( cbGuard, guard );
|
||||
|
||||
chan.~nciu ();
|
||||
this->channelFreeList.release ( & chan );
|
||||
}
|
||||
|
||||
@@ -614,36 +611,11 @@ int cac::printf ( epicsGuard < epicsMutex > & callbackControl,
|
||||
return status;
|
||||
}
|
||||
|
||||
void cac::flushIfRequired ( epicsGuard < epicsMutex > & guard, netiiu & iiu )
|
||||
{
|
||||
guard.assertIdenticalMutex ( this->mutex );
|
||||
|
||||
if ( iiu.flushBlockThreshold ( guard ) ) {
|
||||
iiu.flushRequest ( guard );
|
||||
// the process thread is not permitted to flush as this
|
||||
// can result in a push / pull deadlock on the TCP pipe.
|
||||
// Instead, the process thread scheduals the flush with the
|
||||
// send thread which runs at a higher priority than the
|
||||
// send thread. The same applies to the UDP thread for
|
||||
// locking hierarchy reasons.
|
||||
if ( ! epicsThreadPrivateGet ( caClientCallbackThreadId ) ) {
|
||||
// enable / disable of call back preemption must occur here
|
||||
// because the tcpiiu might disconnect while waiting and its
|
||||
// pointer to this cac might become invalid
|
||||
iiu.blockUntilSendBacklogIsReasonable ( this->notify, guard );
|
||||
}
|
||||
}
|
||||
else {
|
||||
iiu.flushRequestIfAboveEarlyThreshold ( guard );
|
||||
}
|
||||
}
|
||||
|
||||
void cac::writeRequest (
|
||||
epicsGuard < epicsMutex > & guard, nciu & chan, unsigned type,
|
||||
arrayElementCount nElem, const void * pValue )
|
||||
{
|
||||
guard.assertIdenticalMutex ( this->mutex );
|
||||
this->flushIfRequired ( guard, *chan.getPIIU(guard) );
|
||||
chan.getPIIU(guard)->writeRequest ( guard, chan, type, nElem, pValue );
|
||||
}
|
||||
|
||||
@@ -655,8 +627,7 @@ netWriteNotifyIO & cac::writeNotifyRequest (
|
||||
autoPtrRecycle < netWriteNotifyIO > pIO (
|
||||
guard, this->ioTable, *this,
|
||||
netWriteNotifyIO::factory ( this->freeListWriteNotifyIO, icni, notifyIn ) );
|
||||
this->ioTable.add ( *pIO );
|
||||
this->flushIfRequired ( guard, *chan.getPIIU(guard) );
|
||||
this->ioTable.idAssignAdd ( *pIO );
|
||||
chan.getPIIU(guard)->writeNotifyRequest (
|
||||
guard, chan, *pIO, type, nElem, pValue );
|
||||
return *pIO.release();
|
||||
@@ -670,8 +641,7 @@ netReadNotifyIO & cac::readNotifyRequest (
|
||||
autoPtrRecycle < netReadNotifyIO > pIO (
|
||||
guard, this->ioTable, *this,
|
||||
netReadNotifyIO::factory ( this->freeListReadNotifyIO, icni, notifyIn ) );
|
||||
this->ioTable.add ( *pIO );
|
||||
this->flushIfRequired ( guard, *chan.getPIIU(guard) );
|
||||
this->ioTable.idAssignAdd ( *pIO );
|
||||
chan.getPIIU(guard)->readNotifyRequest ( guard, chan, *pIO, type, nElem );
|
||||
return *pIO.release();
|
||||
}
|
||||
@@ -684,15 +654,11 @@ baseNMIU * cac::destroyIO (
|
||||
cbGuard.assertIdenticalMutex ( this->cbMutex );
|
||||
guard.assertIdenticalMutex ( this->mutex );
|
||||
|
||||
// unistall the IO object so that a receive thread will not find it,
|
||||
// but do _not_ hold the callback lock here because this could result
|
||||
// in deadlock
|
||||
baseNMIU * pIO = this->ioTable.remove ( idIn );
|
||||
if ( pIO ) {
|
||||
class netSubscription * pSubscr = pIO->isSubscription ();
|
||||
if ( pSubscr && chan.connected ( guard ) ) {
|
||||
chan.getPIIU(guard)->subscriptionCancelRequest (
|
||||
guard, chan, *pSubscr );
|
||||
if ( pSubscr ) {
|
||||
pSubscr->unsubscribeIfRequired ( guard, chan );
|
||||
}
|
||||
|
||||
// this uninstalls from the list and destroys the IO
|
||||
@@ -760,17 +726,17 @@ netSubscription & cac::subscriptionRequest (
|
||||
nciu & chan, privateInterfaceForIO & privChan,
|
||||
unsigned type, // X aCC 361
|
||||
arrayElementCount nElem, unsigned mask,
|
||||
cacStateNotify & notifyIn )
|
||||
cacStateNotify & notifyIn,
|
||||
bool chanIsInstalled )
|
||||
{
|
||||
guard.assertIdenticalMutex ( this->mutex );
|
||||
autoPtrRecycle < netSubscription > pIO (
|
||||
guard, this->ioTable, *this,
|
||||
netSubscription::factory ( this->freeListSubscription,
|
||||
privChan, type, nElem, mask, notifyIn ) );
|
||||
this->ioTable.add ( *pIO );
|
||||
if ( chan.connected ( guard ) ) {
|
||||
this->flushIfRequired ( guard, *chan.getPIIU(guard) );
|
||||
chan.getPIIU(guard)->subscriptionRequest ( guard, chan, *pIO );
|
||||
this->ioTable.idAssignAdd ( *pIO );
|
||||
if ( chanIsInstalled ) {
|
||||
pIO->subscribeIfRequired ( guard, chan );
|
||||
}
|
||||
return *pIO.release ();
|
||||
}
|
||||
@@ -850,6 +816,7 @@ bool cac::readNotifyRespAction ( callbackManager &, tcpiiu & iiu,
|
||||
// then we need to reinstall the IO into the table
|
||||
netSubscription * pSubscr = pmiu->isSubscription ();
|
||||
if ( pSubscr ) {
|
||||
// this does *not* assign a new resource id
|
||||
this->ioTable.add ( *pmiu );
|
||||
}
|
||||
if ( caStatus == ECA_NORMAL ) {
|
||||
@@ -1189,7 +1156,7 @@ void cac::destroyIIU ( tcpiiu & iiu )
|
||||
}
|
||||
|
||||
assert ( this->pudpiiu );
|
||||
iiu.removeAllChannels ( cbGuard, guard, *this->pudpiiu );
|
||||
iiu.removeAllChannels ( false, cbGuard, guard, *this->pudpiiu );
|
||||
}
|
||||
|
||||
{
|
||||
|
||||
@@ -169,7 +169,7 @@ public:
|
||||
netSubscription & subscriptionRequest (
|
||||
epicsGuard < epicsMutex > &, nciu &, privateInterfaceForIO &,
|
||||
unsigned type, arrayElementCount nElem, unsigned mask,
|
||||
cacStateNotify & );
|
||||
cacStateNotify &, bool channelIsInstalled );
|
||||
baseNMIU * destroyIO (
|
||||
epicsGuard < epicsMutex > & cbGuard,
|
||||
epicsGuard < epicsMutex > & guard,
|
||||
@@ -224,7 +224,6 @@ public:
|
||||
static unsigned lowestPriorityLevelAbove ( unsigned priority );
|
||||
static unsigned highestPriorityLevelBelow ( unsigned priority );
|
||||
void destroyIIU ( tcpiiu & iiu );
|
||||
void flushIfRequired ( epicsGuard < epicsMutex > &, netiiu & );
|
||||
|
||||
private:
|
||||
localHostName hostNameCache;
|
||||
@@ -432,7 +431,7 @@ inline void cac::disconnectAllChannels (
|
||||
{
|
||||
cbGuard.assertIdenticalMutex ( this->cbMutex );
|
||||
guard.assertIdenticalMutex ( this->mutex );
|
||||
iiu.removeAllChannels ( cbGuard, guard, *this->pudpiiu );
|
||||
iiu.removeAllChannels ( false, cbGuard, guard, *this->pudpiiu );
|
||||
}
|
||||
|
||||
inline notifyGuard::notifyGuard ( cacContextNotify & notifyIn ) :
|
||||
|
||||
@@ -184,6 +184,9 @@ public:
|
||||
unsigned level ) const = 0;
|
||||
virtual void initiateConnect (
|
||||
epicsGuard < epicsMutex > & ) = 0;
|
||||
virtual void eliminateExcessiveSendBacklog (
|
||||
epicsGuard < epicsMutex > * pCallbackGuard,
|
||||
epicsGuard < epicsMutex > & mutualExclusionGuard ) = 0;
|
||||
virtual ioStatus read (
|
||||
epicsGuard < epicsMutex > &,
|
||||
unsigned type, arrayElementCount count,
|
||||
@@ -285,8 +288,6 @@ public:
|
||||
virtual int vPrintf ( const char * pformat, va_list args ) const = 0;
|
||||
// backwards compatibility (from here down)
|
||||
virtual void attachToClientCtx () = 0;
|
||||
virtual void blockForEventAndEnableCallbacks (
|
||||
class epicsEvent & event, const double & timeout ) = 0;
|
||||
virtual void callbackProcessingInitiateNotify () = 0;
|
||||
virtual void callbackProcessingCompleteNotify () = 0;
|
||||
};
|
||||
|
||||
@@ -206,6 +206,8 @@ int main ( int argc, char ** argv )
|
||||
}
|
||||
|
||||
if ( epicsNTOH16 ( pCurMsg->m_cmmd ) == CA_PROTO_RSRV_IS_UP ) {
|
||||
bool anomaly = false;
|
||||
epicsTime previousTime;
|
||||
struct sockaddr_in ina;
|
||||
|
||||
/*
|
||||
@@ -246,25 +248,10 @@ int main ( int argc, char ** argv )
|
||||
*/
|
||||
bhe *pBHE = beaconTable.lookup ( ina );
|
||||
if ( pBHE ) {
|
||||
epicsTime previousTime = pBHE->updateTime ( guard );
|
||||
bool anomaly = pBHE->updatePeriod (
|
||||
previousTime = pBHE->updateTime ( guard );
|
||||
anomaly = pBHE->updatePeriod (
|
||||
guard, programBeginTime,
|
||||
currentTime, beaconNumber, protocolRevision );
|
||||
if ( anomaly ) {
|
||||
char date[64];
|
||||
currentTime.strftime ( date, sizeof ( date ),
|
||||
"%Y-%m-%d %T.%09f");
|
||||
char host[64];
|
||||
ipAddrToA ( &ina, host, sizeof ( host ) );
|
||||
printf ( "%-40s %s\n",
|
||||
host, date );
|
||||
if ( interest > 0 ) {
|
||||
printf ( "\testimate=%f current=%f\n",
|
||||
pBHE->period ( guard ),
|
||||
currentTime - previousTime );
|
||||
}
|
||||
fflush(stdout);
|
||||
}
|
||||
}
|
||||
else {
|
||||
/*
|
||||
@@ -283,6 +270,30 @@ int main ( int argc, char ** argv )
|
||||
}
|
||||
}
|
||||
}
|
||||
if ( anomaly || interest > 1 ) {
|
||||
char date[64];
|
||||
currentTime.strftime ( date, sizeof ( date ),
|
||||
"%Y-%m-%d %H:%M:%S.%09f");
|
||||
char host[64];
|
||||
ipAddrToA ( &ina, host, sizeof ( host ) );
|
||||
const char * pPrefix = "";
|
||||
if ( interest > 1 ) {
|
||||
if ( anomaly ) {
|
||||
pPrefix = "* ";
|
||||
}
|
||||
else {
|
||||
pPrefix = " ";
|
||||
}
|
||||
}
|
||||
printf ( "%s%-40s %s\n",
|
||||
pPrefix, host, date );
|
||||
if ( anomaly && interest > 0 ) {
|
||||
printf ( "\testimate=%f current=%f\n",
|
||||
pBHE->period ( guard ),
|
||||
currentTime - previousTime );
|
||||
}
|
||||
fflush(stdout);
|
||||
}
|
||||
}
|
||||
pCurBuf += msgSize;
|
||||
pCurMsg = reinterpret_cast < const caHdr * > ( pCurBuf );
|
||||
|
||||
@@ -75,12 +75,7 @@ arrayElementCount num /* number of values */
|
||||
/* convert "in place" -> nothing to do */
|
||||
if (s == d)
|
||||
return;
|
||||
if(num == 1){
|
||||
strcpy(pDest, pSrc);
|
||||
}
|
||||
else{
|
||||
memcpy(pDest, pSrc, num*MAX_STRING_SIZE);
|
||||
}
|
||||
memcpy(pDest, pSrc, num*MAX_STRING_SIZE);
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -282,10 +277,7 @@ arrayElementCount num /* number of values */
|
||||
if (s == d)
|
||||
return;
|
||||
|
||||
if (num == 1) /* if single value */
|
||||
strcpy(pDest->value, pSrc->value);
|
||||
else
|
||||
memcpy(pDest->value, pSrc->value, (MAX_STRING_SIZE * num));
|
||||
memcpy(pDest->value, pSrc->value, (MAX_STRING_SIZE * num));
|
||||
|
||||
}
|
||||
|
||||
@@ -432,7 +424,9 @@ arrayElementCount num /* number of values */
|
||||
|
||||
pDest->status = dbr_ntohs(pSrc->status);
|
||||
pDest->severity = dbr_ntohs(pSrc->severity);
|
||||
memcpy(pDest->units,pSrc->units,sizeof(pSrc->units));
|
||||
if ( s != d ) {
|
||||
memcpy(pDest->units,pSrc->units,sizeof(pSrc->units));
|
||||
}
|
||||
|
||||
pDest->upper_disp_limit = dbr_ntohs(pSrc->upper_disp_limit);
|
||||
pDest->lower_disp_limit = dbr_ntohs(pSrc->lower_disp_limit);
|
||||
@@ -510,7 +504,9 @@ arrayElementCount num /* number of values */
|
||||
|
||||
pDest->status = dbr_ntohs(pSrc->status);
|
||||
pDest->severity = dbr_ntohs(pSrc->severity);
|
||||
memcpy(pDest->units,pSrc->units,sizeof(pSrc->units));
|
||||
if ( s != d ) {
|
||||
memcpy(pDest->units,pSrc->units,sizeof(pSrc->units));
|
||||
}
|
||||
|
||||
pDest->upper_disp_limit = dbr_ntohl(pSrc->upper_disp_limit);
|
||||
pDest->lower_disp_limit = dbr_ntohl(pSrc->lower_disp_limit);
|
||||
@@ -549,7 +545,9 @@ arrayElementCount num /* number of values */
|
||||
pDest->status = dbr_ntohs(pSrc->status);
|
||||
pDest->severity = dbr_ntohs(pSrc->severity);
|
||||
pDest->no_str = dbr_ntohs(pSrc->no_str);
|
||||
memcpy((void *)pDest->strs,(void *)pSrc->strs,sizeof(pSrc->strs));
|
||||
if ( s != d ) {
|
||||
memcpy((void *)pDest->strs,(void *)pSrc->strs,sizeof(pSrc->strs));
|
||||
}
|
||||
|
||||
if (num == 1) /* single value */
|
||||
pDest->value = dbr_ntohs(pSrc->value);
|
||||
@@ -583,7 +581,9 @@ arrayElementCount num /* number of values */
|
||||
pDest->status = dbr_ntohs(pSrc->status);
|
||||
pDest->severity = dbr_ntohs(pSrc->severity);
|
||||
pDest->precision = dbr_ntohs(pSrc->precision);
|
||||
memcpy(pDest->units,pSrc->units,sizeof(pSrc->units));
|
||||
if ( s != d ) {
|
||||
memcpy(pDest->units,pSrc->units,sizeof(pSrc->units));
|
||||
}
|
||||
|
||||
if (encode) /* vax to ieee convert */
|
||||
{
|
||||
@@ -645,7 +645,9 @@ arrayElementCount num /* number of values */
|
||||
pDest->status = dbr_ntohs(pSrc->status);
|
||||
pDest->severity = dbr_ntohs(pSrc->severity);
|
||||
pDest->precision = dbr_ntohs(pSrc->precision);
|
||||
memcpy(pDest->units,pSrc->units,sizeof(pSrc->units));
|
||||
if ( s != d ) {
|
||||
memcpy(pDest->units,pSrc->units,sizeof(pSrc->units));
|
||||
}
|
||||
|
||||
if (encode) /* vax to ieee convert */
|
||||
{
|
||||
@@ -707,7 +709,9 @@ arrayElementCount num /* number of values */
|
||||
/* vax to ieee or ieee to vax -- same code */
|
||||
pDest->status = dbr_ntohs(pSrc->status);
|
||||
pDest->severity = dbr_ntohs(pSrc->severity);
|
||||
memcpy(pDest->units,pSrc->units,sizeof(pSrc->units));
|
||||
if ( s != d ) {
|
||||
memcpy(pDest->units,pSrc->units,sizeof(pSrc->units));
|
||||
}
|
||||
|
||||
pDest->upper_disp_limit = dbr_ntohs(pSrc->upper_disp_limit);
|
||||
pDest->lower_disp_limit = dbr_ntohs(pSrc->lower_disp_limit);
|
||||
@@ -747,7 +751,9 @@ arrayElementCount num /* number of values */
|
||||
/* vax to ieee or ieee to vax -- same code */
|
||||
pDest->status = dbr_ntohs(pSrc->status);
|
||||
pDest->severity = dbr_ntohs(pSrc->severity);
|
||||
memcpy(pDest->units,pSrc->units,sizeof(pSrc->units));
|
||||
if ( s != d ) {
|
||||
memcpy(pDest->units,pSrc->units,sizeof(pSrc->units));
|
||||
}
|
||||
|
||||
pDest->upper_disp_limit = dbr_ntohl(pSrc->upper_disp_limit);
|
||||
pDest->lower_disp_limit = dbr_ntohl(pSrc->lower_disp_limit);
|
||||
@@ -788,6 +794,9 @@ arrayElementCount num /* number of values */
|
||||
pDest->status = dbr_ntohs(pSrc->status);
|
||||
pDest->severity = dbr_ntohs(pSrc->severity);
|
||||
|
||||
if ( s == d )
|
||||
return;
|
||||
|
||||
pDest->upper_disp_limit = pSrc->upper_disp_limit;
|
||||
pDest->lower_disp_limit = pSrc->lower_disp_limit;
|
||||
pDest->upper_alarm_limit = pSrc->upper_alarm_limit;
|
||||
@@ -826,7 +835,9 @@ arrayElementCount num /* number of values */
|
||||
pDest->status = dbr_ntohs(pSrc->status);
|
||||
pDest->severity = dbr_ntohs(pSrc->severity);
|
||||
pDest->precision = dbr_ntohs(pSrc->precision);
|
||||
memcpy(pDest->units,pSrc->units,sizeof(pSrc->units));
|
||||
if ( s != d ) {
|
||||
memcpy(pDest->units,pSrc->units,sizeof(pSrc->units));
|
||||
}
|
||||
if (encode) /* vax to ieee convert */
|
||||
{
|
||||
if (num == 1){
|
||||
@@ -890,7 +901,9 @@ arrayElementCount num /* number of values */
|
||||
pDest->status = dbr_ntohs(pSrc->status);
|
||||
pDest->severity = dbr_ntohs(pSrc->severity);
|
||||
pDest->precision = dbr_ntohs(pSrc->precision);
|
||||
memcpy(pDest->units,pSrc->units,sizeof(pSrc->units));
|
||||
if ( s != d ) {
|
||||
memcpy(pDest->units,pSrc->units,sizeof(pSrc->units));
|
||||
}
|
||||
if (encode) /* vax to ieee convert */
|
||||
{
|
||||
if (num == 1){
|
||||
@@ -952,7 +965,9 @@ arrayElementCount num /* number of values */
|
||||
pDest->status = dbr_ntohs(pSrc->status);
|
||||
pDest->severity = dbr_ntohs(pSrc->severity);
|
||||
pDest->no_str = dbr_ntohs(pSrc->no_str);
|
||||
memcpy((void *)pDest->strs,(void *)pSrc->strs,sizeof(pSrc->strs));
|
||||
if ( s != d ) {
|
||||
memcpy((void *)pDest->strs,(void *)pSrc->strs,sizeof(pSrc->strs));
|
||||
}
|
||||
|
||||
if (num == 1) /* single value */
|
||||
pDest->value = dbr_ntohs(pSrc->value);
|
||||
@@ -989,6 +1004,9 @@ arrayElementCount num /* number of values */
|
||||
pDest->status = dbr_ntohs(pSrc->status);
|
||||
pDest->severity = dbr_ntohs(pSrc->severity);
|
||||
|
||||
if ( s == d )
|
||||
return;
|
||||
|
||||
if (num == 1) /* single value */
|
||||
pDest->value = pSrc->value;
|
||||
else /* array chan-- multiple pts */
|
||||
@@ -1054,11 +1072,9 @@ arrayElementCount num /* number of values */
|
||||
pDest->stamp.secPastEpoch = dbr_ntohl(pSrc->stamp.secPastEpoch);
|
||||
pDest->stamp.nsec = dbr_ntohl(pSrc->stamp.nsec);
|
||||
|
||||
if (num == 1) /* if single value */
|
||||
strcpy(pDest->value, pSrc->value);
|
||||
else
|
||||
if ( s != d ) {
|
||||
memcpy(pDest->value, pSrc->value, (MAX_STRING_SIZE * num));
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
@@ -1207,6 +1223,9 @@ arrayElementCount num /* number of values */
|
||||
pDest->stamp.secPastEpoch = dbr_ntohl(pSrc->stamp.secPastEpoch);
|
||||
pDest->stamp.nsec = dbr_ntohl(pSrc->stamp.nsec);
|
||||
|
||||
if ( s == d )
|
||||
return;
|
||||
|
||||
if (num == 1) /* single value */
|
||||
pDest->value = pSrc->value;
|
||||
else /* array chan-- multiple pts */
|
||||
@@ -1308,10 +1327,7 @@ arrayElementCount num /* number of values */
|
||||
if (s == d)
|
||||
return;
|
||||
|
||||
if (num == 1) /* if single value */
|
||||
strcpy(pDest->value, pSrc->value);
|
||||
else
|
||||
memcpy(pDest->value, pSrc->value, (MAX_STRING_SIZE * num));
|
||||
memcpy(pDest->value, pSrc->value, (MAX_STRING_SIZE * num));
|
||||
}
|
||||
|
||||
#if defined(CA_FLOAT_MIT)
|
||||
|
||||
@@ -53,11 +53,13 @@ void getCallback::completion (
|
||||
args.status = ECA_NORMAL;
|
||||
args.dbr = pData;
|
||||
caEventCallBackFunc * pFuncTmp = this->pFunc;
|
||||
// fetch client context and destroy prior to releasing
|
||||
// the lock and calling cb in case they destroy channel there
|
||||
this->chan.getClientCtx().destroyGetCallback ( guard, *this );
|
||||
{
|
||||
epicsGuardRelease < epicsMutex > unguard ( guard );
|
||||
( *pFuncTmp ) ( args );
|
||||
}
|
||||
this->chan.getClientCtx().destroyGetCallback ( guard, *this );
|
||||
}
|
||||
|
||||
void getCallback::exception (
|
||||
|
||||
@@ -74,43 +74,34 @@ nciu::nciu ( cac & cacIn, netiiu & iiuIn, cacChannelNotify & chanIn,
|
||||
|
||||
nciu::~nciu ()
|
||||
{
|
||||
delete [] this->pNameStr;
|
||||
}
|
||||
|
||||
// channels are created by the user, and only destroyed by the user
|
||||
// using this routine
|
||||
void nciu::destroy (
|
||||
epicsGuard < epicsMutex > & callbackControlGuard,
|
||||
epicsGuard < epicsMutex > & mutualExclusionGuard )
|
||||
{
|
||||
this->cacCtx.destroyChannel (
|
||||
callbackControlGuard, mutualExclusionGuard, *this );
|
||||
}
|
||||
|
||||
void nciu::destructor (
|
||||
epicsGuard < epicsMutex > & cbGuard,
|
||||
epicsGuard < epicsMutex > & guard )
|
||||
{
|
||||
guard.assertIdenticalMutex ( this->cacCtx.mutexRef () );
|
||||
// Send any side effect IO requests w/o holding the callback lock so that
|
||||
// we do not dead lock.
|
||||
// There is special protection in this routine that prevents blocking if
|
||||
// this is the tcp receive thread.
|
||||
// must not hold callback lock here
|
||||
this->cacCtx.flushIfRequired ( guard, *this->piiu );
|
||||
|
||||
{
|
||||
while ( baseNMIU * pNetIO = this->eventq.first () ) {
|
||||
assert ( this->cacCtx.destroyIO ( cbGuard, guard,
|
||||
assert ( this->cacCtx.destroyIO (
|
||||
callbackControlGuard, mutualExclusionGuard,
|
||||
pNetIO->getId (), *this ) );
|
||||
}
|
||||
|
||||
// if the claim reply has not returned yet then we will issue
|
||||
// the clear channel request to the server when the claim reply
|
||||
// arrives and there is no matching nciu in the client
|
||||
if ( this->connected ( guard ) ) {
|
||||
this->getPIIU(guard)->clearChannelRequest (
|
||||
guard, this->sid, this->id );
|
||||
if ( this->channelNode::isInstalledInServer ( mutualExclusionGuard ) ) {
|
||||
this->getPIIU(mutualExclusionGuard)->clearChannelRequest (
|
||||
mutualExclusionGuard, this->sid, this->id );
|
||||
}
|
||||
|
||||
delete [] this->pNameStr;
|
||||
this->~nciu ();
|
||||
|
||||
this->piiu->uninstallChan (
|
||||
callbackControlGuard, mutualExclusionGuard, *this );
|
||||
|
||||
this->cacCtx.destroyChannel (
|
||||
callbackControlGuard, mutualExclusionGuard, *this );
|
||||
}
|
||||
|
||||
void * nciu::operator new ( size_t ) // X aCC 361
|
||||
@@ -265,6 +256,14 @@ unsigned nciu::nameLen (
|
||||
return this->nameLength;
|
||||
}
|
||||
|
||||
void nciu::eliminateExcessiveSendBacklog (
|
||||
epicsGuard < epicsMutex > * pCallbackGuard,
|
||||
epicsGuard < epicsMutex > & mutualExclusionGuard )
|
||||
{
|
||||
this->piiu->eliminateExcessiveSendBacklog (
|
||||
pCallbackGuard, mutualExclusionGuard );
|
||||
}
|
||||
|
||||
cacChannel::ioStatus nciu::read (
|
||||
epicsGuard < epicsMutex > & guard,
|
||||
unsigned type, arrayElementCount countIn,
|
||||
@@ -372,11 +371,12 @@ void nciu::subscribe (
|
||||
cacStateNotify & notify, ioid *pId )
|
||||
{
|
||||
netSubscription & io = this->cacCtx.subscriptionRequest (
|
||||
guard, *this, *this, type, nElem, mask, notify );
|
||||
guard, *this, *this, type, nElem, mask, notify,
|
||||
this->channelNode::isInstalledInServer ( guard ) );
|
||||
this->eventq.add ( io );
|
||||
if ( pId ) {
|
||||
*pId = io.getId ();
|
||||
}
|
||||
this->eventq.add ( io );
|
||||
}
|
||||
|
||||
void nciu::ioCancel (
|
||||
@@ -542,7 +542,7 @@ void nciu::resubscribe ( epicsGuard < epicsMutex > & guard )
|
||||
// them here.
|
||||
if ( pSubscr ) {
|
||||
try {
|
||||
this->getPIIU(guard)->subscriptionRequest ( guard, *this, *pSubscr );
|
||||
pSubscr->subscribeIfRequired ( guard, *this );
|
||||
}
|
||||
catch ( ... ) {
|
||||
errlogPrintf ( "CAC: failed to send subscription request "
|
||||
|
||||
@@ -58,6 +58,7 @@ class channelNode : public tsDLNode < class nciu >
|
||||
public:
|
||||
channelNode ();
|
||||
bool isConnected ( epicsGuard < epicsMutex > & ) const;
|
||||
bool isInstalledInServer ( epicsGuard < epicsMutex > & ) const;
|
||||
private:
|
||||
enum channelState {
|
||||
cs_none,
|
||||
@@ -92,9 +93,7 @@ class nciu :
|
||||
public:
|
||||
nciu ( cac &, netiiu &, cacChannelNotify &,
|
||||
const char * pNameIn, cacChannel::priLev );
|
||||
void destructor (
|
||||
epicsGuard < epicsMutex > & cbGuard,
|
||||
epicsGuard < epicsMutex > & guard );
|
||||
~nciu ();
|
||||
void connect ( unsigned nativeType,
|
||||
unsigned nativeCount, unsigned sid,
|
||||
epicsGuard < epicsMutex > & cbGuard,
|
||||
@@ -155,9 +154,6 @@ public:
|
||||
epicsGuard < epicsMutex > &, epicsGuard < epicsMutex > & );
|
||||
bool connected ( epicsGuard < epicsMutex > & ) const;
|
||||
|
||||
protected:
|
||||
~nciu ();
|
||||
|
||||
private:
|
||||
tsDLList < class baseNMIU > eventq;
|
||||
caAccessRights accessRightState;
|
||||
@@ -175,6 +171,9 @@ private:
|
||||
epicsGuard < epicsMutex > & mutualExclusionGuard );
|
||||
void initiateConnect (
|
||||
epicsGuard < epicsMutex > & );
|
||||
void eliminateExcessiveSendBacklog (
|
||||
epicsGuard < epicsMutex > * pCallbackGuard,
|
||||
epicsGuard < epicsMutex > & mutualExclusionGuard );
|
||||
ioStatus read (
|
||||
epicsGuard < epicsMutex > &,
|
||||
unsigned type, arrayElementCount count,
|
||||
@@ -319,4 +318,13 @@ inline bool channelNode::isConnected ( epicsGuard < epicsMutex > & ) const
|
||||
this->listMember == cs_subscripUpdateReqPend;
|
||||
}
|
||||
|
||||
inline bool channelNode::isInstalledInServer ( epicsGuard < epicsMutex > & ) const
|
||||
{
|
||||
return
|
||||
this->listMember == cs_connected ||
|
||||
this->listMember == cs_subscripReqPend ||
|
||||
this->listMember == cs_unrespCircuit ||
|
||||
this->listMember == cs_subscripUpdateReqPend;
|
||||
}
|
||||
|
||||
#endif // ifdef nciuh
|
||||
|
||||
@@ -87,6 +87,10 @@ public:
|
||||
epicsGuard < epicsMutex > & ) const;
|
||||
unsigned getMask (
|
||||
epicsGuard < epicsMutex > & ) const;
|
||||
void subscribeIfRequired (
|
||||
epicsGuard < epicsMutex > & guard, nciu & chan );
|
||||
void unsubscribeIfRequired (
|
||||
epicsGuard < epicsMutex > & guard, nciu & chan );
|
||||
void subscriptionUpdateIfRequired (
|
||||
epicsGuard < epicsMutex > &, nciu & );
|
||||
protected:
|
||||
@@ -102,6 +106,7 @@ private:
|
||||
const unsigned type;
|
||||
const unsigned mask;
|
||||
bool updateWhileDisconnected;
|
||||
bool subscribed;
|
||||
class netSubscription * isSubscription ();
|
||||
void * operator new ( size_t );
|
||||
void operator delete ( void * );
|
||||
|
||||
@@ -64,8 +64,8 @@ void netReadNotifyIO::completion (
|
||||
arrayElementCount count, const void * pData )
|
||||
{
|
||||
//guard.assertIdenticalMutex ( this->mutex );
|
||||
this->notify.completion ( guard, type, count, pData );
|
||||
this->privateChanForIO.ioCompletionNotify ( guard, *this );
|
||||
this->notify.completion ( guard, type, count, pData );
|
||||
this->~netReadNotifyIO ();
|
||||
recycle.recycleReadNotifyIO ( guard, *this );
|
||||
}
|
||||
@@ -87,9 +87,9 @@ void netReadNotifyIO::exception (
|
||||
int status, const char *pContext )
|
||||
{
|
||||
//guard.assertIdenticalMutex ( this->mutex );
|
||||
this->privateChanForIO.ioCompletionNotify ( guard, *this );
|
||||
this->notify.exception (
|
||||
guard, status, pContext, UINT_MAX, 0u );
|
||||
this->privateChanForIO.ioCompletionNotify ( guard, *this );
|
||||
this->~netReadNotifyIO ();
|
||||
recycle.recycleReadNotifyIO ( guard, *this );
|
||||
}
|
||||
@@ -101,9 +101,9 @@ void netReadNotifyIO::exception (
|
||||
unsigned type, arrayElementCount count )
|
||||
{
|
||||
//guard.assertIdenticalMutex ( this->mutex )
|
||||
this->privateChanForIO.ioCompletionNotify ( guard, *this );
|
||||
this->notify.exception (
|
||||
guard, status, pContext, type, count );
|
||||
this->privateChanForIO.ioCompletionNotify ( guard, *this );
|
||||
this->~netReadNotifyIO ();
|
||||
recycle.recycleReadNotifyIO ( guard, *this );
|
||||
}
|
||||
|
||||
@@ -37,7 +37,7 @@ netSubscription::netSubscription (
|
||||
unsigned maskIn, cacStateNotify & notifyIn ) :
|
||||
count ( countIn ), privateChanForIO ( chanIn ),
|
||||
notify ( notifyIn ), type ( typeIn ), mask ( maskIn ),
|
||||
updateWhileDisconnected ( false )
|
||||
updateWhileDisconnected ( false ), subscribed ( false )
|
||||
{
|
||||
if ( ! dbr_type_is_valid ( typeIn ) ) {
|
||||
throw cacChannel::badType ();
|
||||
@@ -93,6 +93,9 @@ void netSubscription::exception (
|
||||
epicsGuard < epicsMutex > & guard, cacRecycle & recycle,
|
||||
int status, const char * pContext )
|
||||
{
|
||||
if ( status == ECA_DISCONN ) {
|
||||
this->subscribed = false;
|
||||
}
|
||||
if ( status == ECA_CHANDESTROY ) {
|
||||
this->notify.exception (
|
||||
guard, status, pContext, UINT_MAX, 0 );
|
||||
@@ -118,6 +121,9 @@ void netSubscription::exception (
|
||||
cacRecycle & recycle, int status, const char * pContext,
|
||||
unsigned typeIn, arrayElementCount countIn )
|
||||
{
|
||||
if ( status == ECA_DISCONN ) {
|
||||
this->subscribed = false;
|
||||
}
|
||||
if ( status == ECA_CHANDESTROY ) {
|
||||
this->notify.exception (
|
||||
guard, status, pContext, UINT_MAX, 0 );
|
||||
@@ -154,6 +160,26 @@ void netSubscription::completion (
|
||||
}
|
||||
}
|
||||
|
||||
void netSubscription::subscribeIfRequired (
|
||||
epicsGuard < epicsMutex > & guard, nciu & chan )
|
||||
{
|
||||
if ( ! this->subscribed ) {
|
||||
chan.getPIIU(guard)->subscriptionRequest (
|
||||
guard, chan, *this );
|
||||
this->subscribed = true;
|
||||
}
|
||||
}
|
||||
|
||||
void netSubscription::unsubscribeIfRequired (
|
||||
epicsGuard < epicsMutex > & guard, nciu & chan )
|
||||
{
|
||||
if ( this->subscribed ) {
|
||||
chan.getPIIU(guard)->subscriptionCancelRequest (
|
||||
guard, chan, *this );
|
||||
this->subscribed = false;
|
||||
}
|
||||
}
|
||||
|
||||
void netSubscription::subscriptionUpdateIfRequired (
|
||||
epicsGuard < epicsMutex > & guard, nciu & chan )
|
||||
{
|
||||
|
||||
@@ -86,9 +86,9 @@ void netWriteNotifyIO::exception (
|
||||
cacRecycle & recycle,
|
||||
int status, const char * pContext )
|
||||
{
|
||||
this->privateChanForIO.ioCompletionNotify ( guard, *this );
|
||||
this->notify.exception (
|
||||
guard, status, pContext, UINT_MAX, 0u );
|
||||
this->privateChanForIO.ioCompletionNotify ( guard, *this );
|
||||
this->~netWriteNotifyIO ();
|
||||
recycle.recycleWriteNotifyIO ( guard, *this );
|
||||
}
|
||||
@@ -99,9 +99,9 @@ void netWriteNotifyIO::exception (
|
||||
int status, const char *pContext,
|
||||
unsigned type, arrayElementCount count )
|
||||
{
|
||||
this->privateChanForIO.ioCompletionNotify ( guard, *this );
|
||||
this->notify.exception (
|
||||
guard, status, pContext, type, count );
|
||||
this->privateChanForIO.ioCompletionNotify ( guard, *this );
|
||||
this->~netWriteNotifyIO ();
|
||||
recycle.recycleWriteNotifyIO ( guard, *this );
|
||||
}
|
||||
|
||||
@@ -115,22 +115,12 @@ void netiiu::flushRequest (
|
||||
{
|
||||
}
|
||||
|
||||
bool netiiu::flushBlockThreshold (
|
||||
epicsGuard < epicsMutex > & ) const
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
void netiiu::flushRequestIfAboveEarlyThreshold (
|
||||
void netiiu::eliminateExcessiveSendBacklog (
|
||||
epicsGuard < epicsMutex > *,
|
||||
epicsGuard < epicsMutex > & )
|
||||
{
|
||||
}
|
||||
|
||||
void netiiu::blockUntilSendBacklogIsReasonable
|
||||
( cacContextNotify &, epicsGuard < epicsMutex > & )
|
||||
{
|
||||
}
|
||||
|
||||
void netiiu::requestRecvProcessPostponedFlush (
|
||||
epicsGuard < epicsMutex > & )
|
||||
{
|
||||
|
||||
@@ -49,6 +49,9 @@ public:
|
||||
epicsGuard < epicsMutex > & ) const = 0;
|
||||
virtual bool ca_v42_ok (
|
||||
epicsGuard < epicsMutex > & ) const = 0;
|
||||
virtual void eliminateExcessiveSendBacklog (
|
||||
epicsGuard < epicsMutex > * pCallbackGuard,
|
||||
epicsGuard < epicsMutex > & mutualExclusionGuard ) = 0;
|
||||
virtual void writeRequest (
|
||||
epicsGuard < epicsMutex > &, nciu &,
|
||||
unsigned type, arrayElementCount nElem,
|
||||
@@ -76,12 +79,6 @@ public:
|
||||
nciu & chan, netSubscription & subscr ) = 0;
|
||||
virtual void flushRequest (
|
||||
epicsGuard < epicsMutex > & ) = 0;
|
||||
virtual bool flushBlockThreshold (
|
||||
epicsGuard < epicsMutex > & ) const = 0;
|
||||
virtual void flushRequestIfAboveEarlyThreshold (
|
||||
epicsGuard < epicsMutex > & ) = 0;
|
||||
virtual void blockUntilSendBacklogIsReasonable
|
||||
( cacContextNotify &, epicsGuard < epicsMutex > & ) = 0;
|
||||
virtual void requestRecvProcessPostponedFlush (
|
||||
epicsGuard < epicsMutex > & ) = 0;
|
||||
virtual osiSockAddr getNetworkAddress (
|
||||
|
||||
@@ -71,6 +71,9 @@ public:
|
||||
unsigned level ) const;
|
||||
void initiateConnect (
|
||||
epicsGuard < epicsMutex > & );
|
||||
void eliminateExcessiveSendBacklog (
|
||||
epicsGuard < epicsMutex > * pCallbackGuard,
|
||||
epicsGuard < epicsMutex > & mutualExclusionGuard );
|
||||
void read (
|
||||
epicsGuard < epicsMutex > &,
|
||||
unsigned type, arrayElementCount count,
|
||||
@@ -285,6 +288,8 @@ public:
|
||||
epicsGuard < epicsMutex > &, const char * pChannelName,
|
||||
oldChannelNotify &, cacChannel::priLev pri );
|
||||
void flush ( epicsGuard < epicsMutex > & );
|
||||
void eliminateExcessiveSendBacklog (
|
||||
oldChannelNotify & chan, epicsGuard < epicsMutex > & guard );
|
||||
int pendIO ( const double & timeout );
|
||||
int pendEvent ( const double & timeout );
|
||||
bool ioComplete () const;
|
||||
@@ -434,6 +439,14 @@ inline void oldChannelNotify::initiateConnect (
|
||||
this->io.initiateConnect ( guard );
|
||||
}
|
||||
|
||||
inline void oldChannelNotify::eliminateExcessiveSendBacklog (
|
||||
epicsGuard < epicsMutex > * pCallbackGuard,
|
||||
epicsGuard < epicsMutex > & mutualExclusionGuard )
|
||||
{
|
||||
this->io.eliminateExcessiveSendBacklog (
|
||||
pCallbackGuard, mutualExclusionGuard );
|
||||
}
|
||||
|
||||
inline void oldChannelNotify::ioCancel (
|
||||
epicsGuard < epicsMutex > & cbGuard,
|
||||
epicsGuard < epicsMutex > & guard,
|
||||
@@ -628,4 +641,11 @@ inline unsigned ca_client_context::sequenceNumberOfOutstandingIO (
|
||||
return this->ioSeqNo;
|
||||
}
|
||||
|
||||
inline void ca_client_context::eliminateExcessiveSendBacklog (
|
||||
oldChannelNotify & chan, epicsGuard < epicsMutex > & guard )
|
||||
{
|
||||
chan.eliminateExcessiveSendBacklog (
|
||||
this->pCallbackGuard.get(), guard );
|
||||
}
|
||||
|
||||
#endif // ifndef oldAccessh
|
||||
|
||||
@@ -128,7 +128,7 @@ int oldChannelNotify::replaceAccessRightsEvent (
|
||||
args.ar.read_access = tmp.readPermit ();
|
||||
args.ar.write_access = tmp.writePermit ();
|
||||
epicsGuardRelease < epicsMutex > unguard ( guard );
|
||||
( *pfunc ) ( args );
|
||||
( *this->pAccessRightsFunc ) ( args );
|
||||
}
|
||||
return ECA_NORMAL;
|
||||
}
|
||||
|
||||
@@ -37,6 +37,8 @@ void syncGroupReadNotify::begin (
|
||||
epicsGuard < epicsMutex > & guard,
|
||||
unsigned type, arrayElementCount count )
|
||||
{
|
||||
this->chan->getClientCtx().
|
||||
eliminateExcessiveSendBacklog ( *this->chan, guard );
|
||||
this->ioComplete = false;
|
||||
boolFlagManager mgr ( this->idIsValid );
|
||||
this->chan->read ( guard, type, count, *this, &this->id );
|
||||
|
||||
@@ -35,6 +35,8 @@ void syncGroupWriteNotify::begin (
|
||||
epicsGuard < epicsMutex > & guard, unsigned type,
|
||||
arrayElementCount count, const void * pValueIn )
|
||||
{
|
||||
this->chan->getClientCtx().eliminateExcessiveSendBacklog (
|
||||
*this->chan, guard );
|
||||
this->ioComplete = false;
|
||||
boolFlagManager mgr ( this->idIsValid );
|
||||
this->chan->write ( guard, type, count,
|
||||
|
||||
@@ -155,7 +155,7 @@ void tcpRecvWatchdog::probeResponseNotify (
|
||||
this->probeResponsePending = false;
|
||||
restartDelay = this->period;
|
||||
this->iiu.responsiveCircuitNotify ( cbGuard, guard );
|
||||
debugPrintf ( ("probe response on time - circuit will be tagged reponsive if unresponsive\n") );
|
||||
debugPrintf ( ("probe response on time - circuit was tagged reponsive if unresponsive\n") );
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -164,6 +164,7 @@ void tcpRecvWatchdog::probeResponseNotify (
|
||||
epicsGuardRelease < epicsMutex > cbGuardRelease ( cbGuard );
|
||||
epicsTime expireTime = currentTime + restartDelay;
|
||||
this->timer.start ( *this, expireTime );
|
||||
debugPrintf ( ("recv wd restarted with delay %f\n", restartDelay) );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -1540,43 +1540,52 @@ bool tcpiiu::flush ( epicsGuard < epicsMutex > & guard )
|
||||
return true;
|
||||
}
|
||||
|
||||
// ~tcpiiu() will not return while this->blockingForFlush is greater than zero
|
||||
void tcpiiu::blockUntilSendBacklogIsReasonable (
|
||||
cacContextNotify & notify, epicsGuard < epicsMutex > & guard )
|
||||
void tcpiiu::eliminateExcessiveSendBacklog (
|
||||
epicsGuard < epicsMutex > * pCallbackGuard,
|
||||
epicsGuard < epicsMutex > & mutualExclusionGuard )
|
||||
{
|
||||
guard.assertIdenticalMutex ( this->mutex );
|
||||
mutualExclusionGuard.assertIdenticalMutex ( this->mutex );
|
||||
|
||||
assert ( this->blockingForFlush < UINT_MAX );
|
||||
this->blockingForFlush++;
|
||||
while ( this->sendQue.flushBlockThreshold(0u) && this->state == iiucs_connected ) {
|
||||
epicsGuardRelease < epicsMutex > autoRelease ( guard );
|
||||
notify.blockForEventAndEnableCallbacks ( this->flushBlockEvent, 30.0 );
|
||||
if ( this->sendQue.flushBlockThreshold ( 0u ) ) {
|
||||
this->flushRequest ( mutualExclusionGuard );
|
||||
// the process thread is not permitted to flush as this
|
||||
// can result in a push / pull deadlock on the TCP pipe.
|
||||
// Instead, the process thread scheduals the flush with the
|
||||
// send thread which runs at a higher priority than the
|
||||
// receive thread. The same applies to the UDP thread for
|
||||
// locking hierarchy reasons.
|
||||
if ( ! epicsThreadPrivateGet ( caClientCallbackThreadId ) ) {
|
||||
// enable / disable of call back preemption must occur here
|
||||
// because the tcpiiu might disconnect while waiting and its
|
||||
// pointer to this cac might become invalid
|
||||
assert ( this->blockingForFlush < UINT_MAX );
|
||||
this->blockingForFlush++;
|
||||
while ( this->sendQue.flushBlockThreshold(0u) &&
|
||||
this->state == iiucs_connected ) {
|
||||
epicsGuardRelease < epicsMutex > autoRelease (
|
||||
mutualExclusionGuard );
|
||||
if ( pCallbackGuard ) {
|
||||
epicsGuardRelease < epicsMutex >
|
||||
autoReleaseCB ( *pCallbackGuard );
|
||||
this->flushBlockEvent.wait ( 30.0 );
|
||||
}
|
||||
else {
|
||||
this->flushBlockEvent.wait ( 30.0 );
|
||||
}
|
||||
}
|
||||
assert ( this->blockingForFlush > 0u );
|
||||
this->blockingForFlush--;
|
||||
if ( this->blockingForFlush == 0 ) {
|
||||
this->flushBlockEvent.signal ();
|
||||
}
|
||||
}
|
||||
}
|
||||
assert ( this->blockingForFlush > 0u );
|
||||
this->blockingForFlush--;
|
||||
if ( this->blockingForFlush == 0 ) {
|
||||
this->flushBlockEvent.signal ();
|
||||
}
|
||||
}
|
||||
|
||||
void tcpiiu::flushRequestIfAboveEarlyThreshold (
|
||||
epicsGuard < epicsMutex > & guard )
|
||||
{
|
||||
guard.assertIdenticalMutex ( this->mutex );
|
||||
|
||||
if ( ! this->earlyFlush && this->sendQue.flushEarlyThreshold(0u) ) {
|
||||
else if ( ! this->earlyFlush && this->sendQue.flushEarlyThreshold(0u) ) {
|
||||
this->earlyFlush = true;
|
||||
this->sendThreadFlushEvent.signal ();
|
||||
}
|
||||
}
|
||||
|
||||
bool tcpiiu::flushBlockThreshold (
|
||||
epicsGuard < epicsMutex > & guard ) const
|
||||
{
|
||||
guard.assertIdenticalMutex ( this->mutex );
|
||||
return this->sendQue.flushBlockThreshold ( 0u );
|
||||
}
|
||||
|
||||
osiSockAddr tcpiiu::getNetworkAddress (
|
||||
epicsGuard < epicsMutex > & guard ) const
|
||||
{
|
||||
@@ -1617,6 +1626,7 @@ const char * tcpiiu::pHostName (
|
||||
}
|
||||
|
||||
void tcpiiu::removeAllChannels (
|
||||
bool supressApplicationNotify,
|
||||
epicsGuard < epicsMutex > & cbGuard,
|
||||
epicsGuard < epicsMutex > & guard,
|
||||
udpiiu & discIIU )
|
||||
@@ -1640,14 +1650,18 @@ void tcpiiu::removeAllChannels (
|
||||
pChan->disconnectAllIO ( cbGuard, guard );
|
||||
discIIU.installDisconnectedChannel ( *pChan );
|
||||
pChan->setServerAddressUnknown ( discIIU, guard );
|
||||
pChan->unresponsiveCircuitNotify ( cbGuard, guard );
|
||||
if ( ! supressApplicationNotify ) {
|
||||
pChan->unresponsiveCircuitNotify ( cbGuard, guard );
|
||||
}
|
||||
}
|
||||
|
||||
while ( nciu * pChan = this->connectedList.get () ) {
|
||||
pChan->disconnectAllIO ( cbGuard, guard );
|
||||
discIIU.installDisconnectedChannel ( *pChan );
|
||||
pChan->setServerAddressUnknown ( discIIU, guard );
|
||||
pChan->unresponsiveCircuitNotify ( cbGuard, guard );
|
||||
if ( ! supressApplicationNotify ) {
|
||||
pChan->unresponsiveCircuitNotify ( cbGuard, guard );
|
||||
}
|
||||
}
|
||||
|
||||
while ( nciu * pChan = this->unrespCircuit.get () ) {
|
||||
|
||||
@@ -1229,25 +1229,10 @@ void udpiiu::flushRequest (
|
||||
netiiu::flushRequest ( guard );
|
||||
}
|
||||
|
||||
bool udpiiu::flushBlockThreshold (
|
||||
epicsGuard < epicsMutex > & guard ) const
|
||||
void udpiiu::eliminateExcessiveSendBacklog (
|
||||
epicsGuard < epicsMutex > *,
|
||||
epicsGuard < epicsMutex > & )
|
||||
{
|
||||
guard.assertIdenticalMutex ( this->cacMutex );
|
||||
return netiiu::flushBlockThreshold ( guard );
|
||||
}
|
||||
|
||||
void udpiiu::flushRequestIfAboveEarlyThreshold (
|
||||
epicsGuard < epicsMutex > & guard )
|
||||
{
|
||||
guard.assertIdenticalMutex ( this->cacMutex );
|
||||
netiiu::flushRequestIfAboveEarlyThreshold ( guard );
|
||||
}
|
||||
|
||||
void udpiiu::blockUntilSendBacklogIsReasonable (
|
||||
cacContextNotify & notify, epicsGuard < epicsMutex > & guard )
|
||||
{
|
||||
guard.assertIdenticalMutex ( this->cacMutex );
|
||||
netiiu::blockUntilSendBacklogIsReasonable ( notify, guard );
|
||||
}
|
||||
|
||||
void udpiiu::requestRecvProcessPostponedFlush (
|
||||
|
||||
@@ -215,12 +215,9 @@ private:
|
||||
nciu & chan, netSubscription & subscr );
|
||||
void flushRequest (
|
||||
epicsGuard < epicsMutex > & );
|
||||
bool flushBlockThreshold (
|
||||
epicsGuard < epicsMutex > & ) const;
|
||||
void flushRequestIfAboveEarlyThreshold (
|
||||
epicsGuard < epicsMutex > & );
|
||||
void blockUntilSendBacklogIsReasonable
|
||||
( cacContextNotify &, epicsGuard < epicsMutex > & );
|
||||
void eliminateExcessiveSendBacklog (
|
||||
epicsGuard < epicsMutex > * pCallbackGuard,
|
||||
epicsGuard < epicsMutex > & mutualExclusionGuard );
|
||||
void requestRecvProcessPostponedFlush (
|
||||
epicsGuard < epicsMutex > & );
|
||||
osiSockAddr getNetworkAddress (
|
||||
|
||||
@@ -126,13 +126,10 @@ public:
|
||||
|
||||
void flushRequest (
|
||||
epicsGuard < epicsMutex > & );
|
||||
bool flushBlockThreshold (
|
||||
epicsGuard < epicsMutex > & ) const;
|
||||
void flushRequestIfAboveEarlyThreshold (
|
||||
epicsGuard < epicsMutex > & );
|
||||
void blockUntilSendBacklogIsReasonable
|
||||
( cacContextNotify &, epicsGuard < epicsMutex > & );
|
||||
virtual void show ( unsigned level ) const;
|
||||
void eliminateExcessiveSendBacklog (
|
||||
epicsGuard < epicsMutex > * pCallbackGuard,
|
||||
epicsGuard < epicsMutex > & mutualExclusionGuard );
|
||||
void show ( unsigned level ) const;
|
||||
bool setEchoRequestPending (
|
||||
epicsGuard < epicsMutex > & );
|
||||
void requestRecvProcessPostponedFlush (
|
||||
@@ -165,6 +162,7 @@ public:
|
||||
unsigned channelCount (
|
||||
epicsGuard < epicsMutex > & );
|
||||
void removeAllChannels (
|
||||
bool supressApplicationNotify,
|
||||
epicsGuard < epicsMutex > & cbGuard,
|
||||
epicsGuard < epicsMutex > & guard, udpiiu & );
|
||||
void installChannel ( epicsGuard < epicsMutex > &,
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user