annotate rgbled/Adafruit_NeoPixel/Adafruit_NeoPixel.cpp @ 2143:b27a3a8f9ecb

it's 2023
author drewp@bigasterisk.com
date Wed, 17 May 2023 18:52:11 -0700
parents ef4ae15f2661
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
1231
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1 /*-------------------------------------------------------------------------
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
2 Arduino library to control a wide variety of WS2811- and WS2812-based RGB
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
3 LED devices such as Adafruit FLORA RGB Smart Pixels and NeoPixel strips.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
4 Currently handles 400 and 800 KHz bitstreams on 8, 12 and 16 MHz ATmega
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
5 MCUs, with LEDs wired for RGB or GRB color order. 8 MHz MCUs provide
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
6 output on PORTB and PORTD, while 16 MHz chips can handle most output pins
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
7 (possible exception with upper PORT registers on the Arduino Mega).
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
8
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
9 Written by Phil Burgess / Paint Your Dragon for Adafruit Industries,
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
10 contributions by PJRC and other members of the open source community.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
11
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
12 Adafruit invests time and resources providing this open source code,
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
13 please support Adafruit and open-source hardware by purchasing products
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
14 from Adafruit!
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
15
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
16 -------------------------------------------------------------------------
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
17 This file is part of the Adafruit NeoPixel library.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
18
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
19 NeoPixel is free software: you can redistribute it and/or modify
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
20 it under the terms of the GNU Lesser General Public License as
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
21 published by the Free Software Foundation, either version 3 of
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
22 the License, or (at your option) any later version.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
23
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
24 NeoPixel is distributed in the hope that it will be useful,
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
25 but WITHOUT ANY WARRANTY; without even the implied warranty of
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
26 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
27 GNU Lesser General Public License for more details.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
28
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
29 You should have received a copy of the GNU Lesser General Public
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
30 License along with NeoPixel. If not, see
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
31 <http://www.gnu.org/licenses/>.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
32 -------------------------------------------------------------------------*/
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
33
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
34 #include "Adafruit_NeoPixel.h"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
35
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
36 Adafruit_NeoPixel::Adafruit_NeoPixel(uint16_t n, uint8_t p, uint8_t t) :
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
37 numLEDs(n), numBytes(n * 3), pin(p), brightness(0),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
38 pixels(NULL), type(t), endTime(0)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
39 #ifdef __AVR__
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
40 ,port(portOutputRegister(digitalPinToPort(p))),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
41 pinMask(digitalPinToBitMask(p))
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
42 #endif
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
43 {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
44 if((pixels = (uint8_t *)malloc(numBytes))) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
45 memset(pixels, 0, numBytes);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
46 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
47 if(t & NEO_GRB) { // GRB vs RGB; might add others if needed
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
48 rOffset = 1;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
49 gOffset = 0;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
50 bOffset = 2;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
51 } else if (t & NEO_BRG) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
52 rOffset = 1;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
53 gOffset = 2;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
54 bOffset = 0;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
55 } else {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
56 rOffset = 0;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
57 gOffset = 1;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
58 bOffset = 2;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
59 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
60
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
61 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
62
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
63 Adafruit_NeoPixel::~Adafruit_NeoPixel() {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
64 if(pixels) free(pixels);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
65 pinMode(pin, INPUT);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
66 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
67
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
68 void Adafruit_NeoPixel::begin(void) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
69 pinMode(pin, OUTPUT);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
70 digitalWrite(pin, LOW);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
71 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
72
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
73 void Adafruit_NeoPixel::show(void) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
74
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
75 if(!pixels) return;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
76
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
77 // Data latch = 50+ microsecond pause in the output stream. Rather than
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
78 // put a delay at the end of the function, the ending time is noted and
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
79 // the function will simply hold off (if needed) on issuing the
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
80 // subsequent round of data until the latch time has elapsed. This
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
81 // allows the mainline code to start generating the next frame of data
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
82 // rather than stalling for the latch.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
83 while(!canShow());
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
84 // endTime is a private member (rather than global var) so that mutliple
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
85 // instances on different pins can be quickly issued in succession (each
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
86 // instance doesn't delay the next).
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
87
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
88 // In order to make this code runtime-configurable to work with any pin,
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
89 // SBI/CBI instructions are eschewed in favor of full PORT writes via the
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
90 // OUT or ST instructions. It relies on two facts: that peripheral
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
91 // functions (such as PWM) take precedence on output pins, so our PORT-
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
92 // wide writes won't interfere, and that interrupts are globally disabled
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
93 // while data is being issued to the LEDs, so no other code will be
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
94 // accessing the PORT. The code takes an initial 'snapshot' of the PORT
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
95 // state, computes 'pin high' and 'pin low' values, and writes these back
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
96 // to the PORT register as needed.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
97
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
98 noInterrupts(); // Need 100% focus on instruction timing
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
99
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
100 #ifdef __AVR__
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
101
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
102 volatile uint16_t
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
103 i = numBytes; // Loop counter
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
104 volatile uint8_t
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
105 *ptr = pixels, // Pointer to next byte
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
106 b = *ptr++, // Current byte value
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
107 hi, // PORT w/output bit set high
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
108 lo; // PORT w/output bit set low
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
109
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
110 // Hand-tuned assembly code issues data to the LED drivers at a specific
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
111 // rate. There's separate code for different CPU speeds (8, 12, 16 MHz)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
112 // for both the WS2811 (400 KHz) and WS2812 (800 KHz) drivers. The
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
113 // datastream timing for the LED drivers allows a little wiggle room each
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
114 // way (listed in the datasheets), so the conditions for compiling each
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
115 // case are set up for a range of frequencies rather than just the exact
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
116 // 8, 12 or 16 MHz values, permitting use with some close-but-not-spot-on
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
117 // devices (e.g. 16.5 MHz DigiSpark). The ranges were arrived at based
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
118 // on the datasheet figures and have not been extensively tested outside
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
119 // the canonical 8/12/16 MHz speeds; there's no guarantee these will work
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
120 // close to the extremes (or possibly they could be pushed further).
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
121 // Keep in mind only one CPU speed case actually gets compiled; the
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
122 // resulting program isn't as massive as it might look from source here.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
123
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
124 // 8 MHz(ish) AVR ---------------------------------------------------------
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
125 #if (F_CPU >= 7400000UL) && (F_CPU <= 9500000UL)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
126
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
127 #ifdef NEO_KHZ400
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
128 if((type & NEO_SPDMASK) == NEO_KHZ800) { // 800 KHz bitstream
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
129 #endif
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
130
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
131 volatile uint8_t n1, n2 = 0; // First, next bits out
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
132
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
133 // Squeezing an 800 KHz stream out of an 8 MHz chip requires code
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
134 // specific to each PORT register. At present this is only written
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
135 // to work with pins on PORTD or PORTB, the most likely use case --
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
136 // this covers all the pins on the Adafruit Flora and the bulk of
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
137 // digital pins on the Arduino Pro 8 MHz (keep in mind, this code
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
138 // doesn't even get compiled for 16 MHz boards like the Uno, Mega,
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
139 // Leonardo, etc., so don't bother extending this out of hand).
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
140 // Additional PORTs could be added if you really need them, just
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
141 // duplicate the else and loop and change the PORT. Each add'l
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
142 // PORT will require about 150(ish) bytes of program space.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
143
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
144 // 10 instruction clocks per bit: HHxxxxxLLL
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
145 // OUT instructions: ^ ^ ^ (T=0,2,7)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
146
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
147 #ifdef PORTD // PORTD isn't present on ATtiny85, etc.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
148
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
149 if(port == &PORTD) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
150
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
151 hi = PORTD | pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
152 lo = PORTD & ~pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
153 n1 = lo;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
154 if(b & 0x80) n1 = hi;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
155
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
156 // Dirty trick: RJMPs proceeding to the next instruction are used
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
157 // to delay two clock cycles in one instruction word (rather than
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
158 // using two NOPs). This was necessary in order to squeeze the
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
159 // loop down to exactly 64 words -- the maximum possible for a
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
160 // relative branch.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
161
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
162 asm volatile(
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
163 "headD:" "\n\t" // Clk Pseudocode
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
164 // Bit 7:
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
165 "out %[port] , %[hi]" "\n\t" // 1 PORT = hi
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
166 "mov %[n2] , %[lo]" "\n\t" // 1 n2 = lo
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
167 "out %[port] , %[n1]" "\n\t" // 1 PORT = n1
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
168 "rjmp .+0" "\n\t" // 2 nop nop
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
169 "sbrc %[byte] , 6" "\n\t" // 1-2 if(b & 0x40)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
170 "mov %[n2] , %[hi]" "\n\t" // 0-1 n2 = hi
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
171 "out %[port] , %[lo]" "\n\t" // 1 PORT = lo
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
172 "rjmp .+0" "\n\t" // 2 nop nop
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
173 // Bit 6:
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
174 "out %[port] , %[hi]" "\n\t" // 1 PORT = hi
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
175 "mov %[n1] , %[lo]" "\n\t" // 1 n1 = lo
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
176 "out %[port] , %[n2]" "\n\t" // 1 PORT = n2
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
177 "rjmp .+0" "\n\t" // 2 nop nop
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
178 "sbrc %[byte] , 5" "\n\t" // 1-2 if(b & 0x20)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
179 "mov %[n1] , %[hi]" "\n\t" // 0-1 n1 = hi
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
180 "out %[port] , %[lo]" "\n\t" // 1 PORT = lo
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
181 "rjmp .+0" "\n\t" // 2 nop nop
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
182 // Bit 5:
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
183 "out %[port] , %[hi]" "\n\t" // 1 PORT = hi
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
184 "mov %[n2] , %[lo]" "\n\t" // 1 n2 = lo
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
185 "out %[port] , %[n1]" "\n\t" // 1 PORT = n1
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
186 "rjmp .+0" "\n\t" // 2 nop nop
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
187 "sbrc %[byte] , 4" "\n\t" // 1-2 if(b & 0x10)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
188 "mov %[n2] , %[hi]" "\n\t" // 0-1 n2 = hi
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
189 "out %[port] , %[lo]" "\n\t" // 1 PORT = lo
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
190 "rjmp .+0" "\n\t" // 2 nop nop
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
191 // Bit 4:
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
192 "out %[port] , %[hi]" "\n\t" // 1 PORT = hi
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
193 "mov %[n1] , %[lo]" "\n\t" // 1 n1 = lo
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
194 "out %[port] , %[n2]" "\n\t" // 1 PORT = n2
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
195 "rjmp .+0" "\n\t" // 2 nop nop
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
196 "sbrc %[byte] , 3" "\n\t" // 1-2 if(b & 0x08)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
197 "mov %[n1] , %[hi]" "\n\t" // 0-1 n1 = hi
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
198 "out %[port] , %[lo]" "\n\t" // 1 PORT = lo
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
199 "rjmp .+0" "\n\t" // 2 nop nop
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
200 // Bit 3:
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
201 "out %[port] , %[hi]" "\n\t" // 1 PORT = hi
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
202 "mov %[n2] , %[lo]" "\n\t" // 1 n2 = lo
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
203 "out %[port] , %[n1]" "\n\t" // 1 PORT = n1
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
204 "rjmp .+0" "\n\t" // 2 nop nop
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
205 "sbrc %[byte] , 2" "\n\t" // 1-2 if(b & 0x04)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
206 "mov %[n2] , %[hi]" "\n\t" // 0-1 n2 = hi
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
207 "out %[port] , %[lo]" "\n\t" // 1 PORT = lo
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
208 "rjmp .+0" "\n\t" // 2 nop nop
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
209 // Bit 2:
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
210 "out %[port] , %[hi]" "\n\t" // 1 PORT = hi
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
211 "mov %[n1] , %[lo]" "\n\t" // 1 n1 = lo
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
212 "out %[port] , %[n2]" "\n\t" // 1 PORT = n2
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
213 "rjmp .+0" "\n\t" // 2 nop nop
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
214 "sbrc %[byte] , 1" "\n\t" // 1-2 if(b & 0x02)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
215 "mov %[n1] , %[hi]" "\n\t" // 0-1 n1 = hi
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
216 "out %[port] , %[lo]" "\n\t" // 1 PORT = lo
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
217 "rjmp .+0" "\n\t" // 2 nop nop
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
218 // Bit 1:
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
219 "out %[port] , %[hi]" "\n\t" // 1 PORT = hi
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
220 "mov %[n2] , %[lo]" "\n\t" // 1 n2 = lo
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
221 "out %[port] , %[n1]" "\n\t" // 1 PORT = n1
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
222 "rjmp .+0" "\n\t" // 2 nop nop
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
223 "sbrc %[byte] , 0" "\n\t" // 1-2 if(b & 0x01)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
224 "mov %[n2] , %[hi]" "\n\t" // 0-1 n2 = hi
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
225 "out %[port] , %[lo]" "\n\t" // 1 PORT = lo
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
226 "sbiw %[count], 1" "\n\t" // 2 i-- (don't act on Z flag yet)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
227 // Bit 0:
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
228 "out %[port] , %[hi]" "\n\t" // 1 PORT = hi
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
229 "mov %[n1] , %[lo]" "\n\t" // 1 n1 = lo
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
230 "out %[port] , %[n2]" "\n\t" // 1 PORT = n2
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
231 "ld %[byte] , %a[ptr]+" "\n\t" // 2 b = *ptr++
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
232 "sbrc %[byte] , 7" "\n\t" // 1-2 if(b & 0x80)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
233 "mov %[n1] , %[hi]" "\n\t" // 0-1 n1 = hi
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
234 "out %[port] , %[lo]" "\n\t" // 1 PORT = lo
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
235 "brne headD" "\n" // 2 while(i) (Z flag set above)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
236 : [byte] "+r" (b),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
237 [n1] "+r" (n1),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
238 [n2] "+r" (n2),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
239 [count] "+w" (i)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
240 : [port] "I" (_SFR_IO_ADDR(PORTD)),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
241 [ptr] "e" (ptr),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
242 [hi] "r" (hi),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
243 [lo] "r" (lo));
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
244
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
245 } else if(port == &PORTB) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
246
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
247 #endif // PORTD
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
248
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
249 // Same as above, just switched to PORTB and stripped of comments.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
250 hi = PORTB | pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
251 lo = PORTB & ~pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
252 n1 = lo;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
253 if(b & 0x80) n1 = hi;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
254
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
255 asm volatile(
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
256 "headB:" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
257 "out %[port] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
258 "mov %[n2] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
259 "out %[port] , %[n1]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
260 "rjmp .+0" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
261 "sbrc %[byte] , 6" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
262 "mov %[n2] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
263 "out %[port] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
264 "rjmp .+0" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
265 "out %[port] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
266 "mov %[n1] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
267 "out %[port] , %[n2]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
268 "rjmp .+0" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
269 "sbrc %[byte] , 5" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
270 "mov %[n1] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
271 "out %[port] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
272 "rjmp .+0" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
273 "out %[port] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
274 "mov %[n2] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
275 "out %[port] , %[n1]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
276 "rjmp .+0" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
277 "sbrc %[byte] , 4" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
278 "mov %[n2] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
279 "out %[port] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
280 "rjmp .+0" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
281 "out %[port] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
282 "mov %[n1] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
283 "out %[port] , %[n2]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
284 "rjmp .+0" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
285 "sbrc %[byte] , 3" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
286 "mov %[n1] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
287 "out %[port] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
288 "rjmp .+0" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
289 "out %[port] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
290 "mov %[n2] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
291 "out %[port] , %[n1]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
292 "rjmp .+0" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
293 "sbrc %[byte] , 2" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
294 "mov %[n2] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
295 "out %[port] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
296 "rjmp .+0" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
297 "out %[port] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
298 "mov %[n1] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
299 "out %[port] , %[n2]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
300 "rjmp .+0" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
301 "sbrc %[byte] , 1" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
302 "mov %[n1] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
303 "out %[port] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
304 "rjmp .+0" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
305 "out %[port] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
306 "mov %[n2] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
307 "out %[port] , %[n1]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
308 "rjmp .+0" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
309 "sbrc %[byte] , 0" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
310 "mov %[n2] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
311 "out %[port] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
312 "sbiw %[count], 1" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
313 "out %[port] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
314 "mov %[n1] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
315 "out %[port] , %[n2]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
316 "ld %[byte] , %a[ptr]+" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
317 "sbrc %[byte] , 7" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
318 "mov %[n1] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
319 "out %[port] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
320 "brne headB" "\n"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
321 : [byte] "+r" (b), [n1] "+r" (n1), [n2] "+r" (n2), [count] "+w" (i)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
322 : [port] "I" (_SFR_IO_ADDR(PORTB)), [ptr] "e" (ptr), [hi] "r" (hi),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
323 [lo] "r" (lo));
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
324
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
325 #ifdef PORTD
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
326 } // endif PORTB
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
327 #endif
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
328
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
329 #ifdef NEO_KHZ400
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
330 } else { // end 800 KHz, do 400 KHz
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
331
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
332 // Timing is more relaxed; unrolling the inner loop for each bit is
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
333 // not necessary. Still using the peculiar RJMPs as 2X NOPs, not out
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
334 // of need but just to trim the code size down a little.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
335 // This 400-KHz-datastream-on-8-MHz-CPU code is not quite identical
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
336 // to the 800-on-16 code later -- the hi/lo timing between WS2811 and
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
337 // WS2812 is not simply a 2:1 scale!
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
338
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
339 // 20 inst. clocks per bit: HHHHxxxxxxLLLLLLLLLL
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
340 // ST instructions: ^ ^ ^ (T=0,4,10)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
341
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
342 volatile uint8_t next, bit;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
343
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
344 hi = *port | pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
345 lo = *port & ~pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
346 next = lo;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
347 bit = 8;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
348
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
349 asm volatile(
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
350 "head20:" "\n\t" // Clk Pseudocode (T = 0)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
351 "st %a[port], %[hi]" "\n\t" // 2 PORT = hi (T = 2)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
352 "sbrc %[byte] , 7" "\n\t" // 1-2 if(b & 128)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
353 "mov %[next], %[hi]" "\n\t" // 0-1 next = hi (T = 4)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
354 "st %a[port], %[next]" "\n\t" // 2 PORT = next (T = 6)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
355 "mov %[next] , %[lo]" "\n\t" // 1 next = lo (T = 7)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
356 "dec %[bit]" "\n\t" // 1 bit-- (T = 8)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
357 "breq nextbyte20" "\n\t" // 1-2 if(bit == 0)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
358 "rol %[byte]" "\n\t" // 1 b <<= 1 (T = 10)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
359 "st %a[port], %[lo]" "\n\t" // 2 PORT = lo (T = 12)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
360 "rjmp .+0" "\n\t" // 2 nop nop (T = 14)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
361 "rjmp .+0" "\n\t" // 2 nop nop (T = 16)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
362 "rjmp .+0" "\n\t" // 2 nop nop (T = 18)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
363 "rjmp head20" "\n\t" // 2 -> head20 (next bit out)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
364 "nextbyte20:" "\n\t" // (T = 10)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
365 "st %a[port], %[lo]" "\n\t" // 2 PORT = lo (T = 12)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
366 "nop" "\n\t" // 1 nop (T = 13)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
367 "ldi %[bit] , 8" "\n\t" // 1 bit = 8 (T = 14)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
368 "ld %[byte] , %a[ptr]+" "\n\t" // 2 b = *ptr++ (T = 16)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
369 "sbiw %[count], 1" "\n\t" // 2 i-- (T = 18)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
370 "brne head20" "\n" // 2 if(i != 0) -> (next byte)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
371 : [port] "+e" (port),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
372 [byte] "+r" (b),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
373 [bit] "+r" (bit),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
374 [next] "+r" (next),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
375 [count] "+w" (i)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
376 : [hi] "r" (hi),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
377 [lo] "r" (lo),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
378 [ptr] "e" (ptr));
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
379 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
380 #endif
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
381
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
382 // 12 MHz(ish) AVR --------------------------------------------------------
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
383 #elif (F_CPU >= 11100000UL) && (F_CPU <= 14300000UL)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
384
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
385 #ifdef NEO_KHZ400
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
386 if((type & NEO_SPDMASK) == NEO_KHZ800) { // 800 KHz bitstream
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
387 #endif
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
388
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
389 // In the 12 MHz case, an optimized 800 KHz datastream (no dead time
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
390 // between bytes) requires a PORT-specific loop similar to the 8 MHz
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
391 // code (but a little more relaxed in this case).
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
392
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
393 // 15 instruction clocks per bit: HHHHxxxxxxLLLLL
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
394 // OUT instructions: ^ ^ ^ (T=0,4,10)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
395
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
396 volatile uint8_t next;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
397
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
398 #ifdef PORTD
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
399
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
400 if(port == &PORTD) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
401
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
402 hi = PORTD | pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
403 lo = PORTD & ~pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
404 next = lo;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
405 if(b & 0x80) next = hi;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
406
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
407 // Don't "optimize" the OUT calls into the bitTime subroutine;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
408 // we're exploiting the RCALL and RET as 3- and 4-cycle NOPs!
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
409 asm volatile(
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
410 "headD:" "\n\t" // (T = 0)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
411 "out %[port], %[hi]" "\n\t" // (T = 1)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
412 "rcall bitTimeD" "\n\t" // Bit 7 (T = 15)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
413 "out %[port], %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
414 "rcall bitTimeD" "\n\t" // Bit 6
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
415 "out %[port], %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
416 "rcall bitTimeD" "\n\t" // Bit 5
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
417 "out %[port], %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
418 "rcall bitTimeD" "\n\t" // Bit 4
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
419 "out %[port], %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
420 "rcall bitTimeD" "\n\t" // Bit 3
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
421 "out %[port], %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
422 "rcall bitTimeD" "\n\t" // Bit 2
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
423 "out %[port], %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
424 "rcall bitTimeD" "\n\t" // Bit 1
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
425 // Bit 0:
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
426 "out %[port] , %[hi]" "\n\t" // 1 PORT = hi (T = 1)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
427 "rjmp .+0" "\n\t" // 2 nop nop (T = 3)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
428 "ld %[byte] , %a[ptr]+" "\n\t" // 2 b = *ptr++ (T = 5)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
429 "out %[port] , %[next]" "\n\t" // 1 PORT = next (T = 6)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
430 "mov %[next] , %[lo]" "\n\t" // 1 next = lo (T = 7)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
431 "sbrc %[byte] , 7" "\n\t" // 1-2 if(b & 0x80) (T = 8)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
432 "mov %[next] , %[hi]" "\n\t" // 0-1 next = hi (T = 9)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
433 "nop" "\n\t" // 1 (T = 10)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
434 "out %[port] , %[lo]" "\n\t" // 1 PORT = lo (T = 11)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
435 "sbiw %[count], 1" "\n\t" // 2 i-- (T = 13)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
436 "brne headD" "\n\t" // 2 if(i != 0) -> (next byte)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
437 "rjmp doneD" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
438 "bitTimeD:" "\n\t" // nop nop nop (T = 4)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
439 "out %[port], %[next]" "\n\t" // 1 PORT = next (T = 5)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
440 "mov %[next], %[lo]" "\n\t" // 1 next = lo (T = 6)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
441 "rol %[byte]" "\n\t" // 1 b <<= 1 (T = 7)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
442 "sbrc %[byte], 7" "\n\t" // 1-2 if(b & 0x80) (T = 8)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
443 "mov %[next], %[hi]" "\n\t" // 0-1 next = hi (T = 9)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
444 "nop" "\n\t" // 1 (T = 10)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
445 "out %[port], %[lo]" "\n\t" // 1 PORT = lo (T = 11)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
446 "ret" "\n\t" // 4 nop nop nop nop (T = 15)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
447 "doneD:" "\n"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
448 : [byte] "+r" (b),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
449 [next] "+r" (next),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
450 [count] "+w" (i)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
451 : [port] "I" (_SFR_IO_ADDR(PORTD)),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
452 [ptr] "e" (ptr),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
453 [hi] "r" (hi),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
454 [lo] "r" (lo));
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
455
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
456 } else if(port == &PORTB) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
457
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
458 #endif // PORTD
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
459
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
460 hi = PORTB | pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
461 lo = PORTB & ~pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
462 next = lo;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
463 if(b & 0x80) next = hi;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
464
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
465 // Same as above, just set for PORTB & stripped of comments
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
466 asm volatile(
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
467 "headB:" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
468 "out %[port], %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
469 "rcall bitTimeB" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
470 "out %[port], %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
471 "rcall bitTimeB" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
472 "out %[port], %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
473 "rcall bitTimeB" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
474 "out %[port], %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
475 "rcall bitTimeB" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
476 "out %[port], %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
477 "rcall bitTimeB" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
478 "out %[port], %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
479 "rcall bitTimeB" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
480 "out %[port], %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
481 "rcall bitTimeB" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
482 "out %[port] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
483 "rjmp .+0" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
484 "ld %[byte] , %a[ptr]+" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
485 "out %[port] , %[next]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
486 "mov %[next] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
487 "sbrc %[byte] , 7" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
488 "mov %[next] , %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
489 "nop" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
490 "out %[port] , %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
491 "sbiw %[count], 1" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
492 "brne headB" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
493 "rjmp doneB" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
494 "bitTimeB:" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
495 "out %[port], %[next]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
496 "mov %[next], %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
497 "rol %[byte]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
498 "sbrc %[byte], 7" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
499 "mov %[next], %[hi]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
500 "nop" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
501 "out %[port], %[lo]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
502 "ret" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
503 "doneB:" "\n"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
504 : [byte] "+r" (b), [next] "+r" (next), [count] "+w" (i)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
505 : [port] "I" (_SFR_IO_ADDR(PORTB)), [ptr] "e" (ptr), [hi] "r" (hi),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
506 [lo] "r" (lo));
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
507
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
508 #ifdef PORTD
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
509 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
510 #endif
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
511
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
512 #ifdef NEO_KHZ400
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
513 } else { // 400 KHz
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
514
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
515 // 30 instruction clocks per bit: HHHHHHxxxxxxxxxLLLLLLLLLLLLLLL
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
516 // ST instructions: ^ ^ ^ (T=0,6,15)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
517
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
518 volatile uint8_t next, bit;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
519
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
520 hi = *port | pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
521 lo = *port & ~pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
522 next = lo;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
523 bit = 8;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
524
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
525 asm volatile(
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
526 "head30:" "\n\t" // Clk Pseudocode (T = 0)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
527 "st %a[port], %[hi]" "\n\t" // 2 PORT = hi (T = 2)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
528 "sbrc %[byte] , 7" "\n\t" // 1-2 if(b & 128)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
529 "mov %[next], %[hi]" "\n\t" // 0-1 next = hi (T = 4)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
530 "rjmp .+0" "\n\t" // 2 nop nop (T = 6)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
531 "st %a[port], %[next]" "\n\t" // 2 PORT = next (T = 8)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
532 "rjmp .+0" "\n\t" // 2 nop nop (T = 10)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
533 "rjmp .+0" "\n\t" // 2 nop nop (T = 12)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
534 "rjmp .+0" "\n\t" // 2 nop nop (T = 14)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
535 "nop" "\n\t" // 1 nop (T = 15)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
536 "st %a[port], %[lo]" "\n\t" // 2 PORT = lo (T = 17)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
537 "rjmp .+0" "\n\t" // 2 nop nop (T = 19)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
538 "dec %[bit]" "\n\t" // 1 bit-- (T = 20)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
539 "breq nextbyte30" "\n\t" // 1-2 if(bit == 0)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
540 "rol %[byte]" "\n\t" // 1 b <<= 1 (T = 22)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
541 "rjmp .+0" "\n\t" // 2 nop nop (T = 24)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
542 "rjmp .+0" "\n\t" // 2 nop nop (T = 26)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
543 "rjmp .+0" "\n\t" // 2 nop nop (T = 28)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
544 "rjmp head30" "\n\t" // 2 -> head30 (next bit out)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
545 "nextbyte30:" "\n\t" // (T = 22)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
546 "nop" "\n\t" // 1 nop (T = 23)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
547 "ldi %[bit] , 8" "\n\t" // 1 bit = 8 (T = 24)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
548 "ld %[byte] , %a[ptr]+" "\n\t" // 2 b = *ptr++ (T = 26)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
549 "sbiw %[count], 1" "\n\t" // 2 i-- (T = 28)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
550 "brne head30" "\n" // 1-2 if(i != 0) -> (next byte)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
551 : [port] "+e" (port),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
552 [byte] "+r" (b),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
553 [bit] "+r" (bit),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
554 [next] "+r" (next),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
555 [count] "+w" (i)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
556 : [hi] "r" (hi),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
557 [lo] "r" (lo),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
558 [ptr] "e" (ptr));
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
559 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
560 #endif
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
561
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
562 // 16 MHz(ish) AVR --------------------------------------------------------
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
563 #elif (F_CPU >= 15400000UL) && (F_CPU <= 19000000L)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
564
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
565 #ifdef NEO_KHZ400
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
566 if((type & NEO_SPDMASK) == NEO_KHZ800) { // 800 KHz bitstream
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
567 #endif
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
568
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
569 // WS2811 and WS2812 have different hi/lo duty cycles; this is
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
570 // similar but NOT an exact copy of the prior 400-on-8 code.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
571
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
572 // 20 inst. clocks per bit: HHHHHxxxxxxxxLLLLLLL
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
573 // ST instructions: ^ ^ ^ (T=0,5,13)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
574
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
575 volatile uint8_t next, bit;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
576
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
577 hi = *port | pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
578 lo = *port & ~pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
579 next = lo;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
580 bit = 8;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
581
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
582 asm volatile(
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
583 "head20:" "\n\t" // Clk Pseudocode (T = 0)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
584 "st %a[port], %[hi]" "\n\t" // 2 PORT = hi (T = 2)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
585 "sbrc %[byte], 7" "\n\t" // 1-2 if(b & 128)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
586 "mov %[next], %[hi]" "\n\t" // 0-1 next = hi (T = 4)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
587 "dec %[bit]" "\n\t" // 1 bit-- (T = 5)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
588 "st %a[port], %[next]" "\n\t" // 2 PORT = next (T = 7)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
589 "mov %[next] , %[lo]" "\n\t" // 1 next = lo (T = 8)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
590 "breq nextbyte20" "\n\t" // 1-2 if(bit == 0) (from dec above)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
591 "rol %[byte]" "\n\t" // 1 b <<= 1 (T = 10)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
592 "rjmp .+0" "\n\t" // 2 nop nop (T = 12)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
593 "nop" "\n\t" // 1 nop (T = 13)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
594 "st %a[port], %[lo]" "\n\t" // 2 PORT = lo (T = 15)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
595 "nop" "\n\t" // 1 nop (T = 16)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
596 "rjmp .+0" "\n\t" // 2 nop nop (T = 18)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
597 "rjmp head20" "\n\t" // 2 -> head20 (next bit out)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
598 "nextbyte20:" "\n\t" // (T = 10)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
599 "ldi %[bit] , 8" "\n\t" // 1 bit = 8 (T = 11)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
600 "ld %[byte] , %a[ptr]+" "\n\t" // 2 b = *ptr++ (T = 13)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
601 "st %a[port], %[lo]" "\n\t" // 2 PORT = lo (T = 15)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
602 "nop" "\n\t" // 1 nop (T = 16)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
603 "sbiw %[count], 1" "\n\t" // 2 i-- (T = 18)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
604 "brne head20" "\n" // 2 if(i != 0) -> (next byte)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
605 : [port] "+e" (port),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
606 [byte] "+r" (b),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
607 [bit] "+r" (bit),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
608 [next] "+r" (next),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
609 [count] "+w" (i)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
610 : [ptr] "e" (ptr),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
611 [hi] "r" (hi),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
612 [lo] "r" (lo));
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
613
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
614 #ifdef NEO_KHZ400
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
615 } else { // 400 KHz
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
616
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
617 // The 400 KHz clock on 16 MHz MCU is the most 'relaxed' version.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
618
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
619 // 40 inst. clocks per bit: HHHHHHHHxxxxxxxxxxxxLLLLLLLLLLLLLLLLLLLL
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
620 // ST instructions: ^ ^ ^ (T=0,8,20)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
621
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
622 volatile uint8_t next, bit;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
623
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
624 hi = *port | pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
625 lo = *port & ~pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
626 next = lo;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
627 bit = 8;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
628
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
629 asm volatile(
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
630 "head40:" "\n\t" // Clk Pseudocode (T = 0)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
631 "st %a[port], %[hi]" "\n\t" // 2 PORT = hi (T = 2)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
632 "sbrc %[byte] , 7" "\n\t" // 1-2 if(b & 128)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
633 "mov %[next] , %[hi]" "\n\t" // 0-1 next = hi (T = 4)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
634 "rjmp .+0" "\n\t" // 2 nop nop (T = 6)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
635 "rjmp .+0" "\n\t" // 2 nop nop (T = 8)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
636 "st %a[port], %[next]" "\n\t" // 2 PORT = next (T = 10)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
637 "rjmp .+0" "\n\t" // 2 nop nop (T = 12)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
638 "rjmp .+0" "\n\t" // 2 nop nop (T = 14)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
639 "rjmp .+0" "\n\t" // 2 nop nop (T = 16)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
640 "rjmp .+0" "\n\t" // 2 nop nop (T = 18)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
641 "rjmp .+0" "\n\t" // 2 nop nop (T = 20)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
642 "st %a[port], %[lo]" "\n\t" // 2 PORT = lo (T = 22)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
643 "nop" "\n\t" // 1 nop (T = 23)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
644 "mov %[next] , %[lo]" "\n\t" // 1 next = lo (T = 24)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
645 "dec %[bit]" "\n\t" // 1 bit-- (T = 25)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
646 "breq nextbyte40" "\n\t" // 1-2 if(bit == 0)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
647 "rol %[byte]" "\n\t" // 1 b <<= 1 (T = 27)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
648 "nop" "\n\t" // 1 nop (T = 28)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
649 "rjmp .+0" "\n\t" // 2 nop nop (T = 30)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
650 "rjmp .+0" "\n\t" // 2 nop nop (T = 32)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
651 "rjmp .+0" "\n\t" // 2 nop nop (T = 34)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
652 "rjmp .+0" "\n\t" // 2 nop nop (T = 36)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
653 "rjmp .+0" "\n\t" // 2 nop nop (T = 38)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
654 "rjmp head40" "\n\t" // 2 -> head40 (next bit out)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
655 "nextbyte40:" "\n\t" // (T = 27)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
656 "ldi %[bit] , 8" "\n\t" // 1 bit = 8 (T = 28)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
657 "ld %[byte] , %a[ptr]+" "\n\t" // 2 b = *ptr++ (T = 30)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
658 "rjmp .+0" "\n\t" // 2 nop nop (T = 32)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
659 "st %a[port], %[lo]" "\n\t" // 2 PORT = lo (T = 34)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
660 "rjmp .+0" "\n\t" // 2 nop nop (T = 36)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
661 "sbiw %[count], 1" "\n\t" // 2 i-- (T = 38)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
662 "brne head40" "\n" // 1-2 if(i != 0) -> (next byte)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
663 : [port] "+e" (port),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
664 [byte] "+r" (b),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
665 [bit] "+r" (bit),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
666 [next] "+r" (next),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
667 [count] "+w" (i)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
668 : [ptr] "e" (ptr),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
669 [hi] "r" (hi),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
670 [lo] "r" (lo));
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
671 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
672 #endif
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
673
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
674 #else
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
675 #error "CPU SPEED NOT SUPPORTED"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
676 #endif
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
677
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
678 #elif defined(__arm__)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
679
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
680 #if defined(__MK20DX128__) || defined(__MK20DX256__) // Teensy 3.0 & 3.1
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
681 #define CYCLES_800_T0H (F_CPU / 4000000)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
682 #define CYCLES_800_T1H (F_CPU / 1250000)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
683 #define CYCLES_800 (F_CPU / 800000)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
684 #define CYCLES_400_T0H (F_CPU / 2000000)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
685 #define CYCLES_400_T1H (F_CPU / 833333)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
686 #define CYCLES_400 (F_CPU / 400000)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
687
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
688 uint8_t *p = pixels,
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
689 *end = p + numBytes, pix, mask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
690 volatile uint8_t *set = portSetRegister(pin),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
691 *clr = portClearRegister(pin);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
692 uint32_t cyc;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
693
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
694 ARM_DEMCR |= ARM_DEMCR_TRCENA;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
695 ARM_DWT_CTRL |= ARM_DWT_CTRL_CYCCNTENA;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
696
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
697 #ifdef NEO_KHZ400
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
698 if((type & NEO_SPDMASK) == NEO_KHZ800) { // 800 KHz bitstream
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
699 #endif
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
700 cyc = ARM_DWT_CYCCNT + CYCLES_800;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
701 while(p < end) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
702 pix = *p++;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
703 for(mask = 0x80; mask; mask >>= 1) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
704 while(ARM_DWT_CYCCNT - cyc < CYCLES_800);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
705 cyc = ARM_DWT_CYCCNT;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
706 *set = 1;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
707 if(pix & mask) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
708 while(ARM_DWT_CYCCNT - cyc < CYCLES_800_T1H);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
709 } else {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
710 while(ARM_DWT_CYCCNT - cyc < CYCLES_800_T0H);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
711 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
712 *clr = 1;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
713 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
714 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
715 while(ARM_DWT_CYCCNT - cyc < CYCLES_800);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
716 #ifdef NEO_KHZ400
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
717 } else { // 400 kHz bitstream
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
718 cyc = ARM_DWT_CYCCNT + CYCLES_400;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
719 while(p < end) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
720 pix = *p++;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
721 for(mask = 0x80; mask; mask >>= 1) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
722 while(ARM_DWT_CYCCNT - cyc < CYCLES_400);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
723 cyc = ARM_DWT_CYCCNT;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
724 *set = 1;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
725 if(pix & mask) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
726 while(ARM_DWT_CYCCNT - cyc < CYCLES_400_T1H);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
727 } else {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
728 while(ARM_DWT_CYCCNT - cyc < CYCLES_400_T0H);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
729 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
730 *clr = 1;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
731 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
732 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
733 while(ARM_DWT_CYCCNT - cyc < CYCLES_400);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
734 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
735 #endif
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
736
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
737
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
738
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
739
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
740
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
741 #elif defined(__MKL26Z64__) // Teensy-LC
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
742
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
743 #if F_CPU == 48000000
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
744 uint8_t *p = pixels,
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
745 pix, count, dly,
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
746 bitmask = digitalPinToBitMask(pin);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
747 volatile uint8_t *reg = portSetRegister(pin);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
748 uint32_t num = numBytes;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
749 asm volatile(
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
750 "L%=_begin:" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
751 "ldrb %[pix], [%[p], #0]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
752 "lsl %[pix], #24" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
753 "movs %[count], #7" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
754 "L%=_loop:" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
755 "lsl %[pix], #1" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
756 "bcs L%=_loop_one" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
757 "L%=_loop_zero:"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
758 "strb %[bitmask], [%[reg], #0]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
759 "movs %[dly], #4" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
760 "L%=_loop_delay_T0H:" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
761 "sub %[dly], #1" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
762 "bne L%=_loop_delay_T0H" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
763 "strb %[bitmask], [%[reg], #4]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
764 "movs %[dly], #13" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
765 "L%=_loop_delay_T0L:" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
766 "sub %[dly], #1" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
767 "bne L%=_loop_delay_T0L" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
768 "b L%=_next" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
769 "L%=_loop_one:"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
770 "strb %[bitmask], [%[reg], #0]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
771 "movs %[dly], #13" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
772 "L%=_loop_delay_T1H:" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
773 "sub %[dly], #1" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
774 "bne L%=_loop_delay_T1H" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
775 "strb %[bitmask], [%[reg], #4]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
776 "movs %[dly], #4" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
777 "L%=_loop_delay_T1L:" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
778 "sub %[dly], #1" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
779 "bne L%=_loop_delay_T1L" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
780 "nop" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
781 "L%=_next:" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
782 "sub %[count], #1" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
783 "bne L%=_loop" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
784 "lsl %[pix], #1" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
785 "bcs L%=_last_one" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
786 "L%=_last_zero:"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
787 "strb %[bitmask], [%[reg], #0]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
788 "movs %[dly], #4" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
789 "L%=_last_delay_T0H:" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
790 "sub %[dly], #1" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
791 "bne L%=_last_delay_T0H" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
792 "strb %[bitmask], [%[reg], #4]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
793 "movs %[dly], #10" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
794 "L%=_last_delay_T0L:" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
795 "sub %[dly], #1" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
796 "bne L%=_last_delay_T0L" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
797 "b L%=_repeat" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
798 "L%=_last_one:"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
799 "strb %[bitmask], [%[reg], #0]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
800 "movs %[dly], #13" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
801 "L%=_last_delay_T1H:" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
802 "sub %[dly], #1" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
803 "bne L%=_last_delay_T1H" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
804 "strb %[bitmask], [%[reg], #4]" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
805 "movs %[dly], #1" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
806 "L%=_last_delay_T1L:" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
807 "sub %[dly], #1" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
808 "bne L%=_last_delay_T1L" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
809 "nop" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
810 "L%=_repeat:" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
811 "add %[p], #1" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
812 "sub %[num], #1" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
813 "bne L%=_begin" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
814 "L%=_done:" "\n\t"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
815 : [p] "+r" (p),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
816 [pix] "=&r" (pix),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
817 [count] "=&r" (count),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
818 [dly] "=&r" (dly),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
819 [num] "+r" (num)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
820 : [bitmask] "r" (bitmask),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
821 [reg] "r" (reg)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
822 );
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
823 #else
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
824 #error "Sorry, only 48 MHz is supported, please set Tools > CPU Speed to 48 MHz"
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
825 #endif
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
826
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
827
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
828 #else // Arduino Due
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
829
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
830 #define SCALE VARIANT_MCK / 2UL / 1000000UL
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
831 #define INST (2UL * F_CPU / VARIANT_MCK)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
832 #define TIME_800_0 ((int)(0.40 * SCALE + 0.5) - (5 * INST))
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
833 #define TIME_800_1 ((int)(0.80 * SCALE + 0.5) - (5 * INST))
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
834 #define PERIOD_800 ((int)(1.25 * SCALE + 0.5) - (5 * INST))
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
835 #define TIME_400_0 ((int)(0.50 * SCALE + 0.5) - (5 * INST))
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
836 #define TIME_400_1 ((int)(1.20 * SCALE + 0.5) - (5 * INST))
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
837 #define PERIOD_400 ((int)(2.50 * SCALE + 0.5) - (5 * INST))
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
838
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
839 int pinMask, time0, time1, period, t;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
840 Pio *port;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
841 volatile WoReg *portSet, *portClear, *timeValue, *timeReset;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
842 uint8_t *p, *end, pix, mask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
843
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
844 pmc_set_writeprotect(false);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
845 pmc_enable_periph_clk((uint32_t)TC3_IRQn);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
846 TC_Configure(TC1, 0,
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
847 TC_CMR_WAVE | TC_CMR_WAVSEL_UP | TC_CMR_TCCLKS_TIMER_CLOCK1);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
848 TC_Start(TC1, 0);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
849
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
850 pinMask = g_APinDescription[pin].ulPin; // Don't 'optimize' these into
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
851 port = g_APinDescription[pin].pPort; // declarations above. Want to
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
852 portSet = &(port->PIO_SODR); // burn a few cycles after
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
853 portClear = &(port->PIO_CODR); // starting timer to minimize
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
854 timeValue = &(TC1->TC_CHANNEL[0].TC_CV); // the initial 'while'.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
855 timeReset = &(TC1->TC_CHANNEL[0].TC_CCR);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
856 p = pixels;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
857 end = p + numBytes;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
858 pix = *p++;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
859 mask = 0x80;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
860
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
861 #ifdef NEO_KHZ400
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
862 if((type & NEO_SPDMASK) == NEO_KHZ800) { // 800 KHz bitstream
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
863 #endif
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
864 time0 = TIME_800_0;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
865 time1 = TIME_800_1;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
866 period = PERIOD_800;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
867 #ifdef NEO_KHZ400
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
868 } else { // 400 KHz bitstream
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
869 time0 = TIME_400_0;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
870 time1 = TIME_400_1;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
871 period = PERIOD_400;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
872 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
873 #endif
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
874
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
875 for(t = time0;; t = time0) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
876 if(pix & mask) t = time1;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
877 while(*timeValue < period);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
878 *portSet = pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
879 *timeReset = TC_CCR_CLKEN | TC_CCR_SWTRG;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
880 while(*timeValue < t);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
881 *portClear = pinMask;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
882 if(!(mask >>= 1)) { // This 'inside-out' loop logic utilizes
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
883 if(p >= end) break; // idle time to minimize inter-byte delays.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
884 pix = *p++;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
885 mask = 0x80;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
886 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
887 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
888 while(*timeValue < period); // Wait for last bit
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
889 TC_Stop(TC1, 0);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
890
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
891 #endif // end Arduino Due
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
892
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
893 #endif // end Architecture select
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
894
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
895 interrupts();
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
896 endTime = micros(); // Save EOD time for latch on next call
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
897 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
898
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
899 // Set the output pin number
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
900 void Adafruit_NeoPixel::setPin(uint8_t p) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
901 pinMode(pin, INPUT);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
902 pin = p;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
903 pinMode(p, OUTPUT);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
904 digitalWrite(p, LOW);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
905 #ifdef __AVR__
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
906 port = portOutputRegister(digitalPinToPort(p));
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
907 pinMask = digitalPinToBitMask(p);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
908 #endif
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
909 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
910
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
911 // Set pixel color from separate R,G,B components:
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
912 void Adafruit_NeoPixel::setPixelColor(
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
913 uint16_t n, uint8_t r, uint8_t g, uint8_t b) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
914 if(n < numLEDs) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
915 if(brightness) { // See notes in setBrightness()
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
916 r = (r * brightness) >> 8;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
917 g = (g * brightness) >> 8;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
918 b = (b * brightness) >> 8;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
919 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
920 uint8_t *p = &pixels[n * 3];
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
921 p[rOffset] = r;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
922 p[gOffset] = g;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
923 p[bOffset] = b;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
924 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
925 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
926
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
927 // Set pixel color from 'packed' 32-bit RGB color:
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
928 void Adafruit_NeoPixel::setPixelColor(uint16_t n, uint32_t c) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
929 if(n < numLEDs) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
930 uint8_t
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
931 r = (uint8_t)(c >> 16),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
932 g = (uint8_t)(c >> 8),
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
933 b = (uint8_t)c;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
934 if(brightness) { // See notes in setBrightness()
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
935 r = (r * brightness) >> 8;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
936 g = (g * brightness) >> 8;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
937 b = (b * brightness) >> 8;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
938 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
939 uint8_t *p = &pixels[n * 3];
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
940 p[rOffset] = r;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
941 p[gOffset] = g;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
942 p[bOffset] = b;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
943 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
944 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
945
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
946 // Convert separate R,G,B into packed 32-bit RGB color.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
947 // Packed format is always RGB, regardless of LED strand color order.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
948 uint32_t Adafruit_NeoPixel::Color(uint8_t r, uint8_t g, uint8_t b) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
949 return ((uint32_t)r << 16) | ((uint32_t)g << 8) | b;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
950 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
951
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
952 // Query color from previously-set pixel (returns packed 32-bit RGB value)
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
953 uint32_t Adafruit_NeoPixel::getPixelColor(uint16_t n) const {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
954 if(n >= numLEDs) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
955 // Out of bounds, return no color.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
956 return 0;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
957 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
958 uint8_t *p = &pixels[n * 3];
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
959 uint32_t c = ((uint32_t)p[rOffset] << 16) |
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
960 ((uint32_t)p[gOffset] << 8) |
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
961 (uint32_t)p[bOffset];
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
962 // Adjust this back up to the true color, as setting a pixel color will
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
963 // scale it back down again.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
964 if(brightness) { // See notes in setBrightness()
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
965 //Cast the color to a byte array
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
966 uint8_t * c_ptr =reinterpret_cast<uint8_t*>(&c);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
967 c_ptr[0] = (c_ptr[0] << 8)/brightness;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
968 c_ptr[1] = (c_ptr[1] << 8)/brightness;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
969 c_ptr[2] = (c_ptr[2] << 8)/brightness;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
970 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
971 return c; // Pixel # is out of bounds
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
972 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
973
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
974 // Returns pointer to pixels[] array. Pixel data is stored in device-
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
975 // native format and is not translated here. Application will need to be
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
976 // aware whether pixels are RGB vs. GRB and handle colors appropriately.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
977 uint8_t *Adafruit_NeoPixel::getPixels(void) const {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
978 return pixels;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
979 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
980
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
981 uint16_t Adafruit_NeoPixel::numPixels(void) const {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
982 return numLEDs;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
983 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
984
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
985 // Adjust output brightness; 0=darkest (off), 255=brightest. This does
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
986 // NOT immediately affect what's currently displayed on the LEDs. The
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
987 // next call to show() will refresh the LEDs at this level. However,
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
988 // this process is potentially "lossy," especially when increasing
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
989 // brightness. The tight timing in the WS2811/WS2812 code means there
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
990 // aren't enough free cycles to perform this scaling on the fly as data
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
991 // is issued. So we make a pass through the existing color data in RAM
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
992 // and scale it (subsequent graphics commands also work at this
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
993 // brightness level). If there's a significant step up in brightness,
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
994 // the limited number of steps (quantization) in the old data will be
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
995 // quite visible in the re-scaled version. For a non-destructive
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
996 // change, you'll need to re-render the full strip data. C'est la vie.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
997 void Adafruit_NeoPixel::setBrightness(uint8_t b) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
998 // Stored brightness value is different than what's passed.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
999 // This simplifies the actual scaling math later, allowing a fast
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1000 // 8x8-bit multiply and taking the MSB. 'brightness' is a uint8_t,
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1001 // adding 1 here may (intentionally) roll over...so 0 = max brightness
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1002 // (color values are interpreted literally; no scaling), 1 = min
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1003 // brightness (off), 255 = just below max brightness.
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1004 uint8_t newBrightness = b + 1;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1005 if(newBrightness != brightness) { // Compare against prior value
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1006 // Brightness has changed -- re-scale existing data in RAM
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1007 uint8_t c,
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1008 *ptr = pixels,
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1009 oldBrightness = brightness - 1; // De-wrap old brightness value
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1010 uint16_t scale;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1011 if(oldBrightness == 0) scale = 0; // Avoid /0
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1012 else if(b == 255) scale = 65535 / oldBrightness;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1013 else scale = (((uint16_t)newBrightness << 8) - 1) / oldBrightness;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1014 for(uint16_t i=0; i<numBytes; i++) {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1015 c = *ptr;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1016 *ptr++ = (c * scale) >> 8;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1017 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1018 brightness = newBrightness;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1019 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1020 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1021
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1022 //Return the brightness value
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1023 uint8_t Adafruit_NeoPixel::getBrightness(void) const {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1024 return brightness - 1;
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1025 }
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1026
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1027 void Adafruit_NeoPixel::clear() {
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1028 memset(pixels, 0, numBytes);
ef4ae15f2661 copy in rgb led program for arduino
Drew Perttula <drewp@bigasterisk.com>
parents:
diff changeset
1029 }