Make an LED pulse (smoothly go on and off) without any code interaction
Bean
Posts: 8,129
I needed to make an LED pulse smoothly on and off without any code interaction.
I didn't have a free COG to devote to it.
So I used a COG that wasn't using either of the hardware counters and set them to output slightly different frequencies and connected the LED between the output pins.
It worked very well.
The pulsing time is the difference between the two frequencies (1 Hz for the example code).
Bean
I didn't have a free COG to devote to it.
So I used a COG that wasn't using either of the hardware counters and set them to output slightly different frequencies and connected the LED between the output pins.
It worked very well.
The pulsing time is the difference between the two frequencies (1 Hz for the example code).
Bean
' ' Pulsing (PWM) LED without any code interaction ' Connect LED to pins P0 and P1 (don't forget resistor if needed) ' ' If you connect two LEDs back to back (connections reversed) one will get brighter as the other is getting dimmer ' ' Uses both counters ' ' By Bean, Nov 1, 2012 ' CON _clkmode = xtal1+ pll16x _xinfreq = 5_000_000 Pub Start frqa := 53687 ' 1000 Hz ctra := %00100_000 << 23 + 0 ' NCO mode, pin 0 dira[0]~~ ' Make pin 0 an output frqb := 53740 ' 1001 Hz ctrb := %00100_000 << 23 + 1 ' NCO mode, pin 1 dira[1]~~ ' Make pin 1 an output repeat ' No further actions required
Comments
For the longest time I have been attracted to a blinking led as a sign of life in microcontroller projects, but taking a whole cog to manage an led in an endless loop seemed rather wasteful.
And this really drives home the usefulness of the two timers when used together. The back to back leds can be different colors and I guess that you will have to provide an appropriate resistor to limit current.
However I think by adding two diodes to a red-green 3-wire LED you could get the same trick to do colour-fading?
Edit: I'm guessing that this is running at 1Khz? In that case I probably wouldn't see it...
Edit2: My mistake.. I somehow missed copying the repeat.
Oops. Sorry.
Technically this could be done with a single led, if you only want to use 1 pin on the prop!
I use a cog to blink a led all the time for heartbeat, but using a counter (we have so many and mostly don't use them)
Is a better standard to follow, great idea! And its a simple, oh... right... duh....
I have had more than a few situations where I really had 1 pin only for the led, and no cogs left, so I just made the heartbeat a "toggle" inbetween code that has pauses for other reasons.
This really shows how the extra hardware mostly goes unused in the prop and also shows that we have untapped uses for the propeller, even still.
Having all those counters....that don't rely on any cog or thread(other mcus) really shows that the propeller isn't just another mcu.
Nice idea. Just be aware that if you do things like that the LED will continue blinking even when your application has crashed and died. I once saw a case where an MCU application had crashed but the heartbeat LED was blinking as if everything was OK. Turned out the heart beat LED was driven my an interrupt driven from a timer which continued as normal when the main line had gone off into the weeds.
YES, You can using a single pin.
Change the code so that both counters using the same pin and connect the cathode to that pin.
Connect the anode to +3.3V and you're good to go...
The code will generate a PWM triangle wave on the output pin that goes from 50% to 100%, which may be handy for other uses too.
Bean
I've taken advantage of that to indicate what a program is doing when it goes off into the weeds. Before entering a suspect task, the blink pattern is set to a unique pattern. If you come up later and find the system locked up, you know by the pattern where to start debugging. Can be helpful in case of field deployments where you might need someone else to observe the system status. Normal operation is a sequence of flash patterns.
I use a dual counter arrangement to generate flashes at a programmable rate, color and duration. Program attached is initialized with two pins for r/g led. Then a call to
flash(whichPin, period_ms, flash_ms)
causes the selected pin to pulse low autonomously with the selected period and duration in milliseconds. There is a provision to allow the flash to transition into low power RCslow mode.
It is a nifty use of an otherwise spare counter pair. If could also be used for link-traffic indicators, because the cost of updating a value, is a single opcode, or a couple if you want to merge a system variable like a FIFO pointer, with the Pulse value.
Such 'sign of life' LEDs can be invaluable.
Expanding the idea, I recall an Infineon device, that uses a time modulation scheme, to lower the edge-count (and thus EMC).
From memory, they encoded 4 bits of data into 16 possible edge positions, and started with a known width, to Auto-cal.
Great for low data rate sensor/status links.
I think a Prop could also allow a 38KHz IR style carrier, and modulate that at ~18.063Hz/bit steps via this dF scheme, or I guess you could use the Pin OR feature to generate 38KHz carrier with one timer, and any lower gating OR modulation you wanted with the other.
Maybe this is a question for kuroneko?
Sure, sync the cogs first by init them and have them all wait for a fixed cnt number about 1 second in the future.
Now set up PHSA and PHSB with slighty higher values in each cog.
Though I think it will only be scanning in one direction and not in a KnightRider style.
thats it. that does mean you must track the cog that launched the spinner in the first place
"where are we?", or (oh no!)
"where are we locked up?".
Low frqa and frqb values generate interesting, humanoid-readable patterns. For example, the following is a modified version of Bean's code. With a bicolor r/g LED and the values as entered in the demo, it autonomously generates a repeating pattern of two red flashes followed by two green flashes with nice pauses in between. Make the second parameter 60 instead of 100 and you get alternating red and green. Make the third (phase) parameter 50 instead of 0 and you get a syncopated pattern of 3 and 2 ... 2 and 3.
Only the geeks from Parallax could find such an elegant way to deploy blinking lights and actually save processor resources as well. Congradulations.
What is the logic of these two numbers? I'm trying to see if I can get it to pulse at a different rate than 1 hz.
-Phil
Ok, but how do the numbers 53687 and 53740 correlate to the 1000 Hz and 10001 Hz listed in the code?
So 1000 * 232 / 80_000_000 = 53687.
-Phil
53.6870912 / 1Hz ok call it 54 / Hz.
So you can either add or subtract 54 to 53687 for the desired beat frequency.
Adding or subtracting 10 looks real nice at about 5 seconds blink rate.
BTW, the LED only goes between 50% and 100% brightness but this looks very nice.
Duane J
If you reverse the LED leads it will go from 0% to 50% which is how I use it.
Bean
When you say reverse are you actually meaning connecting the LED to 3.3V?
Duane J
Because the counter outputs are OR'd together the pin is high from 50% to 100% and low from 0% to 50%.
Bean
-Phi