passing variables from task to task

Here you can share completed projects or parts of projects that may be useful to others. You may post files relevant to ZBasic - source code, schematics, etc.
spamiam
Posts: 739
Joined: 13 November 2005, 6:39 AM

Post by spamiam »

GTBecker wrote:Tony's suggestion of using Compare Match to trigger an interrupt describes a prescaler which inherently reduces the signal resolution by the divider ratio.
Follow-up:

Actually the selection of the external counter input (rather than the internal clock) is one of the prescaler options, and results in a 1:1 prescaler value. The counter counts every rising or falling transition (user selected) on the T1 input.

So, there is no loss of the granularity (signal resolution) of the encoder hardware. The OCR1A values does not prescale per-se, but sets the reporting interval, and CTC mode takes care of clearing the counter atomically.

You can adjust the OCR1A value to any arbitrarily lower value if you are finding that the interrupts are coming too infrequently. This is best done during the OC1A interrupt service because the counter value is likely to be small, and you can ratchet up/down the OCR1A value progressively.

To prevent glitching, you need to try to avoid setting the ORC1A lower than the current counter value, or it will miss the interrupt, overflow, and then trigger the interrupt on the next pass. You will have missed 0xFFFF (or is it 0xFFFF+1?) counts entirely.

Even during the OC1A interrupt service, you need to be aware of any latency that may occur. May be as much as 1/512 second, maybe more. At 68KHz encoder signals, the counter could have counted 133 more encoder signals in that time, maybe more. So drastically reducing the OCR1A value might be hazardous.

-Tony
GTBecker
Posts: 616
Joined: 17 January 2006, 19:59 PM
Location: Cape Coral

Post by GTBecker »

spamiam wrote: Even during the OC1A interrupt service, you need to be aware of any latency that may occur. May be as much as 1/512 second, maybe more.
-Tony
Acknowledging a Timer1 interrupt can take an entire tick? I understand that an external hardware interrupt - if enabled - will transfer control within a few hundred microseconds.

My experience has been that an external bidirectional counter, read on a rising edge and cleared on a falling edge, works perfectly at megahertz count rates on a machine tool DRO I designed years ago. The counter just needs to be large enough to be unambiguous when read at your process rate.

We all juggle the hardware-or-code implementation decision of interface functions in our projects. Sometimes a firmware solution is clearly best; sometimes hardware is. I propose that fast rate counting is probably best done outside the processor, but if you can demonstrate a fast bit-responsive variable division prescaler, it would be an interesting method to study.
Tom
spamiam
Posts: 739
Joined: 13 November 2005, 6:39 AM

Post by spamiam »

GTBecker wrote:Acknowledging a Timer1 interrupt can take an entire tick? I understand that an external hardware interrupt - if enabled - will transfer control within a few hundred microseconds.
I am not sure of the amount of latency that will be experienced. My impression from previous discussions on this subject is that it is variable.

I would hope that the latency would be considerably less than one tick (1/512 second), but depending on what else is happening, and what other interrupts are getting serviced, I think it COULD be the better part of a tick latency.

I am not sure of the worst case latency. Don might be able to clarify. Nevertheless, the issues of latency persist no matter what. It only changes the number if counts that might be found in the counter when the OR1A interrupt is being serviced. Better assume it is not still zero.

GTBecker wrote:I propose that fast rate counting is probably best done outside the processor, but if you can demonstrate a fast bit-responsive variable division prescaler, it would be an interesting method to study.
Well, as far as I know, the AVR series procesors do not allow a variable division prescaler on external clock sources to the counter. If nothing else, than the counter/timer clock source is selected BY the prescaler bits. The sounce is internal at one of a few dividers, or external rising, or external falling.

But, with a 16 bit counter, you would have to be getting some massively fast counts to be a big problem for the AVr hardware.

E.G. (considering the raw AVR hardware just as a mental exercise) I would hope that the interrupt service could be completed within about 1000 instructions. If the CPU is running at 16MHz, then there is time to service about 16,000 interrupts per second before you saturate the processor. At 65535 counter ticks per interrupt, you can service something like 1x10^9 counts in a second.

If the ZX hardware operates at a 1000:1 disadvantage (I think the disadvantage is less than this), then one still should be able to service a million ticks in a second before totally saturating the processor.

Of course this is not to say that you can usefully service anything close to that number, but this shows an idea of the saturation level.


So, is dividing the encoder ticks necessary?

-Tony
GTBecker
Posts: 616
Joined: 17 January 2006, 19:59 PM
Location: Cape Coral

Post by GTBecker »

I must not be making myself clear, Tony.

AVR hardware has clock resources called prescalers, yes. An AVR prescaler is a clock rate divider; Atmel makes several divider values available by option to feed counters at selectable rates.

I am using the term prescaler to label the function you described using Compare Match on Timer1. The functional result is similar but the value that is divided is an external signal, not a processor clock.

I think what you are proposing is to dynamically change the Match value to report count changes at a variable rate. To circumvent an error caused by a remant count (a value that's necessarily less than the Match value, thus not reported) when stopped, you suggest lowering the Match value after a timeout of some sort.

If I have that right, you are proposing an interesting form of an adaptive counter. If you pursue that notion, it will either develop into an important tool - or you will learn why not.
Tom
spamiam
Posts: 739
Joined: 13 November 2005, 6:39 AM

Post by spamiam »

GTBecker wrote:I think what you are proposing is to dynamically change the Match value to report count changes at a variable rate. To circumvent an error caused by a remant count (a value that's necessarily less than the Match value, thus not reported) when stopped, you suggest lowering the Match value after a timeout of some sort.

If I have that right, you are proposing an interesting form of an adaptive counter. If you pursue that notion, it will either develop into an important tool - or you will learn why not.
I had suspected that you were using the prescaler term more generically.

Yes, it is possible (actually practically guaranteed) to have un-reported counts in the counter when you reach a stop! These counts might need to e taken into consideration, either for odometer purposes, or at least needing clearing before re-starting motion.

No matter how low you set the OCR1A, (except zero, where an interrupt occurs for each tick), you will have some tick(s) left in the counter upon reaching a halt.

So, unless the OCR1A is actually set to zero, then the counter needs to be manipulated when reaching a stop.

I am proposing some sort of adaptive adjustment of the OCR1A, including getting it down to zero. BUT you need to be able to handle acceleration. The low cutoff for OCR1A probably would need to be the number of counts encountered in your minimum time slice, at maximum acceleration from a standstill.

At the resolution the OP had listed, that is likely to be a couple of hundred.

This adaptive programming, associated with some necessary use of WaitForInterval() for escape timing is an interesting technique.

Right now I am not working at anything near that resolution of encoder counts. Interrupts for individual counts is more like what I need to do. But the OP might be interested in this technique.

PID techniques for the adaptice setting of OCR1A would probably apply in his case. PID might be too complicated, and just some linear proportional adjustments would probably be preferable.


If the OP is interested to pursue this further, I would be happy to lend my timer/counter experience! As for adaptive programming, I have no experience there, just some gut feelings.

-Tony
cdavis
Posts: 9
Joined: 12 June 2006, 10:14 AM
Location: Garden Grove, CA
Contact:

Post by cdavis »

I was wondering if there was any information about how fast the WaitForInterval() function could detect interrupts. I calculated that we would only need to run our motors at 2000 rpm, which would yield an encoder pulserate of about 17000 pulses per second. Would this be slow enough for the WaitForInterval() function?
Casen Davis
dkinzer
Site Admin
Posts: 3120
Joined: 03 September 2005, 13:53 PM
Location: Portland, OR

Post by dkinzer »

cdavis wrote:Would this be slow enough for the WaitForInterval() function?
I suspect that you mean WaitForInterrupt(). In any event, much depends on what needs to be done in response to the the interrupt. You could prototype the code and measure its execution time. Also, keep in mind that execution of the interrupt service code takes time away from the other things that need to be done.

The bottom line is that you need to consider all that needs to be done in your application in order to know if any particular pulse rate can be handled.
- Don Kinzer
cdavis
Posts: 9
Joined: 12 June 2006, 10:14 AM
Location: Garden Grove, CA
Contact:

Post by cdavis »

Thanks don,

It looks like I have some work to do! Thanks for all the help everyone.



Casen
Casen Davis
spamiam
Posts: 739
Joined: 13 November 2005, 6:39 AM

Post by spamiam »

cdavis wrote:Thanks don,

It looks like I have some work to do! Thanks for all the help everyone.



Casen
Obviously you piqued the interest of a number of people, especially me. Keep us apprised of you work and findings!

-Tony
Post Reply