Compare commits
25 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 4b97b5a53c | |||
| 81b0013a57 | |||
| e43935510e | |||
| bddba4be91 | |||
| 4df2642299 | |||
| 261f93ed43 | |||
| 8f68bc021d | |||
| 07acbe990e | |||
| ece0240a5d | |||
| 7583975ab2 | |||
| 6e4d9e2933 | |||
| 3d0896a290 | |||
| 0b9d22b327 | |||
| 9f0147c83e | |||
| f85f010d06 | |||
| fa77ffb099 | |||
| 7893207cb6 | |||
| 7431834bd3 | |||
| 980aeeecdc | |||
| 9042a39a1b | |||
| 1fb017ac64 | |||
| e0d93179a8 | |||
| 18e4821a83 | |||
| eeaffaad96 | |||
| 31fd9d8851 |
25
Db/ecmcSS1Axis.template
Normal file
25
Db/ecmcSS1Axis.template
Normal file
@@ -0,0 +1,25 @@
|
||||
#- Will be a sub record to the axis object, example:
|
||||
#- AXIS_PREFIX=c6015a-02:M1
|
||||
record(stringin,"$(AXIS_PREFIX)-SS1-GrpNam") {
|
||||
field(DESC, "Name of Saftey Grp ")
|
||||
field(VAL, "${NAME}")
|
||||
}
|
||||
|
||||
record(bi,"${AXIS_PREFIX}-SS1-EnaAct"){
|
||||
field(DESC, "Safety PLG active for this axis")
|
||||
field(VAL, 1)
|
||||
field(ONAM, "1")
|
||||
field(ZNAM, "0")
|
||||
}
|
||||
|
||||
record(ai,"${AXIS_PREFIX}-SS1-VelMaxLim"){
|
||||
field(DESC, "Velocity max limit (not safety...)")
|
||||
field(VAL, ${VEL_MAX_LIM=-1})
|
||||
field(PREC, 3)
|
||||
}
|
||||
|
||||
record(ai,"${AXIS_PREFIX}-SS1-VelRestLim"){
|
||||
field(DESC, "Velocity rest limit (not safety...)")
|
||||
field(VAL, ${VEL_REST_LIM=-1})
|
||||
field(PREC, 3)
|
||||
}
|
||||
@@ -51,11 +51,11 @@ record(bi,"${P}SS1-${NAME}-AxsStndStllAct"){
|
||||
field(ONAM, "Standstill")
|
||||
field(ZSV, "NO_ALARM")
|
||||
field(OSV, "NO_ALARM")
|
||||
field(FLNK, "${P}SS1-${NAME}-RedVeloAct.PROC")
|
||||
field(FLNK, "${P}SS1-${NAME}-RedVeloCmdAct.PROC")
|
||||
}
|
||||
|
||||
# // bit 3 reduce velo active
|
||||
record(bi,"${P}SS1-${NAME}-RedVeloAct"){
|
||||
record(bi,"${P}SS1-${NAME}-RedVeloCmdAct"){
|
||||
field(DESC, "SS1-${NAME}: Reduce velo active")
|
||||
field(INP, "${P}SS1-${NAME}-Stat_.B3")
|
||||
field(ZNAM, "Not Active")
|
||||
@@ -63,3 +63,21 @@ record(bi,"${P}SS1-${NAME}-RedVeloAct"){
|
||||
field(ZSV, "NO_ALARM")
|
||||
field(OSV, "NO_ALARM")
|
||||
}
|
||||
|
||||
record(ai,"$(P)SS1-${NAME}-Dly") {
|
||||
field(DESC, "Power off delay [ms]")
|
||||
field(EGU, "ms")
|
||||
field(VAL, "$(DELAY=0)")
|
||||
field(PREC, "0")
|
||||
}
|
||||
|
||||
|
||||
record(stringin,"$(P)SS1-Grp${ID=0}-Nam") {
|
||||
field(DESC, "Name of Grp ${ID=0}")
|
||||
field(VAL, "${NAME}")
|
||||
}
|
||||
|
||||
record(ai,"$(P)SS1-GrpCnt") {
|
||||
field(DESC, "Group Count")
|
||||
field(VAL, "$(COUNT=0)")
|
||||
}
|
||||
11
Db/ecmcSS1Main.template
Normal file
11
Db/ecmcSS1Main.template
Normal file
@@ -0,0 +1,11 @@
|
||||
record(stringin,"$(P)SS1-PnlTyp") {
|
||||
field(DESC, "Panel name")
|
||||
field(VAL, "ecmc_plugin_safety_main.ui")
|
||||
}
|
||||
|
||||
record(bi,"${P}SS1-Loaded"){
|
||||
field(DESC, "Plugin loaded")
|
||||
field(VAL, 1)
|
||||
field(ONAM, "1")
|
||||
field(ZNAM, "0")
|
||||
}
|
||||
29
GNUmakefile
29
GNUmakefile
@@ -2,11 +2,14 @@ include /ioc/tools/driver.makefile
|
||||
|
||||
MODULE = ecmc_plugin_safety
|
||||
|
||||
# "Transfer" module name to plugin
|
||||
USR_CFLAGS +=-DECMC_PLUGIN_MODULE_NAME=${MODULE}
|
||||
|
||||
BUILDCLASSES = Linux
|
||||
ARCH_FILTER = deb10%
|
||||
ARCH_FILTER = deb10% deb12%
|
||||
|
||||
# Run 7.0.6 for now
|
||||
EXCLUDE_VERSIONS+=3 7.0.5 7.0.6
|
||||
EXCLUDE_VERSIONS+=3 7.0.5 7.0.6 7.0.7 7.0.9
|
||||
|
||||
IGNORE_MODULES += asynMotor
|
||||
IGNORE_MODULES += motorBase
|
||||
@@ -15,18 +18,24 @@ USR_CXXFLAGS += -std=c++17
|
||||
OPT_CXXFLAGS_YES = -O3
|
||||
|
||||
# dependencies
|
||||
ecmc_VERSION = 10.0
|
||||
ECmasterECMC_VERSION = v1.1.0
|
||||
ecmc_VERSION = 9.6
|
||||
|
||||
################################################################################
|
||||
# THIS RELATES TO THE EtherCAT MASTER LIBRARY
|
||||
# IT IS OF PARAMOUNT IMPORTANCE TO LOAD THE PROPER KERNEL MODULE
|
||||
# ################################################################################
|
||||
USR_LDFLAGS += -lethercat
|
||||
# ethercat
|
||||
EC_BASE_PATH = /ioc/NeedfulThings/EtherCAT/4epics/
|
||||
USR_CXXFLAGS_deb12-x86_64 += -I${EC_BASE_PATH}${T_A}/include/
|
||||
USR_CXXFLAGS_deb12-x86_64 += -L${EC_BASE_PATH}${T_A}/lib/
|
||||
|
||||
OPT_CXXFLAGS_YES = -O3
|
||||
|
||||
LIB_SYS_LIBS += ethercat
|
||||
USR_LDFLAGS_deb12-x86_64 += -Wl,-rpath=${EC_BASE_PATH}${T_A}/lib/
|
||||
USR_LDFLAGS_deb12-x86_64 += -L ${EC_BASE_PATH}${T_A}/lib/
|
||||
|
||||
USR_LDFLAGS_deb10-x86_64 += -lethercat
|
||||
EC_MASTER_LIB = ${EPICS_MODULES}/ECmasterECMC/${ECmasterECMC_VERSION}/R${EPICSVERSION}/lib/${T_A}
|
||||
USR_LDFLAGS += -Wl,-rpath=${EC_MASTER_LIB}
|
||||
USR_LDFLAGS += -L ${EC_MASTER_LIB}
|
||||
USR_LDFLAGS_deb10-x86_64 += -Wl,-rpath=${EC_MASTER_LIB}
|
||||
USR_LDFLAGS_deb10-x86_64 += -L ${EC_MASTER_LIB}
|
||||
|
||||
BASE_DIR = .
|
||||
SRC_DIR = $(BASE_DIR)/src
|
||||
|
||||
@@ -1,189 +1,94 @@
|
||||
axis:
|
||||
id: 1 # Axis id
|
||||
type: joint # this is for future selection of axis type
|
||||
# mode: CSV # supported mode, CSV and CSP, defaults CSV
|
||||
parameters: 'powerAutoOnOff=2;powerOffDelay=4;powerOnDelay=4;' # additional parameters # Additional params to motor record driver
|
||||
#healthOutput: ec0... # Ethercat entry for health output
|
||||
# autoMode: # Switch drive modes automaticaly for normal motion and homing (smaract for instance)
|
||||
# modeSet: ec0.. # Ethercat entry drive mode write (set CSV,CSP,homing)
|
||||
# modeAct: ec0.. # Ethercat entry drive mode reading (set CSV,CSP,homing)
|
||||
# modeCmdMotion: 9 # Drive mode value for normal motion (written to axis.drvMode.modeSet when normal motion)
|
||||
# modeCmdHome: 10 # Drive mode value for when homing (written to axis.drvMode.modeSet when homing)
|
||||
# features:
|
||||
# blockCom: false # Block communication to axis
|
||||
# allowedFunctions:
|
||||
# homing: true # Allow homing
|
||||
# constantVelocity: true # Allow constant velocity
|
||||
# positioning: true # Allow positioning
|
||||
id: ${AXIS_ID=1} # Axis id
|
||||
parameters: 'powerAutoOnOff=2;powerOffDelay=-1;'
|
||||
# feedSwitchesOutput: ec0.s${BO_SID}.binaryOutput${BO_CH=01} # Ethercat entry for feed switches
|
||||
|
||||
epics:
|
||||
name: Axis1 # Axis anme
|
||||
name: ${AX_NAME=M1} # Axis anme
|
||||
precision: 3 # Decimal count
|
||||
description: very important motor axis # Axis description
|
||||
description: Test cfg # Axis description
|
||||
unit: mm # Unit
|
||||
motorRecord:
|
||||
enable: true
|
||||
description: This is MR
|
||||
fieldInit: 'TWV=1000' # Extra config for Motor record
|
||||
fieldInit: 'RTRY=0,FOFF=Frozen' # Extra config for Motor record
|
||||
|
||||
drive:
|
||||
numerator: 3600 # Fastest speed in engineering units
|
||||
denominator: 32768 # I/O range for ECMC_EC_ALIAS_DRV_VELO_SET
|
||||
# type: 0 # Stepper: 0. DS402: 1 (DS402 = servos and advanced stepper drives)
|
||||
control: ec0.s$(DRV_SLAVE).driveControl01 # Control word ethercat entry
|
||||
numerator: 10 # Fastest speed in eng. units (2000 Fullsteps/s==10mm/s)
|
||||
denominator: 32768 # I/O range for ECMC_EC_ALIAS_DRV_VELO_SET (normally +-16bit)
|
||||
type: 0 # Stepper: 0. DS402: 1 (DS402 = servos and advanced stepper drives)
|
||||
setpoint: ec0.s$(DRV_SID).velocitySetpoint01 # Velocity setpoint if CSV. Position setpoint if CSP
|
||||
control: ec0.s$(DRV_SID).driveControl01 # Control word ethercat entry
|
||||
enable: 0 # Enable bit index in control word (not used if DS402)
|
||||
enabled: 1 # Enabled bit index in status word (not used if DS402)
|
||||
status: ec0.s$(DRV_SLAVE).driveStatus01 # Status word ethercat entry
|
||||
setpoint: ec0.s$(DRV_SLAVE).velocitySetpoint01 # Velocity setpoint if CSV. Position setpoint if CSP
|
||||
reduceTorque: 2 # Reduce torque bit in drive control word
|
||||
reduceTorqueEnable: True # Enable reduce torque functionality
|
||||
# brake:
|
||||
# enable: true # Enable brake
|
||||
# output: ec0... # Ethercat link to brake output
|
||||
# openDelay: 0 # Brake timing parameter in cycles (default 1kHz)
|
||||
# closeAhead: 0 # Brake timing parameter in cycles (default 1kHz)
|
||||
reset: 1 # Reset (if no drive reset bit then leave empty)
|
||||
warning: 2 # Warning (if no drive warning bit then leave empty)
|
||||
error: # max 3
|
||||
- 3 # Error 0 (if no drive error bit then leave empty)
|
||||
- 7 # Error 1 (if no drive error bit then leave empty)
|
||||
- 14 # Error 2 (if no drive error bit then leave empty)
|
||||
reset: 1 # Reset bit in control word (if no drive reset bit then leave empty)
|
||||
reduceTorque: 2 # Reduce torque bit in drive control word
|
||||
reduceTorqueEnable: True # Enable reduce torque functionality
|
||||
status: ec0.s$(DRV_SID).driveStatus01 # Status word ethercat entry
|
||||
enabled: 1 # Enabled bit index in status word (not used if DS402)
|
||||
warning: 2 # Warning bit in status word (if no drive warning bit then leave empty)
|
||||
error: # max 3 error bits in status word
|
||||
- 3 # Error 0 (if no drive error bit then leave empty)
|
||||
- 7 # Error 1 (if no drive error bit then leave empty)
|
||||
- 14 # Error 2 (if no drive error bit then leave empty)
|
||||
|
||||
encoder:
|
||||
numerator: 720 # 2mm Scaling numerator example 360 deg/rev
|
||||
denominator: 8192 # Scaling denominator example 4096 ticks per 360 degree
|
||||
# type: 0 # Type: 0=Incremental, 1=Absolute
|
||||
bits: 16 # Total bit count of encoder raw data
|
||||
# absBits: 0 # Absolute bit count (for absolute encoders) always least significant part of 'bits'
|
||||
# absOffset: 0 # Encoder offset in eng units (for absolute encoders)
|
||||
# mask: '0xFFF00' # Mask applied to raw encoder value
|
||||
position: ec0.s$(ENC_SLAVE).positionActual01 # Ethercat entry for actual position input (encoder)
|
||||
control: ec0.s$(ENC_SLAVE).encoderControl01 # mandatory only if 'reset' is used
|
||||
status: ec0.s$(ENC_SLAVE).encoderStatus01 # mandatory only if 'warning' or 'error' are used
|
||||
# ready: 10 # Bit in encoder status word for encoder ready
|
||||
# source: 0 # 0 = Encoder value from etehrcat hardware, 1 = Encoder value from PLC
|
||||
# reset: 1 # Reset (optional)
|
||||
# warning: 2 # Warning (optional)
|
||||
# error: # max 3 (optional)
|
||||
# - 5 # Error 0
|
||||
# - 9 # Error 1
|
||||
# - 11 # Error 2
|
||||
# filter:
|
||||
# velocity:
|
||||
# size: 100 # Filter size for velocity
|
||||
# enable: true # enable velocity filter
|
||||
# position:
|
||||
# size: 100 # Filter size for encoder value
|
||||
# enable: true # enable encoder value filter
|
||||
# latch:
|
||||
# position: '' # Link to latched value. Used for some homing seqs
|
||||
# control: 0 # Bit in encoder control word to arm latch. Used for some homing seqs
|
||||
# status: 0 # Bit in encoder status word for latch triggered status. Used for some homing seqs
|
||||
# primary: 1 # Use this encoder as primary (for control)
|
||||
# homing:
|
||||
# type: 3 # Homing sequence type
|
||||
# position: -30 # Position to reference encoder to
|
||||
# velocity:
|
||||
# to: 10 # Velocity to cam/sensor (used for some homing seqs)
|
||||
# from: 5 # Velocity from cam/sensor (used for some homing seqs)
|
||||
# acceleration: 20 # Acceleration during homing
|
||||
# deceleration: 100 # Deceleration during homing
|
||||
# refToEncIDAtStartup: 1 # At startup then set the start value of this encoder to actpos of this encoder id
|
||||
# refAtHome: 1 # If homing is executed then set position of this encoder
|
||||
# tolToPrim: 0 # If set then this is the max allowed tolerance between prim encoder and this encoder
|
||||
# postMoveEnable: yes # Enable move after successfull homing
|
||||
# postMovePosition: 10 # Position to move to after successfull homing
|
||||
# trigg: ec0.. # Ethercat entry for triggering drive internal homing seq (seq id 26)
|
||||
# ready: ec0.. # Ethercat entry for readinf drive internal homing seq ready (seq id 26)
|
||||
desc: BISS-C
|
||||
numerator: 1 # Scaling numerator example 1 mm/rev
|
||||
denominator: 4096 # Scaling denominator example 4096 ticks per 360 degree
|
||||
type: 1 # Type: 0=Incremental, 1=Absolute
|
||||
bits: 32 # Total bit count of encoder raw data
|
||||
absBits: 26 # Absolute bit count (for absolute encoders) always least significant part of 'bits'
|
||||
absOffset: -15615 # Encoder offset in eng units (for absolute encoders)
|
||||
position: ec0.s$(ENC_SID).positionActual${ENC_CH=01} # Ethercat entry for actual position input (encoder)
|
||||
status: ec0.s$(ENC_SID).encoderStatus${ENC_CH=01} # mandatory only if 'warning' or 'error' are used
|
||||
ready: 2 # Bit in encoder status word for encoder ready
|
||||
warning: 0 # Warning (optional)
|
||||
error: # max 3 (optional)
|
||||
- 1 # Error 0
|
||||
delayComp: # Delay compensation for time between application of setpoint to reading of encoder (normally atleast 2 cycles)
|
||||
time: 0 # Delay time between set and act [cycles]
|
||||
enable: true # enable (defaults to 1 if not set)
|
||||
|
||||
|
||||
controller:
|
||||
Kp: 1 # Kp proportinal gain
|
||||
Ki: 0.02 # Ki integral gain
|
||||
Kd: 0 # Kd derivative gain
|
||||
limits:
|
||||
minIntegral: -10000
|
||||
maxIntegral: 10000
|
||||
|
||||
# Kff: 1 # Feed forward gain
|
||||
# deadband:
|
||||
# tol: 0.01 # Stop control if within this distance from target for the below time
|
||||
# time: 100
|
||||
# limits:
|
||||
# minOutput: -100 # Minimum controller output
|
||||
# maxOutput: 100 # Maximum controller output
|
||||
# minIntegral: -100 # Minimum integral output
|
||||
# maxIntegral: 100 # Maximum integral output
|
||||
# inner:
|
||||
# Kp: 0.1 # Kp for when close to target
|
||||
# Ki: 0.1 # Ki for when close to target
|
||||
# Kd: 0.1 # Kd for when close to target
|
||||
# tol: 0.1 # Distance from target for when inner PID params will be used, defaults to atTarget tol
|
||||
Kp: 10 # Kp proportinal gain
|
||||
Ki: 0 # Ki integral gain
|
||||
Kd: 0 # Kd derivative gain
|
||||
|
||||
trajectory:
|
||||
# type: 1 # Default 0 = trapetz, 1 = S-curve (ruckig)
|
||||
axis:
|
||||
velocity: 500 # Default velo for axis
|
||||
acceleration: 200 # Default acc for axis
|
||||
deceleration: 200 # Default dec for axis
|
||||
emergencyDeceleration: 1200 # Deceleration when axis in error state
|
||||
velocity: 2 # Default velo for axis
|
||||
acceleration: 2 # Default acc for axis
|
||||
deceleration: 2 # Default dec for axis
|
||||
emergencyDeceleration: 5 # Deceleration when axis in error state
|
||||
jerk: 10 # Default jerk for axis
|
||||
jog:
|
||||
velocity: 5 # Default velo fro JOG (motor record)
|
||||
# modulo:
|
||||
# range: 360 # Modulo range 0..360
|
||||
# type: 0 # Modulo type
|
||||
velocity: 1 # Default velo fro JOG (motor record)
|
||||
|
||||
input:
|
||||
limit:
|
||||
forward: ec0.s$(DRV_SLAVE).driveStatus01.12 # Ethercat entry for low limit switch input
|
||||
# forwardPolarity: 0 # Polarity of forward limit switch
|
||||
backward: ec0.s$(DRV_SLAVE).driveStatus01.11 # Ethercat entry for high limit switch input
|
||||
# backwardPolarity: 0 # Polarity of forward limit switch
|
||||
home: 'ec0.s$(DRV_SLAVE).ONE.0' # Ethercat entry for home switch
|
||||
# homePolarity: 0 # Polarity of home switch
|
||||
interlock: 'ec0.s$(DRV_SLAVE).ONE.0' # Ethercat entry for interlock switch input
|
||||
# interlockPolarity: 0 # Polarity of interlock switch
|
||||
|
||||
# homing:
|
||||
# type: 3 # Homing sequence type
|
||||
# position: -30 # Position to reference encoder to
|
||||
# velocity:
|
||||
# to: 10 # Velocity to cam/sensor (used for some homing seqs)
|
||||
# from: 5 # Velocity from cam/sensor (used for some homing seqs)
|
||||
# acc: 20 # Acceleration during homing
|
||||
# dec: 100 # Deceleration during homing
|
||||
# refToEncIDAtStartup: 1 # At startup then set the start value of this encoder to actpos of this encoder id
|
||||
# refAtHome: 1 # If homing is executed then set position of this encoder
|
||||
# tolToPrim: 0 # If set then this is the max allowed tolerance between prim encoder and this encoder
|
||||
# postMoveEnable: yes # Enable move after successfull homing
|
||||
# postMovePosition: 10 # Position to move to after successfull homing
|
||||
# timeout: 100 # Sequence timeout
|
||||
forward: ec0.s$(DRV_SID).driveStatus01.12 # Ethercat entry for low limit switch input
|
||||
backward: ec0.s$(DRV_SID).driveStatus01.11 # Ethercat entry for high limit switch input
|
||||
home: 'ec0.s$(DRV_SID).ONE.0' # Ethercat entry for home switch
|
||||
interlock: 'ec0.s-1.ONE.0' # Ethercat entry for interlock switch input
|
||||
|
||||
softlimits:
|
||||
enable: false # Enable soft limits
|
||||
forward: 100 # Soft limit position fwd
|
||||
forwardEnable: false # Soft limit position fwd enable
|
||||
backward: -100 # Soft limit position bwd
|
||||
backwardEnable: false # Soft limit position bwd enable
|
||||
enable: true # Enable soft limits
|
||||
forward: 30 # Soft limit position fwd
|
||||
forwardEnable: true # Soft limit position fwd enable
|
||||
backward: -30 # Soft limit position bwd
|
||||
backwardEnable: true # Soft limit position bwd enable
|
||||
|
||||
monitoring:
|
||||
lag:
|
||||
enable: true # Enable position lag monitoring (following error)
|
||||
tolerance: 10 # Allowed tolerance
|
||||
time: 10 # Allowed time outside tolerance target:
|
||||
target:
|
||||
enable: true # Enable at target monitoring (needs to be enabled if using motor record)
|
||||
tolerance: 0.1 # Allowed tolerance
|
||||
time: 10 # Filter time inside tolerance to be at target
|
||||
time: 10 # Allowed time outside tolerance target:
|
||||
velocity:
|
||||
enable: true # Enable velocity monitoring
|
||||
max: 1000 # Allowed max velocity
|
||||
enable: false # Enable velocity monitoring
|
||||
max: 8 # Allowed max velocity
|
||||
time:
|
||||
trajectory: 100 # Time allowed outside max velo before system init halt
|
||||
drive: 200 # Time allowed outside max velo before system disables drive
|
||||
# velocityDifference:
|
||||
# enable: true # Enable velocity diff monitoring (velo set vs velo act)
|
||||
# max: 100 # Allowed max difference
|
||||
# time:
|
||||
# trajectory: 100 # Time allowed outside max diff velo before system init halt
|
||||
# drive: 200 # Time allowed outside max diff velo before system disables drive
|
||||
target:
|
||||
enable: true # Enable at target monitoring (needs to be enabled if using motor record)
|
||||
tolerance: 0.01 # Allowed tolerance
|
||||
time: 10 # Filter time inside tolerance to be at target
|
||||
|
||||
12
iocsh/cfg/enc_open_loop.yaml
Normal file
12
iocsh/cfg/enc_open_loop.yaml
Normal file
@@ -0,0 +1,12 @@
|
||||
encoder:
|
||||
desc: 'Open loop'
|
||||
unit: mm
|
||||
numerator: 1 # Scaling numerator
|
||||
denominator: 12800 # Scaling denominator
|
||||
type: 0 # Type: 0=Incremental, 1=Absolute
|
||||
bits: 16 # Total bit count of encoder raw data
|
||||
absBits: 0 # Absolute bit count (for absolute encoders)
|
||||
absOffset: 0 # Encoder offset in eng units (for absolute encoders)
|
||||
position: ec0.s$(ENC_SID).positionActual01 # Ethercat entry for actual position input (encoder)
|
||||
homing:
|
||||
refToEncIDAtStartup: 1 # Ref encoder at startup (to BISS value)
|
||||
@@ -11,8 +11,7 @@
|
||||
## camon c6025a:SS1-first-Err c6025a:SS1-first-RmpDwnCmdAct c6025a:SS1-first-AxsStndStllAct
|
||||
##
|
||||
|
||||
#epicsEnvSet(IOC,c6025a)
|
||||
require ecmccfg "ENG_MODE=1,MASTER_ID=1"
|
||||
require ecmccfg "ENG_MODE=1,MASTER_ID=0"
|
||||
|
||||
##############################################################################
|
||||
## Load components lib
|
||||
@@ -54,23 +53,22 @@ ${SCRIPTEXEC} ${ECMC_CONFIG_ROOT}loadYamlAxis.cmd, "FILE=./cfg/axis.yaml"
|
||||
require ecmc_plugin_safety
|
||||
|
||||
# Create SS1 group
|
||||
#- EC_RAMP_DOWN : Ethercat entry for ramp down command, input to ecmc (command from safety PLC/system)
|
||||
#- EC_AXES_REST : Ethercat entry for signaling that all axes in group are at rest, output from ecmc (feedback to safety PLC/system)
|
||||
#- EC_AXES_MAX_VELO : Ethercat entry for reducing velocity, input to ecmc (command from safety PLC/system)
|
||||
#- DELAY_MS : Time between rampdown command and STO
|
||||
epicsEnvSet(EC_RAMP_DOWN,"ec${ECMC_EC_MASTER_ID}.s${BI_SLAVE}.binaryInput08.0")
|
||||
epicsEnvSet(EC_AXES_REST,"ec${ECMC_EC_MASTER_ID}.s${BO_SLAVE}.binaryOutput07.0")
|
||||
epicsEnvSet(EC_AXES_MAX_VELO,"ec${ECMC_EC_MASTER_ID}.s${BO_SLAVE}.ONE.0")
|
||||
#- EC_RAMP_DOWN_CMD : EtherCAT entry for ramp down command, input to ecmc (command from safety PLC/system)
|
||||
#- EC_REST_STAT : EtherCAT entry for signaling that all axes in group are at rest, output from ecmc (feedback to safety PLC/system)
|
||||
#- EC_RED_VEL_CMD : EtherCAT entry for reducing velocity, input to ecmc (command from safety PLC/system)
|
||||
#- DELAY_MS : Time between rampdown command and STO
|
||||
epicsEnvSet(EC_RAMP_DOWN_CMD,"ec${ECMC_EC_MASTER_ID}.s${BI_SLAVE}.binaryInput08.0")
|
||||
epicsEnvSet(EC_REST_STAT,"ec${ECMC_EC_MASTER_ID}.s${BO_SLAVE}.binaryOutput07.0")
|
||||
epicsEnvSet(EC_RED_VEL_CMD,"ec${ECMC_EC_MASTER_ID}.s${BO_SLAVE}.ONE.0")
|
||||
epicsEnvSet(SAFETY_TIMEOUT,500)
|
||||
${SCRIPTEXEC} ${ecmc_plugin_safety_DIR}addSS1Group.cmd "NAME=first,EC_RAMP_DOWN=${EC_RAMP_DOWN},EC_AXES_REST=${EC_AXES_REST},EC_AXES_MAX_VELO=${EC_AXES_MAX_VELO=empty},DELAY_MS=${SAFETY_TIMEOUT}"
|
||||
${SCRIPTEXEC} ${ecmc_plugin_safety_DIR}addSS1Group.cmd "NAME=first,EC_RAMP_DOWN_CMD=${EC_RAMP_DOWN_CMD},EC_REST_STAT=${EC_REST_STAT},EC_RED_VEL_CMD=${EC_RED_VEL_CMD=empty},DELAY_MS=${SAFETY_TIMEOUT}"
|
||||
|
||||
#- Add axis
|
||||
#- AX_ID : Axis ID
|
||||
#- VELO_REST_LIM : Velocity at rest limit [unit same as EGU of axis]
|
||||
#- VELO_MAX_LIM : Velocity maximum limit, -1 to disable [unit same as EGU of axis]
|
||||
#- VELO_MAX_LIM : Velocity maximum limit when EC_RED_VEL_CMD, set to -1 to disable [unit same as EGU of axis]
|
||||
${SCRIPTEXEC} ${ecmc_plugin_safety_DIR}addAxisToSafetyGroup.cmd "NAME=first,AX_ID=1,VELO_REST_LIM=1,VELO_MAX_LIM=100"
|
||||
|
||||
|
||||
##############################################################################
|
||||
## Configure diagnostics:
|
||||
#
|
||||
|
||||
77
iocsh/test_lab_rack.script
Normal file
77
iocsh/test_lab_rack.script
Normal file
@@ -0,0 +1,77 @@
|
||||
##############################################################################
|
||||
#- test config for ecmc_plugin_safety
|
||||
#-
|
||||
#- In this config the interface to safety system is liked to simulated ethercat entries:
|
||||
#- * To allow motion:
|
||||
#- caput c6025a:m0s013-Zero 3
|
||||
#- * To simulate interlock from safety system:
|
||||
#- caput c6025a:m0s013-Zero 0
|
||||
#-
|
||||
#- Monitor status with:
|
||||
#- camon c6025a:SS1-first-Err c6025a:SS1-first-RmpDwnCmdAct c6025a:SS1-first-AxsStndStllAct
|
||||
#-
|
||||
#- ethercat slaves
|
||||
#- 0 0:0 PREOP + EK1100 EtherCAT Coupler (2A E-Bus)
|
||||
#- 1 0:1 PREOP + EL2068 8Ch. Dig Output 24V, 0.5A
|
||||
#- 2 0:2 PREOP + EL2819 16K. Dig. Ausgang 24V, 0,5A, Diagnose
|
||||
#- 3 0:3 PREOP + EL5001 1K. SSI Encoder
|
||||
#- 4 0:4 PREOP + EL6224 (IO Link Master)
|
||||
#- 5 0:5 PREOP + EL2008 8K. Dig. Ausgang 24V, 0.5A
|
||||
#- 6 0:6 PREOP + EL2522 2K. Pulse Train Ausgang
|
||||
#- 7 0:7 PREOP + EL5072 2Ch. Inductive sensor interface (LVDT, Half Bridge)
|
||||
#- 8 0:8 PREOP + EL1008 8K. Dig. Eingang 24V, 3ms
|
||||
#- 9 0:9 PREOP + EL5042 2Ch. BiSS-C Encoder
|
||||
#- 10 0:10 PREOP + EL6692 EtherCAT Bridge-Klemme (Prim<69>r)
|
||||
#- 11 0:11 PREOP + EK1100 EtherCAT-Koppler (2A E-Bus)
|
||||
#- 12 0:12 PREOP + EL7031 1K. Schrittmotor-Endstufe (24V, 1.5A)
|
||||
#- 13 0:13 PREOP + EL7201 1K. MDP742 Servo-Motor-Endstufe (50V, 4A)
|
||||
#- 14 0:14 PREOP + EL7041-0052 1Ch. Stepper motor output stage (50V, 5A)
|
||||
#- 15 0:15 PREOP + EL7342 2Ch. DC motor output stage (50V, 3.5A)
|
||||
#- 16 0:16 PREOP + EL7411 BLDC Terminal with incremental encoder/Hall, 50 V DC, 4.
|
||||
#- 17 0:17 PREOP + EL7211-9014 1K. MDP742 Servo-Motor-Endstufe mit OCT (50V, 4,5A
|
||||
#- 18 0:18 PREOP + EL9576 Bremschopper Klemme
|
||||
|
||||
require ecmccfg v10.0.0_RC1 "ENG_MODE=1,MASTER_ID=0,ECMC_VER=v10.0.0_RC1"
|
||||
|
||||
# 0:14 - EL7041 1Ch Stepper
|
||||
${SCRIPTEXEC} ${ecmccfg_DIR}addSlave.cmd, "SLAVE_ID=14,HW_DESC=EL7041-0052"
|
||||
${SCRIPTEXEC} ${ecmccfg_DIR}applyComponent.cmd "COMP=Motor-Generic-2Phase-Stepper, MACROS='I_MAX_MA=1500, I_STDBY_MA=1000, U_NOM_MV=48000, R_COIL_MOHM=1230'"
|
||||
epicsEnvSet(DRV_SID,${ECMC_EC_SLAVE_NUM})
|
||||
|
||||
# 0:9 - EL5042 2Ch BiSS-C Encoder, RLS-LA11
|
||||
${SCRIPTEXEC} ${ecmccfg_DIR}addSlave.cmd, "SLAVE_ID=9,HW_DESC=EL5042"
|
||||
${SCRIPTEXEC} ${ecmccfg_DIR}applyComponent.cmd "COMP=Encoder-RLS-LA11-26bit-BISS-C,CH_ID=1"
|
||||
${SCRIPTEXEC} ${ecmccfg_DIR}applyComponent.cmd "COMP=Encoder-RLS-LA11-26bit-BISS-C,CH_ID=2"
|
||||
epicsEnvSet(ENC_SID,${ECMC_EC_SLAVE_NUM})
|
||||
|
||||
${SCRIPTEXEC} ${ecmccfg_DIR}loadYamlAxis.cmd, "FILE=./cfg/axis.yaml, DEV=${IOC}, AX_NAME=M1, AXIS_ID=1, DRV_SID=${DRV_SID}, ENC_SID=${ENC_SID}, ENC_CH=01"
|
||||
${SCRIPTEXEC} ${ecmccfg_DIR}loadYamlEnc.cmd, "FILE=./cfg/enc_open_loop.yaml, DEV=${IOC}, ENC_SID=${DRV_SID}"
|
||||
|
||||
|
||||
##############################################################################
|
||||
## Load safety plugin
|
||||
require ecmc_plugin_safety v10.0.0_RC1
|
||||
|
||||
# simulate inputs and outputs in drive "ZERO" and ONE dummy-entry
|
||||
epicsEnvSet(BI_SLAVE,${DRV_SID})
|
||||
epicsEnvSet(BO_SLAVE,${DRV_SID})
|
||||
|
||||
# Create SS1 group
|
||||
#- EC_RAMP_DOWN_CMD : Digital Input: Ethercat entry for ramp down command, input to ecmc (command from safety PLC/system)
|
||||
#- EC_AXES_AT_REST_STAT : Digital Output: Ethercat entry for signaling that all axes in group are at rest, output from ecmc (feedback to safety PLC/system)
|
||||
#- EC_AXES_LIM_VELO_CMD : Digital Input: Ethercat entry for reducing velocity, input to ecmc (command from safety PLC/system)
|
||||
#- DELAY_MS : Time between rampdown command and STO
|
||||
epicsEnvSet(EC_RAMP_DOWN_CMD,"ec${ECMC_EC_MASTER_ID}.s${BI_SLAVE}.ONE.0")
|
||||
epicsEnvSet(EC_AXES_AT_REST_STAT,"ec${ECMC_EC_MASTER_ID}.s${BO_SLAVE}.ZERO.0")
|
||||
epicsEnvSet(EC_AXES_LIM_VELO_CMD,"ec${ECMC_EC_MASTER_ID}.s${BO_SLAVE}.ONE.1")
|
||||
epicsEnvSet(SAFETY_TIMEOUT,500)
|
||||
${SCRIPTEXEC} ${ecmc_plugin_safety_DIR}addSS1Group.cmd "NAME=first,EC_RAMP_DOWN_CMD=${EC_RAMP_DOWN_CMD},EC_AXES_AT_REST_STAT=${EC_AXES_AT_REST_STAT},EC_AXES_LIM_VELO_CMD=${EC_AXES_LIM_VELO_CMD=empty},DELAY_MS=${SAFETY_TIMEOUT}"
|
||||
|
||||
#- Add axis
|
||||
#- AX_ID : Axis ID
|
||||
#- VELO_REST_LIM : Velocity at rest limit [unit same as EGU of axis]
|
||||
#- VELO_MAX_LIM : Velocity maximum limit, -1 to disable [unit same as EGU of axis]
|
||||
${SCRIPTEXEC} ${ecmc_plugin_safety_DIR}addAxisToSafetyGroup.cmd "NAME=first,AX_ID=1,VELO_REST_LIM=0.01,VELO_MAX_LIM=1"
|
||||
|
||||
ecmcEpicsEnvSetCalc(S_ID, "${DRV_SID}", "%03d")
|
||||
afterInit "dbpf ${IOC}:m${ECMC_EC_MASTER_ID=0}s${S_ID}-One 0"
|
||||
271
qt/ecmc_plugin_safety_group.ui
Normal file
271
qt/ecmc_plugin_safety_group.ui
Normal file
@@ -0,0 +1,271 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<ui version="4.0">
|
||||
<class>Form</class>
|
||||
<widget class="QWidget" name="Form">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>311</width>
|
||||
<height>269</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="windowTitle">
|
||||
<string>Form</string>
|
||||
</property>
|
||||
<widget class="QGroupBox" name="groupBox">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>5</x>
|
||||
<y>35</y>
|
||||
<width>296</width>
|
||||
<height>151</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="title">
|
||||
<string>Diagnostics</string>
|
||||
</property>
|
||||
<widget class="caLabel" name="calabel_6">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>10</x>
|
||||
<y>60</y>
|
||||
<width>206</width>
|
||||
<height>28</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Reduced velo cmd active:</string>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caLed" name="caled_2">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>245</x>
|
||||
<y>30</y>
|
||||
<width>30</width>
|
||||
<height>30</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="channel" stdset="0">
|
||||
<string notr="true">$(IOC):SS1-$(SAFETY_GRP)-RmpDwnCmdAct</string>
|
||||
</property>
|
||||
<property name="falseColor">
|
||||
<color>
|
||||
<red>0</red>
|
||||
<green>85</green>
|
||||
<blue>0</blue>
|
||||
</color>
|
||||
</property>
|
||||
<property name="trueColor">
|
||||
<color>
|
||||
<red>255</red>
|
||||
<green>0</green>
|
||||
<blue>0</blue>
|
||||
</color>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caLed" name="caled_3">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>245</x>
|
||||
<y>60</y>
|
||||
<width>30</width>
|
||||
<height>30</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="channel" stdset="0">
|
||||
<string notr="true">$(IOC):SS1-$(SAFETY_GRP)-RedVeloCmdAct</string>
|
||||
</property>
|
||||
<property name="falseColor">
|
||||
<color>
|
||||
<red>0</red>
|
||||
<green>85</green>
|
||||
<blue>0</blue>
|
||||
</color>
|
||||
</property>
|
||||
<property name="trueColor">
|
||||
<color>
|
||||
<red>255</red>
|
||||
<green>0</green>
|
||||
<blue>0</blue>
|
||||
</color>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caLabel" name="calabel_5">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>10</x>
|
||||
<y>30</y>
|
||||
<width>246</width>
|
||||
<height>28</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>E-Stop (rampdown cmd active):</string>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caLabel" name="calabel_4">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>10</x>
|
||||
<y>85</y>
|
||||
<width>251</width>
|
||||
<height>26</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Axes at rest:</string>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caLed" name="caled">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>245</x>
|
||||
<y>88</y>
|
||||
<width>30</width>
|
||||
<height>30</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="channel" stdset="0">
|
||||
<string notr="true">$(IOC):SS1-$(SAFETY_GRP)-AxsStndStllAct</string>
|
||||
</property>
|
||||
<property name="falseColor">
|
||||
<color>
|
||||
<red>255</red>
|
||||
<green>0</green>
|
||||
<blue>0</blue>
|
||||
</color>
|
||||
</property>
|
||||
<property name="trueColor">
|
||||
<color>
|
||||
<red>0</red>
|
||||
<green>85</green>
|
||||
<blue>0</blue>
|
||||
</color>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caLineEdit" name="calineedit_47">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>225</x>
|
||||
<y>120</y>
|
||||
<width>61</width>
|
||||
<height>16</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string/>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
|
||||
</property>
|
||||
<property name="channel" stdset="0">
|
||||
<string notr="true">$(IOC):SS1-$(SAFETY_GRP)-Dly</string>
|
||||
</property>
|
||||
<property name="colorMode">
|
||||
<enum>caLineEdit::Default</enum>
|
||||
</property>
|
||||
<property name="alarmHandling">
|
||||
<enum>caLineEdit::onBackground</enum>
|
||||
</property>
|
||||
<property name="precisionMode">
|
||||
<enum>caLineEdit::Channel</enum>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caLabel" name="calabel_7">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>10</x>
|
||||
<y>115</y>
|
||||
<width>206</width>
|
||||
<height>26</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Power off delay [ms]:</string>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
|
||||
</property>
|
||||
</widget>
|
||||
</widget>
|
||||
<widget class="caLabel" name="calabel">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>50</x>
|
||||
<y>5</y>
|
||||
<width>221</width>
|
||||
<height>28</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>SS1 group: $(SAFETY_GRP=)</string>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caMultiLineString" name="camultilinestring">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>10</x>
|
||||
<y>195</y>
|
||||
<width>291</width>
|
||||
<height>61</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="font">
|
||||
<font>
|
||||
<family>Lucida Sans Typewriter</family>
|
||||
<pointsize>8</pointsize>
|
||||
</font>
|
||||
</property>
|
||||
<property name="sizeAdjustPolicy">
|
||||
<enum>QAbstractScrollArea::AdjustToContents</enum>
|
||||
</property>
|
||||
<property name="plainText">
|
||||
<string>NOTE:
|
||||
ecmc_plugin_safety has NO safety rated
|
||||
features. It only acts as an interface to a
|
||||
dedicated safety system.</string>
|
||||
</property>
|
||||
<property name="fontScaleMode" stdset="0">
|
||||
<enum>caMultiLineString::None</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</widget>
|
||||
<customwidgets>
|
||||
<customwidget>
|
||||
<class>caLabel</class>
|
||||
<extends>QLabel</extends>
|
||||
<header>caLabel</header>
|
||||
</customwidget>
|
||||
<customwidget>
|
||||
<class>caLed</class>
|
||||
<extends>QWidget</extends>
|
||||
<header>caLed</header>
|
||||
</customwidget>
|
||||
<customwidget>
|
||||
<class>caLineEdit</class>
|
||||
<extends>QLineEdit</extends>
|
||||
<header>caLineEdit</header>
|
||||
</customwidget>
|
||||
<customwidget>
|
||||
<class>caMultiLineString</class>
|
||||
<extends>QPlainTextEdit</extends>
|
||||
<header>caMultiLineString</header>
|
||||
</customwidget>
|
||||
</customwidgets>
|
||||
<resources/>
|
||||
<connections/>
|
||||
</ui>
|
||||
458
qt/ecmc_plugin_safety_main.ui
Normal file
458
qt/ecmc_plugin_safety_main.ui
Normal file
@@ -0,0 +1,458 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<ui version="4.0">
|
||||
<class>Form</class>
|
||||
<widget class="QWidget" name="Form">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>146</width>
|
||||
<height>315</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="windowTitle">
|
||||
<string>Form</string>
|
||||
</property>
|
||||
<widget class="caLabel" name="calabel">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>5</x>
|
||||
<y>0</y>
|
||||
<width>136</width>
|
||||
<height>36</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string> Safety plugin</string>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="QGroupBox" name="groupBox_6">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>5</x>
|
||||
<y>35</y>
|
||||
<width>136</width>
|
||||
<height>241</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="title">
|
||||
<string>Group:</string>
|
||||
</property>
|
||||
<widget class="caFrame" name="caframe_11">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>5</x>
|
||||
<y>30</y>
|
||||
<width>120</width>
|
||||
<height>30</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="macro">
|
||||
<string notr="true">GRP_ID=01,IOC=$(IOC)</string>
|
||||
</property>
|
||||
<property name="visibility">
|
||||
<enum>caFrame::Calc</enum>
|
||||
</property>
|
||||
<property name="visibilityCalc">
|
||||
<string notr="true">A>=1</string>
|
||||
</property>
|
||||
<property name="channel" stdset="0">
|
||||
<string notr="true">$(IOC):SS1-GrpCnt</string>
|
||||
</property>
|
||||
<widget class="caShellCommand" name="cashellcommand">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>15</x>
|
||||
<y>5</y>
|
||||
<width>100</width>
|
||||
<height>21</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="label">
|
||||
<string notr="true">$(GRP_ID)</string>
|
||||
</property>
|
||||
<property name="labels">
|
||||
<string>$(GRP_ID)</string>
|
||||
</property>
|
||||
<property name="files">
|
||||
<string>bash /ioc/modules/qt/ecmcOpenObject.sh</string>
|
||||
</property>
|
||||
<property name="args">
|
||||
<string>PLG_SAFETY_GRP $(IOC) $(GRP_ID);</string>
|
||||
</property>
|
||||
</widget>
|
||||
</widget>
|
||||
<widget class="caFrame" name="caframe_13">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>5</x>
|
||||
<y>80</y>
|
||||
<width>120</width>
|
||||
<height>30</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="macro">
|
||||
<string notr="true">GRP_ID=03,IOC=$(IOC)</string>
|
||||
</property>
|
||||
<property name="visibility">
|
||||
<enum>caFrame::Calc</enum>
|
||||
</property>
|
||||
<property name="visibilityCalc">
|
||||
<string notr="true">A>=3</string>
|
||||
</property>
|
||||
<property name="channel" stdset="0">
|
||||
<string notr="true">$(IOC):SS1-GrpCnt</string>
|
||||
</property>
|
||||
<widget class="caShellCommand" name="cashellcommand_4">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>15</x>
|
||||
<y>5</y>
|
||||
<width>100</width>
|
||||
<height>21</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="label">
|
||||
<string notr="true">$(GRP_ID)</string>
|
||||
</property>
|
||||
<property name="labels">
|
||||
<string>$(GRP_ID)</string>
|
||||
</property>
|
||||
<property name="files">
|
||||
<string>bash /ioc/modules/qt/ecmcOpenObject.sh</string>
|
||||
</property>
|
||||
<property name="args">
|
||||
<string>PLG_SAFETY_GRP $(IOC) $(GRP_ID);</string>
|
||||
</property>
|
||||
</widget>
|
||||
</widget>
|
||||
<widget class="caFrame" name="caframe_14">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>5</x>
|
||||
<y>105</y>
|
||||
<width>120</width>
|
||||
<height>30</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="macro">
|
||||
<string notr="true">GRP_ID=04,IOC=$(IOC)</string>
|
||||
</property>
|
||||
<property name="visibility">
|
||||
<enum>caFrame::Calc</enum>
|
||||
</property>
|
||||
<property name="visibilityCalc">
|
||||
<string notr="true">A>=4</string>
|
||||
</property>
|
||||
<property name="channel" stdset="0">
|
||||
<string notr="true">$(IOC):SS1-GrpCnt</string>
|
||||
</property>
|
||||
<widget class="caShellCommand" name="cashellcommand_6">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>15</x>
|
||||
<y>5</y>
|
||||
<width>100</width>
|
||||
<height>21</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="label">
|
||||
<string notr="true">$(GRP_ID)</string>
|
||||
</property>
|
||||
<property name="labels">
|
||||
<string>$(GRP_ID)</string>
|
||||
</property>
|
||||
<property name="files">
|
||||
<string>bash /ioc/modules/qt/ecmcOpenObject.sh</string>
|
||||
</property>
|
||||
<property name="args">
|
||||
<string>PLG_SAFETY_GRP $(IOC) $(GRP_ID);</string>
|
||||
</property>
|
||||
</widget>
|
||||
</widget>
|
||||
<widget class="caFrame" name="caframe_15">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>5</x>
|
||||
<y>130</y>
|
||||
<width>120</width>
|
||||
<height>30</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="macro">
|
||||
<string notr="true">GRP_ID=05,IOC=$(IOC)</string>
|
||||
</property>
|
||||
<property name="visibility">
|
||||
<enum>caFrame::Calc</enum>
|
||||
</property>
|
||||
<property name="visibilityCalc">
|
||||
<string notr="true">A>=5</string>
|
||||
</property>
|
||||
<property name="channel" stdset="0">
|
||||
<string notr="true">$(IOC):SS1-GrpCnt</string>
|
||||
</property>
|
||||
<widget class="caShellCommand" name="cashellcommand_7">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>15</x>
|
||||
<y>5</y>
|
||||
<width>100</width>
|
||||
<height>21</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="label">
|
||||
<string notr="true">$(GRP_ID)</string>
|
||||
</property>
|
||||
<property name="labels">
|
||||
<string>$(GRP_ID)</string>
|
||||
</property>
|
||||
<property name="files">
|
||||
<string>bash /ioc/modules/qt/ecmcOpenObject.sh</string>
|
||||
</property>
|
||||
<property name="args">
|
||||
<string>PLG_SAFETY_GRP $(IOC) $(GRP_ID);</string>
|
||||
</property>
|
||||
</widget>
|
||||
</widget>
|
||||
<widget class="caFrame" name="caframe_16">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>5</x>
|
||||
<y>155</y>
|
||||
<width>120</width>
|
||||
<height>30</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="macro">
|
||||
<string notr="true">GRP_ID=06,IOC=$(IOC)</string>
|
||||
</property>
|
||||
<property name="visibility">
|
||||
<enum>caFrame::Calc</enum>
|
||||
</property>
|
||||
<property name="visibilityCalc">
|
||||
<string notr="true">A>=6</string>
|
||||
</property>
|
||||
<property name="channel" stdset="0">
|
||||
<string notr="true">$(IOC):SS1-GrpCnt</string>
|
||||
</property>
|
||||
<widget class="caShellCommand" name="cashellcommand_9">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>15</x>
|
||||
<y>5</y>
|
||||
<width>100</width>
|
||||
<height>21</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="label">
|
||||
<string notr="true">$(GRP_ID)</string>
|
||||
</property>
|
||||
<property name="labels">
|
||||
<string>$(GRP_ID)</string>
|
||||
</property>
|
||||
<property name="files">
|
||||
<string>bash /ioc/modules/qt/ecmcOpenObject.sh</string>
|
||||
</property>
|
||||
<property name="args">
|
||||
<string>PLG_SAFETY_GRP $(IOC) $(GRP_ID);</string>
|
||||
</property>
|
||||
</widget>
|
||||
</widget>
|
||||
<widget class="caFrame" name="caframe_17">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>5</x>
|
||||
<y>180</y>
|
||||
<width>120</width>
|
||||
<height>30</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="macro">
|
||||
<string notr="true">GRP_ID=07,IOC=$(IOC)</string>
|
||||
</property>
|
||||
<property name="visibility">
|
||||
<enum>caFrame::Calc</enum>
|
||||
</property>
|
||||
<property name="visibilityCalc">
|
||||
<string notr="true">A>=7</string>
|
||||
</property>
|
||||
<property name="channel" stdset="0">
|
||||
<string notr="true">$(IOC):SS1-GrpCnt</string>
|
||||
</property>
|
||||
<widget class="caShellCommand" name="cashellcommand_12">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>15</x>
|
||||
<y>5</y>
|
||||
<width>100</width>
|
||||
<height>21</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="label">
|
||||
<string notr="true">$(GRP_ID)</string>
|
||||
</property>
|
||||
<property name="labels">
|
||||
<string>$(GRP_ID)</string>
|
||||
</property>
|
||||
<property name="files">
|
||||
<string>bash /ioc/modules/qt/ecmcOpenObject.sh</string>
|
||||
</property>
|
||||
<property name="args">
|
||||
<string>PLG_SAFETY_GRP $(IOC) $(GRP_ID);</string>
|
||||
</property>
|
||||
</widget>
|
||||
</widget>
|
||||
<widget class="caFrame" name="caframe_18">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>5</x>
|
||||
<y>205</y>
|
||||
<width>120</width>
|
||||
<height>30</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="macro">
|
||||
<string notr="true">GRP_ID=08,IOC=$(IOC)</string>
|
||||
</property>
|
||||
<property name="visibility">
|
||||
<enum>caFrame::Calc</enum>
|
||||
</property>
|
||||
<property name="visibilityCalc">
|
||||
<string notr="true">A>=8</string>
|
||||
</property>
|
||||
<property name="channel" stdset="0">
|
||||
<string notr="true">$(IOC):SS1-GrpCnt</string>
|
||||
</property>
|
||||
<widget class="caShellCommand" name="cashellcommand_13">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>15</x>
|
||||
<y>5</y>
|
||||
<width>100</width>
|
||||
<height>21</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="label">
|
||||
<string notr="true">$(GRP_ID)</string>
|
||||
</property>
|
||||
<property name="labels">
|
||||
<string>$(GRP_ID)</string>
|
||||
</property>
|
||||
<property name="files">
|
||||
<string>bash /ioc/modules/qt/ecmcOpenObject.sh</string>
|
||||
</property>
|
||||
<property name="args">
|
||||
<string>PLG_SAFETY_GRP $(IOC) $(GRP_ID);</string>
|
||||
</property>
|
||||
</widget>
|
||||
</widget>
|
||||
<widget class="caFrame" name="caframe_12">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>5</x>
|
||||
<y>55</y>
|
||||
<width>120</width>
|
||||
<height>30</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="macro">
|
||||
<string notr="true">GRP_ID=02,IOC=$(IOC)</string>
|
||||
</property>
|
||||
<property name="visibility">
|
||||
<enum>caFrame::Calc</enum>
|
||||
</property>
|
||||
<property name="visibilityCalc">
|
||||
<string notr="true">A>=2</string>
|
||||
</property>
|
||||
<property name="channel" stdset="0">
|
||||
<string notr="true">$(IOC):SS1-GrpCnt</string>
|
||||
</property>
|
||||
<widget class="caShellCommand" name="cashellcommand_3">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>15</x>
|
||||
<y>5</y>
|
||||
<width>100</width>
|
||||
<height>21</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="label">
|
||||
<string notr="true">$(GRP_ID)</string>
|
||||
</property>
|
||||
<property name="labels">
|
||||
<string>$(GRP_ID)</string>
|
||||
</property>
|
||||
<property name="files">
|
||||
<string>bash /ioc/modules/qt/ecmcOpenObject.sh</string>
|
||||
</property>
|
||||
<property name="args">
|
||||
<string>PLG_SAFETY_GRP $(IOC) $(GRP_ID);</string>
|
||||
</property>
|
||||
</widget>
|
||||
</widget>
|
||||
</widget>
|
||||
<widget class="caLineEdit" name="calineedit">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>95</x>
|
||||
<y>285</y>
|
||||
<width>41</width>
|
||||
<height>20</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string/>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
|
||||
</property>
|
||||
<property name="channel" stdset="0">
|
||||
<string notr="true">$(IOC):SS1-GrpCnt</string>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caLabel" name="calabel_2">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>10</x>
|
||||
<y>285</y>
|
||||
<width>91</width>
|
||||
<height>21</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Group cnt:</string>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
|
||||
</property>
|
||||
</widget>
|
||||
</widget>
|
||||
<customwidgets>
|
||||
<customwidget>
|
||||
<class>caFrame</class>
|
||||
<extends>QFrame</extends>
|
||||
<header>caFrame</header>
|
||||
<container>1</container>
|
||||
</customwidget>
|
||||
<customwidget>
|
||||
<class>caLabel</class>
|
||||
<extends>QLabel</extends>
|
||||
<header>caLabel</header>
|
||||
</customwidget>
|
||||
<customwidget>
|
||||
<class>caLineEdit</class>
|
||||
<extends>QLineEdit</extends>
|
||||
<header>caLineEdit</header>
|
||||
</customwidget>
|
||||
<customwidget>
|
||||
<class>caShellCommand</class>
|
||||
<extends>QWidget</extends>
|
||||
<header>caShellCommand</header>
|
||||
</customwidget>
|
||||
</customwidgets>
|
||||
<resources/>
|
||||
<connections/>
|
||||
</ui>
|
||||
10
qt/readme.md
Normal file
10
qt/readme.md
Normal file
@@ -0,0 +1,10 @@
|
||||
# Panel for plugin
|
||||
```
|
||||
caqtdm -macro "IOC=c6015a-02,SAFETY_GRP=first" ecmc_plugin_safety_main.ui
|
||||
```
|
||||
|
||||
# Panel to simulate motion safety box
|
||||
To be used together with the test scripts in the iocsh dir
|
||||
```
|
||||
caqtdm -macro "IOC=c6015a-02,BI_S_ID=014,BO_S_ID=014" sim_motion_safety_box.ui
|
||||
```
|
||||
247
qt/sim_motion_safety_box.ui
Normal file
247
qt/sim_motion_safety_box.ui
Normal file
@@ -0,0 +1,247 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<ui version="4.0">
|
||||
<class>Form</class>
|
||||
<widget class="QWidget" name="Form">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>341</width>
|
||||
<height>312</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="windowTitle">
|
||||
<string>Form</string>
|
||||
</property>
|
||||
<widget class="caByteController" name="cabytecontroller">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>55</x>
|
||||
<y>40</y>
|
||||
<width>40</width>
|
||||
<height>70</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="channel" stdset="0">
|
||||
<string notr="true">$(IOC):m$(M_ID=0)s$(BI_S_ID)-One</string>
|
||||
</property>
|
||||
<property name="endBit">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="foreground" stdset="0">
|
||||
<color>
|
||||
<red>78</red>
|
||||
<green>154</green>
|
||||
<blue>6</blue>
|
||||
</color>
|
||||
</property>
|
||||
<property name="background" stdset="0">
|
||||
<color>
|
||||
<red>255</red>
|
||||
<green>0</green>
|
||||
<blue>0</blue>
|
||||
</color>
|
||||
</property>
|
||||
<property name="fontScaleMode" stdset="0">
|
||||
<enum>EPushButton::None</enum>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caByte" name="cabyte">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>55</x>
|
||||
<y>200</y>
|
||||
<width>40</width>
|
||||
<height>70</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="channel" stdset="0">
|
||||
<string notr="true">$(IOC):m$(M_ID=0)s$(BO_S_ID)-Zero</string>
|
||||
</property>
|
||||
<property name="endBit">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="foreground" stdset="0">
|
||||
<color>
|
||||
<red>78</red>
|
||||
<green>154</green>
|
||||
<blue>6</blue>
|
||||
</color>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caLabel" name="calabel">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>125</x>
|
||||
<y>65</y>
|
||||
<width>171</width>
|
||||
<height>28</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>E-Stop command</string>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caLabel" name="calabel_2">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>125</x>
|
||||
<y>140</y>
|
||||
<width>186</width>
|
||||
<height>28</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Reduce velo command</string>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caLabel" name="calabel_3">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>125</x>
|
||||
<y>225</y>
|
||||
<width>161</width>
|
||||
<height>28</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Axes at rest status</string>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caTextEntry" name="catextentry">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>54</x>
|
||||
<y>280</y>
|
||||
<width>41</width>
|
||||
<height>22</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter</set>
|
||||
</property>
|
||||
<property name="channel" stdset="0">
|
||||
<string notr="true">$(IOC):m$(M_ID=0)s$(BI_S_ID)-One</string>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caLabel" name="calabel_4">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>20</x>
|
||||
<y>10</y>
|
||||
<width>301</width>
|
||||
<height>28</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Simulation of motion safety box</string>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caByteController" name="cabytecontroller_2">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>55</x>
|
||||
<y>120</y>
|
||||
<width>40</width>
|
||||
<height>70</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="channel" stdset="0">
|
||||
<string notr="true">$(IOC):m$(M_ID=0)s$(BI_S_ID)-One</string>
|
||||
</property>
|
||||
<property name="startBit">
|
||||
<number>1</number>
|
||||
</property>
|
||||
<property name="endBit">
|
||||
<number>1</number>
|
||||
</property>
|
||||
<property name="foreground" stdset="0">
|
||||
<color>
|
||||
<red>78</red>
|
||||
<green>154</green>
|
||||
<blue>6</blue>
|
||||
</color>
|
||||
</property>
|
||||
<property name="background" stdset="0">
|
||||
<color>
|
||||
<red>255</red>
|
||||
<green>0</green>
|
||||
<blue>0</blue>
|
||||
</color>
|
||||
</property>
|
||||
<property name="fontScaleMode" stdset="0">
|
||||
<enum>EPushButton::None</enum>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caLabel" name="calabel_5">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>135</x>
|
||||
<y>85</y>
|
||||
<width>131</width>
|
||||
<height>28</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>(Ramp down command)</string>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
|
||||
</property>
|
||||
</widget>
|
||||
<widget class="caLabel" name="calabel_6">
|
||||
<property name="geometry">
|
||||
<rect>
|
||||
<x>120</x>
|
||||
<y>275</y>
|
||||
<width>171</width>
|
||||
<height>28</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Command PV (ONE)</string>
|
||||
</property>
|
||||
<property name="alignment">
|
||||
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
|
||||
</property>
|
||||
</widget>
|
||||
</widget>
|
||||
<customwidgets>
|
||||
<customwidget>
|
||||
<class>caTextEntry</class>
|
||||
<extends>caLineEdit</extends>
|
||||
<header>caTextEntry</header>
|
||||
</customwidget>
|
||||
<customwidget>
|
||||
<class>caByteController</class>
|
||||
<extends>QWidget</extends>
|
||||
<header>caByteController</header>
|
||||
</customwidget>
|
||||
<customwidget>
|
||||
<class>caLabel</class>
|
||||
<extends>QLabel</extends>
|
||||
<header>caLabel</header>
|
||||
</customwidget>
|
||||
<customwidget>
|
||||
<class>caLineEdit</class>
|
||||
<extends>QLineEdit</extends>
|
||||
<header>caLineEdit</header>
|
||||
</customwidget>
|
||||
<customwidget>
|
||||
<class>caByte</class>
|
||||
<extends>QWidget</extends>
|
||||
<header>caByte</header>
|
||||
</customwidget>
|
||||
</customwidgets>
|
||||
<resources/>
|
||||
<connections/>
|
||||
</ui>
|
||||
@@ -18,7 +18,7 @@
|
||||
#- NAME : Name of safety group
|
||||
#- AX_ID : Axis ID
|
||||
#- VELO_REST_LIM : Velocity at rest limit [unit same as EGU of axis]
|
||||
#- VELO_MAX_LIM : Velocity maximum limit, -1 to disable [unit same as EGU of axis]
|
||||
#- VELO_MAX_LIM : Velocity maximum limit when EC_RED_VEL_CMD, set to -1 to disable [unit same as EGU of axis]
|
||||
#-
|
||||
#################################################################################
|
||||
|
||||
@@ -26,7 +26,10 @@
|
||||
#- <name> : Name of safety group to add axis to.
|
||||
#- <Axis id> : Axis index to add (ecmc axis index).
|
||||
#- <velo_rest_limit> : Axis at rest velo limit [unit of axis].
|
||||
#- <velo_max_limit> : Axis max velo limit [unit of axis].
|
||||
#- <velo_max_limit> : Velocity maximum limit when EC_RED_VEL_CMD, set to -1 to disable [unit same as EGU of axis]
|
||||
#- <filter_time> : NOT USED (for future implemenation). Time for axis to be below velo limit [ms].
|
||||
|
||||
ecmcAddAxisToSafetyGroup("${NAME}",${AX_ID},${VELO_REST_LIM=0},0,${VELO_MAX_LIM=0.0})
|
||||
|
||||
#- Load SS1 axis records
|
||||
dbLoadRecords("ecmcSS1Axis.template","AXIS_PREFIX=${ECMC_MOTOR_${AX_ID}_FULL_NAME=},NAME=${NAME},VEL_MAX_LIM=${VELO_MAX_LIM=0.0},VEL_REST_LIM=${VELO_REST_LIM=0.0}")
|
||||
|
||||
@@ -15,11 +15,11 @@
|
||||
#-###############################################################################
|
||||
#-
|
||||
#- Arguments:
|
||||
#- NAME : Name of safety group
|
||||
#- EC_RAMP_DOWN : Ethercat entry for ramp down command, input to ecmc (command from safety PLC/system)
|
||||
#- EC_AXES_REST : Ethercat entry for signaling that all axes in group are at rest, output from ecmc (feedback to safety PLC/system)
|
||||
#- EC_AXES_MAX_VELO : Ethercat entry for reducing velocity, input to ecmc (command from safety PLC/system)
|
||||
#- DELAY_MS : Time between rampdown command and STO
|
||||
#- NAME : Name of safety group
|
||||
#- EC_RAMP_DOWN_CMD : Ethercat entry for ramp down command, input to ecmc (command from safety PLC/system)
|
||||
#- EC_AXES_REST_STAT : Ethercat entry for signaling that all axes in group are at rest, output from ecmc (feedback to safety PLC/system)
|
||||
#- EC_AXES_LIM_VELO_CMD : Ethercat entry for reducing velocity, input to ecmc (command from safety PLC/system)
|
||||
#- DELAY_MS : Time between rampdown command and STO
|
||||
#-
|
||||
#################################################################################
|
||||
|
||||
@@ -27,10 +27,14 @@
|
||||
#- <name> : Name of group
|
||||
#- <ec_rampdown_cmd> : Ethercat entry input for rampdown cmd
|
||||
#- <ec_standstill_status> : Ethercat entry output for group standstill status
|
||||
#- <ec_max_velo_cmd> : Ethercat entry input for activation of maximum velo limitation (set to "empty" to disable)
|
||||
#- <ec_red_velo_cmd> : Ethercat entry input for activation of maximum velo limitation (set to "empty" to disable)
|
||||
#- <time_delay_ms> : Time delay of STO [ms]
|
||||
|
||||
ecmcAddSS1SafetyGroup("${NAME}","${EC_RAMP_DOWN}","${EC_AXES_REST}","${EC_AXES_MAX_VELO=empty}",${DELAY_MS=0})
|
||||
|
||||
ecmcAddSS1SafetyGroup("${NAME}","${EC_RAMP_DOWN_CMD}","${EC_AXES_AT_REST_STAT}","${EC_AXES_LIM_VELO_CMD=empty}",${DELAY_MS=0})
|
||||
|
||||
ecmcEpicsEnvSetCalc(ECMC_PLG_SAFETY_GRP_CNT, "${ECMC_PLG_SAFETY_GRP_CNT=0}+1", "%02d")
|
||||
|
||||
#- Load SS1 group records
|
||||
dbLoadRecords("ss1.template","P=${ECMC_PREFIX},NAME=${NAME}")
|
||||
dbLoadRecords("ecmcSS1Group.template","P=${ECMC_PREFIX},NAME=${NAME},ID=${ECMC_PLG_SAFETY_GRP_CNT},COUNT=${ECMC_PLG_SAFETY_GRP_CNT},DELAY=${DELAY_MS=0}")
|
||||
|
||||
|
||||
@@ -8,11 +8,14 @@
|
||||
* Created on: jan 29, 2024
|
||||
* Author: anderssandstrom
|
||||
*
|
||||
* Instructions:
|
||||
* - IMPORTANT: Add "USR_CFLAGS +=-DECMC_PLUGIN_MODULE_NAME=${MODULE}" to GNUMakefile
|
||||
* - All functions and ecmcPluginData struct must be declared static
|
||||
\*************************************************************************/
|
||||
|
||||
// Needed to get headers in ecmc right...
|
||||
#define ECMC_IS_PLUGIN
|
||||
#define ECMC_PLUGIN_VERSION 0
|
||||
#define ECMC_PLUGIN_VERSION 1
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
@@ -31,11 +34,11 @@ static int alreadyLoaded = 0;
|
||||
static int destructs_ = 0;
|
||||
|
||||
/** Optional.
|
||||
* Will be called once after successfull load into ecmc.
|
||||
* Will be called once after successful load into ecmc.
|
||||
* Return value other than 0 will be considered error.
|
||||
* configStr can be used for configuration parameters.
|
||||
**/
|
||||
int safetyConstruct(char *configStr)
|
||||
static int construct(char *configStr)
|
||||
{
|
||||
|
||||
if(alreadyLoaded) {
|
||||
@@ -50,19 +53,19 @@ int safetyConstruct(char *configStr)
|
||||
/** Optional function.
|
||||
* Will be called once at unload.
|
||||
**/
|
||||
void safetyDestruct(void)
|
||||
static void safetyDestruct(void)
|
||||
{
|
||||
destructs_ = 1;
|
||||
deleteAllSafetyGroups();
|
||||
}
|
||||
|
||||
/** Optional function.
|
||||
* Will be called each realtime cycle if definded
|
||||
* ecmcError: Error code of ecmc. Makes it posible for
|
||||
* Will be called each realtime cycle if defined
|
||||
* ecmcError: Error code of ecmc. Makes it possible for
|
||||
* this plugin to react on ecmc errors
|
||||
* Return value other than 0 will be considered to be an error code in ecmc.
|
||||
**/
|
||||
int safetyRealtime(int ecmcError)
|
||||
static int safetyRealtime(int ecmcError)
|
||||
{
|
||||
if(destructs_) return 0;
|
||||
|
||||
@@ -71,10 +74,10 @@ int safetyRealtime(int ecmcError)
|
||||
return 0;
|
||||
}
|
||||
|
||||
/** Link to data source here since all sources should be availabe at this stage
|
||||
/** Link to data source here since all sources should be available at this stage
|
||||
* (for example ecmc PLC variables are defined only at enter of realtime)
|
||||
**/
|
||||
int safetyEnterRT(){
|
||||
static int safetyEnterRT(){
|
||||
return validate();
|
||||
}
|
||||
|
||||
@@ -82,37 +85,12 @@ int safetyEnterRT(){
|
||||
* Will be called once just before leaving realtime mode
|
||||
* Return value other than 0 will be considered error.
|
||||
**/
|
||||
int safetyExitRT(void){
|
||||
static int safetyExitRT(void){
|
||||
return 0;
|
||||
}
|
||||
|
||||
//// Plc function for clear of buffers
|
||||
//double fft_clear(double index) {
|
||||
// return (double)clearFFT((int)index);
|
||||
//}
|
||||
//
|
||||
//// Plc function for enable
|
||||
//double fft_enable(double index, double enable) {
|
||||
// return (double)enableFFT((int)index, (int)enable);
|
||||
//}
|
||||
//
|
||||
//// Plc function for trigg new measurement (will clear buffers)
|
||||
//double fft_trigg(double index) {
|
||||
// return (double)triggFFT((int)index);
|
||||
//}
|
||||
//
|
||||
//// Plc function for enable
|
||||
//double fft_mode(double index, double mode) {
|
||||
// return (double)modeFFT((int)index, (FFT_MODE)((int)mode));
|
||||
//}
|
||||
//
|
||||
//// Plc function for enable
|
||||
//double fft_stat(double index) {
|
||||
// return (double)statFFT((int)index);
|
||||
//}
|
||||
|
||||
// Register data for plugin so ecmc know what to use
|
||||
struct ecmcPluginData pluginDataDef = {
|
||||
static struct ecmcPluginData pluginDataDef = {
|
||||
// Allways use ECMC_PLUG_VERSION_MAGIC
|
||||
.ifVersion = ECMC_PLUG_VERSION_MAGIC,
|
||||
// Name
|
||||
@@ -124,170 +102,19 @@ struct ecmcPluginData pluginDataDef = {
|
||||
,
|
||||
// Plugin version
|
||||
.version = ECMC_PLUGIN_VERSION,
|
||||
// Optional construct func, called once at load. NULL if not definded.
|
||||
.constructFnc = safetyConstruct,
|
||||
// Optional destruct func, called once at unload. NULL if not definded.
|
||||
// Optional construct func, called once at load. NULL if not defined.
|
||||
.constructFnc = construct,
|
||||
// Optional destruct func, called once at unload. NULL if not defined.
|
||||
.destructFnc = safetyDestruct,
|
||||
// Optional func that will be called each rt cycle. NULL if not definded.
|
||||
// Optional func that will be called each rt cycle. NULL if not defined.
|
||||
.realtimeFnc = safetyRealtime,
|
||||
// Optional func that will be called once just before enter realtime mode
|
||||
.realtimeEnterFnc = safetyEnterRT,
|
||||
// Optional func that will be called once just before exit realtime mode
|
||||
.realtimeExitFnc = safetyExitRT,
|
||||
// PLC funcs
|
||||
// .funcs[0] =
|
||||
// { /*----fft_clear----*/
|
||||
// // Function name (this is the name you use in ecmc plc-code)
|
||||
// .funcName = "fft_clear",
|
||||
// // Function description
|
||||
// .funcDesc = "double fft_clear(index) : Clear/reset fft[index].",
|
||||
// /**
|
||||
// * 7 different prototypes allowed (only doubles since reg in plc).
|
||||
// * Only funcArg${argCount} func shall be assigned the rest set to NULL.
|
||||
// **/
|
||||
// .funcArg0 = NULL,
|
||||
// .funcArg1 = fft_clear,
|
||||
// .funcArg2 = NULL,
|
||||
// .funcArg3 = NULL,
|
||||
// .funcArg4 = NULL,
|
||||
// .funcArg5 = NULL,
|
||||
// .funcArg6 = NULL,
|
||||
// .funcArg7 = NULL,
|
||||
// .funcArg8 = NULL,
|
||||
// .funcArg9 = NULL,
|
||||
// .funcArg10 = NULL,
|
||||
// .funcGenericObj = NULL,
|
||||
// },
|
||||
// .funcs[1] =
|
||||
// { /*----fft_enable----*/
|
||||
// // Function name (this is the name you use in ecmc plc-code)
|
||||
// .funcName = "fft_enable",
|
||||
// // Function description
|
||||
// .funcDesc = "double fft_enable(index, enable) : Set enable for fft[index].",
|
||||
// /**
|
||||
// * 7 different prototypes allowed (only doubles since reg in plc).
|
||||
// * Only funcArg${argCount} func shall be assigned the rest set to NULL.
|
||||
// **/
|
||||
// .funcArg0 = NULL,
|
||||
// .funcArg1 = NULL,
|
||||
// .funcArg2 = fft_enable,
|
||||
// .funcArg3 = NULL,
|
||||
// .funcArg4 = NULL,
|
||||
// .funcArg5 = NULL,
|
||||
// .funcArg6 = NULL,
|
||||
// .funcArg7 = NULL,
|
||||
// .funcArg8 = NULL,
|
||||
// .funcArg9 = NULL,
|
||||
// .funcArg10 = NULL,
|
||||
// .funcGenericObj = NULL,
|
||||
// },
|
||||
// .funcs[2] =
|
||||
// { /*----fft_trigg----*/
|
||||
// // Function name (this is the name you use in ecmc plc-code)
|
||||
// .funcName = "fft_trigg",
|
||||
// // Function description
|
||||
// .funcDesc = "double fft_trigg(index) : Trigg new measurement for fft[index]. Will clear buffers.",
|
||||
// /**
|
||||
// * 7 different prototypes allowed (only doubles since reg in plc).
|
||||
// * Only funcArg${argCount} func shall be assigned the rest set to NULL.
|
||||
// **/
|
||||
// .funcArg0 = NULL,
|
||||
// .funcArg1 = fft_trigg,
|
||||
// .funcArg2 = NULL,
|
||||
// .funcArg3 = NULL,
|
||||
// .funcArg4 = NULL,
|
||||
// .funcArg5 = NULL,
|
||||
// .funcArg6 = NULL,
|
||||
// .funcArg7 = NULL,
|
||||
// .funcArg8 = NULL,
|
||||
// .funcArg9 = NULL,
|
||||
// .funcArg10 = NULL,
|
||||
// .funcGenericObj = NULL,
|
||||
// },
|
||||
// .funcs[3] =
|
||||
// { /*----fft_mode----*/
|
||||
// // Function name (this is the name you use in ecmc plc-code)
|
||||
// .funcName = "fft_mode",
|
||||
// // Function description
|
||||
// .funcDesc = "double fft_mode(index, mode) : Set mode Cont(1)/Trigg(2) for fft[index].",
|
||||
// /**
|
||||
// * 7 different prototypes allowed (only doubles since reg in plc).
|
||||
// * Only funcArg${argCount} func shall be assigned the rest set to NULL.
|
||||
// **/
|
||||
// .funcArg0 = NULL,
|
||||
// .funcArg1 = NULL,
|
||||
// .funcArg2 = fft_mode,
|
||||
// .funcArg3 = NULL,
|
||||
// .funcArg4 = NULL,
|
||||
// .funcArg5 = NULL,
|
||||
// .funcArg6 = NULL,
|
||||
// .funcArg7 = NULL,
|
||||
// .funcArg8 = NULL,
|
||||
// .funcArg9 = NULL,
|
||||
// .funcArg10 = NULL,
|
||||
// .funcGenericObj = NULL,
|
||||
// },
|
||||
// .funcs[4] =
|
||||
// { /*----fft_stat----*/
|
||||
// // Function name (this is the name you use in ecmc plc-code)
|
||||
// .funcName = "fft_stat",
|
||||
// // Function description
|
||||
// .funcDesc = "double fft_stat(index) : Get status of fft (NO_STAT, IDLE, ACQ, CALC) for fft[index].",
|
||||
// /**
|
||||
// * 7 different prototypes allowed (only doubles since reg in plc).
|
||||
// * Only funcArg${argCount} func shall be assigned the rest set to NULL.
|
||||
// **/
|
||||
// .funcArg0 = NULL,
|
||||
// .funcArg1 = fft_stat,
|
||||
// .funcArg2 = NULL,
|
||||
// .funcArg3 = NULL,
|
||||
// .funcArg4 = NULL,
|
||||
// .funcArg5 = NULL,
|
||||
// .funcArg6 = NULL,
|
||||
// .funcArg7 = NULL,
|
||||
// .funcArg8 = NULL,
|
||||
// .funcArg9 = NULL,
|
||||
// .funcArg10 = NULL,
|
||||
// .funcGenericObj = NULL,
|
||||
// },
|
||||
.funcs[0] = {0}, // last element set all to zero..
|
||||
// PLC consts
|
||||
/* CONTINIOUS MODE = 1 */
|
||||
// .consts[0] = {
|
||||
// .constName = "fft_CONT",
|
||||
// .constDesc = "FFT Mode: Continious",
|
||||
// .constValue = CONT
|
||||
// },
|
||||
// /* TRIGGERED MODE = 2 */
|
||||
// .consts[1] = {
|
||||
// .constName = "fft_TRIGG",
|
||||
// .constDesc = "FFT Mode :Triggered",
|
||||
// .constValue = TRIGG
|
||||
// },
|
||||
// /* TRIGGERED MODE = 2 */
|
||||
// .consts[2] = {
|
||||
// .constName = "fft_NO_STAT",
|
||||
// .constDesc = "FFT Status: Invalid state",
|
||||
// .constValue = NO_STAT,
|
||||
// },
|
||||
// /* TRIGGERED MODE = 2 */
|
||||
// .consts[3] = {
|
||||
// .constName = "fft_IDLE",
|
||||
// .constDesc = "FFT Status: Idle state (waiting for trigger)",
|
||||
// .constValue = IDLE
|
||||
// },
|
||||
// /* TRIGGERED MODE = 2 */
|
||||
// .consts[4] = {
|
||||
// .constName = "fft_ACQ",
|
||||
// .constDesc = "FFT Status: Acquiring data",
|
||||
// .constValue = ACQ
|
||||
// },
|
||||
// /* TRIGGERED MODE = 2 */
|
||||
// .consts[5] = {
|
||||
// .constName = "fft_CALC",
|
||||
// .constDesc = "FFT Status: Calculating result",
|
||||
// .constValue = CALC
|
||||
// },
|
||||
.consts[0] = {0}, // last element set all to zero..
|
||||
};
|
||||
|
||||
|
||||
@@ -94,6 +94,7 @@ ecmcSS1SafetyGroup::ecmcSS1SafetyGroup(const char *name,
|
||||
limitVeloCmd_ = 0;
|
||||
axesDisabled_ = 0;
|
||||
cfgDbgMode_ = 0;
|
||||
oldStop_ = 0;
|
||||
memset(&status_,0,sizeof(status_));
|
||||
|
||||
parseConfigStr(cfg_string);
|
||||
@@ -621,8 +622,24 @@ void ecmcSS1SafetyGroup::setAxesSafetyInterlocks(int stop) {
|
||||
if(!*saxis) {
|
||||
throw std::runtime_error( "Safety: Axis object NULL.");
|
||||
}
|
||||
setAxisEmergencyStopInterlock((*saxis)->axisId_,stop);
|
||||
|
||||
setAxisEmergencyStopInterlock((*saxis)->axisId_,stop);
|
||||
|
||||
if(!oldStop_ && stop) {
|
||||
//Calcualte new deceleration if delay is defined and abs(velo) > 0
|
||||
if(delayMs_ > 0) {
|
||||
double velo = 0;
|
||||
getAxisTrajVelo((*saxis)->axisId_,&velo);
|
||||
velo = std::abs(velo);
|
||||
if(velo > 0) {
|
||||
double newEmergDec = velo / (ECMC_PLUGIN_RAMP_DOWN_TIME_RATIO * delayMs_ / 1000.0);
|
||||
setAxisEmergDeceleration((*saxis)->axisId_,newEmergDec);
|
||||
printf("Safety %s: Set new emergency deceleration %lf \n",sName_,newEmergDec);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
oldStop_ = stop;
|
||||
}
|
||||
|
||||
void ecmcSS1SafetyGroup::addAxis(int axisId,
|
||||
|
||||
@@ -162,8 +162,9 @@ class ecmcSS1SafetyGroup : public asynPortDriver {
|
||||
ecmcEcEntry *ecEntryRampDown_;
|
||||
ecmcEcEntry *ecEntryStandstill_;
|
||||
ecmcEcEntry *ecEntryLimitVelo_;
|
||||
|
||||
bool oldStop_;
|
||||
static std::string to_string(int value);
|
||||
|
||||
};
|
||||
|
||||
#endif /* ECMC_SAFETY_GROUP_PLG_H_ */
|
||||
|
||||
@@ -25,4 +25,7 @@
|
||||
#define ECMC_PLUGIN_SAFETY_ERROR_CODE 1
|
||||
#define ECMC_PLUGIN_ALREADY_LOADED_ERROR_CODE 2
|
||||
|
||||
// How big part of delay is used for rampdown
|
||||
#define ECMC_PLUGIN_RAMP_DOWN_TIME_RATIO 0.9
|
||||
|
||||
#endif /* ECMC_MOTION_PLG_DEFS_H_ */
|
||||
|
||||
@@ -25,11 +25,11 @@ int setCfgString(const char* cfgString);
|
||||
* \param[in] name Name of safety group.\n
|
||||
* \param[in] ec_rampdown_cmd Name of ethercat entry for ramp down command\n
|
||||
* \param[in] ec_standstill_status Name of ethercat entry all axis standstill status\n
|
||||
* \param[in] time_delay_ms Timedelay between ec_rampdown_cmd going high untill STO is triggered by safety relay.\n
|
||||
* \param[in] time_delay_ms Timedelay between ec_ramp-down_cmd going high until STO is triggered by safety relay.\n
|
||||
*
|
||||
* \return 0 if success or otherwise an error code.\n
|
||||
*/
|
||||
//int createSafetyGroup(name,ec_rampdown_cmd,ec_standstill_status, time_delay_ms);
|
||||
//int createSafetyGroup(name,ec_ramp-down_cmd,ec_standstill_status, time_delay_ms);
|
||||
|
||||
/** \brief Deletes all created objects\n
|
||||
*
|
||||
@@ -41,8 +41,8 @@ void deleteAllSafetyGroups();
|
||||
*
|
||||
* This tells the safety lib to connect to ecmc to find it's data sources.\n
|
||||
* This function should be called just before entering realtime since then all\n
|
||||
* data sources in ecmc will be definded (plc sources are compiled just before runtime\n
|
||||
* so are only fist accesible now).\n
|
||||
* data sources in ecmc will be defined (plc sources are compiled just before runtime\n
|
||||
* so are only fist accessible now).\n
|
||||
* \return 0 if success or otherwise an error code.\n
|
||||
*/
|
||||
int validate();
|
||||
|
||||
@@ -24,3 +24,6 @@
|
||||
epicsEnvSet(ECMC_PLUGIN_FILNAME,"$(ecmc_plugin_safety_DIR)/lib/${EPICS_HOST_ARCH=linux-x86_64}/libecmc_plugin_safety.so")
|
||||
epicsEnvSet(ECMC_PLUGIN_CONFIG,"DBG_PRINT=1;")
|
||||
ecmcConfigOrDie "Cfg.LoadSafetyPlugin(${ECMC_PLUGIN_FILNAME},${ECMC_PLUGIN_CONFIG=""})"
|
||||
|
||||
#- Load SS1 group records
|
||||
dbLoadRecords("ecmcSS1Main.template","P=${ECMC_PREFIX}")
|
||||
|
||||
Reference in New Issue
Block a user