void loop() { if (client.connected()) { isConnected = true; report(); a = client.available(); if (a > 0) { #ifdef DEBUG Serial.print("Bytes Available: "); Serial.println(a, DEC); #endif action = client.read(); #ifdef DEBUG Serial.print("Action received: "); Serial.println(action, DEC); #endif // is the action valid? if (action <= msg_count) { // is there enough data left in the buffer to process this action? // if not, stop and fix if (msgMinLength[action] <= a) { int pin, mode, val, type, speed, address, stop, len, i; switch (action) { case msg_pinMode: // pinMode pin = client.read(); mode = client.read(); #ifdef DEBUG Serial.print("PIN received: "); Serial.println(pin); Serial.print("MODE received: "); Serial.println(mode, HEX); #endif if (mode == 0x00) { pinMode(pin, INPUT); } else if (mode == 0x02) { pinMode(pin, INPUT_PULLUP); } else if (mode == 0x03) { pinMode(pin, INPUT_PULLDOWN); } else if (mode == 0x01) { pinMode(pin, OUTPUT); } else if (mode == 0x04) { pinMode(pin, OUTPUT); if (servos[ToServoIndex(pin)].attached()) { servos[ToServoIndex(pin)].detach(); } servos[ToServoIndex(pin)].attach(pin); } break; case msg_digitalWrite: // digitalWrite pin = client.read(); val = client.read(); #ifdef DEBUG Serial.print("PIN received: "); Serial.println(pin, DEC); Serial.print("VALUE received: "); Serial.println(val, HEX); #endif digitalWrite(pin, val); break; case msg_analogWrite: // analogWrite pin = client.read(); val = client.read(); #ifdef DEBUG Serial.print("PIN received: "); Serial.println(pin, DEC); Serial.print("VALUE received: "); Serial.println(val, HEX); #endif analogWrite(pin, val); break; case msg_digitalRead: // digitalRead pin = client.read(); val = digitalRead(pin); #ifdef DEBUG Serial.print("PIN received: "); Serial.println(pin, DEC); Serial.print("VALUE sent: "); Serial.println(val, HEX); #endif server.write(0x03); // could be (action) server.write(pin); server.write(val); break; case msg_analogRead: // analogRead pin = client.read(); val = analogRead(pin); #ifdef DEBUG Serial.print("PIN received: "); Serial.println(pin, DEC); Serial.print("VALUE sent: "); Serial.println(val, HEX); #endif server.write(0x04); // could be (action) server.write(pin); server.write(val); break; case msg_setAlwaysSendBit: // set always send bit pin = client.read(); val = client.read(); reading[pin] = val; break; // Serial API case msg_serialBegin: // serial.begin type = client.read(); speed = client.read(); if (type == 0) { Serial.begin(SerialSpeed[speed]); } else { Serial1.begin(SerialSpeed[speed]); } break; case msg_serialEnd: // serial.end type = client.read(); if (type == 0) { Serial.end(); } else { Serial1.end(); } break; case msg_serialPeek: // serial.peek type = client.read(); if (type == 0) { val = Serial.peek(); } else { val = Serial1.peek(); } server.write(0x07); server.write(type); server.write(val); break; case msg_serialAvailable: // serial.available() type = client.read(); if (type == 0) { val = Serial.available(); } else { val = Serial1.available(); } server.write(0x07); server.write(type); server.write(val); break; case msg_serialWrite: // serial.write type = client.read(); len = client.read(); for (i = 0; i < len; i++) { if (type == 0) { Serial.write(client.read()); } else { Serial1.write(client.read()); } } break; case msg_serialRead: // serial.read type = client.read(); if (type == 0) { val = Serial.read(); } else { val = Serial1.read(); } server.write(0x16); server.write(type); server.write(val); break; case msg_serialFlush: // serial.flush type = client.read(); if (type == 0) { Serial.flush(); } else { Serial1.flush(); } break; // SPI API case msg_spiBegin: // SPI.begin SPI.begin(); break; case msg_spiEnd: // SPI.end SPI.end(); break; case msg_spiSetBitOrder: // SPI.setBitOrder type = client.read(); SPI.setBitOrder((type ? MSBFIRST : LSBFIRST)); break; case msg_spiSetClockDivider: // SPI.setClockDivider val = client.read(); if (val == 0) { SPI.setClockDivider(SPI_CLOCK_DIV2); } else if (val == 1) { SPI.setClockDivider(SPI_CLOCK_DIV4); } else if (val == 2) { SPI.setClockDivider(SPI_CLOCK_DIV8); } else if (val == 3) { SPI.setClockDivider(SPI_CLOCK_DIV16); } else if (val == 4) { SPI.setClockDivider(SPI_CLOCK_DIV32); } else if (val == 5) { SPI.setClockDivider(SPI_CLOCK_DIV64); } else if (val == 6) { SPI.setClockDivider(SPI_CLOCK_DIV128); } else if (val == 7) { SPI.setClockDivider(SPI_CLOCK_DIV256); } break; case msg_spiSetDataMode: // SPI.setDataMode val = client.read(); if (val == 0) { SPI.setDataMode(SPI_MODE0); } else if (val == 1) { SPI.setDataMode(SPI_MODE1); } else if (val == 2) { SPI.setDataMode(SPI_MODE2); } else if (val == 3) { SPI.setDataMode(SPI_MODE3); } break; case msg_spiTransfer: // SPI.transfer val = client.read(); val = SPI.transfer(val); server.write(0x24); server.write(val); break; // Wire API case msg_wireBegin: // Wire.begin address = client.read(); if (address == 0) { Wire.begin(); } else { Wire.begin(address); } break; case msg_wireRequestFrom: // Wire.requestFrom address = client.read(); val = client.read(); stop = client.read(); Wire.requestFrom(address, val, stop); break; case msg_wireBeginTransmission: // Wire.beginTransmission address = client.read(); Wire.beginTransmission(address); break; case msg_wireEndTransmission: // Wire.endTransmission stop = client.read(); val = Wire.endTransmission(stop); server.write(0x33); // could be (action) server.write(val); break; case msg_wireWrite: // Wire.write len = client.read(); uint8_t wireData[len]; for (i = 0; i< len; i++) { wireData[i] = client.read(); } val = Wire.write(wireData, len); server.write(0x34); // could be (action) server.write(val); break; case msg_wireAvailable: // Wire.available val = Wire.available(); server.write(0x35); // could be (action) server.write(val); break; case msg_wireRead: // Wire.read val = Wire.read(); server.write(0x36); // could be (action) server.write(val); break; case msg_servoWrite: pin = client.read(); val = client.read(); #ifdef DEBUG Serial.print("PIN: "); Serial.println(pin); Serial.print("WRITING TO SERVO: "); Serial.println(val); #endif servos[ToServoIndex(pin)].write(val); break; case msg_servoWriteMicroseconds: pin = client.read(); val = client.read(); #ifdef DEBUG Serial.print("PIN: "); Serial.println(pin); Serial.print("WRITING 'us' TO SERVO: "); Serial.println(val); #endif servos[ToServoIndex(pin)].writeMicroseconds(val); break; case msg_servoRead: pin = client.read(); val = servos[ToServoIndex(pin)].read(); server.write(0x43); // could be (action) server.write(pin); server.write(val); break; case msg_servoDetach: pin = client.read(); servos[ToServoIndex(pin)].detach(); break; default: // noop break; } // <-- This is the end of the switch } // <-- This is the end of if (idx+msgMinLength[] < length) } // <-- This is the end of the valid action check } // <-- This is the end of the length check } else { // Upon disconnection, reset the state if (isConnected) { isConnected = false; reset(); } // If no client is yet connected, check for a new connection client = server.available(); } }
void processInput() { int pin, mode, val, type, speed, address, stop, len, k, i; int byteCount = bytesRead; #if DEBUG Serial.println("--------------PROCESSING"); #endif // Only check if buffer[0] is possibly an action // when there is no action in progress. if (hasAction == false) { if (buffer[0] < ACTION_RANGE) { action = buffer[0]; bytesExpecting = bytesToExpectByAction[action] + 1; hasAction = true; #if DEBUG Serial.print("Bytes Read: "); Serial.println(bytesRead, DEC); Serial.print("Bytes Required: "); Serial.println(bytesExpecting, DEC); Serial.print("Bytes Remaining: "); Serial.println(bytesRead - bytesExpecting, DEC); #endif } } if ((bytesRead - bytesExpecting) < 0) { hasAction = false; bytesExpecting = 0; #if DEBUG Serial.println("Not Enough Bytes."); #endif return; } // When the first byte of buffer is an action and // enough bytes are read, begin processing the action. if (hasAction && bytesRead >= bytesExpecting) { // Copy the expected bytes into the cache and shift // the unused bytes to the beginning of the buffer for (k = 0; k < byteCount; k++) { // Cache the bytes that we're expecting for // this action. if (k < bytesExpecting) { cached[k] = buffer[k]; // #if DEBUG // Serial.print("Cached: "); // Serial.println(cached[k], DEC); // #endif } // Shift the unused buffer to the front buffer[k] = buffer[k + bytesExpecting]; } byteCount -= bytesExpecting; #if DEBUG Serial.print("ACTION: "); Serial.println(action, DEC); #endif // Proceed with action processing switch (action) { case PIN_MODE: // pinMode pin = cached[1]; mode = cached[2]; #if DEBUG Serial.print("PIN: "); Serial.println(pin); Serial.print("MODE: "); Serial.println(mode, HEX); #endif if (pinModeFor[pin] != mode) { if (pinModeFor[pin] == 0x04) { servos[ToServoIndex(pin)].detach(); } pinModeFor[pin] = mode; // The following modes were derived // from uses in core-firmware. if (mode == 0x00) { // INPUT pinMode(pin, INPUT_PULLDOWN); } if (mode == 0x01) { // OUTPUT pinMode(pin, OUTPUT); } if (mode == 0x02) { // ANALOG INPUT pinMode(pin, INPUT); } if (mode == 0x03) { // ANALOG (PWM) OUTPUT pinMode(pin, OUTPUT); } if (mode == 0x04) { // SERVO pinMode(pin, OUTPUT); servos[ToServoIndex(pin)].attach(pin); } } break; case DIGITAL_WRITE: // digitalWrite pin = cached[1]; val = cached[2]; #if DEBUG Serial.print("PIN: "); Serial.println(pin, DEC); Serial.print("VALUE: "); Serial.println(val, HEX); #endif digitalWrite(pin, val); break; case ANALOG_WRITE: // analogWrite pin = cached[1]; val = cached[2]; #if DEBUG Serial.print("PIN: "); Serial.println(pin, DEC); Serial.print("VALUE: "); Serial.println(val, HEX); #endif analogWrite(pin, val); break; case DIGITAL_READ: // digitalRead pin = cached[1]; val = digitalRead(pin); #if DEBUG Serial.print("PIN: "); Serial.println(pin, DEC); Serial.print("VALUE: "); Serial.println(val, HEX); #endif send(0x03, pin, val); break; case ANALOG_READ: // analogRead pin = cached[1]; val = analogRead(pin); #if DEBUG Serial.print("PIN: "); Serial.println(pin, DEC); Serial.print("VALUE: "); Serial.println(val, HEX); #endif send(0x04, pin, val); break; case REPORTING: // Add pin to pin = cached[1]; val = cached[2]; #if DEBUG Serial.print("PIN: "); Serial.println(pin, DEC); Serial.print("TYPE: "); Serial.println(val, DEC); #endif if (analogReporting[pin] == 0 || reporting[pin] == 0) { reporters++; } if (val == 2) { analogReporting[pin] = 1; } else { reporting[pin] = 1; } break; case SET_SAMPLE_INTERVAL: // set the sampling interval in ms sampleInterval = cached[1] + (cached[2] << 7); #if DEBUG Serial.print("SET_SAMPLE_INTERVAL (2 bytes): "); Serial.println(sampleInterval, DEC); #endif // Lower than ~100ms will likely crash the spark, // but if (sampleInterval < 20) { sampleInterval = 20; } break; // // Serial API // case SERIAL_BEGIN: // serial.begin // type = cached[1]; // speed = cached[2]; // if (type == 0) { // Serial.begin(SerialSpeed[speed]); // } else { // Serial1.begin(SerialSpeed[speed]); // } // break; // case SERIAL_END: // serial.end // type = cached[1]; // if (type == 0) { // Serial.end(); // } else { // Serial1.end(); // } // break; // case SERIAL_PEEK: // serial.peek // type = cached[1]; // if (type == 0) { // val = Serial.peek(); // } else { // val = Serial1.peek(); // } // send(0x07, type, val); // break; // case SERIAL_AVAILABLE: // serial.available() // type = cached[1]; // if (type == 0) { // val = Serial.available(); // } else { // val = Serial1.available(); // } // send(0x07, type, val); // break; // case SERIAL_WRITE: // serial.write // type = cached[1]; // len = cached[2]; // for (i = 0; i < len; i++) { // if (type == 0) { // Serial.write(client.read()); // } else { // Serial1.write(client.read()); // } // } // break; // case SERIAL_READ: // serial.read // type = cached[1]; // if (type == 0) { // val = Serial.read(); // } else { // val = Serial1.read(); // } // send(0x16, type, val); // break; // case SERIAL_FLUSH: // serial.flush // type = cached[1]; // if (type == 0) { // Serial.flush(); // } else { // Serial1.flush(); // } // break; // SPI API // case SPI_BEGIN: // SPI.begin // SPI.begin(); // break; // case SPI_END: // SPI.end // SPI.end(); // break; // case SPI_SET_BIT_ORDER: // SPI.setBitOrder // type = cached[1]; // SPI.setBitOrder((type ? MSBFIRST : LSBFIRST)); // break; // case SPI_SET_CLOCK: // SPI.setClockDivider // val = cached[1]; // if (val == 0) { // SPI.setClockDivider(SPI_CLOCK_DIV2); // } else if (val == 1) { // SPI.setClockDivider(SPI_CLOCK_DIV4); // } else if (val == 2) { // SPI.setClockDivider(SPI_CLOCK_DIV8); // } else if (val == 3) { // SPI.setClockDivider(SPI_CLOCK_DIV16); // } else if (val == 4) { // SPI.setClockDivider(SPI_CLOCK_DIV32); // } else if (val == 5) { // SPI.setClockDivider(SPI_CLOCK_DIV64); // } else if (val == 6) { // SPI.setClockDivider(SPI_CLOCK_DIV128); // } else if (val == 7) { // SPI.setClockDivider(SPI_CLOCK_DIV256); // } // break; // case SPI_SET_DATA_MODE: // SPI.setDataMode // val = cached[1]; // if (val == 0) { // SPI.setDataMode(SPI_MODE0); // } else if (val == 1) { // SPI.setDataMode(SPI_MODE1); // } else if (val == 2) { // SPI.setDataMode(SPI_MODE2); // } else if (val == 3) { // SPI.setDataMode(SPI_MODE3); // } // break; // case SPI_TRANSFER: // SPI.transfer // val = cached[1]; // val = SPI.transfer(val); // server.write(0x24); // server.write(val); // break; // // Wire API // case WIRE_BEGIN: // Wire.begin // address = cached[1]; // if (address == 0) { // Wire.begin(); // } else { // Wire.begin(address); // } // break; // case WIRE_REQUEST_FROM: // Wire.requestFrom // address = cached[1]; // val = cached[2]; // stop = cached[3]; // Wire.requestFrom(address, val, stop); // break; // case WIRE_BEGIN_TRANSMISSION: // Wire.beginTransmission // address = cached[1]; // Wire.beginTransmission(address); // break; // case WIRE_END_TRANSMISSION: // Wire.endTransmission // stop = cached[1]; // val = Wire.endTransmission(stop); // server.write(0x33); // could be (action) // server.write(val); // break; // case WIRE_WRITE: // Wire.write // len = cached[1]; // uint8_t wireData[len]; // for (i = 0; i< len; i++) { // wireData[i] = cached[1]; // } // val = Wire.write(wireData, len); // server.write(0x34); // could be (action) // server.write(val); // break; // case WIRE_AVAILABLE: // Wire.available // val = Wire.available(); // server.write(0x35); // could be (action) // server.write(val); // break; // case WIRE_READ: // Wire.read // val = Wire.read(); // server.write(0x36); // could be (action) // server.write(val); // break; case SERVO_WRITE: pin = cached[1]; val = cached[2]; #if DEBUG Serial.print("PIN: "); Serial.println(pin); Serial.print("WRITING TO SERVO: "); Serial.println(val); #endif servos[ToServoIndex(pin)].write(val); break; default: // noop break; } // <-- This is the end of the switch memset(&cached[0], 0, 4); #if DEBUG Serial.print("Unprocessed Bytes: "); Serial.println(byteCount, DEC); #endif // Reset hasAction flag (no longer needed for this opertion) // action and byte read expectation flags hasAction = false; bytesExpecting = 0; // If there were leftover bytes available, // call processInput. This mechanism will // continue until the buffer is exhausted. bytesRead = byteCount; if (byteCount > 2) { #if DEBUG Serial.println("Calling processInput "); #endif processInput(); } else { #if DEBUG Serial.println("RETURN TO LOOP!"); #endif } } }