Fast GPIO using C++ templates. Now with port I/O.

Dependencies:   mbed

Revision:
3:8d217a0bb245
Parent:
2:9c4a8c01862c
Child:
4:b8e40f2a0aac
--- a/FastIO.h	Sat May 22 23:13:55 2010 +0000
+++ b/FastIO.h	Sat May 22 23:31:39 2010 +0000
@@ -6,6 +6,18 @@
 // Super-fast DigitalOut-like class for mbed
 //   by Igor Skochinsky
 
+// includes FastOut, FastPortOut and MaskedPortOut classes
+// usage:
+//   FastOut<LED2> led2;
+//   FastPortOut<Port0, LED_MASK> ledport2;
+//   MaskedPortOut<Port0, LED_MASK> ledport3;
+//   led2 = 1;
+//   ledport2 = LED_MASK;
+//   ledport3 = LED_MASK;
+// MaskedPortOut works the same way as FastPortOut, but it pre-sets the pin mask so that write can be done in one operation
+// this makes things faster but you can't control other pins of the port, even with other classes
+
+
 // pin definitions in PinNames.h start from LPC_GPIO0_BASE for P0_0 and there are 32 pins to a port (0 to 31)
 // Thus:
 // pin = LPC_GPIO0_BASE + port * 32 + bit
@@ -60,7 +72,7 @@
 #define PINSELREG(pin)  (*(volatile uint32_t*)(LPC_PINCON_BASE + 4*(((pin) - P0_0)/16)))
 #define PINSELMASK(pin, v) (v << (((pin - P0_0)%16)*2) )
 
-// usage: FastPortOut<0> led2;
+// usage: FastPortOut<Port0, mask> led2;
 // then use the same assignment operators as with DigitalOut
 template <enum PortName port, uint32_t mask = 0xFFFFFFFF> class FastPortOut
 {
@@ -95,4 +107,40 @@
     operator int() { return read(); };
 };
 
+// usage: MaskedPortOut<Port0, mask> led2;
+// then use the same assignment operators as with DigitalOut
+template <enum PortName port, uint32_t mask = 0xFFFFFFFF> class MaskedPortOut
+{
+public:
+    MaskedPortOut()
+    {
+        // init pins selected by the mask
+        uint32_t pin = LPC_GPIO0_BASE + port * 32;
+        for ( uint32_t pinmask = mask; pinmask !=0; pinmask >>= 1 )
+        {
+            if ( pinmask & 1 )
+            {
+                // set PINSEL bits to 0b00 (GPIO)
+                PINSELREG(pin) &= ~PINSELMASK(pin, 3);
+                // set FIODIR bit to 1 (output)
+                PORTDEF(pin)->FIODIR |= PINMASK(pin);
+            }
+            pin++;
+        }
+        // set mask
+        PORTDEFPORT(port)->FIOMASK = mask;
+    }
+    void write(int value)
+    {
+        PORTDEFPORT(port)->FIOPIN = value;
+    } 
+    int read()
+    {
+        return PORTDEFPORT(port)->FIOPIN;
+    }
+    MaskedPortOut& operator= (int value) { write(value); return *this; };
+    MaskedPortOut& operator= (MaskedPortOut& rhs) { return write(rhs.read()); };
+    operator int() { return read(); };
+};
+
 #endif
\ No newline at end of file