Any way to fire multiple OC’s at the same time (e.g. different time buffers pointed at different outputs, all started at exactly the same time)?
You can have multiple but no way to sync them.
but that’s “fixed” in the next release, right?
Can you explain your application please
I want to send pulse trains to the STEP pin of multiple (3 or 4) stepper controllers to achieve coordinated moves.
I just tried sending 3 consecutive OuputCompare statements (with identical time span buffers). It looks like the delay between phase train starts varies from 75-450us but the phase shift is constant thereafter. If it were constant/predictable I could pad the earlier pulses with a delay to fudge a sync.
Is the instruction rate predictable (e.g. “if I am running one thread, in release mode, and my commands are one after the other, the second command will execute X microseconds after the first”) ?
As long as it is on C# it is not predictable but once it is internally in our native drivers then it is predictable…that is why it is fixed after the initial shift.
One of the issues is I’m assuming outputcompare is spinning up a thread to generate the pulses. When you have multiple threads running it can be tricky to get them all to sync up. I’m new to embedded programming, but on the desktop I would use a global object that all threads block on till it’s state gets set to true. ManualResetEvent is a class you can look into. The issue here too is since outputcompare is a closed library, you’ll effectively have to reinvent that class behavior to implement the syncing. And then it’s still no guarantee, but would be a lot closer. Honestly all outputcompare needs to expose is a parameter that lets you pass in your semaphore object
output compare is done naively using “hardware” interrupts and timers. There are no C# threads, so you cannot really synch multiple OC commands… You should group them in one OC command that takes care of this (OC.Set…)
So you are saying if someone were to spin up say 4 threads that wait on a global flag and they do the appropriate OC.Set to their pin, that this should theoretically get them closer together on the timing.
I misunderstood you. I was referring to using one pin with with one set statement.
[quote]I just tried sending 3 consecutive OuputCompare statements (with identical time span buffers). It looks like the delay between phase train starts varies from 75-450us but the phase shift is constant thereafter. If it were constant/predictable I could pad the earlier pulses with a delay to fudge a sync.
If you need mutiple pins, there is no current way to do it.
Obviously this is highly dependent on your requirements, but you could build one of these (or something like it)
then hook it to one of your digital pins. Then you get pure pwm without microcontroller load, and a simple digital on off switch.
Clearly the downside to this is that you can’t really adjust the timings without hardware. and you’ll have a number of breakout circuits. But if you’ve already utilized all of your PWM channels on your Fez I don’t see many other options.
The appeal of OutputCompare is that I can accomplish variable speed on the stepper while at the same time know how many steps it went. Can’t be done with either the 555 or the 74HC14 options, near as I can tell. I won’t be able to tell how many steps have gone by in between digital pin “on” and “off” commands from Panda (how far the motor has gone) nor will I be able to affect the PWM frequency (motor speed) effectively.
I’m trying to coordinate moves on 2 (3,4) axes and worry about times where the phase shift between pulse trains is on the order of a step period or three. One motor would be “ahead” of the other(s) but a step or more.
What you need to do for something like this is to update all outputs on the same timer tick. You might try using the register class to update the state of a whole port (8-bits) at a time.
I’d only be able to do that at ~10kHz, right? If I did nothing else. And the update rate (step frequency) would not necessarily be constant?
I’m fairly well resigned to the fact it won’t do exactly what I want. Trying now to see if there’s a way I can make it livable without introducing lots more hardware (or native code, however you do that).
New firmware will have parallel port that you might be able to use for that.
On the external circuits you could always split the pulse lead off and back in on an IO port on the panda. Then you can count the pulses and turn it off. I know it’s dirty, but it’s another option.
Not sure I understand what you’re suggesting. Sounds like sending pulses to a stepper drive with external hardware (e.g. 555) and also to Panda digital in? I think this suffers from the same problem as the other ideas – the managed Panda can’t keep up with the unmanaged or external pulsetrain generation.
Well I don’t think that’s been demonstrated per say (that the panda can’t keep up with the pulse generation) The issue was is that the pulse generation is controlled by software that has some variable amount of startup time and he wants to have them synced, or at least synced in a deterministic way.
Solving the problem with an external circuit and reading output status from it may help is all I’m saying. Now if this is wrong that’s ok
The fastest signal I’ve been able to count by polling, using registers, or using interrupts is ~15kHz. Been told in another thread that that’s the best I can expect (http://www.tinyclr.com/forum/2/2323/) (I know that was analog and this is digital but it seems to be similarly limited in either case).
I’m hoping to generate >20-25kHz trains, whether by Panda or by external, so I don’t see how to monitor using (managed, Panda) software. I poked at native code but pinvoke, etc. is over my head for now, unless you know of clear examples somewhere?.
I like your concise problem re-statement, “…the pulse generation is controlled by software that has some variable amount of startup time and he (I) wants to have them synced, or at least synced in a deterministic way.” Nails it.
That’s all we ask for right? A little determinism
I’m going to pickup a bread board today and start getting some components together (new to electronic tinkering at this level). I’m not sure if P/Invoke will get you what you need. But it’s worth a shot. I’ve messed with it plenty in the desktop world.