I added a
dbpf "H3:TEST_PUT" 1
to the st.cmd script before starting the sequencer. The pvPut in the
sequencer program now results in pvCaMonitorHandler() being invoked
just once. So, I think you have to live with the fact that a single
'pvPut' can result in an 'sync'd sequencer event flag being set more
than once (once from status change, once from value change).
With the dbpf done first, I've run the IOC with following program 500
times without getting a 'flag set' message.
program sncTest
float test_put;
assign test_put to "H3:TEST_PUT";
monitor test_put;
evflag test_putEvent;
sync test_put test_putEvent;
ss ss1 {
state init {
when () {
test_put = 40;
pvPut(test_put, SYNC);
} state clear
}
state clear {
when(efTestAndClear(test_putEvent)) { } state wait
}
state wait {
when (efTest(test_putEvent)) {
printf("flag set\n");
} state loop
}
state loop {
when (delay(1000)) { } state loop
}
}
On Oct 3, 2009, at 7:56 PM, Eric Norum wrote:
Tracking this down a little farther. It appears that the
pvCaMonitorHandler in <sequencerTop>/src/pv/pvCa.cc is being invoked
twice. Perhaps once when the PV status changes from 'invalid' and
perhaps once when the PV value is changed? If these happen on
either side of the efTestAndClear call then you'll get the 'flag
set' message.
On Oct 3, 2009, at 7:32 PM, Patrick Thomas wrote:
It happens frequently on this one too, and also prints "should
clear it here"
program sncTest
float test_put;
assign test_put to "H3:TEST_PUT";
monitor test_put;
evflag test_putEvent;
sync test_put test_putEvent;
ss ss1 {
state init {
when () {
efClear(test_putEvent);
test_put = 40;
pvPut(test_put, SYNC);
} state clear
}
state clear {
when(efTestAndClear(test_putEvent)) {
printf("should clear it here\n");
efClear(test_putEvent);
} state wait
}
state wait {
when (efTest(test_putEvent)) {
printf("flag set\n");
sleep(500);
} state wait
}
}
Eric Norum wrote:
Clarification. I ran the example, *with busy loops removed*.
On Oct 3, 2009, at 6:30 PM, Eric Norum wrote:
I ran the example in a script. It's been started 250 times now
and never printed, "flag set".
On Oct 3, 2009, at 5:37 PM, Patrick Thomas wrote:
I'm sorry, I should clarify. It doesn't print the message after
sitting there for a long time. It sometimes prints it when it is
started over again multiple times.
-Patrick
Eric Norum wrote:
I forgot to mention, that I tried your example (with busy loops
removed) on R3.14.11. My test IOC has been sitting there for
half an hour now without printing the message.
On Oct 3, 2009, at 5:13 PM, Eric Norum wrote:
There seems to be a fundamental misunderstanding in your use
of the sequencer. The default action, if no state transition
'when' statement is true, is to stay in the same state waiting
for a statement to come true. Your examples have lots of
statements like:
state clear {
when(efTestAndClear(test_putEvent)) {
efClear(test_putEvent);
} state wait
when () {
} state clear
}
The above code is bad. It sets the sequencer into a busy loop
consuming all available CPU.
I think what you want is the following:
state clear {
when(efTestAndClear(test_putEvent)) {
efClear(test_putEvent);
} state wait
}
This code blocks the sequencer until something 'interesting'
happens at which point it rescans the 'when' statements and
checks to see if any of them are now true.
I suspect that your 'flag' problem is occurring because the
busy loops you've constructed are preventing other threads
from getting the CPU they need.
On Oct 3, 2009, at 4:46 PM, Patrick Thomas wrote:
Hi Mark,
Why does this still sometimes print out the flag?
program sncTest
float test_put;
assign test_put to "H3:TEST_PUT";
monitor test_put;
evflag test_putEvent;
sync test_put test_putEvent;
ss ss1 {
state init {
when () {
efClear(test_putEvent);
test_put = 40;
pvPut(test_put, SYNC);
} state clear
}
state clear {
when(efTestAndClear(test_putEvent)) {
efClear(test_putEvent);
} state wait
when () {
} state clear
}
state wait {
when (efTest(test_putEvent)) {
printf("flag set\n");
} state loop
when () {
} state wait
}
state loop {
when () {
} state loop
}
}
Mark Rivers wrote:
Hi Patrick,
What is it you are trying to do? You are doing both pvPuts
and looking for external changes to the same PV?
If so, then one solution is to ignore events which
correspond to the value that your SNL program set with
pvPut, and only act on events with values that must have
been done by some external agent. Here is an example from
one of my programs:
int abort; assign abort to "{P}{R}Abort.VAL";
monitor abort;
evflag abortMon; sync abort abortMon;
...
ss xpsTrajectoryAbort {
state monitorAbort {
when ((efTestAndClear(abortMon)) && (abort==1) &&
(execState==EXECUTE_STATE_EXECUTING)) {
...
abort=0;
pvPut(abort);
} state monitorAbort
}
}
In this case abort can be set to 1 by the user from outside
the SNL program. If that happens then the SNL program takes
some appropriate action, and does a pvPut of abort back to
0. That would cause another event to be received, but I
ignore that event in the when clause()
when ((efTestAndClear(abortMon)) && (abort==1) &&
(execState==EXECUTE_STATE_EXECUTING)) {
This will always clear event flags on the abort PV, but will
only do the logic inside the when if abort is 1 and
execState is EXECUTE_STATE_EXECUTING.
Mark
________________________________
From: Patrick Thomas [mailto:[email protected]]
Sent: Sat 10/3/2009 12:37 AM
To: Mark Rivers
Cc: [email protected]; [email protected]
Subject: Re: state notation code flags
I see, thank you. So is there a way around this, that is to
make sure
the monitors are received and the flag is set before the
call to efClear
is made, or some way to make a particular pvPut not have
channel access
send out monitors for that record?
Mark Rivers wrote:
I think I have figured it out, the following code shows it
the most
clearly. Adding SYNC to the pvPut command does not seem to
ensure that
it will finish before the next command is processed:
The pvPut command did "finish" before the efClear command
was executed. That means that it wrote its value to the
record, and processed that record and any records that
process as a result of processing that record. That
record told channel access to send out monitors on that PV
to all clients, including your SNL program. It does NOT
wait for those monitors to be received; it simply requests
channel access to send them, which is then done
asynchronously. So the event flag in your SNL program will
be set some time after you do the pvPut. What you are
observing is the expected and documented behavior of EPICS.
Mark
________________________________
From: Patrick Thomas [mailto:[email protected]]
Sent: Fri 10/2/2009 7:03 PM
To: [email protected]
Cc: Mark Rivers; [email protected]
Subject: Re: state notation code flags
I think I have figured it out, the following code shows it
the most
clearly. Adding SYNC to the pvPut command does not seem to
ensure that
it will finish before the next command is processed:
program sncTest
float request_maximum_velocity;
assign request_maximum_velocity to "H3:TEST";
monitor request_maximum_velocity;
evflag request_maximum_velocityEvent;
sync request_maximum_velocity request_maximum_velocityEvent;
ss ss1 {
state init {
when () {
efClear(request_maximum_velocityEvent);
request_maximum_velocity = 40;
pvPut(request_maximum_velocity, SYNC);
efClear(request_maximum_velocityEvent);
} state wait
}
state wait {
when () {
if
(efTest(request_maximum_velocityEvent)) {
printf("flag set\n");
}
} state wait
}
}
Pete R. Jemian wrote:
sounds a bit off ... show the code
Patrick Thomas wrote:
I think I have it narrowed down. It appears that when I
set variable1
equal to variable2 and variable2 has a flag synced to it
(variable1
does not), and then do a pvPut on variable1, sometimes
the flag is
set on variable2 and sometimes it isn't. Am I correct?
Why does this
occur?
Thank you,
Patrick
Mark Rivers wrote:
Patrick,
Event flags can be explicitly set, which is typically
used to allow
communication between state sets. Or event flags can be
synced to a
PV,
and will be set whenever a monitor is received for that
PV, as in the
example I sent you.
You can use the efTest() function outside of a when
statement, just
like
any other function.
Mark
-----Original Message-----
From: Patrick Thomas [mailto:thomas_p@ligo-
wa.caltech.edu] Sent:
Thursday, October 01, 2009 5:20 PM
To: Mark Rivers
Cc: [email protected]
Subject: Re: state notation code flags
Hi Mark,
Are the flags on a monitored variable set whenever the
monitored
variable is used in the code, including a pvPut, pvGet,
assignment,
calculation, or print statement? Is there a way to test
if the flag
is set besides an efTest in a when statement?
Thank you,
Patrick
Mark Rivers wrote:
Hio Patrick,
Here are some code snippets from one of my SNL
programs. It has a
variable nelements assigned to a PV, and a monitor on
that PV. It has
an event flag, nelementsMon that is synced to
nelements. Whenever
nelements changes the event flag will be set. In the
init state I
clear
the event flag, just to be sure it is clear when the SNL
code starts
running (after all PVs connect). I then use
efTestAndClear in a when
statement to take actions when that event flag is set,
and to clear it.
This works fine for me.
int nelements; assign nelements to "{P}
{R}Nelements.VAL";
monitor nelements;
evflag nelementsMon; sync nelements nelementsMon;
/* Initialize things when first starting */
state init {
when() {
/* Clear all event flags */
...
efClear(nelementsMon);
} state monitor_inputs
}
...
state monitor_inputs {
...
when(efTestAndClear(nelementsMon) && (nelements>=1)) {
/* If nelements changes, then change endPulses to
this
value,
* since this is what the user normally wants.
endPulses
can be
* changed again after changing nelements if this
is
desired. */
if (moveMode == MOVE_MODE_RELATIVE)
endPulses = nelements;
else
endPulses = nelements-1;
pvPut(endPulses);
} state monitor_inputs
}
Mark
________________________________
From: [email protected] on behalf of
Patrick Thomas
Sent: Wed 9/30/2009 10:35 PM
To: [email protected]
Subject: state notation code flags
Hi,
I was wondering if there is a way to track at what
point in the state
notation code evflags are getting set and cleared, or
if someone could
clarify under what conditions they get set. I'm having
trouble with
them
getting set somewhere and not being cleared, but I'm
not sure where.
Thank you,
Patrick
--
Eric Norum <[email protected]>
Advanced Photon Source
Argonne National Laboratory
(630) 252-4793
--
Eric Norum <[email protected]>
Advanced Photon Source
Argonne National Laboratory
(630) 252-4793
--
Eric Norum <[email protected]>
Advanced Photon Source
Argonne National Laboratory
(630) 252-4793
--
Eric Norum <[email protected]>
Advanced Photon Source
Argonne National Laboratory
(630) 252-4793
- Replies:
- Re: state notation code flags Patrick Thomas
- Re: state notation code flags Patrick Thomas
- Re: state notation code flags Patrick Thomas
- References:
- state notation code flags Patrick Thomas
- RE: state notation code flags Mark Rivers
- Re: state notation code flags Patrick Thomas
- RE: state notation code flags Mark Rivers
- Re: state notation code flags Patrick Thomas
- Re: state notation code flags Pete R. Jemian
- Re: state notation code flags Patrick Thomas
- RE: state notation code flags Mark Rivers
- Re: state notation code flags Patrick Thomas
- RE: state notation code flags Mark Rivers
- Re: state notation code flags Patrick Thomas
- Re: state notation code flags Eric Norum
- Re: state notation code flags Eric Norum
- Re: state notation code flags Patrick Thomas
- Re: state notation code flags Eric Norum
- Re: state notation code flags Eric Norum
- Re: state notation code flags Patrick Thomas
- Re: state notation code flags Eric Norum
- Navigate by Date:
- Prev:
Re: state notation code flags Eric Norum
- Next:
Re: state notation code flags Patrick Thomas
- Index:
1994
1995
1996
1997
1998
1999
2000
2001
2002
2003
2004
2005
2006
2007
2008
<2009>
2010
2011
2012
2013
2014
2015
2016
2017
2018
2019
2020
2021
2022
2023
2024
- Navigate by Thread:
- Prev:
Re: state notation code flags Eric Norum
- Next:
Re: state notation code flags Patrick Thomas
- Index:
1994
1995
1996
1997
1998
1999
2000
2001
2002
2003
2004
2005
2006
2007
2008
<2009>
2010
2011
2012
2013
2014
2015
2016
2017
2018
2019
2020
2021
2022
2023
2024
|