├── .gitignore ├── LICENSE ├── README.md ├── arduino_cli.h ├── arduino_cli.ino ├── cmd_get.cpp ├── cmd_listen.cpp ├── cmd_send.cpp ├── cmd_set.cpp ├── cmd_tail.cpp ├── execute.cpp ├── help.cpp └── parsePin.cpp /.gitignore: -------------------------------------------------------------------------------- 1 | # ignore all files starting with . or ~ 2 | .* 3 | ~* 4 | 5 | # ignore OS generated files 6 | ehthumbs.db 7 | Thumbs.db 8 | .DS_Store 9 | 10 | # ignore Editor files 11 | *.sublime-project 12 | *.sublime-workspace 13 | *.komodoproject 14 | 15 | # track these files, if they exist 16 | !.gitignore -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Copyright 2020 Athaariq Ardhiansyah 2 | 3 | Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: 4 | 5 | The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. 6 | 7 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Arduino-CLI 2 | 3 | This sketch helps you to debug every I/O pin input or output. So you don't have to program yourself only for testing each pin :) 4 | 5 | Beside of that, if your microcontroller support secondary serial then you can use it with `send` and `listen` command. 6 | 7 | You can also use this sketch to let PC program handles the logic and transport some commands via COM Serial Port. So you don't have to write every command and its behavior. Easy! 8 | 9 | ## How to use 10 | 11 | 1. [Download](https://github.com/Thor-x86/arduino_cli/archive/master.zip) (or clone) this repo 12 | 2. [Install Arduino IDE](https://www.arduino.cc/en/software) 13 | 3. Open `arduino_cli.ino` 14 | 4. Make sure the IDE is configured based on Microcontroller that you'll use 15 | 5. Click ➡ 16 | 6. Wait until finish, then click 🔍 (Serial Monitor) 17 | 7. Now it's ready to be operated, type `help` then hit enter to see available commands -------------------------------------------------------------------------------- /arduino_cli.h: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | #define PIN_INVALID 0xff 4 | 5 | extern void help(String *cmdPtr = NULL); 6 | extern byte parsePin(String *pinStr); 7 | extern void cmd_get(String *cmd, String *args); 8 | extern void cmd_set(String *cmd, String *args); 9 | extern void cmd_tail(String *cmd, String *args); 10 | #ifdef HAVE_HWSERIAL1 11 | // Only for boards with multiple Serial HW 12 | extern void cmd_send(String *cmd, String *args); 13 | extern void cmd_listen(String *cmd, String *args); 14 | #endif 15 | extern void execute(String *cmdName, String *cmdValues); 16 | -------------------------------------------------------------------------------- /arduino_cli.ino: -------------------------------------------------------------------------------- 1 | /** 2 | * Arduino CLI for I/O Testing 3 | * or PC program <=> Arduino communication 4 | * 5 | * By: Athaariq Ardhiansyah 6 | **/ 7 | 8 | #include "arduino_cli.h" 9 | 10 | void setup() 11 | { 12 | // Initialize Serial 13 | Serial.begin(115200); 14 | 15 | // Blink LED if serial not connected 16 | bool isLit = false; 17 | pinMode(LED_BUILTIN, OUTPUT); 18 | while (!Serial) 19 | { 20 | if (isLit) 21 | { 22 | digitalWrite(LED_BUILTIN, LOW); 23 | } 24 | else 25 | { 26 | digitalWrite(LED_BUILTIN, HIGH); 27 | } 28 | isLit = !isLit; 29 | delay(500); 30 | } 31 | digitalWrite(LED_BUILTIN, HIGH); 32 | 33 | // Welcome screen 34 | Serial.println("Welcome to Arduino CLI!"); 35 | Serial.println("Enter \"help\" for information"); 36 | Serial.println(""); 37 | Serial.println("Another projects: https://github.com/Thor-x86"); 38 | Serial.println(""); 39 | } 40 | 41 | void loop() 42 | { 43 | // Get char length 44 | int n = Serial.available(); 45 | 46 | // Parse command if available 47 | if (n > 0) 48 | { 49 | // Lit the LED to indicate working 50 | digitalWrite(LED_BUILTIN, LOW); 51 | 52 | // Prepare variables 53 | bool isReadCommand = true; 54 | String commandName = ""; 55 | String commandValue = ""; 56 | 57 | // Print and resolve name+value 58 | Serial.print("> "); 59 | for (int i = 0; i < n; i++) 60 | { 61 | char currentChar = (char)Serial.read(); 62 | Serial.print(currentChar); 63 | if (currentChar == '\n' || currentChar == '\r') 64 | { 65 | continue; 66 | } 67 | else if (currentChar == ' ' && isReadCommand) 68 | { 69 | isReadCommand = false; 70 | } 71 | else if (isReadCommand) 72 | { 73 | commandName += currentChar; 74 | } 75 | else 76 | { 77 | commandValue += currentChar; 78 | } 79 | } 80 | 81 | // Execute the command 82 | execute(&commandName, &commandValue); 83 | 84 | // Unlit the LED to indicate job done 85 | digitalWrite(LED_BUILTIN, HIGH); 86 | } 87 | } 88 | 89 | void yield() 90 | { 91 | // Workaround for STM32 Arduino core problem 92 | // keep this empty 93 | } -------------------------------------------------------------------------------- /cmd_get.cpp: -------------------------------------------------------------------------------- 1 | #include "arduino_cli.h" 2 | 3 | /** 4 | * Get input from a digital/analog pin 5 | */ 6 | void cmd_get(String *cmd, String *args) { 7 | // Make sure cmd parameter isn't null 8 | if(cmd == NULL) { 9 | Serial.println("ERROR: 1st param of cmd_get must not NULL"); 10 | return; 11 | } 12 | 13 | // Show usage if there is no argument 14 | if(args == NULL) { 15 | help(cmd); 16 | return; 17 | } 18 | 19 | // Prepare variables 20 | String pinStr = ""; 21 | bool hasPinStr = false; 22 | for(int i = 0; i < args->length(); i++) { 23 | char each = args->charAt(i); 24 | if(each == ' ') { 25 | if(hasPinStr) { 26 | Serial.println("Excessive arguments"); 27 | Serial.println(""); 28 | help(cmd); 29 | return; 30 | } else { 31 | hasPinStr = true; 32 | } 33 | } else if(!hasPinStr) { 34 | pinStr += each; 35 | } 36 | } 37 | 38 | // Parse pin string 39 | byte pin = parsePin(&pinStr); 40 | if(pin == PIN_INVALID) { 41 | // CONDITION: Invalid Pin ID 42 | Serial.println("Pin ID \"" + pinStr + "\" is not valid"); 43 | Serial.println(""); 44 | help(cmd); 45 | return; 46 | } 47 | 48 | // Set pin role 49 | pinMode(pin, INPUT); 50 | 51 | // Read and print the data 52 | if(pinStr.charAt(0) == 'A') { 53 | // CONDITION: Analog pin 54 | Serial.println(analogRead(pin)); 55 | } else { 56 | // CONDITION: Digital pin 57 | Serial.println(digitalRead(pin)); 58 | } 59 | Serial.println(""); 60 | } 61 | -------------------------------------------------------------------------------- /cmd_listen.cpp: -------------------------------------------------------------------------------- 1 | #include "arduino_cli.h" 2 | 3 | #ifdef HAVE_HWSERIAL1 4 | /** 5 | * Listen for another Serial Port 6 | */ 7 | void cmd_listen(String *cmd, String *args) { 8 | // Make sure cmd parameter isn't null 9 | if(cmd == NULL) { 10 | Serial.println("ERROR: 1st param of cmd_get must not NULL"); 11 | return; 12 | } 13 | 14 | // Show usage if there is no argument 15 | if(args == NULL) { 16 | help(cmd); 17 | return; 18 | } 19 | 20 | // Prepare variables 21 | String baudrateStr = ""; 22 | bool hasBaudrateStr = false; 23 | for(int i = 0; i < args->length(); i++) { 24 | char each = args->charAt(i); 25 | if(each == ' ') { 26 | if(hasBaudrateStr) { 27 | Serial.println("Excessive arguments"); 28 | Serial.println(""); 29 | help(cmd); 30 | return; 31 | } else { 32 | hasBaudrateStr = true; 33 | } 34 | } else if(!hasBaudrateStr) { 35 | baudrateStr += each; 36 | } 37 | } 38 | 39 | // Parse baudrate 40 | int baudrate = baudrateStr.toInt(); 41 | if(baudrate <= 0) { 42 | if(baudrateStr.length() > 0) { 43 | // CONDITION: Baudrate is invalid 44 | Serial.println("Baudrate must number and more than 0"); 45 | Serial.println(""); 46 | help(cmd); 47 | return; 48 | } else { 49 | // CONDITION: Baudrate is not specified, fallback to default 50 | baudrate = 115200; 51 | } 52 | } 53 | 54 | // Initialize second serial port 55 | Serial1.begin(baudrate); 56 | 57 | // Listen from second serial port 58 | while(true) { 59 | int n = Serial1.available(); 60 | for(int i = 0; i < n; i++) { 61 | Serial.write(Serial1.read()); 62 | } 63 | if(n > 0) { 64 | Serial.flush(); 65 | } 66 | 67 | // Stop loop on hit enter 68 | if(Serial.available() > 0) break; 69 | } 70 | 71 | // Disconnect second serial port 72 | Serial1.end(); 73 | 74 | // Print "stopped" 75 | Serial.println(""); 76 | Serial.println("[Stopped]"); 77 | Serial.println(""); 78 | 79 | // Serial buffer cleanup 80 | int n = Serial.available(); 81 | for(int i = 0; i < n; i++) { 82 | Serial.read(); 83 | } 84 | } 85 | #endif -------------------------------------------------------------------------------- /cmd_send.cpp: -------------------------------------------------------------------------------- 1 | #include "arduino_cli.h" 2 | 3 | #ifdef HAVE_HWSERIAL1 4 | /** 5 | * Send data to another Serial Port 6 | */ 7 | void cmd_send(String *cmd, String *args) { 8 | // Make sure cmd parameter isn't null 9 | if(cmd == NULL) { 10 | Serial.println("ERROR: 1st param of cmd_tail must not NULL"); 11 | return; 12 | } 13 | 14 | // Show usage if there is no argument 15 | if(args == NULL) { 16 | help(cmd); 17 | return; 18 | } 19 | 20 | // Prepare variables 21 | String messageStr = ""; 22 | String baudrateStr = ""; 23 | 24 | // Tokenize arguments 25 | byte argIndex = 0; 26 | bool isInQuote = false; 27 | bool isEscaping = false; 28 | for(byte i = 0; i < args->length(); i++) { 29 | char each = args->charAt(i); 30 | if(each == '"' && !isEscaping) { 31 | isInQuote = !isInQuote; 32 | } else if(each == '\\' && isInQuote && !isEscaping) { 33 | isEscaping = true; 34 | continue; 35 | } else if(each == ' ' && !isInQuote) { 36 | if(argIndex >= 1) { 37 | Serial.println("Excessive arguments"); 38 | Serial.println(""); 39 | help(cmd); 40 | return; 41 | } else { 42 | argIndex++; 43 | } 44 | } else { 45 | if(isEscaping) { 46 | if(each == 'n') { 47 | each = '\n'; 48 | } else if(each == 'r') { 49 | each = '\r'; 50 | } else if(each == 't') { 51 | each = '\t'; 52 | } 53 | } 54 | switch(argIndex) { 55 | case 0: 56 | messageStr += each; 57 | break; 58 | case 1: 59 | baudrateStr += each; 60 | break; 61 | } 62 | } 63 | isEscaping = false; 64 | } 65 | 66 | // Abort if not enough argument 67 | if(args->length() <= 0) { 68 | help(cmd); 69 | return; 70 | } 71 | 72 | // Show error on unclosed quote 73 | if(isInQuote) { 74 | Serial.println("ERROR: Unclosed quote (\")"); 75 | Serial.println(""); 76 | return; 77 | } 78 | 79 | // Parse baudrate 80 | int baudrate = baudrateStr.toInt(); 81 | if(baudrate <= 0) { 82 | if(baudrateStr.length() > 0) { 83 | // CONDITION: Baudrate is invalid 84 | Serial.println("Baudrate must number and more than 0"); 85 | Serial.println(""); 86 | help(cmd); 87 | return; 88 | } else { 89 | // CONDITION: Baudrate is not specified, fallback to default 90 | baudrate = 115200; 91 | } 92 | } 93 | 94 | // Initialize second serial port 95 | Serial1.begin(baudrate); 96 | byte countdown = 10; 97 | while(!Serial1) { 98 | delay(1000); 99 | 100 | // Cleanup first serial, just in case accidental input 101 | int n = Serial.available(); 102 | for(int i = 0; i < n; i++) { 103 | Serial.read(); 104 | } 105 | 106 | if(countdown > 0) { 107 | countdown--; 108 | } else { 109 | Serial.println("Cannot connect to 2nd Serial Port"); 110 | Serial.println(""); 111 | return; 112 | } 113 | } 114 | 115 | // Send message based on data type 116 | if(args->charAt(0) == '"') { 117 | // CONDITION: Message enforced as string 118 | Serial1.print(messageStr); 119 | } else if(messageStr.length() > 1 && messageStr.charAt(0) == '0') { 120 | // CONDITION: Message is raw bytes 121 | String prefix = messageStr.substring(0,2); 122 | byte radix = 0; 123 | if(prefix == "0b") { 124 | radix = 2; 125 | } else if(prefix == "0o") { 126 | radix = 8; 127 | } else if(prefix == "0d") { 128 | radix = 10; 129 | } else if(prefix == "0x") { 130 | radix = 16; 131 | } 132 | 133 | long long messageBytes; 134 | if(radix > 0) { 135 | messageBytes = strtol(&messageStr[2], NULL, radix); 136 | } else { 137 | messageBytes = strtol(&messageStr[0], NULL, 0); 138 | } 139 | 140 | Serial1.write((byte)(messageBytes & 0xff)); 141 | if(messageBytes < 0 || messageBytes > 0xff) { 142 | Serial1.write((byte)((messageBytes >> 8) & 0xff)); 143 | } 144 | if(messageBytes < 0 || messageBytes > 0xffff) { 145 | Serial1.write((byte)((messageBytes >> 16) & 0xff)); 146 | } 147 | if(messageBytes < 0 || messageBytes > 0xffffff) { 148 | Serial1.write((byte)((messageBytes >> 24) & 0xff)); 149 | } 150 | if(messageBytes < 0 || messageBytes > 0xffffffff) { 151 | Serial1.write((byte)((messageBytes >> 32) & 0xff)); 152 | } 153 | if(messageBytes < 0 || messageBytes > 0xffffffffff) { 154 | Serial1.write((byte)((messageBytes >> 40) & 0xff)); 155 | } 156 | if(messageBytes < 0 || messageBytes > 0xffffffffffff) { 157 | Serial1.write((byte)((messageBytes >> 48) & 0xff)); 158 | } 159 | if(messageBytes < 0 || messageBytes > 0xffffffffffffff) { 160 | Serial1.write((byte)((messageBytes >> 56) & 0xff)); 161 | } 162 | if(messageBytes < 0 || messageBytes > 0xffffffffffffffff) { 163 | Serial1.write((byte)((messageBytes >> 64) & 0xff)); 164 | } 165 | Serial1.flush(); 166 | } else { 167 | // CONDITION: Message is either number or plain string 168 | Serial1.print(messageStr); 169 | } 170 | 171 | // Disconnect second serial port 172 | Serial1.end(); 173 | 174 | // Print response 175 | Serial.println("ok"); 176 | Serial.println(""); 177 | } 178 | #endif -------------------------------------------------------------------------------- /cmd_set.cpp: -------------------------------------------------------------------------------- 1 | #include "arduino_cli.h" 2 | 3 | /** 4 | * Set output to a digital/analog pin 5 | */ 6 | void cmd_set(String *cmd, String *args) { 7 | // Make sure cmd parameter isn't null 8 | if(cmd == NULL) { 9 | Serial.println("ERROR: 1st param of cmd_set must not NULL"); 10 | return; 11 | } 12 | 13 | // Show usage if there is no argument 14 | if(args == NULL) { 15 | help(cmd); 16 | return; 17 | } 18 | 19 | // Prepare variables 20 | String pinStr = ""; 21 | String valueStr = ""; 22 | 23 | // Tokenize arguments 24 | byte argIndex = 0; 25 | for(byte i = 0; i < args->length(); i++) { 26 | char each = args->charAt(i); 27 | if(each == ' ') { 28 | if(argIndex >= 1) { 29 | Serial.println("Excessive arguments"); 30 | Serial.println(""); 31 | help(cmd); 32 | return; 33 | } else { 34 | argIndex++; 35 | } 36 | } else { 37 | switch(argIndex) { 38 | case 0: 39 | pinStr += each; 40 | break; 41 | case 1: 42 | valueStr += each; 43 | break; 44 | } 45 | } 46 | } 47 | 48 | // Abort if not enough argument 49 | if(argIndex < 1) { 50 | Serial.println("Missing required argument"); 51 | Serial.println(""); 52 | help(cmd); 53 | return; 54 | } 55 | 56 | // Parse pin string 57 | byte pin = parsePin(&pinStr); 58 | if(pin == PIN_INVALID) { 59 | // CONDITION: Invalid Pin ID 60 | Serial.println("Pin ID \"" + pinStr + "\" is not valid"); 61 | Serial.println(""); 62 | help(cmd); 63 | return; 64 | } 65 | 66 | // Read and print the data 67 | if(pinStr.charAt(0) == 'A') { 68 | // CONDITION: Analog pin 69 | // Parse value string 70 | float value = valueStr.toFloat(); 71 | if(value == 0 && valueStr != "0") { 72 | // CONDITION: Invalid value 73 | Serial.println("Pin ID \"" + pinStr + "\" is analog, so the value must number"); 74 | Serial.println(""); 75 | help(cmd); 76 | return; 77 | } 78 | 79 | // Write value 80 | pinMode(pin, OUTPUT); 81 | analogWrite(pin, value); 82 | } else { 83 | // CONDITION: Digital pin 84 | if(valueStr == "on") { 85 | pinMode(pin, OUTPUT); 86 | digitalWrite(pin, HIGH); 87 | } else if(valueStr == "off") { 88 | pinMode(pin, OUTPUT); 89 | digitalWrite(pin, LOW); 90 | } else { 91 | // CONDITION: Invalid value 92 | Serial.println("Pin ID \"" + pinStr + "\" is digital, so the value must either on or off"); 93 | Serial.println(""); 94 | help(cmd); 95 | return; 96 | } 97 | } 98 | 99 | // Print response 100 | Serial.println("ok"); 101 | Serial.println(""); 102 | } 103 | -------------------------------------------------------------------------------- /cmd_tail.cpp: -------------------------------------------------------------------------------- 1 | #include "arduino_cli.h" 2 | 3 | /** 4 | * Keep reading input from digital/analog pin 5 | */ 6 | void cmd_tail(String *cmd, String *args) { 7 | // Make sure cmd parameter isn't null 8 | if(cmd == NULL) { 9 | Serial.println("ERROR: 1st param of cmd_tail must not NULL"); 10 | return; 11 | } 12 | 13 | // Show usage if there is no argument 14 | if(args == NULL) { 15 | help(cmd); 16 | return; 17 | } 18 | 19 | // Prepare variables 20 | String pinStr = ""; 21 | String intervalStr = ""; 22 | 23 | // Tokenize arguments 24 | byte argIndex = 0; 25 | for(byte i = 0; i < args->length(); i++) { 26 | char each = args->charAt(i); 27 | if(each == ' ') { 28 | if(argIndex >= 1) { 29 | Serial.println("Excessive arguments"); 30 | Serial.println(""); 31 | help(cmd); 32 | return; 33 | } else { 34 | argIndex++; 35 | } 36 | } else { 37 | switch(argIndex) { 38 | case 0: 39 | pinStr += each; 40 | break; 41 | case 1: 42 | intervalStr += each; 43 | break; 44 | } 45 | } 46 | } 47 | 48 | // Abort if not enough argument 49 | if(args->length() <= 0) { 50 | help(cmd); 51 | return; 52 | } 53 | 54 | // Parse pin string 55 | byte pin = parsePin(&pinStr); 56 | if(pin == PIN_INVALID) { 57 | // CONDITION: Invalid Pin ID 58 | Serial.println("Pin ID \"" + pinStr + "\" is not valid"); 59 | Serial.println(""); 60 | help(cmd); 61 | return; 62 | } 63 | 64 | // Parse interval 65 | unsigned int interval = intervalStr.toInt(); 66 | if(interval == 0) { 67 | if(intervalStr.length() > 0) { 68 | // CONDITION: interval_ms is invalid 69 | Serial.println("interval_ms must number, not \"" + intervalStr + "\""); 70 | Serial.println(""); 71 | help(cmd); 72 | return; 73 | } else { 74 | // CONDITION: interval_ms is not specified, fallback to default 75 | interval = 500; 76 | } 77 | } 78 | 79 | // Set pin role 80 | pinMode(pin, INPUT); 81 | 82 | // Read and print the data 83 | if(pinStr.charAt(0) == 'A') { 84 | // CONDITION: Analog pin 85 | while(true) { 86 | Serial.println(analogRead(pin)); 87 | delay(interval); 88 | if(Serial.available() > 0) break; 89 | } 90 | } else { 91 | // CONDITION: Digital pin 92 | while(true) { 93 | Serial.println(digitalRead(pin)); 94 | delay(interval); 95 | if(Serial.available() > 0) break; 96 | } 97 | } 98 | Serial.println(""); 99 | Serial.println("[Stopped]"); 100 | Serial.println(""); 101 | 102 | // Serial buffer cleanup 103 | int n = Serial.available(); 104 | for(int i = 0; i < n; i++) { 105 | Serial.read(); 106 | } 107 | } 108 | -------------------------------------------------------------------------------- /execute.cpp: -------------------------------------------------------------------------------- 1 | #include "arduino_cli.h" 2 | 3 | /** 4 | * Run a command 5 | */ 6 | void execute(String *cmdName, String *cmdValues) { 7 | if(cmdName == NULL) { 8 | help(); 9 | } else if(*cmdName == "get") { 10 | cmd_get(cmdName, cmdValues); 11 | } else if(*cmdName == "set") { 12 | cmd_set(cmdName, cmdValues); 13 | } else if(*cmdName == "tail") { 14 | cmd_tail(cmdName, cmdValues); 15 | } 16 | 17 | // Only for boards with multiple Serial HW 18 | #ifdef HAVE_HWSERIAL1 19 | else if(*cmdName == "send") { 20 | cmd_send(cmdName, cmdValues); 21 | } else if(*cmdName == "listen") { 22 | cmd_listen(cmdName, cmdValues); 23 | } 24 | #endif 25 | 26 | else if(*cmdName == "help") { 27 | if(cmdValues->length() > 0) { 28 | help(cmdValues); 29 | } else { 30 | help(); 31 | } 32 | } else if(*cmdName == "") { 33 | // Do nothing 34 | } else { 35 | help(cmdName); 36 | } 37 | } 38 | -------------------------------------------------------------------------------- /help.cpp: -------------------------------------------------------------------------------- 1 | #include "arduino_cli.h" 2 | 3 | /** 4 | * Display general or command-specific help 5 | */ 6 | void help(String *cmdPtr) { 7 | if(cmdPtr == NULL) { 8 | // CONDITION: Command name isn't specified 9 | Serial.println("Available Commands:"); 10 | Serial.println("get ----- Get input from a digital/analog pin"); 11 | Serial.println("set ----- Set output to a digital/analog pin"); 12 | Serial.println("tail ---- Keep reading input from digital/analog pin"); 13 | #ifdef HAVE_HWSERIAL1 14 | // Only for boards with multiple Serial HW 15 | Serial.println("send ---- Send data to another Serial Port"); 16 | Serial.println("listen -- Listen for another Serial Port"); 17 | #endif 18 | Serial.println("help ---- Show information about available commands"); 19 | Serial.println(""); 20 | Serial.println("Run this command for details: help "); 21 | Serial.println(""); 22 | } else { 23 | // CONDITION: Command name specified 24 | // Get only command name 25 | String cmd = ""; 26 | for(int i = 0; i < cmdPtr->length(); i++) { 27 | char eachChar = cmdPtr->charAt(i); 28 | if(eachChar == ' ') break; 29 | cmd += eachChar; 30 | } 31 | 32 | // Parse command name 33 | if(cmd == "get") { 34 | Serial.println("USAGE: get "); 35 | Serial.println(""); 36 | } else if(cmd == "set") { 37 | Serial.println("USAGE: set "); 38 | Serial.println(""); 39 | } else if(cmd == "tail") { 40 | Serial.println("USAGE: tail [interval_ms]"); 41 | Serial.println(""); 42 | Serial.println("Default:"); 43 | Serial.println(" interval_ms = 500"); 44 | Serial.println(""); 45 | Serial.println("NOTE: Hit enter to stop listening"); 46 | Serial.println(""); 47 | } 48 | #ifdef HAVE_HWSERIAL1 49 | // Only for boards with multiple Serial HW 50 | else if(cmd == "send") { 51 | Serial.println("USAGE: send [baudrate]"); 52 | Serial.println(""); 53 | Serial.println("Default:"); 54 | Serial.println(" baudrate = 115200"); 55 | Serial.println(""); 56 | Serial.println("Examples:"); 57 | Serial.println(" send hello"); 58 | Serial.println(" send \"hello, world!\""); 59 | Serial.println(" send \"first line\\nsecond line\""); 60 | Serial.println(" send 132"); 61 | Serial.println(" send 0b10011011"); 62 | Serial.println(" send 0x7f"); 63 | Serial.println(" send hello 9600"); 64 | Serial.println(" send \"hello, world!\" 9600"); 65 | Serial.println(""); 66 | } else if(cmd == "listen") { 67 | Serial.println("USAGE: listen [baudrate]"); 68 | Serial.println(""); 69 | Serial.println("Default:"); 70 | Serial.println(" baudrate = 115200"); 71 | Serial.println(""); 72 | Serial.println("NOTE: Hit enter to stop listening"); 73 | Serial.println(""); 74 | } 75 | #endif 76 | else if(cmd == "help") { 77 | help(); 78 | } else { 79 | Serial.println("Command \"" + cmd + "\" not found"); 80 | Serial.println(""); 81 | help(); 82 | } 83 | } 84 | } 85 | -------------------------------------------------------------------------------- /parsePin.cpp: -------------------------------------------------------------------------------- 1 | #include "arduino_cli.h" 2 | 3 | byte parsePin(String *pinStr) 4 | { 5 | if (pinStr == NULL) 6 | { 7 | Serial.println("ERROR: cannot parse NULL pin"); 8 | return PIN_INVALID; 9 | } 10 | 11 | byte pin = pinStr->toInt(); 12 | if (pin == 0 && *pinStr != "0") 13 | { 14 | // CONDITION: Non-numeric PIN ID 15 | 16 | if (*pinStr == "") 17 | { 18 | // Just in case A0 isn't available for targeted board 19 | return PIN_INVALID; 20 | } 21 | 22 | #ifdef PIN_A0 23 | else if (*pinStr == "A0") 24 | { 25 | return PIN_A0; 26 | } 27 | #endif 28 | 29 | #ifdef PIN_A1 30 | else if (*pinStr == "A1") 31 | { 32 | return PIN_A1; 33 | } 34 | #endif 35 | 36 | #ifdef PIN_A2 37 | else if (*pinStr == "A2") 38 | { 39 | return PIN_A2; 40 | } 41 | #endif 42 | 43 | #ifdef PIN_A3 44 | else if (*pinStr == "A3") 45 | { 46 | return PIN_A3; 47 | } 48 | #endif 49 | 50 | #ifdef PIN_A4 51 | else if (*pinStr == "A4") 52 | { 53 | return PIN_A4; 54 | } 55 | #endif 56 | 57 | #ifdef PIN_A5 58 | else if (*pinStr == "A5") 59 | { 60 | return PIN_A5; 61 | } 62 | #endif 63 | 64 | #ifdef PIN_A6 65 | else if (*pinStr == "A6") 66 | { 67 | return PIN_A6; 68 | } 69 | #endif 70 | 71 | #ifdef PIN_A7 72 | else if (*pinStr == "A7") 73 | { 74 | return PIN_A7; 75 | } 76 | #endif 77 | 78 | #ifdef PIN_A8 79 | else if (*pinStr == "A8") 80 | { 81 | return PIN_A8; 82 | } 83 | #endif 84 | 85 | #ifdef PIN_A9 86 | else if (*pinStr == "A9") 87 | { 88 | return PIN_A9; 89 | } 90 | #endif 91 | 92 | #ifdef PIN_A10 93 | else if (*pinStr == "A10") 94 | { 95 | return PIN_A10; 96 | } 97 | #endif 98 | 99 | #ifdef PIN_A11 100 | else if (*pinStr == "A11") 101 | { 102 | return PIN_A11; 103 | } 104 | #endif 105 | 106 | #ifdef PIN_A12 107 | else if (*pinStr == "A12") 108 | { 109 | return PIN_A12; 110 | } 111 | #endif 112 | 113 | #ifdef PIN_A13 114 | else if (*pinStr == "A13") 115 | { 116 | return PIN_A13; 117 | } 118 | #endif 119 | 120 | #ifdef PIN_A14 121 | else if (*pinStr == "A14") 122 | { 123 | return PIN_A14; 124 | } 125 | #endif 126 | 127 | #ifdef PIN_A15 128 | else if (*pinStr == "A15") 129 | { 130 | return PIN_A15; 131 | } 132 | #endif 133 | 134 | #ifdef PIN_A16 135 | else if (*pinStr == "A16") 136 | { 137 | return PIN_A16; 138 | } 139 | #endif 140 | 141 | #ifdef PIN_A17 142 | else if (*pinStr == "A17") 143 | { 144 | return PIN_A17; 145 | } 146 | #endif 147 | 148 | #ifdef PIN_A18 149 | else if (*pinStr == "A18") 150 | { 151 | return PIN_A18; 152 | } 153 | #endif 154 | 155 | #ifdef PIN_A19 156 | else if (*pinStr == "A19") 157 | { 158 | return PIN_A19; 159 | } 160 | #endif 161 | 162 | #ifdef PIN_A20 163 | else if (*pinStr == "A20") 164 | { 165 | return PIN_A20; 166 | } 167 | #endif 168 | 169 | #ifdef PIN_A21 170 | else if (*pinStr == "A21") 171 | { 172 | return PIN_A21; 173 | } 174 | #endif 175 | 176 | #ifdef PIN_A22 177 | else if (*pinStr == "A22") 178 | { 179 | return PIN_A22; 180 | } 181 | #endif 182 | 183 | #ifdef PIN_A23 184 | else if (*pinStr == "A23") 185 | { 186 | return PIN_A23; 187 | } 188 | #endif 189 | 190 | #ifdef PA1 191 | else if (*pinStr == "PA1") 192 | { 193 | return PA1; 194 | } 195 | #endif 196 | 197 | #ifdef PA2 198 | else if (*pinStr == "PA2") 199 | { 200 | return PA2; 201 | } 202 | #endif 203 | 204 | #ifdef PA3 205 | else if (*pinStr == "PA3") 206 | { 207 | return PA3; 208 | } 209 | #endif 210 | 211 | #ifdef PA4 212 | else if (*pinStr == "PA4") 213 | { 214 | return PA4; 215 | } 216 | #endif 217 | 218 | #ifdef PA5 219 | else if (*pinStr == "PA5") 220 | { 221 | return PA5; 222 | } 223 | #endif 224 | 225 | #ifdef PA6 226 | else if (*pinStr == "PA6") 227 | { 228 | return PA6; 229 | } 230 | #endif 231 | 232 | #ifdef PA7 233 | else if (*pinStr == "PA7") 234 | { 235 | return PA7; 236 | } 237 | #endif 238 | 239 | #ifdef PA8 240 | else if (*pinStr == "PA8") 241 | { 242 | return PA8; 243 | } 244 | #endif 245 | 246 | #ifdef PA9 247 | else if (*pinStr == "PA9") 248 | { 249 | return PA9; 250 | } 251 | #endif 252 | 253 | #ifdef PA10 254 | else if (*pinStr == "PA10") 255 | { 256 | return PA10; 257 | } 258 | #endif 259 | 260 | #ifdef PA11 261 | else if (*pinStr == "PA11") 262 | { 263 | return PA11; 264 | } 265 | #endif 266 | 267 | #ifdef PA12 268 | else if (*pinStr == "PA12") 269 | { 270 | return PA12; 271 | } 272 | #endif 273 | 274 | #ifdef PA13 275 | else if (*pinStr == "PA13") 276 | { 277 | return PA13; 278 | } 279 | #endif 280 | 281 | #ifdef PA14 282 | else if (*pinStr == "PA14") 283 | { 284 | return PA14; 285 | } 286 | #endif 287 | 288 | #ifdef PA15 289 | else if (*pinStr == "PA15") 290 | { 291 | return PA15; 292 | } 293 | #endif 294 | 295 | #ifdef PB1 296 | else if (*pinStr == "PB1") 297 | { 298 | return PB1; 299 | } 300 | #endif 301 | 302 | #ifdef PB2 303 | else if (*pinStr == "PB2") 304 | { 305 | return PB2; 306 | } 307 | #endif 308 | 309 | #ifdef PB3 310 | else if (*pinStr == "PB3") 311 | { 312 | return PB3; 313 | } 314 | #endif 315 | 316 | #ifdef PB4 317 | else if (*pinStr == "PB4") 318 | { 319 | return PB4; 320 | } 321 | #endif 322 | 323 | #ifdef PB5 324 | else if (*pinStr == "PB5") 325 | { 326 | return PB5; 327 | } 328 | #endif 329 | 330 | #ifdef PB6 331 | else if (*pinStr == "PB6") 332 | { 333 | return PB6; 334 | } 335 | #endif 336 | 337 | #ifdef PB7 338 | else if (*pinStr == "PB7") 339 | { 340 | return PB7; 341 | } 342 | #endif 343 | 344 | #ifdef PB8 345 | else if (*pinStr == "PB8") 346 | { 347 | return PB8; 348 | } 349 | #endif 350 | 351 | #ifdef PB9 352 | else if (*pinStr == "PB9") 353 | { 354 | return PB9; 355 | } 356 | #endif 357 | 358 | #ifdef PB10 359 | else if (*pinStr == "PB10") 360 | { 361 | return PB10; 362 | } 363 | #endif 364 | 365 | #ifdef PB11 366 | else if (*pinStr == "PB11") 367 | { 368 | return PB11; 369 | } 370 | #endif 371 | 372 | #ifdef PB12 373 | else if (*pinStr == "PB12") 374 | { 375 | return PB12; 376 | } 377 | #endif 378 | 379 | #ifdef PB13 380 | else if (*pinStr == "PB13") 381 | { 382 | return PB13; 383 | } 384 | #endif 385 | 386 | #ifdef PB14 387 | else if (*pinStr == "PB14") 388 | { 389 | return PB14; 390 | } 391 | #endif 392 | 393 | #ifdef PB15 394 | else if (*pinStr == "PB15") 395 | { 396 | return PB15; 397 | } 398 | #endif 399 | 400 | #ifdef PC1 401 | else if (*pinStr == "PC1") 402 | { 403 | return PC1; 404 | } 405 | #endif 406 | 407 | #ifdef PC2 408 | else if (*pinStr == "PC2") 409 | { 410 | return PC2; 411 | } 412 | #endif 413 | 414 | #ifdef PC3 415 | else if (*pinStr == "PC3") 416 | { 417 | return PC3; 418 | } 419 | #endif 420 | 421 | #ifdef PC4 422 | else if (*pinStr == "PC4") 423 | { 424 | return PC4; 425 | } 426 | #endif 427 | 428 | #ifdef PC5 429 | else if (*pinStr == "PC5") 430 | { 431 | return PC5; 432 | } 433 | #endif 434 | 435 | #ifdef PC6 436 | else if (*pinStr == "PC6") 437 | { 438 | return PC6; 439 | } 440 | #endif 441 | 442 | #ifdef PC7 443 | else if (*pinStr == "PC7") 444 | { 445 | return PC7; 446 | } 447 | #endif 448 | 449 | #ifdef PC8 450 | else if (*pinStr == "PC8") 451 | { 452 | return PC8; 453 | } 454 | #endif 455 | 456 | #ifdef PC9 457 | else if (*pinStr == "PC9") 458 | { 459 | return PC9; 460 | } 461 | #endif 462 | 463 | #ifdef PC10 464 | else if (*pinStr == "PC10") 465 | { 466 | return PC10; 467 | } 468 | #endif 469 | 470 | #ifdef PC11 471 | else if (*pinStr == "PC11") 472 | { 473 | return PC11; 474 | } 475 | #endif 476 | 477 | #ifdef PC12 478 | else if (*pinStr == "PC12") 479 | { 480 | return PC12; 481 | } 482 | #endif 483 | 484 | #ifdef PC13 485 | else if (*pinStr == "PC13") 486 | { 487 | return PC13; 488 | } 489 | #endif 490 | 491 | #ifdef PC14 492 | else if (*pinStr == "PC14") 493 | { 494 | return PC14; 495 | } 496 | #endif 497 | 498 | #ifdef PC15 499 | else if (*pinStr == "PC15") 500 | { 501 | return PC15; 502 | } 503 | #endif 504 | 505 | #ifdef PD1 506 | else if (*pinStr == "PD1") 507 | { 508 | return PD1; 509 | } 510 | #endif 511 | 512 | #ifdef PD2 513 | else if (*pinStr == "PD2") 514 | { 515 | return PD2; 516 | } 517 | #endif 518 | 519 | #ifdef PD3 520 | else if (*pinStr == "PD3") 521 | { 522 | return PD3; 523 | } 524 | #endif 525 | 526 | #ifdef PD4 527 | else if (*pinStr == "PD4") 528 | { 529 | return PD4; 530 | } 531 | #endif 532 | 533 | #ifdef PD5 534 | else if (*pinStr == "PD5") 535 | { 536 | return PD5; 537 | } 538 | #endif 539 | 540 | #ifdef PD6 541 | else if (*pinStr == "PD6") 542 | { 543 | return PD6; 544 | } 545 | #endif 546 | 547 | #ifdef PD7 548 | else if (*pinStr == "PD7") 549 | { 550 | return PD7; 551 | } 552 | #endif 553 | 554 | #ifdef PD8 555 | else if (*pinStr == "PD8") 556 | { 557 | return PD8; 558 | } 559 | #endif 560 | 561 | #ifdef PD9 562 | else if (*pinStr == "PD9") 563 | { 564 | return PD9; 565 | } 566 | #endif 567 | 568 | #ifdef PD10 569 | else if (*pinStr == "PD10") 570 | { 571 | return PD10; 572 | } 573 | #endif 574 | 575 | #ifdef PD11 576 | else if (*pinStr == "PD11") 577 | { 578 | return PD11; 579 | } 580 | #endif 581 | 582 | #ifdef PD12 583 | else if (*pinStr == "PD12") 584 | { 585 | return PD12; 586 | } 587 | #endif 588 | 589 | #ifdef PD13 590 | else if (*pinStr == "PD13") 591 | { 592 | return PD13; 593 | } 594 | #endif 595 | 596 | #ifdef PD14 597 | else if (*pinStr == "PD14") 598 | { 599 | return PD14; 600 | } 601 | #endif 602 | 603 | #ifdef PD15 604 | else if (*pinStr == "PD15") 605 | { 606 | return PD15; 607 | } 608 | #endif 609 | 610 | // CONDITION: Non-numeric PIN ID but not supported 611 | return PIN_INVALID; 612 | } 613 | else 614 | { 615 | // CONDITION: Numeric PIN ID 616 | return pin; 617 | } 618 | } 619 | --------------------------------------------------------------------------------