From 90556d1ddd0c160de84a9c3682245663c488d1c9 Mon Sep 17 00:00:00 2001 From: Donald Linton Date: Wed, 8 Jan 2020 07:02:36 -0500 Subject: [PATCH 1/4] put library in development mode to allow example editing --- .development | 1 + 1 file changed, 1 insertion(+) create mode 100644 .development diff --git a/.development b/.development new file mode 100644 index 0000000..792d600 --- /dev/null +++ b/.development @@ -0,0 +1 @@ +# From 424425514b98a472bca9cea9b55000f937f59a1d Mon Sep 17 00:00:00 2001 From: Donald Linton Date: Wed, 8 Jan 2020 16:54:46 -0500 Subject: [PATCH 2/4] Add virtual wrapper classes --- examples/Benchmark/Benchmark.ino | 4 +- examples/BenchmarkI/BenchmarkI.ino | 316 +++++++++++++++++++++++++++++ examples/BenchmarkV/BenchmarkV.ino | 205 +++++++++++++++++++ src/Hardware/AVR/GPIO.h | 10 + src/Hardware/SAM/GPIO.h | 8 + src/IGPIO.h | 154 ++++++++++++++ 6 files changed, 696 insertions(+), 1 deletion(-) create mode 100644 examples/BenchmarkI/BenchmarkI.ino create mode 100644 examples/BenchmarkV/BenchmarkV.ino create mode 100644 src/IGPIO.h diff --git a/examples/Benchmark/Benchmark.ino b/examples/Benchmark/Benchmark.ino index db2679a..8b9e14b 100644 --- a/examples/Benchmark/Benchmark.ino +++ b/examples/Benchmark/Benchmark.ino @@ -1,6 +1,7 @@ -#include "GPIO.h" +#include "IGPIO.h" #include "benchmark.h" + GPIO button; GPIO led; #define BUTTON_PIN 12 @@ -163,4 +164,5 @@ void loop() Serial.println(); delay(2000); + while(true) ; } diff --git a/examples/BenchmarkI/BenchmarkI.ino b/examples/BenchmarkI/BenchmarkI.ino new file mode 100644 index 0000000..ed848d4 --- /dev/null +++ b/examples/BenchmarkI/BenchmarkI.ino @@ -0,0 +1,316 @@ +#include "GPIO.h" +#include "benchmark.h" + +/* + * NANO GPIO +16:06:16.704 -> 1.1 Arduino core digitalRead: 3.836 +16:06:16.704 -> 1.2 Arduino core digitalWrite(HIGH): 4.216 +16:06:16.704 -> 1.3 Arduino core digitalWrite(LOW): 4.088 +16:06:16.739 -> 1.4 Arduino core toggle; digitalRead-digitalWrite: 8.236 +16:06:16.739 -> 1.5 Arduino core toggle; digitalWrite: 8.304 +16:06:16.774 -> 2.1 GPIO pin value operator: 0.064 +16:06:16.774 -> 2.2 GPIO high member function: 0.128 +16:06:16.774 -> 2.3 GPIO low member function: 0.132 +16:06:16.774 -> 2.4 GPIO assignment HIGH: 0.132 +16:06:16.774 -> 2.5 GPIO assignment LOW: 0.132 +16:06:16.807 -> 2.6 GPIO toggle; value and assignment operator: 0.344 +16:06:16.807 -> 2.7 GPIO toggle; high and low member functions: 0.248 +16:06:16.807 -> 2.8 GPIO toggle; assignment operator, HIGH/LOW: 0.248 +16:06:16.807 -> 2.9 GPIO toggle member function: 0.124 +16:06:16.843 -> + + NANO VGPIO +16:10:40.288 -> 1.1 Arduino core digitalRead: 3.836 +16:10:40.288 -> 1.2 Arduino core digitalWrite(HIGH): 4.216 +16:10:40.321 -> 1.3 Arduino core digitalWrite(LOW): 4.084 +16:10:40.321 -> 1.4 Arduino core toggle; digitalRead-digitalWrite: 8.236 +16:10:40.321 -> 1.5 Arduino core toggle; digitalWrite: 8.304 +16:10:40.356 -> 2.1 VGPIO pin value operator: 0.064 +16:10:40.356 -> 2.2 VGPIO high member function: 0.756 +16:10:40.356 -> 2.3 VGPIO low member function: 0.756 +16:10:40.390 -> 2.4 VGPIO assignment HIGH: 0.132 +16:10:40.390 -> 2.5 VGPIO assignment LOW: 0.132 +16:10:40.390 -> 2.6 VGPIO toggle; value and assignment operator: 1.356 +16:10:40.390 -> 2.7 VGPIO toggle; high and low member functions: 1.512 +16:10:40.424 -> 2.8 VGPIO toggle; assignment operator, HIGH/LOW: 0.256 +16:10:40.424 -> 2.9 VGPIO toggle member function: 0.756 +16:10:40.424 -> + + NANO IGPIO +16:20:32.106 -> 1.1 Arduino core digitalRead: 3.840 +16:20:32.106 -> 1.2 Arduino core digitalWrite(HIGH): 4.216 +16:20:32.140 -> 1.3 Arduino core digitalWrite(LOW): 4.084 +16:20:32.140 -> 1.4 Arduino core toggle; digitalRead-digitalWrite: 8.236 +16:20:32.175 -> 1.5 Arduino core toggle; digitalWrite: 8.304 +16:20:32.175 -> 2.1 IGPIO pin value operator: 1.512 +16:20:32.175 -> 2.2 IGPIO high member function: 1.448 +16:20:32.212 -> 2.3 IGPIO low member function: 1.452 +16:20:32.212 -> 2.4 IGPIO assignment HIGH: 1.700 +16:20:32.212 -> 2.5 IGPIO assignment LOW: 1.764 +16:20:32.212 -> 2.6 IGPIO toggle; value and assignment operator: 2.924 +16:20:32.246 -> 2.7 IGPIO toggle; high and low member functions: 2.896 +16:20:32.246 -> 2.8 IGPIO toggle; assignment operator, HIGH/LOW: 3.460 +16:20:32.246 -> 2.9 IGPIO toggle member function: 1.444 +16:20:32.281 -> + + MEGA GPIO +16:26:50.265 -> 1.1 Arduino core digitalRead: 6.412 +16:26:50.299 -> 1.2 Arduino core digitalWrite(HIGH): 6.916 +16:26:50.299 -> 1.3 Arduino core digitalWrite(LOW): 6.792 +16:26:50.332 -> 1.4 Arduino core toggle; digitalRead-digitalWrite: 13.204 +16:26:50.366 -> 1.5 Arduino core toggle; digitalWrite: 13.712 +16:26:50.366 -> 2.1 GPIO pin value operator: 0.064 +16:26:50.366 -> 2.2 GPIO high member function: 0.124 +16:26:50.366 -> 2.3 GPIO low member function: 0.124 +16:26:50.401 -> 2.4 GPIO assignment HIGH: 0.124 +16:26:50.401 -> 2.5 GPIO assignment LOW: 0.128 +16:26:50.401 -> 2.6 GPIO toggle; value and assignment operator: 0.352 +16:26:50.401 -> 2.7 GPIO toggle; high and low member functions: 0.256 +16:26:50.434 -> 2.8 GPIO toggle; assignment operator, HIGH/LOW: 0.248 +16:26:50.434 -> 2.9 GPIO toggle member function: 0.132 +16:26:50.434 -> 3.1 Arduino core digitalRead: 6.284 +16:26:50.468 -> 3.2 Arduino core digitalWrite(HIGH): 7.168 +16:26:50.468 -> 3.3 Arduino core digitalWrite(LOW): 7.048 +16:26:50.468 -> 3.4 Arduino core toggle; digitalRead-digitalWrite: 13.652 +16:26:50.502 -> 3.5 Arduino core toggle; digitalWrite: 14.208 +16:26:50.536 -> 4.1 GPIO pin value operator: 0.128 +16:26:50.536 -> 4.2 GPIO high member function: 0.504 +16:26:50.536 -> 4.3 GPIO low member function: 0.504 +16:26:50.536 -> 4.4 GPIO assignment HIGH: 0.508 +16:26:50.571 -> 4.5 GPIO assignment LOW: 0.504 +16:26:50.571 -> 4.6 GPIO toggle; value and assignment operator: 0.944 +16:26:50.571 -> 4.7 GPIO toggle; high and low member functions: 1.008 +16:26:50.571 -> 4.8 GPIO toggle; assignment operator: 1.012 +16:26:50.606 -> 4.9 GPIO toggle member function: 0.500 +16:26:50.606 -> + + MEGA VGPIO +16:26:20.659 -> 1.1 Arduino core digitalRead: 6.412 +16:26:20.659 -> 1.2 Arduino core digitalWrite(HIGH): 6.920 +16:26:20.693 -> 1.3 Arduino core digitalWrite(LOW): 6.796 +16:26:20.693 -> 1.4 Arduino core toggle; digitalRead-digitalWrite: 13.204 +16:26:20.728 -> 1.5 Arduino core toggle; digitalWrite: 13.712 +16:26:20.761 -> 2.1 VGPIO pin value operator: 0.068 +16:26:20.761 -> 2.2 VGPIO high member function: 0.820 +16:26:20.761 -> 2.3 VGPIO low member function: 0.820 +16:26:20.761 -> 2.4 VGPIO assignment HIGH: 0.124 +16:26:20.761 -> 2.5 VGPIO assignment LOW: 0.124 +16:26:20.795 -> 2.6 VGPIO toggle; value and assignment operator: 1.660 +16:26:20.795 -> 2.7 VGPIO toggle; high and low member functions: 1.636 +16:26:20.795 -> 2.8 VGPIO toggle; assignment operator, HIGH/LOW: 0.256 +16:26:20.829 -> 2.9 VGPIO toggle member function: 0.820 +16:26:20.829 -> 3.1 Arduino core digitalRead: 6.356 +16:26:20.829 -> 3.2 Arduino core digitalWrite(HIGH): 7.232 +16:26:20.864 -> 3.3 Arduino core digitalWrite(LOW): 7.104 +16:26:20.864 -> 3.4 Arduino core toggle; digitalRead-digitalWrite: 13.768 +16:26:20.899 -> 3.5 Arduino core toggle; digitalWrite: 14.344 +16:26:20.899 -> 4.1 VGPIO pin value operator: 0.132 +16:26:20.932 -> 4.2 VGPIO high member function: 1.448 +16:26:20.932 -> 4.3 VGPIO low member function: 1.448 +16:26:20.932 -> 4.4 VGPIO assignment HIGH: 1.576 +16:26:20.932 -> 4.5 VGPIO assignment LOW: 1.764 +16:26:20.966 -> 4.6 VGPIO toggle; value and assignment operator: 2.072 +16:26:20.966 -> 4.7 VGPIO toggle; high and low member functions: 2.892 +16:26:20.966 -> 4.8 VGPIO toggle; assignment operator: 3.332 +16:26:21.000 -> 4.9 VGPIO toggle member function: 1.452 +16:26:21.000 -> + + + MEGA IGPIO +16:24:12.181 -> 1.1 Arduino core digitalRead: 6.420 +16:24:12.181 -> 1.2 Arduino core digitalWrite(HIGH): 6.920 +16:24:12.181 -> 1.3 Arduino core digitalWrite(LOW): 6.792 +16:24:12.216 -> 1.4 Arduino core toggle; digitalRead-digitalWrite: 13.212 +16:24:12.251 -> 1.5 Arduino core toggle; digitalWrite: 13.704 +16:24:12.251 -> 2.1 IGPIO pin value operator: 1.700 +16:24:12.251 -> 2.2 IGPIO high member function: 1.572 +16:24:12.286 -> 2.3 IGPIO low member function: 1.572 +16:24:12.286 -> 2.4 IGPIO assignment HIGH: 1.828 +16:24:12.286 -> 2.5 IGPIO assignment LOW: 1.884 +16:24:12.286 -> 2.6 IGPIO toggle; value and assignment operator: 3.176 +16:24:12.319 -> 2.7 IGPIO toggle; high and low member functions: 3.152 +16:24:12.319 -> 2.8 IGPIO toggle; assignment operator, HIGH/LOW: 3.712 +16:24:12.352 -> 2.9 IGPIO toggle member function: 1.572 +16:24:12.352 -> 3.1 Arduino core digitalRead: 6.356 +16:24:12.352 -> 3.2 Arduino core digitalWrite(HIGH): 7.236 +16:24:12.386 -> 3.3 Arduino core digitalWrite(LOW): 7.108 +16:24:12.386 -> 3.4 Arduino core toggle; digitalRead-digitalWrite: 13.776 +16:24:12.421 -> 3.5 Arduino core toggle; digitalWrite: 14.336 +16:24:12.421 -> 4.1 IGPIO pin value operator: 1.140 +16:24:12.455 -> 4.2 IGPIO high member function: 1.452 +16:24:12.455 -> 4.3 IGPIO low member function: 1.444 +16:24:12.455 -> 4.4 IGPIO assignment HIGH: 1.576 +16:24:12.455 -> 4.5 IGPIO assignment LOW: 1.760 +16:24:12.488 -> 4.6 IGPIO toggle; value and assignment operator: 2.076 +16:24:12.488 -> 4.7 IGPIO toggle; high and low member functions: 2.896 +16:24:12.488 -> 4.8 IGPIO toggle; assignment operator: 3.328 +16:24:12.523 -> 4.9 IGPIO toggle member function: 1.452 +16:24:12.523 -> + + */ +const IGPIO& button = VGPIO(); +const IGPIO& led = VGPIO(); +#define BUTTON_PIN 12 +#define LED_PIN 13 + +void setup() +{ + Serial.begin(57600); + while (!Serial); + delay(1000); + + // Set pin mode; Arduino style + pinMode(LED_PIN, OUTPUT); + pinMode(BUTTON_PIN, INPUT_PULLUP); + + // Set pin mode; GPIO style + led.output(); + button.input(); + button.pullup(); + + // Calculate baseline + BENCHMARK_BASELINE(1000); +} + +void loop() +{ + BENCHMARK("1.1 Arduino core digitalRead", 1000) { + bool state = digitalRead(BUTTON_PIN); + (void) state; + } + + BENCHMARK("1.2 Arduino core digitalWrite(HIGH)", 1000) { + digitalWrite(LED_PIN, HIGH); + } + + BENCHMARK("1.3 Arduino core digitalWrite(LOW)", 1000) { + digitalWrite(LED_PIN, LOW); + } + + BENCHMARK("1.4 Arduino core toggle; digitalRead-digitalWrite", 1000) { + digitalWrite(LED_PIN, !digitalRead(LED_PIN)); + } + + BENCHMARK("1.5 Arduino core toggle; digitalWrite", 1000) { + digitalWrite(LED_PIN, HIGH); + digitalWrite(LED_PIN, LOW); + } + + BENCHMARK("2.1 IGPIO pin value operator", 1000) { + bool state = button; + (void) state; + } + + BENCHMARK("2.2 IGPIO high member function", 1000) { + led.high(); + } + + BENCHMARK("2.3 IGPIO low member function", 1000) { + led.low(); + } + + BENCHMARK("2.4 IGPIO assignment HIGH", 1000) { + led = HIGH; + } + + BENCHMARK("2.5 IGPIO assignment LOW", 1000) { + led = LOW; + } + + BENCHMARK("2.6 IGPIO toggle; value and assignment operator", 1000) { + led.write( !led.read() ); + } + + BENCHMARK("2.7 IGPIO toggle; high and low member functions", 1000) { + led.high(); + led.low(); + } + + BENCHMARK("2.8 IGPIO toggle; assignment operator, HIGH/LOW", 1000) { + led = HIGH; + led = LOW; + } + + BENCHMARK("2.9 IGPIO toggle member function", 1000) { + led.toggle(); + } + +#ifdef PORTH + + // IGPIO atomic access of io ports with higher address. These + // benchmarks are for Arduino Mega pins that use ports above address + // 0x40 (PORTH, PORTJ, PINK and PINL). See Hardware/AVR/Board.h. + +#define DIN_PIN 6 +#define DOUT_PIN 7 + const IGPIO& din = VGPIO(); + const IGPIO& dout = VGPIO(); + din.input(); + dout.input(); + + BENCHMARK("3.1 Arduino core digitalRead", 1000) { + bool state = digitalRead(DIN_PIN); + (void) state; + } + + BENCHMARK("3.2 Arduino core digitalWrite(HIGH)", 1000) { + digitalWrite(DOUT_PIN, HIGH); + } + + BENCHMARK("3.3 Arduino core digitalWrite(LOW)", 1000) { + digitalWrite(DOUT_PIN, LOW); + } + + BENCHMARK("3.4 Arduino core toggle; digitalRead-digitalWrite", 1000) { + digitalWrite(DOUT_PIN, !digitalRead(DOUT_PIN)); + } + + BENCHMARK("3.5 Arduino core toggle; digitalWrite", 1000) { + digitalWrite(DOUT_PIN, HIGH); + digitalWrite(DOUT_PIN, LOW); + } + + BENCHMARK("4.1 IGPIO pin value operator", 1000) { + bool state = din; + (void) state; + } + + BENCHMARK("4.2 IGPIO high member function", 1000) { + dout.high(); + } + + BENCHMARK("4.3 IGPIO low member function", 1000) { + dout.low(); + } + + BENCHMARK("4.4 IGPIO assignment HIGH", 1000) { + dout = HIGH; + } + + BENCHMARK("4.5 IGPIO assignment LOW", 1000) { + dout = LOW; + } + + BENCHMARK("4.6 IGPIO toggle; value and assignment operator", 1000) { + dout.write( !dout.read() ); + } + + BENCHMARK("4.7 IGPIO toggle; high and low member functions", 1000) { + dout.high(); + dout.low(); + } + + BENCHMARK("4.8 IGPIO toggle; assignment operator", 1000) { + dout = HIGH; + dout = LOW; + } + + BENCHMARK("4.9 IGPIO toggle member function", 1000) { + dout.toggle(); + } +#endif + + Serial.println(); + delay(2000); + while(true) ; +} diff --git a/examples/BenchmarkV/BenchmarkV.ino b/examples/BenchmarkV/BenchmarkV.ino new file mode 100644 index 0000000..e6acbe0 --- /dev/null +++ b/examples/BenchmarkV/BenchmarkV.ino @@ -0,0 +1,205 @@ +#include "GPIO.h" +#include "benchmark.h" + +/* + * NANO GPIO +16:06:16.704 -> 1.1 Arduino core digitalRead: 3.836 +16:06:16.704 -> 1.2 Arduino core digitalWrite(HIGH): 4.216 +16:06:16.704 -> 1.3 Arduino core digitalWrite(LOW): 4.088 +16:06:16.739 -> 1.4 Arduino core toggle; digitalRead-digitalWrite: 8.236 +16:06:16.739 -> 1.5 Arduino core toggle; digitalWrite: 8.304 +16:06:16.774 -> 2.1 GPIO pin value operator: 0.064 +16:06:16.774 -> 2.2 GPIO high member function: 0.128 +16:06:16.774 -> 2.3 GPIO low member function: 0.132 +16:06:16.774 -> 2.4 GPIO assignment HIGH: 0.132 +16:06:16.774 -> 2.5 GPIO assignment LOW: 0.132 +16:06:16.807 -> 2.6 GPIO toggle; value and assignment operator: 0.344 +16:06:16.807 -> 2.7 GPIO toggle; high and low member functions: 0.248 +16:06:16.807 -> 2.8 GPIO toggle; assignment operator, HIGH/LOW: 0.248 +16:06:16.807 -> 2.9 GPIO toggle member function: 0.124 +16:06:16.843 -> + + NANO VGPIO +16:10:40.288 -> 1.1 Arduino core digitalRead: 3.836 +16:10:40.288 -> 1.2 Arduino core digitalWrite(HIGH): 4.216 +16:10:40.321 -> 1.3 Arduino core digitalWrite(LOW): 4.084 +16:10:40.321 -> 1.4 Arduino core toggle; digitalRead-digitalWrite: 8.236 +16:10:40.321 -> 1.5 Arduino core toggle; digitalWrite: 8.304 +16:10:40.356 -> 2.1 VGPIO pin value operator: 0.064 +16:10:40.356 -> 2.2 VGPIO high member function: 0.756 +16:10:40.356 -> 2.3 VGPIO low member function: 0.756 +16:10:40.390 -> 2.4 VGPIO assignment HIGH: 0.132 +16:10:40.390 -> 2.5 VGPIO assignment LOW: 0.132 +16:10:40.390 -> 2.6 VGPIO toggle; value and assignment operator: 1.356 +16:10:40.390 -> 2.7 VGPIO toggle; high and low member functions: 1.512 +16:10:40.424 -> 2.8 VGPIO toggle; assignment operator, HIGH/LOW: 0.256 +16:10:40.424 -> 2.9 VGPIO toggle member function: 0.756 +16:10:40.424 -> + + + */ +VGPIO button; +VGPIO led; +#define BUTTON_PIN 12 +#define LED_PIN 13 + +void setup() +{ + Serial.begin(57600); + while (!Serial); + + // Set pin mode; Arduino style + pinMode(LED_PIN, OUTPUT); + pinMode(BUTTON_PIN, INPUT_PULLUP); + + // Set pin mode; GPIO style + led.output(); + button.input(); + button.pullup(); + + // Calculate baseline + BENCHMARK_BASELINE(1000); +} + +void loop() +{ + BENCHMARK("1.1 Arduino core digitalRead", 1000) { + bool state = digitalRead(BUTTON_PIN); + (void) state; + } + + BENCHMARK("1.2 Arduino core digitalWrite(HIGH)", 1000) { + digitalWrite(LED_PIN, HIGH); + } + + BENCHMARK("1.3 Arduino core digitalWrite(LOW)", 1000) { + digitalWrite(LED_PIN, LOW); + } + + BENCHMARK("1.4 Arduino core toggle; digitalRead-digitalWrite", 1000) { + digitalWrite(LED_PIN, !digitalRead(LED_PIN)); + } + + BENCHMARK("1.5 Arduino core toggle; digitalWrite", 1000) { + digitalWrite(LED_PIN, HIGH); + digitalWrite(LED_PIN, LOW); + } + + BENCHMARK("2.1 VGPIO pin value operator", 1000) { + bool state = button; + (void) state; + } + + BENCHMARK("2.2 VGPIO high member function", 1000) { + led.high(); + } + + BENCHMARK("2.3 VGPIO low member function", 1000) { + led.low(); + } + + BENCHMARK("2.4 VGPIO assignment HIGH", 1000) { + led = HIGH; + } + + BENCHMARK("2.5 VGPIO assignment LOW", 1000) { + led = LOW; + } + + BENCHMARK("2.6 VGPIO toggle; value and assignment operator", 1000) { + led = !led; + } + + BENCHMARK("2.7 VGPIO toggle; high and low member functions", 1000) { + led.high(); + led.low(); + } + + BENCHMARK("2.8 VGPIO toggle; assignment operator, HIGH/LOW", 1000) { + led = HIGH; + led = LOW; + } + + BENCHMARK("2.9 VGPIO toggle member function", 1000) { + led.toggle(); + } + +#ifdef PORTH + + // VGPIO atomic access of io ports with higher address. These + // benchmarks are for Arduino Mega pins that use ports above address + // 0x40 (PORTH, PORTJ, PINK and PINL). See Hardware/AVR/Board.h. + +#define DIN_PIN 6 +#define DOUT_PIN 7 + VGPIO din; + VGPIO dout; + din.input(); + dout.input(); + + BENCHMARK("3.1 Arduino core digitalRead", 1000) { + bool state = digitalRead(DIN_PIN); + (void) state; + } + + BENCHMARK("3.2 Arduino core digitalWrite(HIGH)", 1000) { + digitalWrite(DOUT_PIN, HIGH); + } + + BENCHMARK("3.3 Arduino core digitalWrite(LOW)", 1000) { + digitalWrite(DOUT_PIN, LOW); + } + + BENCHMARK("3.4 Arduino core toggle; digitalRead-digitalWrite", 1000) { + digitalWrite(DOUT_PIN, !digitalRead(DOUT_PIN)); + } + + BENCHMARK("3.5 Arduino core toggle; digitalWrite", 1000) { + digitalWrite(DOUT_PIN, HIGH); + digitalWrite(DOUT_PIN, LOW); + } + + BENCHMARK("4.1 VGPIO pin value operator", 1000) { + bool state = din; + (void) state; + } + + BENCHMARK("4.2 VGPIO high member function", 1000) { + dout.high(); + } + + BENCHMARK("4.3 VGPIO low member function", 1000) { + dout.low(); + } + + BENCHMARK("4.4 VGPIO assignment HIGH", 1000) { + dout = HIGH; + } + + BENCHMARK("4.5 VGPIO assignment LOW", 1000) { + dout = LOW; + } + + BENCHMARK("4.6 VGPIO toggle; value and assignment operator", 1000) { + dout = !dout; + } + + BENCHMARK("4.7 VGPIO toggle; high and low member functions", 1000) { + dout.high(); + dout.low(); + } + + BENCHMARK("4.8 VGPIO toggle; assignment operator", 1000) { + dout = HIGH; + dout = LOW; + } + + BENCHMARK("4.9 VGPIO toggle member function", 1000) { + dout.toggle(); + } +#endif + + Serial.println(); + delay(2000); + while(true) ; +} diff --git a/src/Hardware/AVR/GPIO.h b/src/Hardware/AVR/GPIO.h index b5dc299..08a4268 100644 --- a/src/Hardware/AVR/GPIO.h +++ b/src/Hardware/AVR/GPIO.h @@ -30,6 +30,14 @@ template class GPIO { public: + + /** + * Return the encapsulated pin + */ + unsigned int pin() { + return (unsigned int) PIN; + } + /** * Set pin to input mode. */ @@ -190,4 +198,6 @@ class GPIO { /** Pin bit position mask in control registers. */ static const uint8_t MASK = GPIO_MASK(PIN); }; + + #endif diff --git a/src/Hardware/SAM/GPIO.h b/src/Hardware/SAM/GPIO.h index 7fd8795..a8e49e1 100644 --- a/src/Hardware/SAM/GPIO.h +++ b/src/Hardware/SAM/GPIO.h @@ -30,6 +30,13 @@ template class GPIO { public: + /** + * Return the encapsulated pin + */ + unsigned int pin() { + return (unsigned int) PIN; + } + /** * Construct pin instance and initiate. */ @@ -209,4 +216,5 @@ class GPIO { } } }; + #endif diff --git a/src/IGPIO.h b/src/IGPIO.h new file mode 100644 index 0000000..a19f048 --- /dev/null +++ b/src/IGPIO.h @@ -0,0 +1,154 @@ +/** + * @file GPIO.h + * @version 1.0 + * + * @section License + * Copyright (C) 2017, Mikael Patel + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + */ + +#ifndef IGPIO_H +#define IGPIO_H + +#include + +/** + * A non-templated pure virtual interface base class for the processor-specific + * General Purpose Digital I/O pin template classes. Those classes areighly + * optimized pin access. The PIN address is a bit pointer to the port control + * register. See Hardware/AVR/Board.h for details. + * + * This base class allows GPIO objects to be passed as parameters to other + * non-templated classes and functions. + */ + +class IGPIO { + public: + /** + * Default constructor + */ + IGPIO(){}; + + /** + * Virtual destructor + */ + virtual ~IGPIO(){}; + + /** + * Test if another IGPIO object uses the same pin. + */ + inline bool operator==(IGPIO &that) { return pin() == that.pin(); } + + /** + * Get the assigned pin. + */ + virtual unsigned int pin() = 0; + + /** + * Set pin to input mode. + */ + virtual void input() = 0; + + /** + * Used with input() to activate internal pullup resistor on + * input pin. + */ + virtual void pullup() = 0; + + /** + * Set pin to output mode. + */ + virtual void output() = 0; + + /** + * Open-drain pin. Use input() for high and output() for low. + */ + virtual void open_drain() = 0; + + /** + * Return current pin state. + * @return state. + */ + virtual bool read() = 0; + + /** + * Return current pin state. Shorthand for read(). + * @return state. + */ + virtual operator bool() = 0; + + /** + * Set pin low(0). Shorthand for write(LOW). + */ + virtual void low() = 0; + + /** + * Set pin high(1). Shorthand for write(HIGH). + */ + virtual void high() = 0; + + /** + * Toggle pin state. Shorthand for write(!read()). + */ + virtual void toggle() = 0; + + /** + * Set pin to given state. Non-zero value will set the pin HIGH(1), + * and zero value will set the pin LOW(0). + * @param[in] value to set pin. + */ + virtual void write(int value) = 0; + + /** + * Set pin to given state. Non-zero value will set the pin HIGH(1), + * and zero value will set the pin LOW(0). Shorthand for write(value). + * @param[in] value to set pin. + */ + virtual void operator=(int value) = 0; + + /** + * Generate pulse with given width in micro-seconds. Interrupts + * are disabled while generating the pulse. + * @param[in] width in micro-seconds. + */ + virtual void pulse(uint16_t width) = 0; + + /** + * Detect pulse and return width in micro-seconds. + * @return width in micro-seconds. + */ + virtual int pulse() = 0; +}; + + +template +class VGPIO : public IGPIO, public GPIO { + public: + inline bool operator==(IGPIO &that) { return pin() == that.pin(); } + unsigned int pin() { return GPIO::pin(); } + void input() { GPIO::input(); } + void pullup() { GPIO::pullup(); } + void output() { GPIO::output(); } + void open_drain() { GPIO::open_drain(); } + bool read() { return GPIO::read(); } + operator bool() { return GPIO::read(); } + void low() { GPIO::low(); } + void high() { GPIO::high(); } + void toggle() { GPIO::toggle(); } + void write(int value) { GPIO::write(value); }; + void operator=(int value) { GPIO::write(value); } + void pulse(uint16_t width) { GPIO::pulse(width); } + int pulse() { return GPIO::pulse(); } + +}; + +#endif \ No newline at end of file From 06e0b759e251051ad2419d3629fc9929e106f7c5 Mon Sep 17 00:00:00 2001 From: Donald Linton Date: Thu, 16 Jan 2020 15:30:57 -0500 Subject: [PATCH 3/4] const party --- src/Hardware/AVR/GPIO.h | 30 +++++++++++++++--------------- src/Hardware/SAM/GPIO.h | 32 ++++++++++++++++---------------- 2 files changed, 31 insertions(+), 31 deletions(-) diff --git a/src/Hardware/AVR/GPIO.h b/src/Hardware/AVR/GPIO.h index 08a4268..2d9098e 100644 --- a/src/Hardware/AVR/GPIO.h +++ b/src/Hardware/AVR/GPIO.h @@ -34,14 +34,14 @@ class GPIO { /** * Return the encapsulated pin */ - unsigned int pin() { + unsigned int pin() const { return (unsigned int) PIN; } /** * Set pin to input mode. */ - GPIO& input() + const GPIO& input() const __attribute__((always_inline)) { GPIO_ATOMIC(SFR()->ddr &= ~MASK); @@ -52,7 +52,7 @@ class GPIO { * Used with input() to activate internal pullup resistor on * input pin. */ - void pullup() + void pullup() const __attribute__((always_inline)) { high(); @@ -61,7 +61,7 @@ class GPIO { /** * Set pin to output mode. */ - void output() + void output() const __attribute__((always_inline)) { GPIO_ATOMIC(SFR()->ddr |= MASK); @@ -70,7 +70,7 @@ class GPIO { /** * Open-drain pin. Use input() for high and output() for low. */ - void open_drain() + void open_drain() const __attribute__((always_inline)) { input(); @@ -81,7 +81,7 @@ class GPIO { * Return current pin state. * @return state. */ - bool read() + bool read() const __attribute__((always_inline)) { return ((SFR()->pin & MASK) != 0); @@ -91,7 +91,7 @@ class GPIO { * Return current pin state. Shorthand for read(). * @return state. */ - operator bool() + operator bool() const __attribute__((always_inline)) { return (read()); @@ -100,7 +100,7 @@ class GPIO { /** * Set pin low(0). Shorthand for write(LOW). */ - void low() + void low() const __attribute__((always_inline)) { GPIO_ATOMIC(SFR()->port &= ~MASK); @@ -109,7 +109,7 @@ class GPIO { /** * Set pin high(1). Shorthand for write(HIGH). */ - void high() + void high() const __attribute__((always_inline)) { GPIO_ATOMIC(SFR()->port |= MASK); @@ -118,7 +118,7 @@ class GPIO { /** * Toggle pin state. Shorthand for write(!read()). */ - void toggle() + void toggle() const __attribute__((always_inline)) { GPIO_ATOMIC(SFR()->pin |= MASK); @@ -129,7 +129,7 @@ class GPIO { * and zero value will set the pin LOW(0). * @param[in] value to set pin. */ - void write(int value) + void write(int value) const __attribute__((always_inline)) { if (value) high(); else low(); @@ -140,7 +140,7 @@ class GPIO { * and zero value will set the pin LOW(0). Shorthand for write(value). * @param[in] value to set pin. */ - void operator=(int value) + void operator=(int value) const __attribute__((always_inline)) { write(value); @@ -151,7 +151,7 @@ class GPIO { * are disabled while generating the pulse. * @param[in] width in micro-seconds. */ - void pulse(uint16_t width) + void pulse(uint16_t width) const { if (width == 0) return; uint16_t count = ((width * (F_CPU / 1000000L)) / 4); @@ -168,7 +168,7 @@ class GPIO { * Detect pulse and return width in micro-seconds. * @return width in micro-seconds. */ - int pulse() + int pulse() const { bool s0 = read(); while (read() == s0); @@ -189,7 +189,7 @@ class GPIO { * Return pointer to control registers. * @return pointer. */ - gpio_reg_t* SFR() + gpio_reg_t* SFR() const __attribute__((always_inline)) { return ((gpio_reg_t*) GPIO_REG(PIN)); diff --git a/src/Hardware/SAM/GPIO.h b/src/Hardware/SAM/GPIO.h index a8e49e1..dc66b0b 100644 --- a/src/Hardware/SAM/GPIO.h +++ b/src/Hardware/SAM/GPIO.h @@ -33,7 +33,7 @@ class GPIO { /** * Return the encapsulated pin */ - unsigned int pin() { + unsigned int pin() const { return (unsigned int) PIN; } @@ -49,7 +49,7 @@ class GPIO { /** * Set pin to input mode. */ - GPIO& input() + GPIO& input() const __attribute__((always_inline)) { SFR()->PIO_ODR = MASK; @@ -60,7 +60,7 @@ class GPIO { * Used with input() to activate internal pullup resistor on * input pin. */ - void pullup() + void pullup() const __attribute__((always_inline)) { SFR()->PIO_PUER = MASK; @@ -69,7 +69,7 @@ class GPIO { /** * Set pin to output mode. */ - void output() + void output() const __attribute__((always_inline)) { SFR()->PIO_OER = MASK; @@ -78,7 +78,7 @@ class GPIO { /** * Open-drain pin. Use input() for high and output() for low. */ - void open_drain() + void open_drain() const __attribute__((always_inline)) { SFR()->PIO_CODR = MASK; @@ -89,7 +89,7 @@ class GPIO { * Return current pin state. * @return state. */ - bool read() + bool read() const __attribute__((always_inline)) { return ((SFR()->PIO_PDSR & MASK) != 0); @@ -99,7 +99,7 @@ class GPIO { * Return current pin state. Shorthand for read(). * @return state. */ - operator bool() + operator bool() const __attribute__((always_inline)) { return (read()); @@ -108,7 +108,7 @@ class GPIO { /** * Set pin low(0). Shorthand for write(LOW). */ - void low() + void low() const __attribute__((always_inline)) { SFR()->PIO_CODR = MASK; @@ -117,7 +117,7 @@ class GPIO { /** * Set pin high(1). Shorthand for write(HIGH). */ - void high() + void high() const __attribute__((always_inline)) { SFR()->PIO_SODR = MASK; @@ -126,7 +126,7 @@ class GPIO { /** * Toggle pin state. Shorthand for write(!read()). */ - void toggle() + void toggle() const __attribute__((always_inline)) { write(!read()); @@ -137,7 +137,7 @@ class GPIO { * and zero value will set the pin LOW(0). * @param[in] value to set pin. */ - void write(int value) + void write(int value) const __attribute__((always_inline)) { if (value) high(); else low(); @@ -148,7 +148,7 @@ class GPIO { * and zero value will set the pin LOW(0). Shorthand for write(value). * @param[in] value to set pin. */ - void operator=(int value) + void operator=(int value) const __attribute__((always_inline)) { write(value); @@ -159,7 +159,7 @@ class GPIO { * are disabled while generating the pulse. * @param[in] width in micro-seconds. */ - void pulse(uint16_t width) + void pulse(uint16_t width) const { if (width == 0) return; toggle(); @@ -171,7 +171,7 @@ class GPIO { * Detect pulse and return width in micro-seconds. * @return width in micro-seconds. */ - int pulse() + int pulse() const { bool s0 = read(); while (read() == s0); @@ -188,7 +188,7 @@ class GPIO { * Return pointer to control registers. * @return pointer. */ - Pio* SFR() + Pio* SFR() const __attribute__((always_inline)) { switch (GPIO_REG(PIN)) { @@ -204,7 +204,7 @@ class GPIO { * Return parallel input/output port identity. * @return identity. */ - uint32_t ID_PIO() + uint32_t ID_PIO() const __attribute__((always_inline)) { switch (GPIO_REG(PIN)) { From df976dede6e676c107991460a64adf5295fba9b8 Mon Sep 17 00:00:00 2001 From: Donald Linton Date: Sun, 26 Jan 2020 07:28:08 -0500 Subject: [PATCH 4/4] benchmarks for IGPIO.h interface and virtual classes --- examples/BenchmarkI/BenchmarkI.ino | 186 +++++++---------------------- examples/BenchmarkV/BenchmarkV.ino | 39 +----- src/IGPIO.h | 60 +++++----- 3 files changed, 72 insertions(+), 213 deletions(-) diff --git a/examples/BenchmarkI/BenchmarkI.ino b/examples/BenchmarkI/BenchmarkI.ino index ed848d4..cb403fa 100644 --- a/examples/BenchmarkI/BenchmarkI.ino +++ b/examples/BenchmarkI/BenchmarkI.ino @@ -1,152 +1,48 @@ -#include "GPIO.h" +#include "IGPIO.h" #include "benchmark.h" /* - * NANO GPIO -16:06:16.704 -> 1.1 Arduino core digitalRead: 3.836 -16:06:16.704 -> 1.2 Arduino core digitalWrite(HIGH): 4.216 -16:06:16.704 -> 1.3 Arduino core digitalWrite(LOW): 4.088 -16:06:16.739 -> 1.4 Arduino core toggle; digitalRead-digitalWrite: 8.236 -16:06:16.739 -> 1.5 Arduino core toggle; digitalWrite: 8.304 -16:06:16.774 -> 2.1 GPIO pin value operator: 0.064 -16:06:16.774 -> 2.2 GPIO high member function: 0.128 -16:06:16.774 -> 2.3 GPIO low member function: 0.132 -16:06:16.774 -> 2.4 GPIO assignment HIGH: 0.132 -16:06:16.774 -> 2.5 GPIO assignment LOW: 0.132 -16:06:16.807 -> 2.6 GPIO toggle; value and assignment operator: 0.344 -16:06:16.807 -> 2.7 GPIO toggle; high and low member functions: 0.248 -16:06:16.807 -> 2.8 GPIO toggle; assignment operator, HIGH/LOW: 0.248 -16:06:16.807 -> 2.9 GPIO toggle member function: 0.124 -16:06:16.843 -> - - NANO VGPIO -16:10:40.288 -> 1.1 Arduino core digitalRead: 3.836 -16:10:40.288 -> 1.2 Arduino core digitalWrite(HIGH): 4.216 -16:10:40.321 -> 1.3 Arduino core digitalWrite(LOW): 4.084 -16:10:40.321 -> 1.4 Arduino core toggle; digitalRead-digitalWrite: 8.236 -16:10:40.321 -> 1.5 Arduino core toggle; digitalWrite: 8.304 -16:10:40.356 -> 2.1 VGPIO pin value operator: 0.064 -16:10:40.356 -> 2.2 VGPIO high member function: 0.756 -16:10:40.356 -> 2.3 VGPIO low member function: 0.756 -16:10:40.390 -> 2.4 VGPIO assignment HIGH: 0.132 -16:10:40.390 -> 2.5 VGPIO assignment LOW: 0.132 -16:10:40.390 -> 2.6 VGPIO toggle; value and assignment operator: 1.356 -16:10:40.390 -> 2.7 VGPIO toggle; high and low member functions: 1.512 -16:10:40.424 -> 2.8 VGPIO toggle; assignment operator, HIGH/LOW: 0.256 -16:10:40.424 -> 2.9 VGPIO toggle member function: 0.756 -16:10:40.424 -> - - NANO IGPIO -16:20:32.106 -> 1.1 Arduino core digitalRead: 3.840 -16:20:32.106 -> 1.2 Arduino core digitalWrite(HIGH): 4.216 -16:20:32.140 -> 1.3 Arduino core digitalWrite(LOW): 4.084 -16:20:32.140 -> 1.4 Arduino core toggle; digitalRead-digitalWrite: 8.236 -16:20:32.175 -> 1.5 Arduino core toggle; digitalWrite: 8.304 -16:20:32.175 -> 2.1 IGPIO pin value operator: 1.512 -16:20:32.175 -> 2.2 IGPIO high member function: 1.448 -16:20:32.212 -> 2.3 IGPIO low member function: 1.452 -16:20:32.212 -> 2.4 IGPIO assignment HIGH: 1.700 -16:20:32.212 -> 2.5 IGPIO assignment LOW: 1.764 -16:20:32.212 -> 2.6 IGPIO toggle; value and assignment operator: 2.924 -16:20:32.246 -> 2.7 IGPIO toggle; high and low member functions: 2.896 -16:20:32.246 -> 2.8 IGPIO toggle; assignment operator, HIGH/LOW: 3.460 -16:20:32.246 -> 2.9 IGPIO toggle member function: 1.444 -16:20:32.281 -> - - MEGA GPIO -16:26:50.265 -> 1.1 Arduino core digitalRead: 6.412 -16:26:50.299 -> 1.2 Arduino core digitalWrite(HIGH): 6.916 -16:26:50.299 -> 1.3 Arduino core digitalWrite(LOW): 6.792 -16:26:50.332 -> 1.4 Arduino core toggle; digitalRead-digitalWrite: 13.204 -16:26:50.366 -> 1.5 Arduino core toggle; digitalWrite: 13.712 -16:26:50.366 -> 2.1 GPIO pin value operator: 0.064 -16:26:50.366 -> 2.2 GPIO high member function: 0.124 -16:26:50.366 -> 2.3 GPIO low member function: 0.124 -16:26:50.401 -> 2.4 GPIO assignment HIGH: 0.124 -16:26:50.401 -> 2.5 GPIO assignment LOW: 0.128 -16:26:50.401 -> 2.6 GPIO toggle; value and assignment operator: 0.352 -16:26:50.401 -> 2.7 GPIO toggle; high and low member functions: 0.256 -16:26:50.434 -> 2.8 GPIO toggle; assignment operator, HIGH/LOW: 0.248 -16:26:50.434 -> 2.9 GPIO toggle member function: 0.132 -16:26:50.434 -> 3.1 Arduino core digitalRead: 6.284 -16:26:50.468 -> 3.2 Arduino core digitalWrite(HIGH): 7.168 -16:26:50.468 -> 3.3 Arduino core digitalWrite(LOW): 7.048 -16:26:50.468 -> 3.4 Arduino core toggle; digitalRead-digitalWrite: 13.652 -16:26:50.502 -> 3.5 Arduino core toggle; digitalWrite: 14.208 -16:26:50.536 -> 4.1 GPIO pin value operator: 0.128 -16:26:50.536 -> 4.2 GPIO high member function: 0.504 -16:26:50.536 -> 4.3 GPIO low member function: 0.504 -16:26:50.536 -> 4.4 GPIO assignment HIGH: 0.508 -16:26:50.571 -> 4.5 GPIO assignment LOW: 0.504 -16:26:50.571 -> 4.6 GPIO toggle; value and assignment operator: 0.944 -16:26:50.571 -> 4.7 GPIO toggle; high and low member functions: 1.008 -16:26:50.571 -> 4.8 GPIO toggle; assignment operator: 1.012 -16:26:50.606 -> 4.9 GPIO toggle member function: 0.500 -16:26:50.606 -> - - MEGA VGPIO -16:26:20.659 -> 1.1 Arduino core digitalRead: 6.412 -16:26:20.659 -> 1.2 Arduino core digitalWrite(HIGH): 6.920 -16:26:20.693 -> 1.3 Arduino core digitalWrite(LOW): 6.796 -16:26:20.693 -> 1.4 Arduino core toggle; digitalRead-digitalWrite: 13.204 -16:26:20.728 -> 1.5 Arduino core toggle; digitalWrite: 13.712 -16:26:20.761 -> 2.1 VGPIO pin value operator: 0.068 -16:26:20.761 -> 2.2 VGPIO high member function: 0.820 -16:26:20.761 -> 2.3 VGPIO low member function: 0.820 -16:26:20.761 -> 2.4 VGPIO assignment HIGH: 0.124 -16:26:20.761 -> 2.5 VGPIO assignment LOW: 0.124 -16:26:20.795 -> 2.6 VGPIO toggle; value and assignment operator: 1.660 -16:26:20.795 -> 2.7 VGPIO toggle; high and low member functions: 1.636 -16:26:20.795 -> 2.8 VGPIO toggle; assignment operator, HIGH/LOW: 0.256 -16:26:20.829 -> 2.9 VGPIO toggle member function: 0.820 -16:26:20.829 -> 3.1 Arduino core digitalRead: 6.356 -16:26:20.829 -> 3.2 Arduino core digitalWrite(HIGH): 7.232 -16:26:20.864 -> 3.3 Arduino core digitalWrite(LOW): 7.104 -16:26:20.864 -> 3.4 Arduino core toggle; digitalRead-digitalWrite: 13.768 -16:26:20.899 -> 3.5 Arduino core toggle; digitalWrite: 14.344 -16:26:20.899 -> 4.1 VGPIO pin value operator: 0.132 -16:26:20.932 -> 4.2 VGPIO high member function: 1.448 -16:26:20.932 -> 4.3 VGPIO low member function: 1.448 -16:26:20.932 -> 4.4 VGPIO assignment HIGH: 1.576 -16:26:20.932 -> 4.5 VGPIO assignment LOW: 1.764 -16:26:20.966 -> 4.6 VGPIO toggle; value and assignment operator: 2.072 -16:26:20.966 -> 4.7 VGPIO toggle; high and low member functions: 2.892 -16:26:20.966 -> 4.8 VGPIO toggle; assignment operator: 3.332 -16:26:21.000 -> 4.9 VGPIO toggle member function: 1.452 -16:26:21.000 -> - + * UNO GPIO baseline +07:13:50.128 -> 1.1 Arduino core digitalRead: 3.836 +07:13:50.128 -> 1.2 Arduino core digitalWrite(HIGH): 4.216 +07:13:50.128 -> 1.3 Arduino core digitalWrite(LOW): 4.088 +07:13:50.162 -> 1.4 Arduino core toggle; digitalRead-digitalWrite: 8.236 +07:13:50.162 -> 1.5 Arduino core toggle; digitalWrite: 8.304 + +07:13:50.197 -> 2.1 GPIO pin value operator: 0.064 +07:13:50.197 -> 2.2 GPIO high member function: 0.128 +07:13:50.197 -> 2.3 GPIO low member function: 0.132 +07:13:50.197 -> 2.4 GPIO assignment HIGH: 0.132 +07:13:50.197 -> 2.5 GPIO assignment LOW: 0.132 +07:13:50.234 -> 2.6 GPIO toggle; value and assignment operator: 0.344 +07:13:50.234 -> 2.7 GPIO toggle; high and low member functions: 0.248 +07:13:50.234 -> 2.8 GPIO toggle; assignment operator, HIGH/LOW: 0.248 +07:13:50.234 -> 2.9 GPIO toggle member function: 0.124 + + * UNO VGPIO +07:12:45.468 -> 2.1 VGPIO pin value operator: 0.064 +07:12:45.468 -> 2.2 VGPIO high member function: 0.756 +07:12:45.468 -> 2.3 VGPIO low member function: 0.756 +07:12:45.503 -> 2.4 VGPIO assignment HIGH: 0.132 +07:12:45.503 -> 2.5 VGPIO assignment LOW: 0.132 +07:12:45.503 -> 2.6 VGPIO toggle; value and assignment operator: 1.356 +07:12:45.503 -> 2.7 VGPIO toggle; high and low member functions: 1.512 +07:12:45.538 -> 2.8 VGPIO toggle; assignment operator, HIGH/LOW: 0.256 +07:12:45.538 -> 2.9 VGPIO toggle member function: 0.756 + + * UNO IGPIO +1.1 Arduino core digitalRead: 3.840 +07:10:08.171 -> 2.1 IGPIO pin value operator: 1.512 +07:10:08.171 -> 2.2 IGPIO high member function: 1.448 +07:10:08.171 -> 2.3 IGPIO low member function: 1.452 +07:10:08.206 -> 2.4 IGPIO assignment HIGH: 1.700 +07:10:08.206 -> 2.5 IGPIO assignment LOW: 1.764 +07:10:08.206 -> 2.6 IGPIO toggle; value and assignment operator: 2.924 +07:10:08.206 -> 2.7 IGPIO toggle; high and low member functions: 2.892 +07:10:08.240 -> 2.8 IGPIO toggle; assignment operator, HIGH/LOW: 3.456 +07:10:08.240 -> 2.9 IGPIO toggle member function: 1.452 +07:10:08.275 -> - MEGA IGPIO -16:24:12.181 -> 1.1 Arduino core digitalRead: 6.420 -16:24:12.181 -> 1.2 Arduino core digitalWrite(HIGH): 6.920 -16:24:12.181 -> 1.3 Arduino core digitalWrite(LOW): 6.792 -16:24:12.216 -> 1.4 Arduino core toggle; digitalRead-digitalWrite: 13.212 -16:24:12.251 -> 1.5 Arduino core toggle; digitalWrite: 13.704 -16:24:12.251 -> 2.1 IGPIO pin value operator: 1.700 -16:24:12.251 -> 2.2 IGPIO high member function: 1.572 -16:24:12.286 -> 2.3 IGPIO low member function: 1.572 -16:24:12.286 -> 2.4 IGPIO assignment HIGH: 1.828 -16:24:12.286 -> 2.5 IGPIO assignment LOW: 1.884 -16:24:12.286 -> 2.6 IGPIO toggle; value and assignment operator: 3.176 -16:24:12.319 -> 2.7 IGPIO toggle; high and low member functions: 3.152 -16:24:12.319 -> 2.8 IGPIO toggle; assignment operator, HIGH/LOW: 3.712 -16:24:12.352 -> 2.9 IGPIO toggle member function: 1.572 -16:24:12.352 -> 3.1 Arduino core digitalRead: 6.356 -16:24:12.352 -> 3.2 Arduino core digitalWrite(HIGH): 7.236 -16:24:12.386 -> 3.3 Arduino core digitalWrite(LOW): 7.108 -16:24:12.386 -> 3.4 Arduino core toggle; digitalRead-digitalWrite: 13.776 -16:24:12.421 -> 3.5 Arduino core toggle; digitalWrite: 14.336 -16:24:12.421 -> 4.1 IGPIO pin value operator: 1.140 -16:24:12.455 -> 4.2 IGPIO high member function: 1.452 -16:24:12.455 -> 4.3 IGPIO low member function: 1.444 -16:24:12.455 -> 4.4 IGPIO assignment HIGH: 1.576 -16:24:12.455 -> 4.5 IGPIO assignment LOW: 1.760 -16:24:12.488 -> 4.6 IGPIO toggle; value and assignment operator: 2.076 -16:24:12.488 -> 4.7 IGPIO toggle; high and low member functions: 2.896 -16:24:12.488 -> 4.8 IGPIO toggle; assignment operator: 3.328 -16:24:12.523 -> 4.9 IGPIO toggle member function: 1.452 -16:24:12.523 -> - */ const IGPIO& button = VGPIO(); const IGPIO& led = VGPIO(); diff --git a/examples/BenchmarkV/BenchmarkV.ino b/examples/BenchmarkV/BenchmarkV.ino index e6acbe0..acd16fe 100644 --- a/examples/BenchmarkV/BenchmarkV.ino +++ b/examples/BenchmarkV/BenchmarkV.ino @@ -1,43 +1,6 @@ -#include "GPIO.h" +#include "IGPIO.h" #include "benchmark.h" -/* - * NANO GPIO -16:06:16.704 -> 1.1 Arduino core digitalRead: 3.836 -16:06:16.704 -> 1.2 Arduino core digitalWrite(HIGH): 4.216 -16:06:16.704 -> 1.3 Arduino core digitalWrite(LOW): 4.088 -16:06:16.739 -> 1.4 Arduino core toggle; digitalRead-digitalWrite: 8.236 -16:06:16.739 -> 1.5 Arduino core toggle; digitalWrite: 8.304 -16:06:16.774 -> 2.1 GPIO pin value operator: 0.064 -16:06:16.774 -> 2.2 GPIO high member function: 0.128 -16:06:16.774 -> 2.3 GPIO low member function: 0.132 -16:06:16.774 -> 2.4 GPIO assignment HIGH: 0.132 -16:06:16.774 -> 2.5 GPIO assignment LOW: 0.132 -16:06:16.807 -> 2.6 GPIO toggle; value and assignment operator: 0.344 -16:06:16.807 -> 2.7 GPIO toggle; high and low member functions: 0.248 -16:06:16.807 -> 2.8 GPIO toggle; assignment operator, HIGH/LOW: 0.248 -16:06:16.807 -> 2.9 GPIO toggle member function: 0.124 -16:06:16.843 -> - - NANO VGPIO -16:10:40.288 -> 1.1 Arduino core digitalRead: 3.836 -16:10:40.288 -> 1.2 Arduino core digitalWrite(HIGH): 4.216 -16:10:40.321 -> 1.3 Arduino core digitalWrite(LOW): 4.084 -16:10:40.321 -> 1.4 Arduino core toggle; digitalRead-digitalWrite: 8.236 -16:10:40.321 -> 1.5 Arduino core toggle; digitalWrite: 8.304 -16:10:40.356 -> 2.1 VGPIO pin value operator: 0.064 -16:10:40.356 -> 2.2 VGPIO high member function: 0.756 -16:10:40.356 -> 2.3 VGPIO low member function: 0.756 -16:10:40.390 -> 2.4 VGPIO assignment HIGH: 0.132 -16:10:40.390 -> 2.5 VGPIO assignment LOW: 0.132 -16:10:40.390 -> 2.6 VGPIO toggle; value and assignment operator: 1.356 -16:10:40.390 -> 2.7 VGPIO toggle; high and low member functions: 1.512 -16:10:40.424 -> 2.8 VGPIO toggle; assignment operator, HIGH/LOW: 0.256 -16:10:40.424 -> 2.9 VGPIO toggle member function: 0.756 -16:10:40.424 -> - - - */ VGPIO button; VGPIO led; #define BUTTON_PIN 12 diff --git a/src/IGPIO.h b/src/IGPIO.h index a19f048..9ef2f64 100644 --- a/src/IGPIO.h +++ b/src/IGPIO.h @@ -46,108 +46,108 @@ class IGPIO { /** * Test if another IGPIO object uses the same pin. */ - inline bool operator==(IGPIO &that) { return pin() == that.pin(); } + inline bool operator==(IGPIO &that) const { return pin() == that.pin(); } /** * Get the assigned pin. */ - virtual unsigned int pin() = 0; + virtual unsigned int pin() const = 0; /** * Set pin to input mode. */ - virtual void input() = 0; + virtual void input() const = 0; /** * Used with input() to activate internal pullup resistor on * input pin. */ - virtual void pullup() = 0; + virtual void pullup() const = 0; /** * Set pin to output mode. */ - virtual void output() = 0; + virtual void output() const = 0; /** * Open-drain pin. Use input() for high and output() for low. */ - virtual void open_drain() = 0; + virtual void open_drain() const = 0; /** * Return current pin state. * @return state. */ - virtual bool read() = 0; + virtual bool read() const = 0; /** * Return current pin state. Shorthand for read(). * @return state. */ - virtual operator bool() = 0; + virtual operator bool() const = 0; /** * Set pin low(0). Shorthand for write(LOW). */ - virtual void low() = 0; + virtual void low() const = 0; /** * Set pin high(1). Shorthand for write(HIGH). */ - virtual void high() = 0; + virtual void high() const = 0; /** * Toggle pin state. Shorthand for write(!read()). */ - virtual void toggle() = 0; + virtual void toggle() const = 0; /** * Set pin to given state. Non-zero value will set the pin HIGH(1), * and zero value will set the pin LOW(0). * @param[in] value to set pin. */ - virtual void write(int value) = 0; + virtual void write(int value) const = 0; /** * Set pin to given state. Non-zero value will set the pin HIGH(1), * and zero value will set the pin LOW(0). Shorthand for write(value). * @param[in] value to set pin. */ - virtual void operator=(int value) = 0; + virtual void operator=(int value) const = 0; /** * Generate pulse with given width in micro-seconds. Interrupts * are disabled while generating the pulse. * @param[in] width in micro-seconds. */ - virtual void pulse(uint16_t width) = 0; + virtual void pulse(uint16_t width) const = 0; /** * Detect pulse and return width in micro-seconds. * @return width in micro-seconds. */ - virtual int pulse() = 0; + virtual int pulse() const = 0; }; template class VGPIO : public IGPIO, public GPIO { public: - inline bool operator==(IGPIO &that) { return pin() == that.pin(); } - unsigned int pin() { return GPIO::pin(); } - void input() { GPIO::input(); } - void pullup() { GPIO::pullup(); } - void output() { GPIO::output(); } - void open_drain() { GPIO::open_drain(); } - bool read() { return GPIO::read(); } - operator bool() { return GPIO::read(); } - void low() { GPIO::low(); } - void high() { GPIO::high(); } - void toggle() { GPIO::toggle(); } - void write(int value) { GPIO::write(value); }; - void operator=(int value) { GPIO::write(value); } - void pulse(uint16_t width) { GPIO::pulse(width); } - int pulse() { return GPIO::pulse(); } + inline bool operator==(IGPIO &that) const { return pin() == that.pin(); } + unsigned int pin() const { return GPIO::pin(); } + void input() const { GPIO::input(); } + void pullup() const { GPIO::pullup(); } + void output() const { GPIO::output(); } + void open_drain() const { GPIO::open_drain(); } + bool read() const { return GPIO::read(); } + operator bool() const { return GPIO::read(); } + void low() const { GPIO::low(); } + void high() const { GPIO::high(); } + void toggle() const { GPIO::toggle(); } + void write(int value) const { GPIO::write(value); }; + void operator=(int value) const { GPIO::write(value); } + void pulse(uint16_t width) const { GPIO::pulse(width); } + int pulse() const { return GPIO::pulse(); } };