Closed prjemian closed 1 year ago
My motivation is to set the MRES for soft motors to some ridiculous precision (say 1e-5 or so) and the raw motor count seems to be limited.
The ridiculous precision corresponds to motors that simulate a Bragg angle rotation. These rotations require precision of 10 microdegrees to step the motor through the effective energy resolution.
The RMP field of the motor record is limited to 32-bits:
Changing it will break compatibility with EPICS base 3.15, iirc.
Ok. I'll try to stay within that limit. Will report if additional problem identified.
Specifically, -2147483648 <= RMP <= 2147483647, correct?
So, with MRES=1e-5, then travel between user soft limits of +/- 20,000 should be possible with tripping the (simulated) limit switch, correct?
Could RMP be changed to DBF_DOUBLE? That allows exact representation of integers up to about 52 bits.
So, with MRES=1e-5, then travel between user soft limits of +/- 20,000 should be possible with tripping the (simulated) limit switch, correct?
Yes.
Could RMP be changed to DBF_DOUBLE? That allows exact representation of integers up to about 52 bits.
I don't know what the unintended consequences of changing it to DBF_DOUBLE would be. I am unlikely to have time to test that change until the APS upgrade is complete.
With motor 7.2.2, synApps 6.2.1, asyn 4.42, XXX master, just downloaded and built within the hour, using these motors:
iocshLoad("$(MOTOR)/iocsh/motorSim.iocsh", "INSTANCE=motorSim, HOME_POS=0, NUM_AXES=56, HIGH_LIM=32000, LOW_LIM=-32000, SUB=substitutions/motorSim.substitutions")
And the substitutions file (built from bash script) has these lines:
file "$(MOTOR)/db/asyn_motor.db"
{
pattern
{N, M, ADDR, DESC, EGU, DIR, VELO, VBAS, ACCL, BDST, BVEL, BACC, MRES, PREC, INIT}
{1, "m1", 0, "motor 1", degrees, Pos, 1, .1, .2, 0, 1, .2, 0.01, 5, ""}
{2, "m2", 1, "motor 2", degrees, Pos, 1, .1, .2, 0, 1, .2, 0.01, 5, ""}
{3, "m3", 2, "motor 3", degrees, Pos, 1, .1, .2, 0, 1, .2, 0.01, 5, ""}
{4, "m4", 3, "motor 4", degrees, Pos, 1, .1, .2, 0, 1, .2, 0.01, 5, ""}
{5, "m5", 4, "motor 5", degrees, Pos, 1, .1, .2, 0, 1, .2, 0.01, 5, ""}
{6, "m6", 5, "motor 6", degrees, Pos, 1, .1, .2, 0, 1, .2, 0.01, 5, ""}
{7, "m7", 6, "motor 7", degrees, Pos, 1, .1, .2, 0, 1, .2, 0.01, 5, ""}
{8, "m8", 7, "motor 8", degrees, Pos, 1, .1, .2, 0, 1, .2, 0.01, 5, ""}
{9, "m9", 8, "motor 9", degrees, Pos, 1, .1, .2, 0, 1, .2, 0.01, 5, ""}
...
{56, "m56", 55, "motor 56", degrees, Pos, 1, .1, .2, 0, 1, .2, 0.01, 5, ""}
}
When the IOC is started, this is what one of the motors (sky:m5
by name) shows:
@prjemian, is there a problem on those caQtDM screens? If so, it isn't jumping out at me.
Here is the problem I have seen:
When the SREV field is changed from 200 steps/rev to 200,000 steps/rev, the MRES=1e-5, as expected.
Note that HLM and LLM are not affected by this change in SREV, as expected.
When the motor is moved from zero to 0.35 (any target above 0.32), a hard limit is shown and the RBV is pegged to 0.32000. This is clearly within the travel limits as shown.
That comes from this line, specifically HIGH_LIM=32000, which is setting the limit in counts:
iocshLoad("$(MOTOR)/iocsh/motorSim.iocsh", "INSTANCE=motorSim, HOME_POS=0, NUM_AXES=56, HIGH_LIM=32000, LOW_LIM=-32000, SUB=substitutions/motorSim.substitutions")
HIGH_LIM
is not HLM
?
HIGH_LIM
is notHLM
?
No. It is an argument passed to motorSimCreate to allow hardware limits to be simulated by the motor driver:
Oh. In raw motor pulses, not user units, correct? I'll reconfigure with 1000x the default numbers and retry.
Oh. In raw motor pulses, not user units, correct? I'll reconfigure with 1000x the default numbers and retry.
Correct.
I'm trying with sed -i s:'32000':'32000000':g ./motors.iocsh
To stay within (2^31)-1, I'll dial that down to 20,000,000
That will fix this issue, thanks!
What confused me is that the value for HIGH_LIM becomes the HLM value when the IOC is first booted (unless the DHLM macro is provided to asyn_motor.db). I was expecting the IOC to consider the MRES between these numbers. Similar for LOW_LIM and LLM.
What confused me is that the value for HIGH_LIM becomes the HLM value when the IOC is first booted (unless the DHLM macro is provided to asyn_motor.db). I was expecting the IOC to consider the MRES between these numbers. Similar for LOW_LIM and LLM.
It should probably be considered a bug that the HIGH_LIM and LOW_LIM values are also used as the default values for DHLM & DLLM:
Right. I suggest adding DHLM
and DLLM
macros (with some reasonable defaults) in motorMotorSim/motorSimApp/iocsh/motorSim.iocsh
, line 34:
dbLoadTemplate("$(SUB=$(MOTOR)/iocsh/EXAMPLE_motorSim.substitutions)", "P=$(PREFIX), DTYP='asynMotor', PORT=$(INSTANCE)$(CONTROLLER=0), DHLM=$(HIGH_LIM=32000), DLLM=$(LOW_LIM=-32000)")
I've created a branch for improving the motorMotorSim examples. That is a change I plan to make to motorSim.iocsh.
Originally posted by @prjemian in https://github.com/epics-modules/xxx/issues/46#issuecomment-775008691