mirror of
https://github.com/esp8266/Arduino.git
synced 2025-04-19 23:22:16 +03:00
use Eclipse auto Format to get rip auf the tab, space and code style inconsistency
This commit is contained in:
parent
78ee754677
commit
f165a0afcd
@ -1,21 +1,21 @@
|
||||
/*
|
||||
Arduino.h - Main include file for the Arduino SDK
|
||||
Copyright (c) 2005-2013 Arduino Team. All right reserved.
|
||||
Arduino.h - Main include file for the Arduino SDK
|
||||
Copyright (c) 2005-2013 Arduino Team. All right reserved.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef Arduino_h
|
||||
#define Arduino_h
|
||||
@ -30,7 +30,7 @@
|
||||
#include "pgmspace.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C"{
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
void yield(void);
|
||||
@ -144,7 +144,6 @@ volatile uint32_t* portOutputRegister(uint32_t port);
|
||||
volatile uint32_t* portInputRegister(uint32_t port);
|
||||
volatile uint32_t* portModeRegister(uint32_t port);
|
||||
|
||||
|
||||
#define NOT_A_PIN 0
|
||||
#define NOT_A_PORT 0
|
||||
#define NOT_AN_INTERRUPT -1
|
||||
|
@ -1,21 +1,21 @@
|
||||
/*
|
||||
Client.h - Base class that provides Client
|
||||
Copyright (c) 2011 Adrian McEwen. All right reserved.
|
||||
Client.h - Base class that provides Client
|
||||
Copyright (c) 2011 Adrian McEwen. All right reserved.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef client_h
|
||||
#define client_h
|
||||
@ -23,23 +23,26 @@
|
||||
#include "Stream.h"
|
||||
#include "IPAddress.h"
|
||||
|
||||
class Client : public Stream {
|
||||
class Client: public Stream {
|
||||
|
||||
public:
|
||||
virtual int connect(IPAddress ip, uint16_t port) =0;
|
||||
virtual int connect(const char *host, uint16_t port) =0;
|
||||
virtual size_t write(uint8_t) =0;
|
||||
virtual size_t write(const uint8_t *buf, size_t size) =0;
|
||||
virtual int available() = 0;
|
||||
virtual int read() = 0;
|
||||
virtual int read(uint8_t *buf, size_t size) = 0;
|
||||
virtual int peek() = 0;
|
||||
virtual void flush() = 0;
|
||||
virtual void stop() = 0;
|
||||
virtual uint8_t connected() = 0;
|
||||
virtual operator bool() = 0;
|
||||
protected:
|
||||
uint8_t* rawIPAddress(IPAddress& addr) { return addr.raw_address(); };
|
||||
public:
|
||||
virtual int connect(IPAddress ip, uint16_t port) =0;
|
||||
virtual int connect(const char *host, uint16_t port) =0;
|
||||
virtual size_t write(uint8_t) =0;
|
||||
virtual size_t write(const uint8_t *buf, size_t size) =0;
|
||||
virtual int available() = 0;
|
||||
virtual int read() = 0;
|
||||
virtual int read(uint8_t *buf, size_t size) = 0;
|
||||
virtual int peek() = 0;
|
||||
virtual void flush() = 0;
|
||||
virtual void stop() = 0;
|
||||
virtual uint8_t connected() = 0;
|
||||
virtual operator bool() = 0;
|
||||
protected:
|
||||
uint8_t* rawIPAddress(IPAddress& addr) {
|
||||
return addr.raw_address();
|
||||
}
|
||||
;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
@ -61,11 +61,9 @@ extern "C" {
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
// ####################################################################################################
|
||||
// ####################################################################################################
|
||||
// ####################################################################################################
|
||||
|
||||
HardwareSerial Serial(UART0);
|
||||
HardwareSerial Serial1(UART1);
|
||||
|
||||
@ -105,285 +103,285 @@ UARTnr_t uart_get_debug();
|
||||
|
||||
void ICACHE_FLASH_ATTR uart_interrupt_handler(uart_t* uart) {
|
||||
|
||||
// -------------- UART 0 --------------
|
||||
uint32_t status = READ_PERI_REG(UART_INT_ST(0));
|
||||
if(Serial.isRxEnabled()) {
|
||||
if(status & UART_RXFIFO_FULL_INT_ST) {
|
||||
while(true) {
|
||||
int rx_count = (READ_PERI_REG(UART_STATUS(0)) >> UART_RXFIFO_CNT_S) & UART_RXFIFO_CNT;
|
||||
if(!rx_count) break;
|
||||
// -------------- UART 0 --------------
|
||||
uint32_t status = READ_PERI_REG(UART_INT_ST(0));
|
||||
if(Serial.isRxEnabled()) {
|
||||
if(status & UART_RXFIFO_FULL_INT_ST) {
|
||||
while(true) {
|
||||
int rx_count = (READ_PERI_REG(UART_STATUS(0)) >> UART_RXFIFO_CNT_S) & UART_RXFIFO_CNT;
|
||||
if(!rx_count)
|
||||
break;
|
||||
|
||||
while(rx_count--) {
|
||||
char c = READ_PERI_REG(UART_FIFO(0)) & 0xFF;
|
||||
Serial._rx_complete_irq(c);
|
||||
}
|
||||
}
|
||||
WRITE_PERI_REG(UART_INT_CLR(0), UART_RXFIFO_FULL_INT_CLR);
|
||||
}
|
||||
}
|
||||
if(Serial.isTxEnabled()) {
|
||||
if(status & UART_TXFIFO_EMPTY_INT_ST) {
|
||||
WRITE_PERI_REG(UART_INT_CLR(0), UART_TXFIFO_EMPTY_INT_CLR);
|
||||
Serial._tx_empty_irq();
|
||||
}
|
||||
}
|
||||
while(rx_count--) {
|
||||
char c = READ_PERI_REG(UART_FIFO(0)) & 0xFF;
|
||||
Serial._rx_complete_irq(c);
|
||||
}
|
||||
}
|
||||
WRITE_PERI_REG(UART_INT_CLR(0), UART_RXFIFO_FULL_INT_CLR);
|
||||
}
|
||||
}
|
||||
if(Serial.isTxEnabled()) {
|
||||
if(status & UART_TXFIFO_EMPTY_INT_ST) {
|
||||
WRITE_PERI_REG(UART_INT_CLR(0), UART_TXFIFO_EMPTY_INT_CLR);
|
||||
Serial._tx_empty_irq();
|
||||
}
|
||||
}
|
||||
|
||||
// -------------- UART 1 --------------
|
||||
// -------------- UART 1 --------------
|
||||
|
||||
status = READ_PERI_REG(UART_INT_ST(1));
|
||||
if(Serial1.isRxEnabled()) {
|
||||
if(status & UART_RXFIFO_FULL_INT_ST) {
|
||||
while(true) {
|
||||
int rx_count = (READ_PERI_REG(UART_STATUS(1)) >> UART_RXFIFO_CNT_S) & UART_RXFIFO_CNT;
|
||||
if(!rx_count) break;
|
||||
status = READ_PERI_REG(UART_INT_ST(1));
|
||||
if(Serial1.isRxEnabled()) {
|
||||
if(status & UART_RXFIFO_FULL_INT_ST) {
|
||||
while(true) {
|
||||
int rx_count = (READ_PERI_REG(UART_STATUS(1)) >> UART_RXFIFO_CNT_S) & UART_RXFIFO_CNT;
|
||||
if(!rx_count)
|
||||
break;
|
||||
|
||||
while(rx_count--) {
|
||||
char c = READ_PERI_REG(UART_FIFO(1)) & 0xFF;
|
||||
Serial1._rx_complete_irq(c);
|
||||
}
|
||||
}
|
||||
WRITE_PERI_REG(UART_INT_CLR(1), UART_RXFIFO_FULL_INT_CLR);
|
||||
}
|
||||
}
|
||||
if(Serial1.isTxEnabled()) {
|
||||
status = READ_PERI_REG(UART_INT_ST(1));
|
||||
if(status & UART_TXFIFO_EMPTY_INT_ST) {
|
||||
WRITE_PERI_REG(UART_INT_CLR(1), UART_TXFIFO_EMPTY_INT_CLR);
|
||||
Serial1._tx_empty_irq();
|
||||
}
|
||||
}
|
||||
while(rx_count--) {
|
||||
char c = READ_PERI_REG(UART_FIFO(1)) & 0xFF;
|
||||
Serial1._rx_complete_irq(c);
|
||||
}
|
||||
}
|
||||
WRITE_PERI_REG(UART_INT_CLR(1), UART_RXFIFO_FULL_INT_CLR);
|
||||
}
|
||||
}
|
||||
if(Serial1.isTxEnabled()) {
|
||||
status = READ_PERI_REG(UART_INT_ST(1));
|
||||
if(status & UART_TXFIFO_EMPTY_INT_ST) {
|
||||
WRITE_PERI_REG(UART_INT_CLR(1), UART_TXFIFO_EMPTY_INT_CLR);
|
||||
Serial1._tx_empty_irq();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// ####################################################################################################
|
||||
|
||||
void ICACHE_FLASH_ATTR uart_wait_for_tx_fifo(uart_t* uart, size_t size_needed) {
|
||||
if(uart->txEnabled) {
|
||||
while(true) {
|
||||
size_t tx_count = (READ_PERI_REG(UART_STATUS(uart->uart_nr)) >> UART_TXFIFO_CNT_S) & UART_TXFIFO_CNT;
|
||||
if(tx_count <= (UART_TX_FIFO_SIZE - size_needed)) break;
|
||||
}
|
||||
}
|
||||
if(uart->txEnabled) {
|
||||
while(true) {
|
||||
size_t tx_count = (READ_PERI_REG(UART_STATUS(uart->uart_nr)) >> UART_TXFIFO_CNT_S) & UART_TXFIFO_CNT;
|
||||
if(tx_count <= (UART_TX_FIFO_SIZE - size_needed))
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR uart_get_tx_fifo_room(uart_t* uart) {
|
||||
if(uart->txEnabled) {
|
||||
return UART_TX_FIFO_SIZE - ((READ_PERI_REG(UART_STATUS(uart->uart_nr)) >> UART_TXFIFO_CNT_S) & UART_TXFIFO_CNT);
|
||||
}
|
||||
return 0;
|
||||
if(uart->txEnabled) {
|
||||
return UART_TX_FIFO_SIZE - ((READ_PERI_REG(UART_STATUS(uart->uart_nr)) >> UART_TXFIFO_CNT_S) & UART_TXFIFO_CNT);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR uart_wait_for_transmit(uart_t* uart) {
|
||||
if(uart->txEnabled) {
|
||||
uart_wait_for_tx_fifo(uart, UART_TX_FIFO_SIZE);
|
||||
}
|
||||
if(uart->txEnabled) {
|
||||
uart_wait_for_tx_fifo(uart, UART_TX_FIFO_SIZE);
|
||||
}
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR uart_transmit_char(uart_t* uart, char c) {
|
||||
if(uart->txEnabled) {
|
||||
WRITE_PERI_REG(UART_FIFO(uart->uart_nr), c);
|
||||
}
|
||||
if(uart->txEnabled) {
|
||||
WRITE_PERI_REG(UART_FIFO(uart->uart_nr), c);
|
||||
}
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR uart_transmit(uart_t* uart, const char* buf, size_t size) {
|
||||
if(uart->txEnabled) {
|
||||
while(size) {
|
||||
size_t part_size = (size > UART_TX_FIFO_SIZE) ? UART_TX_FIFO_SIZE : size;
|
||||
size -= part_size;
|
||||
if(uart->txEnabled) {
|
||||
while(size) {
|
||||
size_t part_size = (size > UART_TX_FIFO_SIZE) ? UART_TX_FIFO_SIZE : size;
|
||||
size -= part_size;
|
||||
|
||||
uart_wait_for_tx_fifo(uart, part_size);
|
||||
for(; part_size; --part_size, ++buf)
|
||||
WRITE_PERI_REG(UART_FIFO(uart->uart_nr), *buf);
|
||||
}
|
||||
}
|
||||
uart_wait_for_tx_fifo(uart, part_size);
|
||||
for(; part_size; --part_size, ++buf)
|
||||
WRITE_PERI_REG(UART_FIFO(uart->uart_nr), *buf);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR uart_flush(uart_t* uart) {
|
||||
uint32_t tmp = 0x00000000;
|
||||
uint32_t tmp = 0x00000000;
|
||||
|
||||
if(uart->rxEnabled) {
|
||||
tmp |= UART_RXFIFO_RST;
|
||||
}
|
||||
if(uart->rxEnabled) {
|
||||
tmp |= UART_RXFIFO_RST;
|
||||
}
|
||||
|
||||
if(uart->txEnabled) {
|
||||
tmp |= UART_TXFIFO_RST;
|
||||
}
|
||||
if(uart->txEnabled) {
|
||||
tmp |= UART_TXFIFO_RST;
|
||||
}
|
||||
|
||||
SET_PERI_REG_MASK(UART_CONF0(uart->uart_nr), tmp);
|
||||
CLEAR_PERI_REG_MASK(UART_CONF0(uart->uart_nr), tmp);
|
||||
SET_PERI_REG_MASK(UART_CONF0(uart->uart_nr), tmp);
|
||||
CLEAR_PERI_REG_MASK(UART_CONF0(uart->uart_nr), tmp);
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR uart_interrupt_enable(uart_t* uart) {
|
||||
WRITE_PERI_REG(UART_INT_CLR(uart->uart_nr), 0x1ff);
|
||||
ETS_UART_INTR_ATTACH(&uart_interrupt_handler, uart); // uart parameter is not osed in irq function!
|
||||
if(uart->rxEnabled) {
|
||||
SET_PERI_REG_MASK(UART_INT_ENA(uart->uart_nr), UART_RXFIFO_FULL_INT_ENA);
|
||||
}
|
||||
ETS_UART_INTR_ENABLE();
|
||||
WRITE_PERI_REG(UART_INT_CLR(uart->uart_nr), 0x1ff);
|
||||
ETS_UART_INTR_ATTACH(&uart_interrupt_handler, uart); // uart parameter is not osed in irq function!
|
||||
if(uart->rxEnabled) {
|
||||
SET_PERI_REG_MASK(UART_INT_ENA(uart->uart_nr), UART_RXFIFO_FULL_INT_ENA);
|
||||
}
|
||||
ETS_UART_INTR_ENABLE();
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR uart_interrupt_disable(uart_t* uart) {
|
||||
if(uart->rxEnabled) {
|
||||
CLEAR_PERI_REG_MASK(UART_INT_ENA(uart->uart_nr), UART_RXFIFO_FULL_INT_ENA);
|
||||
}
|
||||
if(uart->txEnabled) {
|
||||
CLEAR_PERI_REG_MASK(UART_INT_ENA(uart->uart_nr), UART_TXFIFO_EMPTY_INT_ENA);
|
||||
}
|
||||
//ETS_UART_INTR_DISABLE(); // never disable irq complete may its needed by the other Serial Interface!
|
||||
if(uart->rxEnabled) {
|
||||
CLEAR_PERI_REG_MASK(UART_INT_ENA(uart->uart_nr), UART_RXFIFO_FULL_INT_ENA);
|
||||
}
|
||||
if(uart->txEnabled) {
|
||||
CLEAR_PERI_REG_MASK(UART_INT_ENA(uart->uart_nr), UART_TXFIFO_EMPTY_INT_ENA);
|
||||
}
|
||||
//ETS_UART_INTR_DISABLE(); // never disable irq complete may its needed by the other Serial Interface!
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR uart_arm_tx_interrupt(uart_t* uart) {
|
||||
if(uart->txEnabled) {
|
||||
SET_PERI_REG_MASK(UART_INT_ENA(uart->uart_nr), UART_TXFIFO_EMPTY_INT_ENA);
|
||||
}
|
||||
if(uart->txEnabled) {
|
||||
SET_PERI_REG_MASK(UART_INT_ENA(uart->uart_nr), UART_TXFIFO_EMPTY_INT_ENA);
|
||||
}
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR uart_disarm_tx_interrupt(uart_t* uart) {
|
||||
if(uart->txEnabled) {
|
||||
CLEAR_PERI_REG_MASK(UART_INT_ENA(uart->uart_nr), UART_TXFIFO_EMPTY_INT_ENA);
|
||||
}
|
||||
if(uart->txEnabled) {
|
||||
CLEAR_PERI_REG_MASK(UART_INT_ENA(uart->uart_nr), UART_TXFIFO_EMPTY_INT_ENA);
|
||||
}
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR uart_set_baudrate(uart_t* uart, int baud_rate) {
|
||||
uart->baud_rate = baud_rate;
|
||||
uart_div_modify(uart->uart_nr, UART_CLK_FREQ / (uart->baud_rate));
|
||||
uart->baud_rate = baud_rate;
|
||||
uart_div_modify(uart->uart_nr, UART_CLK_FREQ / (uart->baud_rate));
|
||||
}
|
||||
|
||||
int ICACHE_FLASH_ATTR uart_get_baudrate(uart_t* uart) {
|
||||
return uart->baud_rate;
|
||||
return uart->baud_rate;
|
||||
}
|
||||
|
||||
uart_t* ICACHE_FLASH_ATTR uart_init(UARTnr_t uart_nr, int baudrate) {
|
||||
|
||||
uint32_t conf1 = 0x00000000;
|
||||
uart_t* uart = (uart_t*) os_malloc(sizeof(uart_t));
|
||||
uart->uart_nr = uart_nr;
|
||||
uint32_t conf1 = 0x00000000;
|
||||
uart_t* uart = (uart_t*) os_malloc(sizeof(uart_t));
|
||||
uart->uart_nr = uart_nr;
|
||||
|
||||
switch(uart->uart_nr) {
|
||||
case UART0:
|
||||
PIN_PULLUP_DIS(PERIPHS_IO_MUX_U0TXD_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_U0TXD_U, FUNC_U0TXD);
|
||||
PIN_PULLUP_EN(PERIPHS_IO_MUX_U0RXD_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_U0RXD_U, FUNC_U0RXD);
|
||||
uart->rxEnabled = true;
|
||||
uart->txEnabled = true;
|
||||
uart->rxPin = 3;
|
||||
uart->txPin = 1;
|
||||
break;
|
||||
case UART1:
|
||||
PIN_PULLUP_DIS(PERIPHS_IO_MUX_GPIO2_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_GPIO2_U, FUNC_U1TXD_BK);
|
||||
uart->rxEnabled = false;
|
||||
uart->txEnabled = true;
|
||||
uart->rxPin = 255;
|
||||
uart->txPin = 2;
|
||||
break;
|
||||
case UART_NO:
|
||||
default:
|
||||
// big fail!
|
||||
break;
|
||||
}
|
||||
uart_set_baudrate(uart, baudrate);
|
||||
WRITE_PERI_REG(UART_CONF0(uart->uart_nr), 0x3 << UART_BIT_NUM_S); // 8n1
|
||||
switch(uart->uart_nr) {
|
||||
case UART0:
|
||||
PIN_PULLUP_DIS(PERIPHS_IO_MUX_U0TXD_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_U0TXD_U, FUNC_U0TXD);
|
||||
PIN_PULLUP_EN(PERIPHS_IO_MUX_U0RXD_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_U0RXD_U, FUNC_U0RXD);
|
||||
uart->rxEnabled = true;
|
||||
uart->txEnabled = true;
|
||||
uart->rxPin = 3;
|
||||
uart->txPin = 1;
|
||||
break;
|
||||
case UART1:
|
||||
PIN_PULLUP_DIS(PERIPHS_IO_MUX_GPIO2_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_GPIO2_U, FUNC_U1TXD_BK);
|
||||
uart->rxEnabled = false;
|
||||
uart->txEnabled = true;
|
||||
uart->rxPin = 255;
|
||||
uart->txPin = 2;
|
||||
break;
|
||||
case UART_NO:
|
||||
default:
|
||||
// big fail!
|
||||
break;
|
||||
}
|
||||
uart_set_baudrate(uart, baudrate);
|
||||
WRITE_PERI_REG(UART_CONF0(uart->uart_nr), 0x3 << UART_BIT_NUM_S); // 8n1
|
||||
|
||||
uart_flush(uart);
|
||||
uart_interrupt_enable(uart);
|
||||
uart_flush(uart);
|
||||
uart_interrupt_enable(uart);
|
||||
|
||||
if(uart->rxEnabled) {
|
||||
conf1 |= ((0x01 & UART_RXFIFO_FULL_THRHD) << UART_RXFIFO_FULL_THRHD_S);
|
||||
}
|
||||
if(uart->rxEnabled) {
|
||||
conf1 |= ((0x01 & UART_RXFIFO_FULL_THRHD) << UART_RXFIFO_FULL_THRHD_S);
|
||||
}
|
||||
|
||||
if(uart->txEnabled) {
|
||||
conf1 |= ((0x20 & UART_TXFIFO_EMPTY_THRHD) << UART_TXFIFO_EMPTY_THRHD_S);
|
||||
}
|
||||
if(uart->txEnabled) {
|
||||
conf1 |= ((0x20 & UART_TXFIFO_EMPTY_THRHD) << UART_TXFIFO_EMPTY_THRHD_S);
|
||||
}
|
||||
|
||||
WRITE_PERI_REG(UART_CONF1(uart->uart_nr), conf1);
|
||||
WRITE_PERI_REG(UART_CONF1(uart->uart_nr), conf1);
|
||||
|
||||
return uart;
|
||||
return uart;
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR uart_uninit(uart_t* uart) {
|
||||
uart_interrupt_disable(uart);
|
||||
uart_interrupt_disable(uart);
|
||||
|
||||
switch(uart->rxPin) {
|
||||
case 3:
|
||||
PIN_PULLUP_DIS(PERIPHS_IO_MUX_U0RXD_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_U0RXD_U, FUNC_GPIO3);
|
||||
break;
|
||||
case 13:
|
||||
PIN_PULLUP_DIS(PERIPHS_IO_MUX_MTCK_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTCK_U, FUNC_GPIO13);
|
||||
break;
|
||||
}
|
||||
switch(uart->rxPin) {
|
||||
case 3:
|
||||
PIN_PULLUP_DIS(PERIPHS_IO_MUX_U0RXD_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_U0RXD_U, FUNC_GPIO3);
|
||||
break;
|
||||
case 13:
|
||||
PIN_PULLUP_DIS(PERIPHS_IO_MUX_MTCK_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTCK_U, FUNC_GPIO13);
|
||||
break;
|
||||
}
|
||||
|
||||
switch(uart->rxPin) {
|
||||
case 1:
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_U0TXD_U, FUNC_GPIO1);
|
||||
break;
|
||||
case 2:
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_GPIO2_U, FUNC_GPIO2);
|
||||
break;
|
||||
case 15:
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTDO_U, FUNC_GPIO15);
|
||||
break;
|
||||
}
|
||||
switch(uart->rxPin) {
|
||||
case 1:
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_U0TXD_U, FUNC_GPIO1);
|
||||
break;
|
||||
case 2:
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_GPIO2_U, FUNC_GPIO2);
|
||||
break;
|
||||
case 15:
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTDO_U, FUNC_GPIO15);
|
||||
break;
|
||||
}
|
||||
|
||||
pinMode(uart->rxPin, INPUT);
|
||||
pinMode(uart->txPin, INPUT);
|
||||
|
||||
pinMode(uart->rxPin , INPUT);
|
||||
pinMode(uart->txPin , INPUT);
|
||||
|
||||
os_free(uart);
|
||||
os_free(uart);
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR uart_swap(uart_t* uart) {
|
||||
switch(uart->uart_nr) {
|
||||
case UART0:
|
||||
if(uart->txPin == 1 && uart->rxPin == 3) {
|
||||
switch(uart->uart_nr) {
|
||||
case UART0:
|
||||
if(uart->txPin == 1 && uart->rxPin == 3) {
|
||||
|
||||
PIN_PULLUP_DIS(PERIPHS_IO_MUX_MTCK_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTCK_U, FUNC_UART0_CTS);
|
||||
PIN_PULLUP_DIS(PERIPHS_IO_MUX_MTCK_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTCK_U, FUNC_UART0_CTS);
|
||||
|
||||
PIN_PULLUP_EN(PERIPHS_IO_MUX_MTDO_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTDO_U, FUNC_UART0_RTS);
|
||||
PIN_PULLUP_EN(PERIPHS_IO_MUX_MTDO_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTDO_U, FUNC_UART0_RTS);
|
||||
|
||||
//SWAP PIN : U0TXD<==>U0RTS(MTDO, GPIO15) , U0RXD<==>U0CTS(MTCK, GPIO13)
|
||||
SET_PERI_REG_MASK(0x3ff00028, BIT2);
|
||||
//SWAP PIN : U0TXD<==>U0RTS(MTDO, GPIO15) , U0RXD<==>U0CTS(MTCK, GPIO13)
|
||||
SET_PERI_REG_MASK(0x3ff00028, BIT2);
|
||||
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_U0RXD_U, FUNC_GPIO3);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_U0TXD_U, FUNC_GPIO1);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_U0RXD_U, FUNC_GPIO3);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_U0TXD_U, FUNC_GPIO1);
|
||||
|
||||
pinMode(uart->rxPin, INPUT);
|
||||
pinMode(uart->txPin, INPUT);
|
||||
|
||||
pinMode(uart->rxPin, INPUT);
|
||||
pinMode(uart->txPin, INPUT);
|
||||
uart->rxPin = 13;
|
||||
uart->txPin = 15;
|
||||
|
||||
uart->rxPin = 13;
|
||||
uart->txPin = 15;
|
||||
} else {
|
||||
PIN_PULLUP_DIS(PERIPHS_IO_MUX_U0TXD_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_U0TXD_U, FUNC_U0TXD);
|
||||
|
||||
} else {
|
||||
PIN_PULLUP_DIS(PERIPHS_IO_MUX_U0TXD_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_U0TXD_U, FUNC_U0TXD);
|
||||
PIN_PULLUP_EN(PERIPHS_IO_MUX_U0RXD_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_U0RXD_U, FUNC_U0RXD);
|
||||
|
||||
PIN_PULLUP_EN(PERIPHS_IO_MUX_U0RXD_U);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_U0RXD_U, FUNC_U0RXD);
|
||||
CLEAR_PERI_REG_MASK(0x3ff00028, BIT2);
|
||||
|
||||
CLEAR_PERI_REG_MASK(0x3ff00028, BIT2);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTCK_U, FUNC_GPIO13);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTDO_U, FUNC_GPIO15);
|
||||
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTCK_U, FUNC_GPIO13);
|
||||
PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTDO_U, FUNC_GPIO15);
|
||||
pinMode(uart->rxPin, INPUT);
|
||||
pinMode(uart->txPin, INPUT);
|
||||
uart->rxPin = 3;
|
||||
uart->txPin = 1;
|
||||
}
|
||||
|
||||
|
||||
pinMode(uart->rxPin, INPUT);
|
||||
pinMode(uart->txPin, INPUT);
|
||||
uart->rxPin = 3;
|
||||
uart->txPin = 1;
|
||||
}
|
||||
|
||||
break;
|
||||
case UART1:
|
||||
// current no swap possible! see GPIO pins used by UART
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case UART1:
|
||||
// current no swap possible! see GPIO pins used by UART
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// ####################################################################################################
|
||||
@ -423,26 +421,26 @@ void ICACHE_FLASH_ATTR uart1_write_char(char c) {
|
||||
|
||||
static UARTnr_t s_uart_debug_nr = UART_NO;
|
||||
void ICACHE_FLASH_ATTR uart_set_debug(UARTnr_t uart_nr) {
|
||||
s_uart_debug_nr = uart_nr;
|
||||
switch(s_uart_debug_nr) {
|
||||
case UART0:
|
||||
system_set_os_print(1);
|
||||
ets_install_putc1((void *) &uart0_write_char);
|
||||
break;
|
||||
case UART1:
|
||||
system_set_os_print(1);
|
||||
ets_install_putc1((void *) &uart1_write_char);
|
||||
break;
|
||||
case UART_NO:
|
||||
default:
|
||||
system_set_os_print(0);
|
||||
ets_install_putc1((void *) &uart_ignore_char);
|
||||
break;
|
||||
}
|
||||
s_uart_debug_nr = uart_nr;
|
||||
switch(s_uart_debug_nr) {
|
||||
case UART0:
|
||||
system_set_os_print(1);
|
||||
ets_install_putc1((void *) &uart0_write_char);
|
||||
break;
|
||||
case UART1:
|
||||
system_set_os_print(1);
|
||||
ets_install_putc1((void *) &uart1_write_char);
|
||||
break;
|
||||
case UART_NO:
|
||||
default:
|
||||
system_set_os_print(0);
|
||||
ets_install_putc1((void *) &uart_ignore_char);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
UARTnr_t ICACHE_FLASH_ATTR uart_get_debug() {
|
||||
return s_uart_debug_nr;
|
||||
return s_uart_debug_nr;
|
||||
}
|
||||
|
||||
// ####################################################################################################
|
||||
@ -450,143 +448,148 @@ UARTnr_t ICACHE_FLASH_ATTR uart_get_debug() {
|
||||
// ####################################################################################################
|
||||
|
||||
ICACHE_FLASH_ATTR HardwareSerial::HardwareSerial(UARTnr_t uart_nr) :
|
||||
_uart(0), _tx_buffer(0), _rx_buffer(0), _written(false) {
|
||||
_uart_nr = uart_nr;
|
||||
_uart(0), _tx_buffer(0), _rx_buffer(0), _written(false) {
|
||||
_uart_nr = uart_nr;
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR HardwareSerial::begin(unsigned long baud, byte config) {
|
||||
|
||||
// disable debug for this interface
|
||||
if(uart_get_debug() == _uart_nr) {
|
||||
uart_set_debug(UART_NO);
|
||||
}
|
||||
// disable debug for this interface
|
||||
if(uart_get_debug() == _uart_nr) {
|
||||
uart_set_debug(UART_NO);
|
||||
}
|
||||
|
||||
_uart = uart_init(_uart_nr, baud);
|
||||
_uart = uart_init(_uart_nr, baud);
|
||||
|
||||
if(_uart->rxEnabled) {
|
||||
_rx_buffer = new cbuf(SERIAL_RX_BUFFER_SIZE);
|
||||
}
|
||||
if(_uart->txEnabled) {
|
||||
_tx_buffer = new cbuf(SERIAL_TX_BUFFER_SIZE);
|
||||
}
|
||||
_written = false;
|
||||
delay(1);
|
||||
if(_uart->rxEnabled) {
|
||||
_rx_buffer = new cbuf(SERIAL_RX_BUFFER_SIZE);
|
||||
}
|
||||
if(_uart->txEnabled) {
|
||||
_tx_buffer = new cbuf(SERIAL_TX_BUFFER_SIZE);
|
||||
}
|
||||
_written = false;
|
||||
delay(1);
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR HardwareSerial::end() {
|
||||
uart_uninit(_uart);
|
||||
delete _rx_buffer;
|
||||
delete _tx_buffer;
|
||||
_uart = 0;
|
||||
_rx_buffer = 0;
|
||||
_tx_buffer = 0;
|
||||
uart_uninit(_uart);
|
||||
delete _rx_buffer;
|
||||
delete _tx_buffer;
|
||||
_uart = 0;
|
||||
_rx_buffer = 0;
|
||||
_tx_buffer = 0;
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR HardwareSerial::swap() {
|
||||
uart_swap(_uart);
|
||||
uart_swap(_uart);
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR HardwareSerial::setDebugOutput(bool en) {
|
||||
if(en) {
|
||||
uart_set_debug(_uart->uart_nr);
|
||||
} else {
|
||||
// disable debug for this interface
|
||||
if(uart_get_debug() == _uart_nr) {
|
||||
uart_set_debug(UART_NO);
|
||||
}
|
||||
}
|
||||
if(en) {
|
||||
uart_set_debug(_uart->uart_nr);
|
||||
} else {
|
||||
// disable debug for this interface
|
||||
if(uart_get_debug() == _uart_nr) {
|
||||
uart_set_debug(UART_NO);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bool ICACHE_FLASH_ATTR HardwareSerial::isTxEnabled(void) {
|
||||
if(_uart == 0) return false;
|
||||
return _uart->txEnabled;
|
||||
if(_uart == 0)
|
||||
return false;
|
||||
return _uart->txEnabled;
|
||||
}
|
||||
|
||||
bool ICACHE_FLASH_ATTR HardwareSerial::isRxEnabled(void) {
|
||||
if(_uart == 0) return false;
|
||||
return _uart->rxEnabled;
|
||||
if(_uart == 0)
|
||||
return false;
|
||||
return _uart->rxEnabled;
|
||||
}
|
||||
|
||||
int ICACHE_FLASH_ATTR HardwareSerial::available(void) {
|
||||
if(_uart->rxEnabled) {
|
||||
return static_cast<int>(_rx_buffer->getSize());
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
if(_uart->rxEnabled) {
|
||||
return static_cast<int>(_rx_buffer->getSize());
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
int ICACHE_FLASH_ATTR HardwareSerial::peek(void) {
|
||||
if(_uart->rxEnabled) {
|
||||
return _rx_buffer->peek();
|
||||
} else {
|
||||
return -1;
|
||||
}
|
||||
if(_uart->rxEnabled) {
|
||||
return _rx_buffer->peek();
|
||||
} else {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
int ICACHE_FLASH_ATTR HardwareSerial::read(void) {
|
||||
if(_uart->rxEnabled) {
|
||||
return _rx_buffer->read();
|
||||
} else {
|
||||
return -1;
|
||||
}
|
||||
if(_uart->rxEnabled) {
|
||||
return _rx_buffer->read();
|
||||
} else {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
int ICACHE_FLASH_ATTR HardwareSerial::availableForWrite(void) {
|
||||
if(_uart->txEnabled) {
|
||||
return static_cast<int>(_tx_buffer->room());
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
if(_uart->txEnabled) {
|
||||
return static_cast<int>(_tx_buffer->room());
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR HardwareSerial::flush() {
|
||||
if(!_uart->txEnabled) return;
|
||||
if(!_written) return;
|
||||
if(!_uart->txEnabled)
|
||||
return;
|
||||
if(!_written)
|
||||
return;
|
||||
|
||||
while(_tx_buffer->getSize() || uart_get_tx_fifo_room(_uart) < UART_TX_FIFO_SIZE)
|
||||
yield();
|
||||
while(_tx_buffer->getSize() || uart_get_tx_fifo_room(_uart) < UART_TX_FIFO_SIZE)
|
||||
yield();
|
||||
|
||||
_written = false;
|
||||
_written = false;
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR HardwareSerial::write(uint8_t c) {
|
||||
if(!_uart->txEnabled) return 0;
|
||||
_written = true;
|
||||
size_t room = uart_get_tx_fifo_room(_uart);
|
||||
if(room > 0 && _tx_buffer->empty()) {
|
||||
uart_transmit_char(_uart, c);
|
||||
if(room < 10) {
|
||||
uart_arm_tx_interrupt(_uart);
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
if(!_uart->txEnabled)
|
||||
return 0;
|
||||
_written = true;
|
||||
size_t room = uart_get_tx_fifo_room(_uart);
|
||||
if(room > 0 && _tx_buffer->empty()) {
|
||||
uart_transmit_char(_uart, c);
|
||||
if(room < 10) {
|
||||
uart_arm_tx_interrupt(_uart);
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
while(_tx_buffer->room() == 0) {
|
||||
yield();
|
||||
}
|
||||
while(_tx_buffer->room() == 0) {
|
||||
yield();
|
||||
}
|
||||
|
||||
_tx_buffer->write(c);
|
||||
return 1;
|
||||
_tx_buffer->write(c);
|
||||
return 1;
|
||||
}
|
||||
|
||||
ICACHE_FLASH_ATTR HardwareSerial::operator bool() const {
|
||||
return _uart != 0;
|
||||
return _uart != 0;
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR HardwareSerial::_rx_complete_irq(char c) {
|
||||
_rx_buffer->write(c);
|
||||
_rx_buffer->write(c);
|
||||
}
|
||||
|
||||
void ICACHE_FLASH_ATTR HardwareSerial::_tx_empty_irq(void) {
|
||||
size_t queued = _tx_buffer->getSize();
|
||||
if(!queued) {
|
||||
uart_disarm_tx_interrupt(_uart);
|
||||
return;
|
||||
}
|
||||
size_t queued = _tx_buffer->getSize();
|
||||
if(!queued) {
|
||||
uart_disarm_tx_interrupt(_uart);
|
||||
return;
|
||||
}
|
||||
|
||||
size_t room = uart_get_tx_fifo_room(_uart);
|
||||
int n = static_cast<int>((queued < room) ? queued : room);
|
||||
while(n--) {
|
||||
uart_transmit_char(_uart, _tx_buffer->read());
|
||||
}
|
||||
size_t room = uart_get_tx_fifo_room(_uart);
|
||||
int n = static_cast<int>((queued < room) ? queued : room);
|
||||
while(n--) {
|
||||
uart_transmit_char(_uart, _tx_buffer->read());
|
||||
}
|
||||
}
|
||||
|
@ -62,66 +62,64 @@
|
||||
class cbuf;
|
||||
|
||||
typedef enum {
|
||||
UART0 = 0,
|
||||
UART1 = 1,
|
||||
UART_NO = 0xFF
|
||||
UART0 = 0, UART1 = 1, UART_NO = 0xFF
|
||||
} UARTnr_t;
|
||||
|
||||
typedef struct {
|
||||
UARTnr_t uart_nr;
|
||||
int baud_rate;
|
||||
bool rxEnabled;
|
||||
bool txEnabled;
|
||||
uint8_t rxPin;
|
||||
uint8_t txPin;
|
||||
UARTnr_t uart_nr;
|
||||
int baud_rate;
|
||||
bool rxEnabled;
|
||||
bool txEnabled;
|
||||
uint8_t rxPin;
|
||||
uint8_t txPin;
|
||||
} uart_t;
|
||||
|
||||
class HardwareSerial: public Stream {
|
||||
public:
|
||||
HardwareSerial(UARTnr_t uart_nr);
|
||||
public:
|
||||
HardwareSerial(UARTnr_t uart_nr);
|
||||
|
||||
void begin(unsigned long baud) {
|
||||
begin(baud, 0);
|
||||
}
|
||||
void begin(unsigned long, uint8_t);
|
||||
void end();
|
||||
void swap(); //use GPIO13 and GPIO15 as RX and TX
|
||||
int available(void) override;
|
||||
int peek(void) override;
|
||||
int read(void) override;
|
||||
int availableForWrite(void);
|
||||
void flush(void) override;
|
||||
size_t write(uint8_t) override;
|
||||
inline size_t write(unsigned long n) {
|
||||
return write((uint8_t) n);
|
||||
}
|
||||
inline size_t write(long n) {
|
||||
return write((uint8_t) n);
|
||||
}
|
||||
inline size_t write(unsigned int n) {
|
||||
return write((uint8_t) n);
|
||||
}
|
||||
inline size_t write(int n) {
|
||||
return write((uint8_t) n);
|
||||
}
|
||||
using Print::write; // pull in write(str) and write(buf, size) from Print
|
||||
operator bool() const;
|
||||
void begin(unsigned long baud) {
|
||||
begin(baud, 0);
|
||||
}
|
||||
void begin(unsigned long, uint8_t);
|
||||
void end();
|
||||
void swap(); //use GPIO13 and GPIO15 as RX and TX
|
||||
int available(void) override;
|
||||
int peek(void) override;
|
||||
int read(void) override;
|
||||
int availableForWrite(void);
|
||||
void flush(void) override;
|
||||
size_t write(uint8_t) override;
|
||||
inline size_t write(unsigned long n) {
|
||||
return write((uint8_t) n);
|
||||
}
|
||||
inline size_t write(long n) {
|
||||
return write((uint8_t) n);
|
||||
}
|
||||
inline size_t write(unsigned int n) {
|
||||
return write((uint8_t) n);
|
||||
}
|
||||
inline size_t write(int n) {
|
||||
return write((uint8_t) n);
|
||||
}
|
||||
using Print::write; // pull in write(str) and write(buf, size) from Print
|
||||
operator bool() const;
|
||||
|
||||
void setDebugOutput(bool);
|
||||
bool isTxEnabled(void);
|
||||
bool isRxEnabled(void);
|
||||
void setDebugOutput(bool);
|
||||
bool isTxEnabled(void);
|
||||
bool isRxEnabled(void);
|
||||
|
||||
protected:
|
||||
friend void uart_interrupt_handler(uart_t* uart);
|
||||
void _rx_complete_irq(char c);
|
||||
void _tx_empty_irq(void);
|
||||
protected:
|
||||
friend void uart_interrupt_handler(uart_t* uart);
|
||||
void _rx_complete_irq(char c);
|
||||
void _tx_empty_irq(void);
|
||||
|
||||
protected:
|
||||
UARTnr_t _uart_nr;
|
||||
uart_t* _uart;
|
||||
cbuf* _tx_buffer;
|
||||
cbuf* _rx_buffer;
|
||||
bool _written;
|
||||
protected:
|
||||
UARTnr_t _uart_nr;
|
||||
uart_t* _uart;
|
||||
cbuf* _tx_buffer;
|
||||
cbuf* _rx_buffer;
|
||||
bool _written;
|
||||
};
|
||||
|
||||
extern HardwareSerial Serial;
|
||||
|
@ -1,71 +1,62 @@
|
||||
/*
|
||||
IPAddress.cpp - Base class that provides IPAddress
|
||||
Copyright (c) 2011 Adrian McEwen. All right reserved.
|
||||
IPAddress.cpp - Base class that provides IPAddress
|
||||
Copyright (c) 2011 Adrian McEwen. All right reserved.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#include <Arduino.h>
|
||||
#include <IPAddress.h>
|
||||
#include <Print.h>
|
||||
|
||||
IPAddress::IPAddress()
|
||||
{
|
||||
IPAddress::IPAddress() {
|
||||
_address.dword = 0;
|
||||
}
|
||||
|
||||
IPAddress::IPAddress(uint8_t first_octet, uint8_t second_octet, uint8_t third_octet, uint8_t fourth_octet)
|
||||
{
|
||||
IPAddress::IPAddress(uint8_t first_octet, uint8_t second_octet, uint8_t third_octet, uint8_t fourth_octet) {
|
||||
_address.bytes[0] = first_octet;
|
||||
_address.bytes[1] = second_octet;
|
||||
_address.bytes[2] = third_octet;
|
||||
_address.bytes[3] = fourth_octet;
|
||||
}
|
||||
|
||||
IPAddress::IPAddress(uint32_t address)
|
||||
{
|
||||
IPAddress::IPAddress(uint32_t address) {
|
||||
_address.dword = address;
|
||||
}
|
||||
|
||||
IPAddress::IPAddress(const uint8_t *address)
|
||||
{
|
||||
IPAddress::IPAddress(const uint8_t *address) {
|
||||
memcpy(_address.bytes, address, sizeof(_address.bytes));
|
||||
}
|
||||
|
||||
IPAddress& IPAddress::operator=(const uint8_t *address)
|
||||
{
|
||||
IPAddress& IPAddress::operator=(const uint8_t *address) {
|
||||
memcpy(_address.bytes, address, sizeof(_address.bytes));
|
||||
return *this;
|
||||
}
|
||||
|
||||
IPAddress& IPAddress::operator=(uint32_t address)
|
||||
{
|
||||
IPAddress& IPAddress::operator=(uint32_t address) {
|
||||
_address.dword = address;
|
||||
return *this;
|
||||
}
|
||||
|
||||
bool IPAddress::operator==(const uint8_t* addr) const
|
||||
{
|
||||
bool IPAddress::operator==(const uint8_t* addr) const {
|
||||
return memcmp(addr, _address.bytes, sizeof(_address.bytes)) == 0;
|
||||
}
|
||||
|
||||
size_t IPAddress::printTo(Print& p) const
|
||||
{
|
||||
size_t IPAddress::printTo(Print& p) const {
|
||||
size_t n = 0;
|
||||
for (int i =0; i < 3; i++)
|
||||
{
|
||||
for(int i = 0; i < 3; i++) {
|
||||
n += p.print(_address.bytes[i], DEC);
|
||||
n += p.print('.');
|
||||
}
|
||||
|
@ -1,21 +1,21 @@
|
||||
/*
|
||||
IPAddress.h - Base class that provides IPAddress
|
||||
Copyright (c) 2011 Adrian McEwen. All right reserved.
|
||||
IPAddress.h - Base class that provides IPAddress
|
||||
Copyright (c) 2011 Adrian McEwen. All right reserved.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef IPAddress_h
|
||||
#define IPAddress_h
|
||||
@ -25,51 +25,60 @@
|
||||
|
||||
// A class to make it easier to handle and pass around IP addresses
|
||||
|
||||
class IPAddress : public Printable {
|
||||
private:
|
||||
union {
|
||||
uint8_t bytes[4]; // IPv4 address
|
||||
uint32_t dword;
|
||||
} _address;
|
||||
class IPAddress: public Printable {
|
||||
private:
|
||||
union {
|
||||
uint8_t bytes[4]; // IPv4 address
|
||||
uint32_t dword;
|
||||
} _address;
|
||||
|
||||
// Access the raw byte array containing the address. Because this returns a pointer
|
||||
// to the internal structure rather than a copy of the address this function should only
|
||||
// be used when you know that the usage of the returned uint8_t* will be transient and not
|
||||
// stored.
|
||||
uint8_t* raw_address() { return _address.bytes; };
|
||||
// Access the raw byte array containing the address. Because this returns a pointer
|
||||
// to the internal structure rather than a copy of the address this function should only
|
||||
// be used when you know that the usage of the returned uint8_t* will be transient and not
|
||||
// stored.
|
||||
uint8_t* raw_address() {
|
||||
return _address.bytes;
|
||||
}
|
||||
|
||||
public:
|
||||
// Constructors
|
||||
IPAddress();
|
||||
IPAddress(uint8_t first_octet, uint8_t second_octet, uint8_t third_octet, uint8_t fourth_octet);
|
||||
IPAddress(uint32_t address);
|
||||
IPAddress(const uint8_t *address);
|
||||
public:
|
||||
// Constructors
|
||||
IPAddress();
|
||||
IPAddress(uint8_t first_octet, uint8_t second_octet, uint8_t third_octet, uint8_t fourth_octet);
|
||||
IPAddress(uint32_t address);
|
||||
IPAddress(const uint8_t *address);
|
||||
|
||||
// Overloaded cast operator to allow IPAddress objects to be used where a pointer
|
||||
// to a four-byte uint8_t array is expected
|
||||
operator uint32_t() const { return _address.dword; };
|
||||
bool operator==(const IPAddress& addr) const { return _address.dword == addr._address.dword; };
|
||||
bool operator==(const uint8_t* addr) const;
|
||||
// Overloaded cast operator to allow IPAddress objects to be used where a pointer
|
||||
// to a four-byte uint8_t array is expected
|
||||
operator uint32_t() const {
|
||||
return _address.dword;
|
||||
}
|
||||
bool operator==(const IPAddress& addr) const {
|
||||
return _address.dword == addr._address.dword;
|
||||
}
|
||||
bool operator==(const uint8_t* addr) const;
|
||||
|
||||
// Overloaded index operator to allow getting and setting individual octets of the address
|
||||
uint8_t operator[](int index) const { return _address.bytes[index]; };
|
||||
uint8_t& operator[](int index) { return _address.bytes[index]; };
|
||||
// Overloaded index operator to allow getting and setting individual octets of the address
|
||||
uint8_t operator[](int index) const {
|
||||
return _address.bytes[index];
|
||||
}
|
||||
uint8_t& operator[](int index) {
|
||||
return _address.bytes[index];
|
||||
}
|
||||
|
||||
// Overloaded copy operators to allow initialisation of IPAddress objects from other types
|
||||
IPAddress& operator=(const uint8_t *address);
|
||||
IPAddress& operator=(uint32_t address);
|
||||
// Overloaded copy operators to allow initialisation of IPAddress objects from other types
|
||||
IPAddress& operator=(const uint8_t *address);
|
||||
IPAddress& operator=(uint32_t address);
|
||||
|
||||
virtual size_t printTo(Print& p) const;
|
||||
virtual size_t printTo(Print& p) const;
|
||||
|
||||
friend class EthernetClass;
|
||||
friend class UDP;
|
||||
friend class Client;
|
||||
friend class Server;
|
||||
friend class DhcpClass;
|
||||
friend class DNSClient;
|
||||
friend class EthernetClass;
|
||||
friend class UDP;
|
||||
friend class Client;
|
||||
friend class Server;
|
||||
friend class DhcpClass;
|
||||
friend class DNSClient;
|
||||
};
|
||||
|
||||
const IPAddress INADDR_NONE(0,0,0,0);
|
||||
|
||||
const IPAddress INADDR_NONE(0, 0, 0, 0);
|
||||
|
||||
#endif
|
||||
|
@ -34,215 +34,197 @@ extern "C" {
|
||||
// Public Methods //////////////////////////////////////////////////////////////
|
||||
|
||||
/* default implementation: may be overridden */
|
||||
size_t ICACHE_FLASH_ATTR Print::write(const uint8_t *buffer, size_t size)
|
||||
{
|
||||
size_t n = 0;
|
||||
while (size--) {
|
||||
n += write(*buffer++);
|
||||
}
|
||||
return n;
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::print(const String &s)
|
||||
{
|
||||
return write(s.c_str(), s.length());
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::print(const char str[])
|
||||
{
|
||||
return write(str);
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::print(char c)
|
||||
{
|
||||
return write(c);
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::print(unsigned char b, int base)
|
||||
{
|
||||
return print((unsigned long) b, base);
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::print(int n, int base)
|
||||
{
|
||||
return print((long) n, base);
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::print(unsigned int n, int base)
|
||||
{
|
||||
return print((unsigned long) n, base);
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::print(long n, int base)
|
||||
{
|
||||
if (base == 0) {
|
||||
return write(n);
|
||||
} else if (base == 10) {
|
||||
if (n < 0) {
|
||||
int t = print('-');
|
||||
n = -n;
|
||||
return printNumber(n, 10) + t;
|
||||
size_t ICACHE_FLASH_ATTR Print::write(const uint8_t *buffer, size_t size) {
|
||||
size_t n = 0;
|
||||
while(size--) {
|
||||
n += write(*buffer++);
|
||||
}
|
||||
return printNumber(n, 10);
|
||||
} else {
|
||||
return printNumber(n, base);
|
||||
}
|
||||
return n;
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::print(unsigned long n, int base)
|
||||
{
|
||||
if (base == 0) return write(n);
|
||||
else return printNumber(n, base);
|
||||
size_t ICACHE_FLASH_ATTR Print::print(const String &s) {
|
||||
return write(s.c_str(), s.length());
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::print(double n, int digits)
|
||||
{
|
||||
return printFloat(n, digits);
|
||||
size_t ICACHE_FLASH_ATTR Print::print(const char str[]) {
|
||||
return write(str);
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::print(const Printable& x)
|
||||
{
|
||||
return x.printTo(*this);
|
||||
size_t ICACHE_FLASH_ATTR Print::print(char c) {
|
||||
return write(c);
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(void)
|
||||
{
|
||||
size_t n = print("\r\n");
|
||||
return n;
|
||||
size_t ICACHE_FLASH_ATTR Print::print(unsigned char b, int base) {
|
||||
return print((unsigned long) b, base);
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(const String &s)
|
||||
{
|
||||
size_t n = print(s);
|
||||
n += println();
|
||||
return n;
|
||||
size_t ICACHE_FLASH_ATTR Print::print(int n, int base) {
|
||||
return print((long) n, base);
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(const char c[])
|
||||
{
|
||||
size_t n = print(c);
|
||||
n += println();
|
||||
return n;
|
||||
size_t ICACHE_FLASH_ATTR Print::print(unsigned int n, int base) {
|
||||
return print((unsigned long) n, base);
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(char c)
|
||||
{
|
||||
size_t n = print(c);
|
||||
n += println();
|
||||
return n;
|
||||
size_t ICACHE_FLASH_ATTR Print::print(long n, int base) {
|
||||
if(base == 0) {
|
||||
return write(n);
|
||||
} else if(base == 10) {
|
||||
if(n < 0) {
|
||||
int t = print('-');
|
||||
n = -n;
|
||||
return printNumber(n, 10) + t;
|
||||
}
|
||||
return printNumber(n, 10);
|
||||
} else {
|
||||
return printNumber(n, base);
|
||||
}
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(unsigned char b, int base)
|
||||
{
|
||||
size_t n = print(b, base);
|
||||
n += println();
|
||||
return n;
|
||||
size_t ICACHE_FLASH_ATTR Print::print(unsigned long n, int base) {
|
||||
if(base == 0)
|
||||
return write(n);
|
||||
else
|
||||
return printNumber(n, base);
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(int num, int base)
|
||||
{
|
||||
size_t n = print(num, base);
|
||||
n += println();
|
||||
return n;
|
||||
size_t ICACHE_FLASH_ATTR Print::print(double n, int digits) {
|
||||
return printFloat(n, digits);
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(unsigned int num, int base)
|
||||
{
|
||||
size_t n = print(num, base);
|
||||
n += println();
|
||||
return n;
|
||||
size_t ICACHE_FLASH_ATTR Print::print(const Printable& x) {
|
||||
return x.printTo(*this);
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(long num, int base)
|
||||
{
|
||||
size_t n = print(num, base);
|
||||
n += println();
|
||||
return n;
|
||||
size_t ICACHE_FLASH_ATTR Print::println(void) {
|
||||
size_t n = print("\r\n");
|
||||
return n;
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(unsigned long num, int base)
|
||||
{
|
||||
size_t n = print(num, base);
|
||||
n += println();
|
||||
return n;
|
||||
size_t ICACHE_FLASH_ATTR Print::println(const String &s) {
|
||||
size_t n = print(s);
|
||||
n += println();
|
||||
return n;
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(double num, int digits)
|
||||
{
|
||||
size_t n = print(num, digits);
|
||||
n += println();
|
||||
return n;
|
||||
size_t ICACHE_FLASH_ATTR Print::println(const char c[]) {
|
||||
size_t n = print(c);
|
||||
n += println();
|
||||
return n;
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(const Printable& x)
|
||||
{
|
||||
size_t n = print(x);
|
||||
n += println();
|
||||
return n;
|
||||
size_t ICACHE_FLASH_ATTR Print::println(char c) {
|
||||
size_t n = print(c);
|
||||
n += println();
|
||||
return n;
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(unsigned char b, int base) {
|
||||
size_t n = print(b, base);
|
||||
n += println();
|
||||
return n;
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(int num, int base) {
|
||||
size_t n = print(num, base);
|
||||
n += println();
|
||||
return n;
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(unsigned int num, int base) {
|
||||
size_t n = print(num, base);
|
||||
n += println();
|
||||
return n;
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(long num, int base) {
|
||||
size_t n = print(num, base);
|
||||
n += println();
|
||||
return n;
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(unsigned long num, int base) {
|
||||
size_t n = print(num, base);
|
||||
n += println();
|
||||
return n;
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(double num, int digits) {
|
||||
size_t n = print(num, digits);
|
||||
n += println();
|
||||
return n;
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::println(const Printable& x) {
|
||||
size_t n = print(x);
|
||||
n += println();
|
||||
return n;
|
||||
}
|
||||
|
||||
// Private Methods /////////////////////////////////////////////////////////////
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::printNumber(unsigned long n, uint8_t base) {
|
||||
char buf[8 * sizeof(long) + 1]; // Assumes 8-bit chars plus zero byte.
|
||||
char *str = &buf[sizeof(buf) - 1];
|
||||
char buf[8 * sizeof(long) + 1]; // Assumes 8-bit chars plus zero byte.
|
||||
char *str = &buf[sizeof(buf) - 1];
|
||||
|
||||
*str = '\0';
|
||||
*str = '\0';
|
||||
|
||||
// prevent crash if called with base == 1
|
||||
if (base < 2) base = 10;
|
||||
// prevent crash if called with base == 1
|
||||
if(base < 2)
|
||||
base = 10;
|
||||
|
||||
do {
|
||||
unsigned long m = n;
|
||||
n /= base;
|
||||
char c = m - base * n;
|
||||
*--str = c < 10 ? c + '0' : c + 'A' - 10;
|
||||
} while(n);
|
||||
do {
|
||||
unsigned long m = n;
|
||||
n /= base;
|
||||
char c = m - base * n;
|
||||
*--str = c < 10 ? c + '0' : c + 'A' - 10;
|
||||
} while(n);
|
||||
|
||||
return write(str);
|
||||
return write(str);
|
||||
}
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Print::printFloat(double number, uint8_t digits)
|
||||
{
|
||||
size_t n = 0;
|
||||
size_t ICACHE_FLASH_ATTR Print::printFloat(double number, uint8_t digits) {
|
||||
size_t n = 0;
|
||||
|
||||
if (isnan(number)) return print("nan");
|
||||
if (isinf(number)) return print("inf");
|
||||
if (number > 4294967040.0) return print ("ovf"); // constant determined empirically
|
||||
if (number <-4294967040.0) return print ("ovf"); // constant determined empirically
|
||||
if(isnan(number))
|
||||
return print("nan");
|
||||
if(isinf(number))
|
||||
return print("inf");
|
||||
if(number > 4294967040.0)
|
||||
return print("ovf"); // constant determined empirically
|
||||
if(number < -4294967040.0)
|
||||
return print("ovf"); // constant determined empirically
|
||||
|
||||
// Handle negative numbers
|
||||
if (number < 0.0)
|
||||
{
|
||||
n += print('-');
|
||||
number = -number;
|
||||
}
|
||||
// Handle negative numbers
|
||||
if(number < 0.0) {
|
||||
n += print('-');
|
||||
number = -number;
|
||||
}
|
||||
|
||||
// Round correctly so that print(1.999, 2) prints as "2.00"
|
||||
double rounding = 0.5;
|
||||
for (uint8_t i=0; i<digits; ++i)
|
||||
rounding /= 10.0;
|
||||
// Round correctly so that print(1.999, 2) prints as "2.00"
|
||||
double rounding = 0.5;
|
||||
for(uint8_t i = 0; i < digits; ++i)
|
||||
rounding /= 10.0;
|
||||
|
||||
number += rounding;
|
||||
number += rounding;
|
||||
|
||||
// Extract the integer part of the number and print it
|
||||
unsigned long int_part = (unsigned long)number;
|
||||
double remainder = number - (double)int_part;
|
||||
n += print(int_part);
|
||||
// Extract the integer part of the number and print it
|
||||
unsigned long int_part = (unsigned long) number;
|
||||
double remainder = number - (double) int_part;
|
||||
n += print(int_part);
|
||||
|
||||
// Print the decimal point, but only if there are digits beyond
|
||||
if (digits > 0) {
|
||||
n += print(".");
|
||||
}
|
||||
// Print the decimal point, but only if there are digits beyond
|
||||
if(digits > 0) {
|
||||
n += print(".");
|
||||
}
|
||||
|
||||
// Extract digits from the remainder one at a time
|
||||
while (digits-- > 0)
|
||||
{
|
||||
remainder *= 10.0;
|
||||
int toPrint = int(remainder);
|
||||
n += print(toPrint);
|
||||
remainder -= toPrint;
|
||||
}
|
||||
// Extract digits from the remainder one at a time
|
||||
while(digits-- > 0) {
|
||||
remainder *= 10.0;
|
||||
int toPrint = int(remainder);
|
||||
n += print(toPrint);
|
||||
remainder -= toPrint;
|
||||
}
|
||||
|
||||
return n;
|
||||
return n;
|
||||
}
|
||||
|
@ -1,21 +1,21 @@
|
||||
/*
|
||||
Print.h - Base class that provides print() and println()
|
||||
Copyright (c) 2008 David A. Mellis. All right reserved.
|
||||
Print.h - Base class that provides print() and println()
|
||||
Copyright (c) 2008 David A. Mellis. All right reserved.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef Print_h
|
||||
#define Print_h
|
||||
@ -31,52 +31,60 @@
|
||||
#define OCT 8
|
||||
#define BIN 2
|
||||
|
||||
class Print
|
||||
{
|
||||
private:
|
||||
int write_error;
|
||||
size_t printNumber(unsigned long, uint8_t);
|
||||
size_t printFloat(double, uint8_t);
|
||||
protected:
|
||||
void setWriteError(int err = 1) { write_error = err; }
|
||||
public:
|
||||
Print() : write_error(0) {}
|
||||
class Print {
|
||||
private:
|
||||
int write_error;
|
||||
size_t printNumber(unsigned long, uint8_t);
|
||||
size_t printFloat(double, uint8_t);
|
||||
protected:
|
||||
void setWriteError(int err = 1) {
|
||||
write_error = err;
|
||||
}
|
||||
public:
|
||||
Print() :
|
||||
write_error(0) {
|
||||
}
|
||||
|
||||
int getWriteError() { return write_error; }
|
||||
void clearWriteError() { setWriteError(0); }
|
||||
int getWriteError() {
|
||||
return write_error;
|
||||
}
|
||||
void clearWriteError() {
|
||||
setWriteError(0);
|
||||
}
|
||||
|
||||
virtual size_t write(uint8_t) = 0;
|
||||
size_t write(const char *str) {
|
||||
if (str == NULL) return 0;
|
||||
return write((const uint8_t *)str, strlen(str));
|
||||
}
|
||||
virtual size_t write(const uint8_t *buffer, size_t size);
|
||||
size_t write(const char *buffer, size_t size) {
|
||||
return write((const uint8_t *)buffer, size);
|
||||
}
|
||||
virtual size_t write(uint8_t) = 0;
|
||||
size_t write(const char *str) {
|
||||
if(str == NULL)
|
||||
return 0;
|
||||
return write((const uint8_t *) str, strlen(str));
|
||||
}
|
||||
virtual size_t write(const uint8_t *buffer, size_t size);
|
||||
size_t write(const char *buffer, size_t size) {
|
||||
return write((const uint8_t *) buffer, size);
|
||||
}
|
||||
|
||||
size_t print(const String &);
|
||||
size_t print(const char[]);
|
||||
size_t print(char);
|
||||
size_t print(unsigned char, int = DEC);
|
||||
size_t print(int, int = DEC);
|
||||
size_t print(unsigned int, int = DEC);
|
||||
size_t print(long, int = DEC);
|
||||
size_t print(unsigned long, int = DEC);
|
||||
size_t print(double, int = 2);
|
||||
size_t print(const Printable&);
|
||||
size_t print(const String &);
|
||||
size_t print(const char[]);
|
||||
size_t print(char);
|
||||
size_t print(unsigned char, int = DEC);
|
||||
size_t print(int, int = DEC);
|
||||
size_t print(unsigned int, int = DEC);
|
||||
size_t print(long, int = DEC);
|
||||
size_t print(unsigned long, int = DEC);
|
||||
size_t print(double, int = 2);
|
||||
size_t print(const Printable&);
|
||||
|
||||
size_t println(const String &s);
|
||||
size_t println(const char[]);
|
||||
size_t println(char);
|
||||
size_t println(unsigned char, int = DEC);
|
||||
size_t println(int, int = DEC);
|
||||
size_t println(unsigned int, int = DEC);
|
||||
size_t println(long, int = DEC);
|
||||
size_t println(unsigned long, int = DEC);
|
||||
size_t println(double, int = 2);
|
||||
size_t println(const Printable&);
|
||||
size_t println(void);
|
||||
size_t println(const String &s);
|
||||
size_t println(const char[]);
|
||||
size_t println(char);
|
||||
size_t println(unsigned char, int = DEC);
|
||||
size_t println(int, int = DEC);
|
||||
size_t println(unsigned int, int = DEC);
|
||||
size_t println(long, int = DEC);
|
||||
size_t println(unsigned long, int = DEC);
|
||||
size_t println(double, int = 2);
|
||||
size_t println(const Printable&);
|
||||
size_t println(void);
|
||||
};
|
||||
|
||||
#endif
|
||||
|
@ -1,21 +1,21 @@
|
||||
/*
|
||||
Printable.h - Interface class that allows printing of complex types
|
||||
Copyright (c) 2011 Adrian McEwen. All right reserved.
|
||||
Printable.h - Interface class that allows printing of complex types
|
||||
Copyright (c) 2011 Adrian McEwen. All right reserved.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef Printable_h
|
||||
#define Printable_h
|
||||
@ -25,15 +25,14 @@
|
||||
class Print;
|
||||
|
||||
/** The Printable class provides a way for new classes to allow themselves to be printed.
|
||||
By deriving from Printable and implementing the printTo method, it will then be possible
|
||||
for users to print out instances of this class by passing them into the usual
|
||||
Print::print and Print::println methods.
|
||||
*/
|
||||
By deriving from Printable and implementing the printTo method, it will then be possible
|
||||
for users to print out instances of this class by passing them into the usual
|
||||
Print::print and Print::println methods.
|
||||
*/
|
||||
|
||||
class Printable
|
||||
{
|
||||
public:
|
||||
virtual size_t printTo(Print& p) const = 0;
|
||||
class Printable {
|
||||
public:
|
||||
virtual size_t printTo(Print& p) const = 0;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
@ -1,30 +1,30 @@
|
||||
/*
|
||||
Server.h - Base class that provides Server
|
||||
Copyright (c) 2011 Adrian McEwen. All right reserved.
|
||||
Server.h - Base class that provides Server
|
||||
Copyright (c) 2011 Adrian McEwen. All right reserved.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef server_h
|
||||
#define server_h
|
||||
|
||||
#include "Print.h"
|
||||
|
||||
class Server : public Print {
|
||||
public:
|
||||
virtual void begin() =0;
|
||||
class Server: public Print {
|
||||
public:
|
||||
virtual void begin() =0;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
@ -22,50 +22,52 @@
|
||||
|
||||
#include "Arduino.h"
|
||||
#include "Stream.h"
|
||||
extern "C"{
|
||||
#include "c_types.h"
|
||||
extern "C" {
|
||||
#include "c_types.h"
|
||||
}
|
||||
#define PARSE_TIMEOUT 1000 // default number of milli-seconds to wait
|
||||
#define NO_SKIP_CHAR 1 // a magic char not found in a valid ASCII numeric field
|
||||
|
||||
// private method to read stream with timeout
|
||||
int ICACHE_FLASH_ATTR Stream::timedRead()
|
||||
{
|
||||
int c;
|
||||
_startMillis = millis();
|
||||
do {
|
||||
c = read();
|
||||
if (c >= 0) return c;
|
||||
yield();
|
||||
} while(millis() - _startMillis < _timeout);
|
||||
return -1; // -1 indicates timeout
|
||||
int ICACHE_FLASH_ATTR Stream::timedRead() {
|
||||
int c;
|
||||
_startMillis = millis();
|
||||
do {
|
||||
c = read();
|
||||
if(c >= 0)
|
||||
return c;
|
||||
yield();
|
||||
} while(millis() - _startMillis < _timeout);
|
||||
return -1; // -1 indicates timeout
|
||||
}
|
||||
|
||||
// private method to peek stream with timeout
|
||||
int ICACHE_FLASH_ATTR Stream::timedPeek()
|
||||
{
|
||||
int c;
|
||||
_startMillis = millis();
|
||||
do {
|
||||
c = peek();
|
||||
if (c >= 0) return c;
|
||||
yield();
|
||||
} while(millis() - _startMillis < _timeout);
|
||||
return -1; // -1 indicates timeout
|
||||
int ICACHE_FLASH_ATTR Stream::timedPeek() {
|
||||
int c;
|
||||
_startMillis = millis();
|
||||
do {
|
||||
c = peek();
|
||||
if(c >= 0)
|
||||
return c;
|
||||
yield();
|
||||
} while(millis() - _startMillis < _timeout);
|
||||
return -1; // -1 indicates timeout
|
||||
}
|
||||
|
||||
// returns peek of the next digit in the stream or -1 if timeout
|
||||
// discards non-numeric characters
|
||||
int ICACHE_FLASH_ATTR Stream::peekNextDigit()
|
||||
{
|
||||
int c;
|
||||
while (1) {
|
||||
c = timedPeek();
|
||||
if (c < 0) return c; // timeout
|
||||
if (c == '-') return c;
|
||||
if (c >= '0' && c <= '9') return c;
|
||||
read(); // discard non-numeric
|
||||
}
|
||||
int ICACHE_FLASH_ATTR Stream::peekNextDigit() {
|
||||
int c;
|
||||
while(1) {
|
||||
c = timedPeek();
|
||||
if(c < 0)
|
||||
return c; // timeout
|
||||
if(c == '-')
|
||||
return c;
|
||||
if(c >= '0' && c <= '9')
|
||||
return c;
|
||||
read(); // discard non-numeric
|
||||
}
|
||||
}
|
||||
|
||||
// Public Methods
|
||||
@ -73,144 +75,132 @@ int ICACHE_FLASH_ATTR Stream::peekNextDigit()
|
||||
|
||||
void ICACHE_FLASH_ATTR Stream::setTimeout(unsigned long timeout) // sets the maximum number of milliseconds to wait
|
||||
{
|
||||
_timeout = timeout;
|
||||
_timeout = timeout;
|
||||
}
|
||||
|
||||
// find returns true if the target string is found
|
||||
bool ICACHE_FLASH_ATTR Stream::find(const char *target)
|
||||
{
|
||||
return findUntil(target, (char*)"");
|
||||
// find returns true if the target string is found
|
||||
bool ICACHE_FLASH_ATTR Stream::find(const char *target) {
|
||||
return findUntil(target, (char*) "");
|
||||
}
|
||||
|
||||
// reads data from the stream until the target string of given length is found
|
||||
// returns true if target string is found, false if timed out
|
||||
bool ICACHE_FLASH_ATTR Stream::find(const char *target, size_t length)
|
||||
{
|
||||
return findUntil(target, length, NULL, 0);
|
||||
bool ICACHE_FLASH_ATTR Stream::find(const char *target, size_t length) {
|
||||
return findUntil(target, length, NULL, 0);
|
||||
}
|
||||
|
||||
// as find but search ends if the terminator string is found
|
||||
bool ICACHE_FLASH_ATTR Stream::findUntil(const char *target, const char *terminator)
|
||||
{
|
||||
return findUntil(target, strlen(target), terminator, strlen(terminator));
|
||||
bool ICACHE_FLASH_ATTR Stream::findUntil(const char *target, const char *terminator) {
|
||||
return findUntil(target, strlen(target), terminator, strlen(terminator));
|
||||
}
|
||||
|
||||
// reads data from the stream until the target string of the given length is found
|
||||
// search terminated if the terminator string is found
|
||||
// returns true if target string is found, false if terminated or timed out
|
||||
bool ICACHE_FLASH_ATTR Stream::findUntil(const char *target, size_t targetLen, const char *terminator, size_t termLen)
|
||||
{
|
||||
size_t index = 0; // maximum target string length is 64k bytes!
|
||||
size_t termIndex = 0;
|
||||
int c;
|
||||
bool ICACHE_FLASH_ATTR Stream::findUntil(const char *target, size_t targetLen, const char *terminator, size_t termLen) {
|
||||
size_t index = 0; // maximum target string length is 64k bytes!
|
||||
size_t termIndex = 0;
|
||||
int c;
|
||||
|
||||
if( *target == 0)
|
||||
return true; // return true if target is a null string
|
||||
while( (c = timedRead()) > 0){
|
||||
if(*target == 0)
|
||||
return true; // return true if target is a null string
|
||||
while((c = timedRead()) > 0) {
|
||||
|
||||
if(c != target[index])
|
||||
index = 0; // reset index if any char does not match
|
||||
if(c != target[index])
|
||||
index = 0; // reset index if any char does not match
|
||||
|
||||
if( c == target[index]){
|
||||
//////Serial.print("found "); Serial.write(c); Serial.print("index now"); Serial.println(index+1);
|
||||
if(++index >= targetLen){ // return true if all chars in the target match
|
||||
return true;
|
||||
}
|
||||
if(c == target[index]) {
|
||||
//////Serial.print("found "); Serial.write(c); Serial.print("index now"); Serial.println(index+1);
|
||||
if(++index >= targetLen) { // return true if all chars in the target match
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
if(termLen > 0 && c == terminator[termIndex]) {
|
||||
if(++termIndex >= termLen)
|
||||
return false; // return false if terminate string found before target string
|
||||
} else
|
||||
termIndex = 0;
|
||||
}
|
||||
|
||||
if(termLen > 0 && c == terminator[termIndex]){
|
||||
if(++termIndex >= termLen)
|
||||
return false; // return false if terminate string found before target string
|
||||
}
|
||||
else
|
||||
termIndex = 0;
|
||||
}
|
||||
return false;
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
// returns the first valid (long) integer value from the current position.
|
||||
// initial characters that are not digits (or the minus sign) are skipped
|
||||
// function is terminated by the first character that is not a digit.
|
||||
long ICACHE_FLASH_ATTR Stream::parseInt()
|
||||
{
|
||||
return parseInt(NO_SKIP_CHAR); // terminate on first non-digit character (or timeout)
|
||||
long ICACHE_FLASH_ATTR Stream::parseInt() {
|
||||
return parseInt(NO_SKIP_CHAR); // terminate on first non-digit character (or timeout)
|
||||
}
|
||||
|
||||
// as above but a given skipChar is ignored
|
||||
// this allows format characters (typically commas) in values to be ignored
|
||||
long ICACHE_FLASH_ATTR Stream::parseInt(char skipChar)
|
||||
{
|
||||
boolean isNegative = false;
|
||||
long value = 0;
|
||||
int c;
|
||||
long ICACHE_FLASH_ATTR Stream::parseInt(char skipChar) {
|
||||
boolean isNegative = false;
|
||||
long value = 0;
|
||||
int c;
|
||||
|
||||
c = peekNextDigit();
|
||||
// ignore non numeric leading characters
|
||||
if(c < 0)
|
||||
return 0; // zero returned if timeout
|
||||
c = peekNextDigit();
|
||||
// ignore non numeric leading characters
|
||||
if(c < 0)
|
||||
return 0; // zero returned if timeout
|
||||
|
||||
do{
|
||||
if(c == skipChar)
|
||||
; // ignore this charactor
|
||||
else if(c == '-')
|
||||
isNegative = true;
|
||||
else if(c >= '0' && c <= '9') // is c a digit?
|
||||
value = value * 10 + c - '0';
|
||||
read(); // consume the character we got with peek
|
||||
c = timedPeek();
|
||||
}
|
||||
while( (c >= '0' && c <= '9') || c == skipChar );
|
||||
do {
|
||||
if(c == skipChar)
|
||||
; // ignore this charactor
|
||||
else if(c == '-')
|
||||
isNegative = true;
|
||||
else if(c >= '0' && c <= '9') // is c a digit?
|
||||
value = value * 10 + c - '0';
|
||||
read(); // consume the character we got with peek
|
||||
c = timedPeek();
|
||||
} while((c >= '0' && c <= '9') || c == skipChar);
|
||||
|
||||
if(isNegative)
|
||||
value = -value;
|
||||
return value;
|
||||
if(isNegative)
|
||||
value = -value;
|
||||
return value;
|
||||
}
|
||||
|
||||
|
||||
// as parseInt but returns a floating point value
|
||||
float ICACHE_FLASH_ATTR Stream::parseFloat()
|
||||
{
|
||||
return parseFloat(NO_SKIP_CHAR);
|
||||
float ICACHE_FLASH_ATTR Stream::parseFloat() {
|
||||
return parseFloat(NO_SKIP_CHAR);
|
||||
}
|
||||
|
||||
// as above but the given skipChar is ignored
|
||||
// this allows format characters (typically commas) in values to be ignored
|
||||
float ICACHE_FLASH_ATTR Stream::parseFloat(char skipChar){
|
||||
boolean isNegative = false;
|
||||
boolean isFraction = false;
|
||||
long value = 0;
|
||||
int c;
|
||||
float fraction = 1.0;
|
||||
float ICACHE_FLASH_ATTR Stream::parseFloat(char skipChar) {
|
||||
boolean isNegative = false;
|
||||
boolean isFraction = false;
|
||||
long value = 0;
|
||||
int c;
|
||||
float fraction = 1.0;
|
||||
|
||||
c = peekNextDigit();
|
||||
c = peekNextDigit();
|
||||
// ignore non numeric leading characters
|
||||
if(c < 0)
|
||||
return 0; // zero returned if timeout
|
||||
if(c < 0)
|
||||
return 0; // zero returned if timeout
|
||||
|
||||
do{
|
||||
if(c == skipChar)
|
||||
; // ignore
|
||||
else if(c == '-')
|
||||
isNegative = true;
|
||||
else if (c == '.')
|
||||
isFraction = true;
|
||||
else if(c >= '0' && c <= '9') { // is c a digit?
|
||||
value = value * 10 + c - '0';
|
||||
if(isFraction)
|
||||
fraction *= 0.1;
|
||||
}
|
||||
read(); // consume the character we got with peek
|
||||
c = timedPeek();
|
||||
}
|
||||
while( (c >= '0' && c <= '9') || c == '.' || c == skipChar );
|
||||
do {
|
||||
if(c == skipChar)
|
||||
; // ignore
|
||||
else if(c == '-')
|
||||
isNegative = true;
|
||||
else if(c == '.')
|
||||
isFraction = true;
|
||||
else if(c >= '0' && c <= '9') { // is c a digit?
|
||||
value = value * 10 + c - '0';
|
||||
if(isFraction)
|
||||
fraction *= 0.1;
|
||||
}
|
||||
read(); // consume the character we got with peek
|
||||
c = timedPeek();
|
||||
} while((c >= '0' && c <= '9') || c == '.' || c == skipChar);
|
||||
|
||||
if(isNegative)
|
||||
value = -value;
|
||||
if(isFraction)
|
||||
return value * fraction;
|
||||
else
|
||||
return value;
|
||||
if(isNegative)
|
||||
value = -value;
|
||||
if(isFraction)
|
||||
return value * fraction;
|
||||
else
|
||||
return value;
|
||||
}
|
||||
|
||||
// read characters from stream into buffer
|
||||
@ -218,57 +208,53 @@ float ICACHE_FLASH_ATTR Stream::parseFloat(char skipChar){
|
||||
// returns the number of characters placed in the buffer
|
||||
// the buffer is NOT null terminated.
|
||||
//
|
||||
size_t ICACHE_FLASH_ATTR Stream::readBytes(char *buffer, size_t length)
|
||||
{
|
||||
size_t count = 0;
|
||||
while (count < length) {
|
||||
int c = timedRead();
|
||||
if (c < 0) break;
|
||||
*buffer++ = (char)c;
|
||||
count++;
|
||||
}
|
||||
return count;
|
||||
size_t ICACHE_FLASH_ATTR Stream::readBytes(char *buffer, size_t length) {
|
||||
size_t count = 0;
|
||||
while(count < length) {
|
||||
int c = timedRead();
|
||||
if(c < 0)
|
||||
break;
|
||||
*buffer++ = (char) c;
|
||||
count++;
|
||||
}
|
||||
return count;
|
||||
}
|
||||
|
||||
|
||||
// as readBytes with terminator character
|
||||
// terminates if length characters have been read, timeout, or if the terminator character detected
|
||||
// returns the number of characters placed in the buffer (0 means no valid data found)
|
||||
|
||||
size_t ICACHE_FLASH_ATTR Stream::readBytesUntil(char terminator, char *buffer, size_t length)
|
||||
{
|
||||
if (length < 1) return 0;
|
||||
size_t index = 0;
|
||||
while (index < length) {
|
||||
size_t ICACHE_FLASH_ATTR Stream::readBytesUntil(char terminator, char *buffer, size_t length) {
|
||||
if(length < 1)
|
||||
return 0;
|
||||
size_t index = 0;
|
||||
while(index < length) {
|
||||
int c = timedRead();
|
||||
if(c < 0 || c == terminator)
|
||||
break;
|
||||
*buffer++ = (char) c;
|
||||
index++;
|
||||
}
|
||||
return index; // return number of characters, not including null terminator
|
||||
}
|
||||
|
||||
String ICACHE_FLASH_ATTR Stream::readString() {
|
||||
String ret;
|
||||
int c = timedRead();
|
||||
if (c < 0 || c == terminator) break;
|
||||
*buffer++ = (char)c;
|
||||
index++;
|
||||
}
|
||||
return index; // return number of characters, not including null terminator
|
||||
while(c >= 0) {
|
||||
ret += (char) c;
|
||||
c = timedRead();
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
String ICACHE_FLASH_ATTR Stream::readString()
|
||||
{
|
||||
String ret;
|
||||
int c = timedRead();
|
||||
while (c >= 0)
|
||||
{
|
||||
ret += (char)c;
|
||||
c = timedRead();
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
String ICACHE_FLASH_ATTR Stream::readStringUntil(char terminator)
|
||||
{
|
||||
String ret;
|
||||
int c = timedRead();
|
||||
while (c >= 0 && c != terminator)
|
||||
{
|
||||
ret += (char)c;
|
||||
c = timedRead();
|
||||
}
|
||||
return ret;
|
||||
String ICACHE_FLASH_ATTR Stream::readStringUntil(char terminator) {
|
||||
String ret;
|
||||
int c = timedRead();
|
||||
while(c >= 0 && c != terminator) {
|
||||
ret += (char) c;
|
||||
c = timedRead();
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
@ -1,23 +1,23 @@
|
||||
/*
|
||||
Stream.h - base class for character-based streams.
|
||||
Copyright (c) 2010 David A. Mellis. All right reserved.
|
||||
Stream.h - base class for character-based streams.
|
||||
Copyright (c) 2010 David A. Mellis. All right reserved.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
|
||||
parsing functions based on TextFinder library by Michael Margolis
|
||||
*/
|
||||
parsing functions based on TextFinder library by Michael Margolis
|
||||
*/
|
||||
|
||||
#ifndef Stream_h
|
||||
#define Stream_h
|
||||
@ -27,76 +27,88 @@
|
||||
|
||||
// compatability macros for testing
|
||||
/*
|
||||
#define getInt() parseInt()
|
||||
#define getInt(skipChar) parseInt(skipchar)
|
||||
#define getFloat() parseFloat()
|
||||
#define getFloat(skipChar) parseFloat(skipChar)
|
||||
#define getString( pre_string, post_string, buffer, length)
|
||||
readBytesBetween( pre_string, terminator, buffer, length)
|
||||
*/
|
||||
#define getInt() parseInt()
|
||||
#define getInt(skipChar) parseInt(skipchar)
|
||||
#define getFloat() parseFloat()
|
||||
#define getFloat(skipChar) parseFloat(skipChar)
|
||||
#define getString( pre_string, post_string, buffer, length)
|
||||
readBytesBetween( pre_string, terminator, buffer, length)
|
||||
*/
|
||||
|
||||
class Stream : public Print
|
||||
{
|
||||
protected:
|
||||
unsigned long _timeout; // number of milliseconds to wait for the next char before aborting timed read
|
||||
unsigned long _startMillis; // used for timeout measurement
|
||||
int timedRead(); // private method to read stream with timeout
|
||||
int timedPeek(); // private method to peek stream with timeout
|
||||
int peekNextDigit(); // returns the next numeric digit in the stream or -1 if timeout
|
||||
class Stream: public Print {
|
||||
protected:
|
||||
unsigned long _timeout; // number of milliseconds to wait for the next char before aborting timed read
|
||||
unsigned long _startMillis; // used for timeout measurement
|
||||
int timedRead(); // private method to read stream with timeout
|
||||
int timedPeek(); // private method to peek stream with timeout
|
||||
int peekNextDigit(); // returns the next numeric digit in the stream or -1 if timeout
|
||||
|
||||
public:
|
||||
virtual int available() = 0;
|
||||
virtual int read() = 0;
|
||||
virtual int peek() = 0;
|
||||
virtual void flush() = 0;
|
||||
public:
|
||||
virtual int available() = 0;
|
||||
virtual int read() = 0;
|
||||
virtual int peek() = 0;
|
||||
virtual void flush() = 0;
|
||||
|
||||
Stream() {_timeout=1000;}
|
||||
Stream() {
|
||||
_timeout = 1000;
|
||||
}
|
||||
|
||||
// parsing methods
|
||||
|
||||
void setTimeout(unsigned long timeout); // sets maximum milliseconds to wait for stream data, default is 1 second
|
||||
void setTimeout(unsigned long timeout); // sets maximum milliseconds to wait for stream data, default is 1 second
|
||||
|
||||
bool find(const char *target); // reads data from the stream until the target string is found
|
||||
bool find(uint8_t *target) { return find ((char *)target); }
|
||||
// returns true if target string is found, false if timed out (see setTimeout)
|
||||
bool find(const char *target); // reads data from the stream until the target string is found
|
||||
bool find(uint8_t *target) {
|
||||
return find((char *) target);
|
||||
}
|
||||
// returns true if target string is found, false if timed out (see setTimeout)
|
||||
|
||||
bool find(const char *target, size_t length); // reads data from the stream until the target string of given length is found
|
||||
bool find(const uint8_t *target, size_t length) { return find ((char *)target, length); }
|
||||
// returns true if target string is found, false if timed out
|
||||
bool find(const char *target, size_t length); // reads data from the stream until the target string of given length is found
|
||||
bool find(const uint8_t *target, size_t length) {
|
||||
return find((char *) target, length);
|
||||
}
|
||||
// returns true if target string is found, false if timed out
|
||||
|
||||
bool findUntil(const char *target, const char *terminator); // as find but search ends if the terminator string is found
|
||||
bool findUntil(const uint8_t *target, const char *terminator) { return findUntil((char *)target, terminator); }
|
||||
bool findUntil(const char *target, const char *terminator); // as find but search ends if the terminator string is found
|
||||
bool findUntil(const uint8_t *target, const char *terminator) {
|
||||
return findUntil((char *) target, terminator);
|
||||
}
|
||||
|
||||
bool findUntil(const char *target, size_t targetLen, const char *terminate, size_t termLen); // as above but search ends if the terminate string is found
|
||||
bool findUntil(const uint8_t *target, size_t targetLen, const char *terminate, size_t termLen) {return findUntil((char *)target, targetLen, terminate, termLen); }
|
||||
bool findUntil(const char *target, size_t targetLen, const char *terminate, size_t termLen); // as above but search ends if the terminate string is found
|
||||
bool findUntil(const uint8_t *target, size_t targetLen, const char *terminate, size_t termLen) {
|
||||
return findUntil((char *) target, targetLen, terminate, termLen);
|
||||
}
|
||||
|
||||
long parseInt(); // returns the first valid (long) integer value from the current position.
|
||||
// initial characters that are not digits (or the minus sign) are skipped
|
||||
// integer is terminated by the first character that is not a digit.
|
||||
|
||||
long parseInt(); // returns the first valid (long) integer value from the current position.
|
||||
// initial characters that are not digits (or the minus sign) are skipped
|
||||
// integer is terminated by the first character that is not a digit.
|
||||
float parseFloat(); // float version of parseInt
|
||||
|
||||
float parseFloat(); // float version of parseInt
|
||||
size_t readBytes(char *buffer, size_t length); // read chars from stream into buffer
|
||||
size_t readBytes(uint8_t *buffer, size_t length) {
|
||||
return readBytes((char *) buffer, length);
|
||||
}
|
||||
// terminates if length characters have been read or timeout (see setTimeout)
|
||||
// returns the number of characters placed in the buffer (0 means no valid data found)
|
||||
|
||||
size_t readBytes( char *buffer, size_t length); // read chars from stream into buffer
|
||||
size_t readBytes( uint8_t *buffer, size_t length) { return readBytes((char *)buffer, length); }
|
||||
// terminates if length characters have been read or timeout (see setTimeout)
|
||||
// returns the number of characters placed in the buffer (0 means no valid data found)
|
||||
size_t readBytesUntil(char terminator, char *buffer, size_t length); // as readBytes with terminator character
|
||||
size_t readBytesUntil(char terminator, uint8_t *buffer, size_t length) {
|
||||
return readBytesUntil(terminator, (char *) buffer, length);
|
||||
}
|
||||
// terminates if length characters have been read, timeout, or if the terminator character detected
|
||||
// returns the number of characters placed in the buffer (0 means no valid data found)
|
||||
|
||||
size_t readBytesUntil( char terminator, char *buffer, size_t length); // as readBytes with terminator character
|
||||
size_t readBytesUntil( char terminator, uint8_t *buffer, size_t length) { return readBytesUntil(terminator, (char *)buffer, length); }
|
||||
// terminates if length characters have been read, timeout, or if the terminator character detected
|
||||
// returns the number of characters placed in the buffer (0 means no valid data found)
|
||||
// Arduino String functions to be added here
|
||||
String readString();
|
||||
String readStringUntil(char terminator);
|
||||
|
||||
// Arduino String functions to be added here
|
||||
String readString();
|
||||
String readStringUntil(char terminator);
|
||||
protected:
|
||||
long parseInt(char skipChar); // as above but the given skipChar is ignored
|
||||
// as above but the given skipChar is ignored
|
||||
// this allows format characters (typically commas) in values to be ignored
|
||||
|
||||
protected:
|
||||
long parseInt(char skipChar); // as above but the given skipChar is ignored
|
||||
// as above but the given skipChar is ignored
|
||||
// this allows format characters (typically commas) in values to be ignored
|
||||
|
||||
float parseFloat(char skipChar); // as above but the given skipChar is ignored
|
||||
float parseFloat(char skipChar); // as above but the given skipChar is ignored
|
||||
};
|
||||
|
||||
#endif
|
||||
|
@ -1,49 +1,49 @@
|
||||
/* Tone.cpp
|
||||
|
||||
A Tone Generator Library
|
||||
A Tone Generator Library
|
||||
|
||||
Written by Brett Hagman
|
||||
Written by Brett Hagman
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
|
||||
Version Modified By Date Comments
|
||||
------- ----------- -------- --------
|
||||
0001 B Hagman 09/08/02 Initial coding
|
||||
0002 B Hagman 09/08/18 Multiple pins
|
||||
0003 B Hagman 09/08/18 Moved initialization from constructor to begin()
|
||||
0004 B Hagman 09/09/26 Fixed problems with ATmega8
|
||||
0005 B Hagman 09/11/23 Scanned prescalars for best fit on 8 bit timers
|
||||
09/11/25 Changed pin toggle method to XOR
|
||||
09/11/25 Fixed timer0 from being excluded
|
||||
0006 D Mellis 09/12/29 Replaced objects with functions
|
||||
0007 M Sproul 10/08/29 Changed #ifdefs from cpu to register
|
||||
0008 S Kanemoto 12/06/22 Fixed for Leonardo by @maris_HY
|
||||
*************************************************/
|
||||
Version Modified By Date Comments
|
||||
------- ----------- -------- --------
|
||||
0001 B Hagman 09/08/02 Initial coding
|
||||
0002 B Hagman 09/08/18 Multiple pins
|
||||
0003 B Hagman 09/08/18 Moved initialization from constructor to begin()
|
||||
0004 B Hagman 09/09/26 Fixed problems with ATmega8
|
||||
0005 B Hagman 09/11/23 Scanned prescalars for best fit on 8 bit timers
|
||||
09/11/25 Changed pin toggle method to XOR
|
||||
09/11/25 Fixed timer0 from being excluded
|
||||
0006 D Mellis 09/12/29 Replaced objects with functions
|
||||
0007 M Sproul 10/08/29 Changed #ifdefs from cpu to register
|
||||
0008 S Kanemoto 12/06/22 Fixed for Leonardo by @maris_HY
|
||||
*************************************************/
|
||||
|
||||
#include "Arduino.h"
|
||||
#include "pins_arduino.h"
|
||||
|
||||
|
||||
static int8_t toneBegin(uint8_t _pin)
|
||||
{
|
||||
static int8_t toneBegin(uint8_t _pin) {
|
||||
//TODO implement tone
|
||||
return 0;
|
||||
}
|
||||
|
||||
void tone(uint8_t _pin, unsigned int frequency, unsigned long duration)
|
||||
{
|
||||
void tone(uint8_t _pin, unsigned int frequency, unsigned long duration) {
|
||||
//TODO implement tone
|
||||
}
|
||||
|
||||
void noTone(uint8_t _pin)
|
||||
{
|
||||
void noTone(uint8_t _pin) {
|
||||
//TODO implement tone
|
||||
}
|
||||
|
@ -38,51 +38,53 @@
|
||||
#include <Stream.h>
|
||||
#include <IPAddress.h>
|
||||
|
||||
class UDP : public Stream {
|
||||
class UDP: public Stream {
|
||||
|
||||
public:
|
||||
virtual uint8_t begin(uint16_t) =0; // initialize, start listening on specified port. Returns 1 if successful, 0 if there are no sockets available to use
|
||||
virtual void stop() =0; // Finish with the UDP socket
|
||||
public:
|
||||
virtual uint8_t begin(uint16_t) =0; // initialize, start listening on specified port. Returns 1 if successful, 0 if there are no sockets available to use
|
||||
virtual void stop() =0; // Finish with the UDP socket
|
||||
|
||||
// Sending UDP packets
|
||||
// Sending UDP packets
|
||||
|
||||
// Start building up a packet to send to the remote host specific in ip and port
|
||||
// Returns 1 if successful, 0 if there was a problem with the supplied IP address or port
|
||||
virtual int beginPacket(IPAddress ip, uint16_t port) =0;
|
||||
// Start building up a packet to send to the remote host specific in host and port
|
||||
// Returns 1 if successful, 0 if there was a problem resolving the hostname or port
|
||||
virtual int beginPacket(const char *host, uint16_t port) =0;
|
||||
// Finish off this packet and send it
|
||||
// Returns 1 if the packet was sent successfully, 0 if there was an error
|
||||
virtual int endPacket() =0;
|
||||
// Write a single byte into the packet
|
||||
virtual size_t write(uint8_t) =0;
|
||||
// Write size bytes from buffer into the packet
|
||||
virtual size_t write(const uint8_t *buffer, size_t size) =0;
|
||||
// Start building up a packet to send to the remote host specific in ip and port
|
||||
// Returns 1 if successful, 0 if there was a problem with the supplied IP address or port
|
||||
virtual int beginPacket(IPAddress ip, uint16_t port) =0;
|
||||
// Start building up a packet to send to the remote host specific in host and port
|
||||
// Returns 1 if successful, 0 if there was a problem resolving the hostname or port
|
||||
virtual int beginPacket(const char *host, uint16_t port) =0;
|
||||
// Finish off this packet and send it
|
||||
// Returns 1 if the packet was sent successfully, 0 if there was an error
|
||||
virtual int endPacket() =0;
|
||||
// Write a single byte into the packet
|
||||
virtual size_t write(uint8_t) =0;
|
||||
// Write size bytes from buffer into the packet
|
||||
virtual size_t write(const uint8_t *buffer, size_t size) =0;
|
||||
|
||||
// Start processing the next available incoming packet
|
||||
// Returns the size of the packet in bytes, or 0 if no packets are available
|
||||
virtual int parsePacket() =0;
|
||||
// Number of bytes remaining in the current packet
|
||||
virtual int available() =0;
|
||||
// Read a single byte from the current packet
|
||||
virtual int read() =0;
|
||||
// Read up to len bytes from the current packet and place them into buffer
|
||||
// Returns the number of bytes read, or 0 if none are available
|
||||
virtual int read(unsigned char* buffer, size_t len) =0;
|
||||
// Read up to len characters from the current packet and place them into buffer
|
||||
// Returns the number of characters read, or 0 if none are available
|
||||
virtual int read(char* buffer, size_t len) =0;
|
||||
// Return the next byte from the current packet without moving on to the next byte
|
||||
virtual int peek() =0;
|
||||
virtual void flush() =0; // Finish reading the current packet
|
||||
// Start processing the next available incoming packet
|
||||
// Returns the size of the packet in bytes, or 0 if no packets are available
|
||||
virtual int parsePacket() =0;
|
||||
// Number of bytes remaining in the current packet
|
||||
virtual int available() =0;
|
||||
// Read a single byte from the current packet
|
||||
virtual int read() =0;
|
||||
// Read up to len bytes from the current packet and place them into buffer
|
||||
// Returns the number of bytes read, or 0 if none are available
|
||||
virtual int read(unsigned char* buffer, size_t len) =0;
|
||||
// Read up to len characters from the current packet and place them into buffer
|
||||
// Returns the number of characters read, or 0 if none are available
|
||||
virtual int read(char* buffer, size_t len) =0;
|
||||
// Return the next byte from the current packet without moving on to the next byte
|
||||
virtual int peek() =0;
|
||||
virtual void flush() =0; // Finish reading the current packet
|
||||
|
||||
// Return the IP address of the host who sent the current incoming packet
|
||||
virtual IPAddress remoteIP() =0;
|
||||
// Return the port of the host who sent the current incoming packet
|
||||
virtual uint16_t remotePort() =0;
|
||||
protected:
|
||||
uint8_t* rawIPAddress(IPAddress& addr) { return addr.raw_address(); };
|
||||
// Return the IP address of the host who sent the current incoming packet
|
||||
virtual IPAddress remoteIP() =0;
|
||||
// Return the port of the host who sent the current incoming packet
|
||||
virtual uint16_t remotePort() =0;
|
||||
protected:
|
||||
uint8_t* rawIPAddress(IPAddress& addr) {
|
||||
return addr.raw_address();
|
||||
}
|
||||
};
|
||||
|
||||
#endif
|
||||
|
@ -24,7 +24,6 @@
|
||||
#define isascii(__c) ((unsigned)(__c)<=0177)
|
||||
#define toascii(__c) ((__c)&0177)
|
||||
|
||||
|
||||
// WCharacter.h prototypes
|
||||
inline boolean isAlphaNumeric(int c) __attribute__((always_inline));
|
||||
inline boolean isAlpha(int c) __attribute__((always_inline));
|
||||
@ -41,131 +40,99 @@ inline boolean isUpperCase(int c) __attribute__((always_inline));
|
||||
inline boolean isHexadecimalDigit(int c) __attribute__((always_inline));
|
||||
inline int toAscii(int c) __attribute__((always_inline));
|
||||
inline int toLowerCase(int c) __attribute__((always_inline));
|
||||
inline int toUpperCase(int c)__attribute__((always_inline));
|
||||
|
||||
inline int toUpperCase(int c) __attribute__((always_inline));
|
||||
|
||||
// Checks for an alphanumeric character.
|
||||
// It is equivalent to (isalpha(c) || isdigit(c)).
|
||||
inline boolean isAlphaNumeric(int c)
|
||||
{
|
||||
return ( isalnum(c) == 0 ? false : true);
|
||||
inline boolean isAlphaNumeric(int c) {
|
||||
return (isalnum(c) == 0 ? false : true);
|
||||
}
|
||||
|
||||
|
||||
// Checks for an alphabetic character.
|
||||
// It is equivalent to (isupper(c) || islower(c)).
|
||||
inline boolean isAlpha(int c)
|
||||
{
|
||||
return ( isalpha(c) == 0 ? false : true);
|
||||
inline boolean isAlpha(int c) {
|
||||
return (isalpha(c) == 0 ? false : true);
|
||||
}
|
||||
|
||||
|
||||
// Checks whether c is a 7-bit unsigned char value
|
||||
// that fits into the ASCII character set.
|
||||
inline boolean isAscii(int c)
|
||||
{
|
||||
return ( isascii (c) == 0 ? false : true);
|
||||
inline boolean isAscii(int c) {
|
||||
return ( isascii (c) == 0 ? false : true);
|
||||
}
|
||||
|
||||
|
||||
// Checks for a blank character, that is, a space or a tab.
|
||||
inline boolean isWhitespace(int c)
|
||||
{
|
||||
return ( isblank (c) == 0 ? false : true);
|
||||
inline boolean isWhitespace(int c) {
|
||||
return (isblank(c) == 0 ? false : true);
|
||||
}
|
||||
|
||||
|
||||
// Checks for a control character.
|
||||
inline boolean isControl(int c)
|
||||
{
|
||||
return ( iscntrl (c) == 0 ? false : true);
|
||||
inline boolean isControl(int c) {
|
||||
return (iscntrl(c) == 0 ? false : true);
|
||||
}
|
||||
|
||||
|
||||
// Checks for a digit (0 through 9).
|
||||
inline boolean isDigit(int c)
|
||||
{
|
||||
return ( isdigit (c) == 0 ? false : true);
|
||||
inline boolean isDigit(int c) {
|
||||
return (isdigit(c) == 0 ? false : true);
|
||||
}
|
||||
|
||||
|
||||
// Checks for any printable character except space.
|
||||
inline boolean isGraph(int c)
|
||||
{
|
||||
return ( isgraph (c) == 0 ? false : true);
|
||||
inline boolean isGraph(int c) {
|
||||
return (isgraph(c) == 0 ? false : true);
|
||||
}
|
||||
|
||||
|
||||
// Checks for a lower-case character.
|
||||
inline boolean isLowerCase(int c)
|
||||
{
|
||||
return (islower (c) == 0 ? false : true);
|
||||
inline boolean isLowerCase(int c) {
|
||||
return (islower(c) == 0 ? false : true);
|
||||
}
|
||||
|
||||
|
||||
// Checks for any printable character including space.
|
||||
inline boolean isPrintable(int c)
|
||||
{
|
||||
return ( isprint (c) == 0 ? false : true);
|
||||
inline boolean isPrintable(int c) {
|
||||
return (isprint(c) == 0 ? false : true);
|
||||
}
|
||||
|
||||
|
||||
// Checks for any printable character which is not a space
|
||||
// or an alphanumeric character.
|
||||
inline boolean isPunct(int c)
|
||||
{
|
||||
return ( ispunct (c) == 0 ? false : true);
|
||||
inline boolean isPunct(int c) {
|
||||
return (ispunct(c) == 0 ? false : true);
|
||||
}
|
||||
|
||||
|
||||
// Checks for white-space characters. For the avr-libc library,
|
||||
// these are: space, formfeed ('\f'), newline ('\n'), carriage
|
||||
// return ('\r'), horizontal tab ('\t'), and vertical tab ('\v').
|
||||
inline boolean isSpace(int c)
|
||||
{
|
||||
return ( isspace (c) == 0 ? false : true);
|
||||
inline boolean isSpace(int c) {
|
||||
return (isspace(c) == 0 ? false : true);
|
||||
}
|
||||
|
||||
|
||||
// Checks for an uppercase letter.
|
||||
inline boolean isUpperCase(int c)
|
||||
{
|
||||
return ( isupper (c) == 0 ? false : true);
|
||||
inline boolean isUpperCase(int c) {
|
||||
return (isupper(c) == 0 ? false : true);
|
||||
}
|
||||
|
||||
|
||||
// Checks for a hexadecimal digits, i.e. one of 0 1 2 3 4 5 6 7
|
||||
// 8 9 a b c d e f A B C D E F.
|
||||
inline boolean isHexadecimalDigit(int c)
|
||||
{
|
||||
return ( isxdigit (c) == 0 ? false : true);
|
||||
inline boolean isHexadecimalDigit(int c) {
|
||||
return (isxdigit(c) == 0 ? false : true);
|
||||
}
|
||||
|
||||
|
||||
// Converts c to a 7-bit unsigned char value that fits into the
|
||||
// ASCII character set, by clearing the high-order bits.
|
||||
inline int toAscii(int c)
|
||||
{
|
||||
return toascii (c);
|
||||
inline int toAscii(int c) {
|
||||
return toascii(c);
|
||||
}
|
||||
|
||||
|
||||
// Warning:
|
||||
// Many people will be unhappy if you use this function.
|
||||
// This function will convert accented letters into random
|
||||
// characters.
|
||||
|
||||
// Converts the letter c to lower case, if possible.
|
||||
inline int toLowerCase(int c)
|
||||
{
|
||||
return tolower (c);
|
||||
inline int toLowerCase(int c) {
|
||||
return tolower(c);
|
||||
}
|
||||
|
||||
|
||||
// Converts the letter c to upper case, if possible.
|
||||
inline int toUpperCase(int c)
|
||||
{
|
||||
return toupper (c);
|
||||
inline int toUpperCase(int c) {
|
||||
return toupper(c);
|
||||
}
|
||||
|
||||
#endif
|
@ -1,60 +1,61 @@
|
||||
/* -*- mode: jde; c-basic-offset: 2; indent-tabs-mode: nil -*- */
|
||||
|
||||
/*
|
||||
Part of the Wiring project - http://wiring.org.co
|
||||
Copyright (c) 2004-06 Hernando Barragan
|
||||
Modified 13 August 2006, David A. Mellis for Arduino - http://www.arduino.cc/
|
||||
Part of the Wiring project - http://wiring.org.co
|
||||
Copyright (c) 2004-06 Hernando Barragan
|
||||
Modified 13 August 2006, David A. Mellis for Arduino - http://www.arduino.cc/
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General
|
||||
Public License along with this library; if not, write to the
|
||||
Free Software Foundation, Inc., 59 Temple Place, Suite 330,
|
||||
Boston, MA 02111-1307 USA
|
||||
You should have received a copy of the GNU Lesser General
|
||||
Public License along with this library; if not, write to the
|
||||
Free Software Foundation, Inc., 59 Temple Place, Suite 330,
|
||||
Boston, MA 02111-1307 USA
|
||||
|
||||
$Id$
|
||||
*/
|
||||
$Id$
|
||||
*/
|
||||
|
||||
extern "C" {
|
||||
#include <stdlib.h>
|
||||
#include <stdlib.h>
|
||||
}
|
||||
|
||||
void randomSeed(unsigned int seed)
|
||||
{
|
||||
if (seed != 0) {
|
||||
srand(seed);
|
||||
}
|
||||
void randomSeed(unsigned int seed) {
|
||||
if(seed != 0) {
|
||||
srand(seed);
|
||||
}
|
||||
}
|
||||
|
||||
long random(long howbig)
|
||||
{
|
||||
if (howbig == 0) {
|
||||
return 0;
|
||||
}
|
||||
return rand() % howbig;
|
||||
long random(long howbig) {
|
||||
if(howbig == 0) {
|
||||
return 0;
|
||||
}
|
||||
return rand() % howbig;
|
||||
}
|
||||
|
||||
long random(long howsmall, long howbig)
|
||||
{
|
||||
if (howsmall >= howbig) {
|
||||
return howsmall;
|
||||
}
|
||||
long diff = howbig - howsmall;
|
||||
return random(diff) + howsmall;
|
||||
long random(long howsmall, long howbig) {
|
||||
if(howsmall >= howbig) {
|
||||
return howsmall;
|
||||
}
|
||||
long diff = howbig - howsmall;
|
||||
return random(diff) + howsmall;
|
||||
}
|
||||
|
||||
long map(long x, long in_min, long in_max, long out_min, long out_max)
|
||||
{
|
||||
return (x - in_min) * (out_max - out_min) / (in_max - in_min) + out_min;
|
||||
long map(long x, long in_min, long in_max, long out_min, long out_max) {
|
||||
return (x - in_min) * (out_max - out_min) / (in_max - in_min) + out_min;
|
||||
}
|
||||
|
||||
unsigned int makeWord(unsigned int w) { return w; }
|
||||
unsigned int makeWord(unsigned char h, unsigned char l) { return (h << 8) | l; }
|
||||
unsigned int makeWord(unsigned int w) {
|
||||
return w;
|
||||
}
|
||||
|
||||
unsigned int makeWord(unsigned char h, unsigned char l) {
|
||||
return (h << 8) | l;
|
||||
}
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -1,23 +1,23 @@
|
||||
/*
|
||||
WString.h - String library for Wiring & Arduino
|
||||
...mostly rewritten by Paul Stoffregen...
|
||||
Copyright (c) 2009-10 Hernando Barragan. All right reserved.
|
||||
Copyright 2011, Paul Stoffregen, paul@pjrc.com
|
||||
WString.h - String library for Wiring & Arduino
|
||||
...mostly rewritten by Paul Stoffregen...
|
||||
Copyright (c) 2009-10 Hernando Barragan. All right reserved.
|
||||
Copyright 2011, Paul Stoffregen, paul@pjrc.com
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef String_class_h
|
||||
#define String_class_h
|
||||
@ -37,176 +37,243 @@ typedef char* __FlashStringHelper;
|
||||
#define F(str) str
|
||||
|
||||
// The string class
|
||||
class String
|
||||
{
|
||||
// use a function pointer to allow for "if (s)" without the
|
||||
// complications of an operator bool(). for more information, see:
|
||||
// http://www.artima.com/cppsource/safebool.html
|
||||
typedef void (String::*StringIfHelperType)() const;
|
||||
void StringIfHelper() const {}
|
||||
class String {
|
||||
// use a function pointer to allow for "if (s)" without the
|
||||
// complications of an operator bool(). for more information, see:
|
||||
// http://www.artima.com/cppsource/safebool.html
|
||||
typedef void (String::*StringIfHelperType)() const;
|
||||
void StringIfHelper() const {
|
||||
}
|
||||
|
||||
public:
|
||||
// constructors
|
||||
// creates a copy of the initial value.
|
||||
// if the initial value is null or invalid, or if memory allocation
|
||||
// fails, the string will be marked as invalid (i.e. "if (s)" will
|
||||
// be false).
|
||||
String(const char *cstr = "");
|
||||
String(const String &str);
|
||||
#ifdef __GXX_EXPERIMENTAL_CXX0X__
|
||||
String(String &&rval);
|
||||
String(StringSumHelper &&rval);
|
||||
#endif
|
||||
explicit String(char c);
|
||||
explicit String(unsigned char, unsigned char base=10);
|
||||
explicit String(int, unsigned char base=10);
|
||||
explicit String(unsigned int, unsigned char base=10);
|
||||
explicit String(long, unsigned char base=10);
|
||||
explicit String(unsigned long, unsigned char base=10);
|
||||
explicit String(float, unsigned char decimalPlaces=2);
|
||||
explicit String(double, unsigned char decimalPlaces=2);
|
||||
~String(void);
|
||||
public:
|
||||
// constructors
|
||||
// creates a copy of the initial value.
|
||||
// if the initial value is null or invalid, or if memory allocation
|
||||
// fails, the string will be marked as invalid (i.e. "if (s)" will
|
||||
// be false).
|
||||
String(const char *cstr = "");
|
||||
String(const String &str);
|
||||
#ifdef __GXX_EXPERIMENTAL_CXX0X__
|
||||
String(String &&rval);
|
||||
String(StringSumHelper &&rval);
|
||||
#endif
|
||||
explicit String(char c);
|
||||
explicit String(unsigned char, unsigned char base = 10);
|
||||
explicit String(int, unsigned char base = 10);
|
||||
explicit String(unsigned int, unsigned char base = 10);
|
||||
explicit String(long, unsigned char base = 10);
|
||||
explicit String(unsigned long, unsigned char base = 10);
|
||||
explicit String(float, unsigned char decimalPlaces = 2);
|
||||
explicit String(double, unsigned char decimalPlaces = 2);
|
||||
~String(void);
|
||||
|
||||
// memory management
|
||||
// return true on success, false on failure (in which case, the string
|
||||
// is left unchanged). reserve(0), if successful, will validate an
|
||||
// invalid string (i.e., "if (s)" will be true afterwards)
|
||||
unsigned char reserve(unsigned int size);
|
||||
inline unsigned int length(void) const {return len;}
|
||||
// memory management
|
||||
// return true on success, false on failure (in which case, the string
|
||||
// is left unchanged). reserve(0), if successful, will validate an
|
||||
// invalid string (i.e., "if (s)" will be true afterwards)
|
||||
unsigned char reserve(unsigned int size);
|
||||
inline unsigned int length(void) const {
|
||||
return len;
|
||||
}
|
||||
|
||||
// creates a copy of the assigned value. if the value is null or
|
||||
// invalid, or if the memory allocation fails, the string will be
|
||||
// marked as invalid ("if (s)" will be false).
|
||||
String & operator = (const String &rhs);
|
||||
String & operator = (const char *cstr);
|
||||
#ifdef __GXX_EXPERIMENTAL_CXX0X__
|
||||
String & operator = (String &&rval);
|
||||
String & operator = (StringSumHelper &&rval);
|
||||
#endif
|
||||
// creates a copy of the assigned value. if the value is null or
|
||||
// invalid, or if the memory allocation fails, the string will be
|
||||
// marked as invalid ("if (s)" will be false).
|
||||
String & operator =(const String &rhs);
|
||||
String & operator =(const char *cstr);
|
||||
#ifdef __GXX_EXPERIMENTAL_CXX0X__
|
||||
String & operator =(String &&rval);
|
||||
String & operator =(StringSumHelper &&rval);
|
||||
#endif
|
||||
|
||||
// concatenate (works w/ built-in types)
|
||||
// concatenate (works w/ built-in types)
|
||||
|
||||
// returns true on success, false on failure (in which case, the string
|
||||
// is left unchanged). if the argument is null or invalid, the
|
||||
// concatenation is considered unsucessful.
|
||||
unsigned char concat(const String &str);
|
||||
unsigned char concat(const char *cstr);
|
||||
unsigned char concat(char c);
|
||||
unsigned char concat(unsigned char c);
|
||||
unsigned char concat(int num);
|
||||
unsigned char concat(unsigned int num);
|
||||
unsigned char concat(long num);
|
||||
unsigned char concat(unsigned long num);
|
||||
unsigned char concat(float num);
|
||||
unsigned char concat(double num);
|
||||
// returns true on success, false on failure (in which case, the string
|
||||
// is left unchanged). if the argument is null or invalid, the
|
||||
// concatenation is considered unsucessful.
|
||||
unsigned char concat(const String &str);
|
||||
unsigned char concat(const char *cstr);
|
||||
unsigned char concat(char c);
|
||||
unsigned char concat(unsigned char c);
|
||||
unsigned char concat(int num);
|
||||
unsigned char concat(unsigned int num);
|
||||
unsigned char concat(long num);
|
||||
unsigned char concat(unsigned long num);
|
||||
unsigned char concat(float num);
|
||||
unsigned char concat(double num);
|
||||
|
||||
// if there's not enough memory for the concatenated value, the string
|
||||
// will be left unchanged (but this isn't signalled in any way)
|
||||
String & operator += (const String &rhs) {concat(rhs); return (*this);}
|
||||
String & operator += (const char *cstr) {concat(cstr); return (*this);}
|
||||
String & operator += (char c) {concat(c); return (*this);}
|
||||
String & operator += (unsigned char num) {concat(num); return (*this);}
|
||||
String & operator += (int num) {concat(num); return (*this);}
|
||||
String & operator += (unsigned int num) {concat(num); return (*this);}
|
||||
String & operator += (long num) {concat(num); return (*this);}
|
||||
String & operator += (unsigned long num) {concat(num); return (*this);}
|
||||
String & operator += (float num) {concat(num); return (*this);}
|
||||
String & operator += (double num) {concat(num); return (*this);}
|
||||
// if there's not enough memory for the concatenated value, the string
|
||||
// will be left unchanged (but this isn't signalled in any way)
|
||||
String & operator +=(const String &rhs) {
|
||||
concat(rhs);
|
||||
return (*this);
|
||||
}
|
||||
String & operator +=(const char *cstr) {
|
||||
concat(cstr);
|
||||
return (*this);
|
||||
}
|
||||
String & operator +=(char c) {
|
||||
concat(c);
|
||||
return (*this);
|
||||
}
|
||||
String & operator +=(unsigned char num) {
|
||||
concat(num);
|
||||
return (*this);
|
||||
}
|
||||
String & operator +=(int num) {
|
||||
concat(num);
|
||||
return (*this);
|
||||
}
|
||||
String & operator +=(unsigned int num) {
|
||||
concat(num);
|
||||
return (*this);
|
||||
}
|
||||
String & operator +=(long num) {
|
||||
concat(num);
|
||||
return (*this);
|
||||
}
|
||||
String & operator +=(unsigned long num) {
|
||||
concat(num);
|
||||
return (*this);
|
||||
}
|
||||
String & operator +=(float num) {
|
||||
concat(num);
|
||||
return (*this);
|
||||
}
|
||||
String & operator +=(double num) {
|
||||
concat(num);
|
||||
return (*this);
|
||||
}
|
||||
|
||||
friend StringSumHelper & operator + (const StringSumHelper &lhs, const String &rhs);
|
||||
friend StringSumHelper & operator + (const StringSumHelper &lhs, const char *cstr);
|
||||
friend StringSumHelper & operator + (const StringSumHelper &lhs, char c);
|
||||
friend StringSumHelper & operator + (const StringSumHelper &lhs, unsigned char num);
|
||||
friend StringSumHelper & operator + (const StringSumHelper &lhs, int num);
|
||||
friend StringSumHelper & operator + (const StringSumHelper &lhs, unsigned int num);
|
||||
friend StringSumHelper & operator + (const StringSumHelper &lhs, long num);
|
||||
friend StringSumHelper & operator + (const StringSumHelper &lhs, unsigned long num);
|
||||
friend StringSumHelper & operator + (const StringSumHelper &lhs, float num);
|
||||
friend StringSumHelper & operator + (const StringSumHelper &lhs, double num);
|
||||
friend StringSumHelper & operator +(const StringSumHelper &lhs, const String &rhs);
|
||||
friend StringSumHelper & operator +(const StringSumHelper &lhs, const char *cstr);
|
||||
friend StringSumHelper & operator +(const StringSumHelper &lhs, char c);
|
||||
friend StringSumHelper & operator +(const StringSumHelper &lhs, unsigned char num);
|
||||
friend StringSumHelper & operator +(const StringSumHelper &lhs, int num);
|
||||
friend StringSumHelper & operator +(const StringSumHelper &lhs, unsigned int num);
|
||||
friend StringSumHelper & operator +(const StringSumHelper &lhs, long num);
|
||||
friend StringSumHelper & operator +(const StringSumHelper &lhs, unsigned long num);
|
||||
friend StringSumHelper & operator +(const StringSumHelper &lhs, float num);
|
||||
friend StringSumHelper & operator +(const StringSumHelper &lhs, double num);
|
||||
|
||||
// comparison (only works w/ Strings and "strings")
|
||||
operator StringIfHelperType() const { return buffer ? &String::StringIfHelper : 0; }
|
||||
int compareTo(const String &s) const;
|
||||
unsigned char equals(const String &s) const;
|
||||
unsigned char equals(const char *cstr) const;
|
||||
unsigned char operator == (const String &rhs) const {return equals(rhs);}
|
||||
unsigned char operator == (const char *cstr) const {return equals(cstr);}
|
||||
unsigned char operator != (const String &rhs) const {return !equals(rhs);}
|
||||
unsigned char operator != (const char *cstr) const {return !equals(cstr);}
|
||||
unsigned char operator < (const String &rhs) const;
|
||||
unsigned char operator > (const String &rhs) const;
|
||||
unsigned char operator <= (const String &rhs) const;
|
||||
unsigned char operator >= (const String &rhs) const;
|
||||
unsigned char equalsIgnoreCase(const String &s) const;
|
||||
unsigned char startsWith( const String &prefix) const;
|
||||
unsigned char startsWith(const String &prefix, unsigned int offset) const;
|
||||
unsigned char endsWith(const String &suffix) const;
|
||||
// comparison (only works w/ Strings and "strings")
|
||||
operator StringIfHelperType() const {
|
||||
return buffer ? &String::StringIfHelper : 0;
|
||||
}
|
||||
int compareTo(const String &s) const;
|
||||
unsigned char equals(const String &s) const;
|
||||
unsigned char equals(const char *cstr) const;
|
||||
unsigned char operator ==(const String &rhs) const {
|
||||
return equals(rhs);
|
||||
}
|
||||
unsigned char operator ==(const char *cstr) const {
|
||||
return equals(cstr);
|
||||
}
|
||||
unsigned char operator !=(const String &rhs) const {
|
||||
return !equals(rhs);
|
||||
}
|
||||
unsigned char operator !=(const char *cstr) const {
|
||||
return !equals(cstr);
|
||||
}
|
||||
unsigned char operator <(const String &rhs) const;
|
||||
unsigned char operator >(const String &rhs) const;
|
||||
unsigned char operator <=(const String &rhs) const;
|
||||
unsigned char operator >=(const String &rhs) const;
|
||||
unsigned char equalsIgnoreCase(const String &s) const;
|
||||
unsigned char startsWith(const String &prefix) const;
|
||||
unsigned char startsWith(const String &prefix, unsigned int offset) const;
|
||||
unsigned char endsWith(const String &suffix) const;
|
||||
|
||||
// character acccess
|
||||
char charAt(unsigned int index) const;
|
||||
void setCharAt(unsigned int index, char c);
|
||||
char operator [] (unsigned int index) const;
|
||||
char& operator [] (unsigned int index);
|
||||
void getBytes(unsigned char *buf, unsigned int bufsize, unsigned int index=0) const;
|
||||
void toCharArray(char *buf, unsigned int bufsize, unsigned int index=0) const
|
||||
{getBytes((unsigned char *)buf, bufsize, index);}
|
||||
const char * c_str() const { return buffer; }
|
||||
// character acccess
|
||||
char charAt(unsigned int index) const;
|
||||
void setCharAt(unsigned int index, char c);
|
||||
char operator [](unsigned int index) const;
|
||||
char& operator [](unsigned int index);
|
||||
void getBytes(unsigned char *buf, unsigned int bufsize, unsigned int index = 0) const;
|
||||
void toCharArray(char *buf, unsigned int bufsize, unsigned int index = 0) const {
|
||||
getBytes((unsigned char *) buf, bufsize, index);
|
||||
}
|
||||
const char * c_str() const {
|
||||
return buffer;
|
||||
}
|
||||
|
||||
// search
|
||||
int indexOf( char ch ) const;
|
||||
int indexOf( char ch, unsigned int fromIndex ) const;
|
||||
int indexOf( const String &str ) const;
|
||||
int indexOf( const String &str, unsigned int fromIndex ) const;
|
||||
int lastIndexOf( char ch ) const;
|
||||
int lastIndexOf( char ch, unsigned int fromIndex ) const;
|
||||
int lastIndexOf( const String &str ) const;
|
||||
int lastIndexOf( const String &str, unsigned int fromIndex ) const;
|
||||
String substring( unsigned int beginIndex ) const { return substring(beginIndex, len); };
|
||||
String substring( unsigned int beginIndex, unsigned int endIndex ) const;
|
||||
// search
|
||||
int indexOf(char ch) const;
|
||||
int indexOf(char ch, unsigned int fromIndex) const;
|
||||
int indexOf(const String &str) const;
|
||||
int indexOf(const String &str, unsigned int fromIndex) const;
|
||||
int lastIndexOf(char ch) const;
|
||||
int lastIndexOf(char ch, unsigned int fromIndex) const;
|
||||
int lastIndexOf(const String &str) const;
|
||||
int lastIndexOf(const String &str, unsigned int fromIndex) const;
|
||||
String substring(unsigned int beginIndex) const {
|
||||
return substring(beginIndex, len);
|
||||
}
|
||||
;
|
||||
String substring(unsigned int beginIndex, unsigned int endIndex) const;
|
||||
|
||||
// modification
|
||||
void replace(char find, char replace);
|
||||
void replace(const String& find, const String& replace);
|
||||
void remove(unsigned int index);
|
||||
void remove(unsigned int index, unsigned int count);
|
||||
void toLowerCase(void);
|
||||
void toUpperCase(void);
|
||||
void trim(void);
|
||||
// modification
|
||||
void replace(char find, char replace);
|
||||
void replace(const String& find, const String& replace);
|
||||
void remove(unsigned int index);
|
||||
void remove(unsigned int index, unsigned int count);
|
||||
void toLowerCase(void);
|
||||
void toUpperCase(void);
|
||||
void trim(void);
|
||||
|
||||
// parsing/conversion
|
||||
long toInt(void) const;
|
||||
float toFloat(void) const;
|
||||
// parsing/conversion
|
||||
long toInt(void) const;
|
||||
float toFloat(void) const;
|
||||
|
||||
protected:
|
||||
char *buffer; // the actual char array
|
||||
unsigned int capacity; // the array length minus one (for the '\0')
|
||||
unsigned int len; // the String length (not counting the '\0')
|
||||
protected:
|
||||
void init(void);
|
||||
void invalidate(void);
|
||||
unsigned char changeBuffer(unsigned int maxStrLen);
|
||||
unsigned char concat(const char *cstr, unsigned int length);
|
||||
protected:
|
||||
char *buffer; // the actual char array
|
||||
unsigned int capacity; // the array length minus one (for the '\0')
|
||||
unsigned int len; // the String length (not counting the '\0')
|
||||
protected:
|
||||
void init(void);
|
||||
void invalidate(void);
|
||||
unsigned char changeBuffer(unsigned int maxStrLen);
|
||||
unsigned char concat(const char *cstr, unsigned int length);
|
||||
|
||||
// copy and move
|
||||
String & copy(const char *cstr, unsigned int length);
|
||||
#ifdef __GXX_EXPERIMENTAL_CXX0X__
|
||||
void move(String &rhs);
|
||||
#endif
|
||||
// copy and move
|
||||
String & copy(const char *cstr, unsigned int length);
|
||||
#ifdef __GXX_EXPERIMENTAL_CXX0X__
|
||||
void move(String &rhs);
|
||||
#endif
|
||||
};
|
||||
|
||||
class StringSumHelper : public String
|
||||
{
|
||||
public:
|
||||
StringSumHelper(const String &s) : String(s) {}
|
||||
StringSumHelper(const char *p) : String(p) {}
|
||||
StringSumHelper(char c) : String(c) {}
|
||||
StringSumHelper(unsigned char num) : String(num) {}
|
||||
StringSumHelper(int num) : String(num) {}
|
||||
StringSumHelper(unsigned int num) : String(num) {}
|
||||
StringSumHelper(long num) : String(num) {}
|
||||
StringSumHelper(unsigned long num) : String(num) {}
|
||||
StringSumHelper(float num) : String(num) {}
|
||||
StringSumHelper(double num) : String(num) {}
|
||||
class StringSumHelper: public String {
|
||||
public:
|
||||
StringSumHelper(const String &s) :
|
||||
String(s) {
|
||||
}
|
||||
StringSumHelper(const char *p) :
|
||||
String(p) {
|
||||
}
|
||||
StringSumHelper(char c) :
|
||||
String(c) {
|
||||
}
|
||||
StringSumHelper(unsigned char num) :
|
||||
String(num) {
|
||||
}
|
||||
StringSumHelper(int num) :
|
||||
String(num) {
|
||||
}
|
||||
StringSumHelper(unsigned int num) :
|
||||
String(num) {
|
||||
}
|
||||
StringSumHelper(long num) :
|
||||
String(num) {
|
||||
}
|
||||
StringSumHelper(unsigned long num) :
|
||||
String(num) {
|
||||
}
|
||||
StringSumHelper(float num) :
|
||||
String(num) {
|
||||
}
|
||||
StringSumHelper(double num) :
|
||||
String(num) {
|
||||
}
|
||||
};
|
||||
|
||||
#endif // __cplusplus
|
||||
|
@ -1,20 +1,20 @@
|
||||
/*
|
||||
Copyright (c) 2014 Arduino. All right reserved.
|
||||
Copyright (c) 2014 Arduino. All right reserved.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#include <stdlib.h>
|
||||
extern "C" {
|
||||
@ -26,36 +26,36 @@ extern "C" {
|
||||
}
|
||||
|
||||
void *operator new(size_t size) {
|
||||
return os_malloc(size);
|
||||
return os_malloc(size);
|
||||
}
|
||||
|
||||
void *operator new[](size_t size) {
|
||||
return os_malloc(size);
|
||||
return os_malloc(size);
|
||||
}
|
||||
|
||||
void operator delete(void * ptr) {
|
||||
os_free(ptr);
|
||||
os_free(ptr);
|
||||
}
|
||||
|
||||
void operator delete[](void * ptr) {
|
||||
os_free(ptr);
|
||||
os_free(ptr);
|
||||
}
|
||||
|
||||
extern "C" void __cxa_pure_virtual(void) __attribute__ ((__noreturn__));
|
||||
extern "C" void __cxa_deleted_virtual(void) __attribute__ ((__noreturn__));
|
||||
|
||||
void __cxa_pure_virtual(void) {
|
||||
abort();
|
||||
abort();
|
||||
}
|
||||
|
||||
void __cxa_deleted_virtual(void) {
|
||||
abort();
|
||||
abort();
|
||||
}
|
||||
|
||||
namespace std {
|
||||
void __throw_bad_function_call() {
|
||||
void __throw_bad_function_call() {
|
||||
abort();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// TODO: rebuild windows toolchain to make this unnecessary:
|
||||
|
@ -1,21 +1,21 @@
|
||||
/*
|
||||
binary.h - Definitions for binary constants
|
||||
Copyright (c) 2006 David A. Mellis. All right reserved.
|
||||
binary.h - Definitions for binary constants
|
||||
Copyright (c) 2006 David A. Mellis. All right reserved.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef Binary_h
|
||||
#define Binary_h
|
||||
|
@ -1,148 +1,120 @@
|
||||
/*
|
||||
cbuf.h - Circular buffer implementation
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
cbuf.h - Circular buffer implementation
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef __cbuf_h
|
||||
#define __cbuf_h
|
||||
|
||||
#include <stdint.h>
|
||||
class cbuf
|
||||
{
|
||||
public:
|
||||
cbuf(size_t size)
|
||||
: _size(size)
|
||||
, _buf(new char[size])
|
||||
, _bufend(_buf + size)
|
||||
, _begin(_buf)
|
||||
, _end(_begin)
|
||||
{
|
||||
}
|
||||
|
||||
~cbuf()
|
||||
{
|
||||
delete[] _buf;
|
||||
}
|
||||
|
||||
size_t getSize() const
|
||||
{
|
||||
if (_end >= _begin)
|
||||
return _end - _begin;
|
||||
|
||||
return _size - (_begin - _end);
|
||||
}
|
||||
|
||||
size_t room() const
|
||||
{
|
||||
if (_end >= _begin)
|
||||
return _size - (_end - _begin) - 1;
|
||||
|
||||
return _begin - _end - 1;
|
||||
}
|
||||
|
||||
bool empty() const
|
||||
{
|
||||
return _begin == _end;
|
||||
}
|
||||
|
||||
int peek()
|
||||
{
|
||||
if (_end == _begin)
|
||||
return -1;
|
||||
|
||||
return static_cast<int>(*_begin);
|
||||
}
|
||||
|
||||
int read()
|
||||
{
|
||||
if (getSize() == 0)
|
||||
return -1;
|
||||
|
||||
char result = *_begin;
|
||||
if (++_begin == _bufend)
|
||||
_begin = _buf;
|
||||
return static_cast<int>(result);
|
||||
}
|
||||
|
||||
size_t read(char* dst, size_t size)
|
||||
{
|
||||
size_t bytes_available = getSize();
|
||||
size_t size_to_read = (size < bytes_available) ? size : bytes_available;
|
||||
size_t size_read = size_to_read;
|
||||
if (_end < _begin && size_to_read > _bufend - _begin)
|
||||
{
|
||||
size_t top_size = _bufend - _begin;
|
||||
memcpy(dst, _begin, top_size);
|
||||
_begin = _buf;
|
||||
size_to_read -= top_size;
|
||||
dst += top_size;
|
||||
class cbuf {
|
||||
public:
|
||||
cbuf(size_t size) :
|
||||
_size(size), _buf(new char[size]), _bufend(_buf + size), _begin(_buf), _end(_begin) {
|
||||
}
|
||||
memcpy(dst, _begin, size_to_read);
|
||||
_begin += size_to_read;
|
||||
if (_begin == _bufend)
|
||||
_begin = _buf;
|
||||
return size_read;
|
||||
}
|
||||
|
||||
size_t write(char c)
|
||||
{
|
||||
if (room() == 0)
|
||||
return 0;
|
||||
|
||||
*_end = c;
|
||||
if (++_end == _bufend)
|
||||
_end = _buf;
|
||||
return 1;
|
||||
}
|
||||
|
||||
size_t write(const char* src, size_t size)
|
||||
{
|
||||
size_t bytes_available = room();
|
||||
size_t size_to_write = (size < bytes_available) ? size : bytes_available;
|
||||
size_t size_written = size_to_write;
|
||||
if (_end > _begin && size_to_write > _bufend - _end)
|
||||
{
|
||||
size_t top_size = _bufend - _end;
|
||||
memcpy(_end, src, top_size);
|
||||
_end = _buf;
|
||||
size_to_write -= top_size;
|
||||
src += top_size;
|
||||
~cbuf() {
|
||||
delete[] _buf;
|
||||
}
|
||||
memcpy(_end, src, size_to_write);
|
||||
_end += size_to_write;
|
||||
if (_end == _bufend)
|
||||
|
||||
size_t getSize() const {
|
||||
if(_end >= _begin) return _end - _begin;
|
||||
|
||||
return _size - (_begin - _end);
|
||||
}
|
||||
|
||||
size_t room() const {
|
||||
if(_end >= _begin) return _size - (_end - _begin) - 1;
|
||||
|
||||
return _begin - _end - 1;
|
||||
}
|
||||
|
||||
bool empty() const {
|
||||
return _begin == _end;
|
||||
}
|
||||
|
||||
int peek() {
|
||||
if(_end == _begin) return -1;
|
||||
|
||||
return static_cast<int>(*_begin);
|
||||
}
|
||||
|
||||
int read() {
|
||||
if(getSize() == 0) return -1;
|
||||
|
||||
char result = *_begin;
|
||||
if(++_begin == _bufend) _begin = _buf;
|
||||
return static_cast<int>(result);
|
||||
}
|
||||
|
||||
size_t read(char* dst, size_t size) {
|
||||
size_t bytes_available = getSize();
|
||||
size_t size_to_read = (size < bytes_available) ? size : bytes_available;
|
||||
size_t size_read = size_to_read;
|
||||
if(_end < _begin && size_to_read > _bufend - _begin) {
|
||||
size_t top_size = _bufend - _begin;
|
||||
memcpy(dst, _begin, top_size);
|
||||
_begin = _buf;
|
||||
size_to_read -= top_size;
|
||||
dst += top_size;
|
||||
}
|
||||
memcpy(dst, _begin, size_to_read);
|
||||
_begin += size_to_read;
|
||||
if(_begin == _bufend) _begin = _buf;
|
||||
return size_read;
|
||||
}
|
||||
|
||||
size_t write(char c) {
|
||||
if(room() == 0) return 0;
|
||||
|
||||
*_end = c;
|
||||
if(++_end == _bufend) _end = _buf;
|
||||
return 1;
|
||||
}
|
||||
|
||||
size_t write(const char* src, size_t size) {
|
||||
size_t bytes_available = room();
|
||||
size_t size_to_write = (size < bytes_available) ? size : bytes_available;
|
||||
size_t size_written = size_to_write;
|
||||
if(_end > _begin && size_to_write > _bufend - _end) {
|
||||
size_t top_size = _bufend - _end;
|
||||
memcpy(_end, src, top_size);
|
||||
_end = _buf;
|
||||
size_to_write -= top_size;
|
||||
src += top_size;
|
||||
}
|
||||
memcpy(_end, src, size_to_write);
|
||||
_end += size_to_write;
|
||||
if(_end == _bufend) _end = _buf;
|
||||
return size_written;
|
||||
}
|
||||
|
||||
void flush() {
|
||||
_begin = _buf;
|
||||
_end = _buf;
|
||||
return size_written;
|
||||
}
|
||||
}
|
||||
|
||||
void flush()
|
||||
{
|
||||
_begin = _buf;
|
||||
_end = _buf;
|
||||
}
|
||||
|
||||
private:
|
||||
size_t _size;
|
||||
char* _buf;
|
||||
char* _bufend;
|
||||
char* _begin;
|
||||
char* _end;
|
||||
private:
|
||||
size_t _size;
|
||||
char* _buf;
|
||||
char* _bufend;
|
||||
char* _begin;
|
||||
char* _end;
|
||||
};
|
||||
|
||||
|
||||
#endif//__cbuf_h
|
||||
|
@ -1,23 +1,22 @@
|
||||
/*
|
||||
cont.h - continuations support for Xtensa call0 ABI
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
cont.h - continuations support for Xtensa call0 ABI
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
|
||||
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 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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef CONT_H_
|
||||
#define CONT_H_
|
||||
@ -26,29 +25,28 @@
|
||||
#define CONT_STACKSIZE 4096
|
||||
#endif
|
||||
|
||||
typedef struct cont_
|
||||
{
|
||||
void (*pc_ret)(void);
|
||||
unsigned* sp_ret;
|
||||
typedef struct cont_ {
|
||||
void (*pc_ret)(void);
|
||||
unsigned* sp_ret;
|
||||
|
||||
void (*pc_yield)(void);
|
||||
unsigned* sp_yield;
|
||||
void (*pc_yield)(void);
|
||||
unsigned* sp_yield;
|
||||
|
||||
unsigned* stack_end;
|
||||
unsigned stack_guard1;
|
||||
unsigned* stack_end;
|
||||
unsigned stack_guard1;
|
||||
|
||||
unsigned stack[CONT_STACKSIZE / 4];
|
||||
unsigned stack[CONT_STACKSIZE / 4];
|
||||
|
||||
unsigned stack_guard2;
|
||||
unsigned* struct_start;
|
||||
unsigned stack_guard2;
|
||||
unsigned* struct_start;
|
||||
} cont_t;
|
||||
|
||||
// Initialize the cont_t structure before calling cont_run
|
||||
void cont_init (cont_t*);
|
||||
void cont_init(cont_t*);
|
||||
|
||||
// Run function pfn in a separate stack, or continue execution
|
||||
// at the point where cont_yield was called
|
||||
void cont_run(cont_t*, void(*pfn)(void));
|
||||
void cont_run(cont_t*, void (*pfn)(void));
|
||||
|
||||
// Return to the point where cont_run was called, saving the
|
||||
// execution state (registers and stack)
|
||||
@ -56,6 +54,6 @@ void cont_yield(cont_t*);
|
||||
|
||||
// Check guard bytes around the stack. Return 0 in case everything is ok,
|
||||
// return 1 if guard bytes were overwritten.
|
||||
int cont_check(cont_t* cont);
|
||||
int cont_check(cont_t* cont);
|
||||
|
||||
#endif /* CONT_H_ */
|
||||
|
@ -1,40 +1,36 @@
|
||||
/*
|
||||
cont_util.s - continuations support for Xtensa call0 ABI
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
cont_util.s - continuations support for Xtensa call0 ABI
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#include "cont.h"
|
||||
|
||||
#define CONT_STACKGUARD 0xfeefeffe
|
||||
|
||||
void cont_init(cont_t* cont)
|
||||
{
|
||||
cont->stack_guard1 = CONT_STACKGUARD;
|
||||
cont->stack_guard2 = CONT_STACKGUARD;
|
||||
cont->stack_end = cont->stack + (sizeof(cont->stack) / 4 - 1);
|
||||
cont->struct_start = (unsigned*) cont;
|
||||
void cont_init(cont_t* cont) {
|
||||
cont->stack_guard1 = CONT_STACKGUARD;
|
||||
cont->stack_guard2 = CONT_STACKGUARD;
|
||||
cont->stack_end = cont->stack + (sizeof(cont->stack) / 4 - 1);
|
||||
cont->struct_start = (unsigned*) cont;
|
||||
}
|
||||
|
||||
int cont_check(cont_t* cont)
|
||||
{
|
||||
if (cont->stack_guard1 != CONT_STACKGUARD ||
|
||||
cont->stack_guard2 != CONT_STACKGUARD )
|
||||
return 1;
|
||||
int cont_check(cont_t* cont) {
|
||||
if(cont->stack_guard1 != CONT_STACKGUARD || cont->stack_guard2 != CONT_STACKGUARD) return 1;
|
||||
|
||||
return 0;
|
||||
return 0;
|
||||
}
|
||||
|
@ -1,28 +1,27 @@
|
||||
/*
|
||||
main.cpp - platform initialization and context switching
|
||||
emulation
|
||||
main.cpp - platform initialization and context switching
|
||||
emulation
|
||||
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
//This may be used to change user task stack size:
|
||||
//#define CONT_STACKSIZE 4096
|
||||
|
||||
#include <Arduino.h>
|
||||
extern "C" {
|
||||
#include "ets_sys.h"
|
||||
@ -35,26 +34,26 @@ extern "C" {
|
||||
#define LOOP_TASK_PRIORITY 0
|
||||
#define LOOP_QUEUE_SIZE 1
|
||||
|
||||
int atexit(void (*func)()) { return 0; }
|
||||
int atexit(void (*func)()) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
extern "C" void ets_update_cpu_frequency(int freqmhz);
|
||||
void initVariant() __attribute__((weak));
|
||||
void initVariant() { }
|
||||
void initVariant() {
|
||||
}
|
||||
|
||||
extern void loop();
|
||||
extern void setup();
|
||||
|
||||
void preloop_update_frequency() __attribute__((weak));
|
||||
void preloop_update_frequency()
|
||||
{
|
||||
void preloop_update_frequency() {
|
||||
#if defined(F_CPU) && (F_CPU == 16000000L)
|
||||
REG_SET_BIT(0x3ff00014, BIT(0));
|
||||
ets_update_cpu_frequency(160);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
|
||||
extern void (*__init_array_start)(void);
|
||||
extern void (*__init_array_end)(void);
|
||||
|
||||
@ -63,39 +62,32 @@ static os_event_t g_loop_queue[LOOP_QUEUE_SIZE];
|
||||
|
||||
static uint32_t g_micros_at_task_start;
|
||||
|
||||
extern "C" uint32_t esp_micros_at_task_start()
|
||||
{
|
||||
extern "C" uint32_t esp_micros_at_task_start() {
|
||||
return g_micros_at_task_start;
|
||||
}
|
||||
|
||||
extern "C" void abort()
|
||||
{
|
||||
while(1){}
|
||||
extern "C" void abort() {
|
||||
while(1) {
|
||||
}
|
||||
}
|
||||
|
||||
extern "C" void esp_yield()
|
||||
{
|
||||
extern "C" void esp_yield() {
|
||||
cont_yield(&g_cont);
|
||||
}
|
||||
|
||||
extern "C" void esp_schedule()
|
||||
{
|
||||
extern "C" void esp_schedule() {
|
||||
system_os_post(LOOP_TASK_PRIORITY, 0, 0);
|
||||
}
|
||||
|
||||
extern "C" void __yield()
|
||||
{
|
||||
extern "C" void __yield() {
|
||||
esp_schedule();
|
||||
esp_yield();
|
||||
}
|
||||
extern "C" void yield(void) __attribute__ ((weak, alias("__yield")));
|
||||
|
||||
|
||||
static void loop_wrapper()
|
||||
{
|
||||
static void loop_wrapper() {
|
||||
static bool setup_done = false;
|
||||
if (!setup_done)
|
||||
{
|
||||
if(!setup_done) {
|
||||
setup();
|
||||
setup_done = true;
|
||||
}
|
||||
@ -104,33 +96,28 @@ static void loop_wrapper()
|
||||
esp_schedule();
|
||||
}
|
||||
|
||||
static void loop_task(os_event_t *events)
|
||||
{
|
||||
static void loop_task(os_event_t *events) {
|
||||
g_micros_at_task_start = system_get_time();
|
||||
cont_run(&g_cont, &loop_wrapper);
|
||||
if (cont_check(&g_cont) != 0)
|
||||
{
|
||||
if(cont_check(&g_cont) != 0) {
|
||||
ets_printf("\r\nheap collided with sketch stack\r\n");
|
||||
abort();
|
||||
}
|
||||
}
|
||||
|
||||
static void do_global_ctors(void)
|
||||
{
|
||||
static void do_global_ctors(void) {
|
||||
void (**p)(void);
|
||||
for (p = &__init_array_start; p != &__init_array_end; ++p)
|
||||
(*p)();
|
||||
for(p = &__init_array_start; p != &__init_array_end; ++p)
|
||||
(*p)();
|
||||
}
|
||||
|
||||
void init_done()
|
||||
{
|
||||
void init_done() {
|
||||
do_global_ctors();
|
||||
esp_schedule();
|
||||
}
|
||||
|
||||
extern "C" {
|
||||
void user_init(void)
|
||||
{
|
||||
void user_init(void) {
|
||||
uart_div_modify(0, UART_CLK_FREQ / (115200));
|
||||
|
||||
init();
|
||||
@ -139,10 +126,9 @@ void user_init(void)
|
||||
|
||||
cont_init(&g_cont);
|
||||
|
||||
system_os_task( loop_task,
|
||||
LOOP_TASK_PRIORITY,
|
||||
g_loop_queue,
|
||||
LOOP_QUEUE_SIZE);
|
||||
system_os_task(loop_task,
|
||||
LOOP_TASK_PRIORITY, g_loop_queue,
|
||||
LOOP_QUEUE_SIZE);
|
||||
|
||||
system_init_done_cb(&init_done);
|
||||
}
|
||||
|
@ -30,167 +30,170 @@
|
||||
#define strcpy ets_strcpy
|
||||
|
||||
int atoi(const char* s) {
|
||||
return (int) atol(s);
|
||||
return (int) atol(s);
|
||||
}
|
||||
|
||||
long atol(const char* s) {
|
||||
const char * tmp;
|
||||
return strtol(s, &tmp, 10);
|
||||
const char * tmp;
|
||||
return strtol(s, &tmp, 10);
|
||||
}
|
||||
|
||||
double atof(const char* s) {
|
||||
const char * tmp;
|
||||
return strtod(s, &tmp);
|
||||
const char * tmp;
|
||||
return strtod(s, &tmp);
|
||||
}
|
||||
|
||||
void reverse(char* begin, char* end) {
|
||||
char *is = begin;
|
||||
char *ie = end - 1;
|
||||
while(is < ie) {
|
||||
char tmp = *ie;
|
||||
*ie = *is;
|
||||
*is = tmp;
|
||||
++is;
|
||||
--ie;
|
||||
}
|
||||
char *is = begin;
|
||||
char *ie = end - 1;
|
||||
while(is < ie) {
|
||||
char tmp = *ie;
|
||||
*ie = *is;
|
||||
*is = tmp;
|
||||
++is;
|
||||
--ie;
|
||||
}
|
||||
}
|
||||
|
||||
char* itoa(int value, char* result, int base) {
|
||||
if(base < 2 || base > 16) {
|
||||
*result = 0;
|
||||
return result;
|
||||
}
|
||||
if(base < 2 || base > 16) {
|
||||
*result = 0;
|
||||
return result;
|
||||
}
|
||||
|
||||
char* out = result;
|
||||
int quotient = abs(value);
|
||||
char* out = result;
|
||||
int quotient = abs(value);
|
||||
|
||||
do {
|
||||
const int tmp = quotient / base;
|
||||
*out = "0123456789abcdef"[quotient - (tmp * base)];
|
||||
++out;
|
||||
quotient = tmp;
|
||||
} while(quotient);
|
||||
do {
|
||||
const int tmp = quotient / base;
|
||||
*out = "0123456789abcdef"[quotient - (tmp * base)];
|
||||
++out;
|
||||
quotient = tmp;
|
||||
} while(quotient);
|
||||
|
||||
// Apply negative sign
|
||||
if(value < 0) *out++ = '-';
|
||||
// Apply negative sign
|
||||
if(value < 0)
|
||||
*out++ = '-';
|
||||
|
||||
reverse(result, out);
|
||||
*out = 0;
|
||||
return result;
|
||||
reverse(result, out);
|
||||
*out = 0;
|
||||
return result;
|
||||
}
|
||||
|
||||
char* ltoa(long value, char* result, int base) {
|
||||
if(base < 2 || base > 16) {
|
||||
*result = 0;
|
||||
return result;
|
||||
}
|
||||
if(base < 2 || base > 16) {
|
||||
*result = 0;
|
||||
return result;
|
||||
}
|
||||
|
||||
char* out = result;
|
||||
long quotient = abs(value);
|
||||
char* out = result;
|
||||
long quotient = abs(value);
|
||||
|
||||
do {
|
||||
const long tmp = quotient / base;
|
||||
*out = "0123456789abcdef"[quotient - (tmp * base)];
|
||||
++out;
|
||||
quotient = tmp;
|
||||
} while(quotient);
|
||||
do {
|
||||
const long tmp = quotient / base;
|
||||
*out = "0123456789abcdef"[quotient - (tmp * base)];
|
||||
++out;
|
||||
quotient = tmp;
|
||||
} while(quotient);
|
||||
|
||||
// Apply negative sign
|
||||
if(value < 0) *out++ = '-';
|
||||
// Apply negative sign
|
||||
if(value < 0)
|
||||
*out++ = '-';
|
||||
|
||||
reverse(result, out);
|
||||
*out = 0;
|
||||
return result;
|
||||
reverse(result, out);
|
||||
*out = 0;
|
||||
return result;
|
||||
}
|
||||
|
||||
char* utoa(unsigned value, char* result, int base) {
|
||||
if(base < 2 || base > 16) {
|
||||
*result = 0;
|
||||
return result;
|
||||
}
|
||||
if(base < 2 || base > 16) {
|
||||
*result = 0;
|
||||
return result;
|
||||
}
|
||||
|
||||
char* out = result;
|
||||
unsigned quotient = value;
|
||||
char* out = result;
|
||||
unsigned quotient = value;
|
||||
|
||||
do {
|
||||
const unsigned tmp = quotient / base;
|
||||
*out = "0123456789abcdef"[quotient - (tmp * base)];
|
||||
++out;
|
||||
quotient = tmp;
|
||||
} while(quotient);
|
||||
do {
|
||||
const unsigned tmp = quotient / base;
|
||||
*out = "0123456789abcdef"[quotient - (tmp * base)];
|
||||
++out;
|
||||
quotient = tmp;
|
||||
} while(quotient);
|
||||
|
||||
reverse(result, out);
|
||||
*out = 0;
|
||||
return result;
|
||||
reverse(result, out);
|
||||
*out = 0;
|
||||
return result;
|
||||
}
|
||||
|
||||
char* ultoa(unsigned long value, char* result, int base) {
|
||||
if(base < 2 || base > 16) {
|
||||
*result = 0;
|
||||
return result;
|
||||
}
|
||||
if(base < 2 || base > 16) {
|
||||
*result = 0;
|
||||
return result;
|
||||
}
|
||||
|
||||
char* out = result;
|
||||
unsigned long quotient = value;
|
||||
char* out = result;
|
||||
unsigned long quotient = value;
|
||||
|
||||
do {
|
||||
const unsigned long tmp = quotient / base;
|
||||
*out = "0123456789abcdef"[quotient - (tmp * base)];
|
||||
++out;
|
||||
quotient = tmp;
|
||||
} while(quotient);
|
||||
do {
|
||||
const unsigned long tmp = quotient / base;
|
||||
*out = "0123456789abcdef"[quotient - (tmp * base)];
|
||||
++out;
|
||||
quotient = tmp;
|
||||
} while(quotient);
|
||||
|
||||
reverse(result, out);
|
||||
*out = 0;
|
||||
return result;
|
||||
reverse(result, out);
|
||||
*out = 0;
|
||||
return result;
|
||||
}
|
||||
|
||||
char * dtostrf(double number, signed char width, unsigned char prec, char *s) {
|
||||
size_t n = 0;
|
||||
size_t n = 0;
|
||||
|
||||
if(isnan(number)) {
|
||||
strcpy(s, "nan");
|
||||
return s;
|
||||
}
|
||||
if(isinf(number)) {
|
||||
strcpy(s, "inf");
|
||||
return s;
|
||||
}
|
||||
if(isnan(number)) {
|
||||
strcpy(s, "nan");
|
||||
return s;
|
||||
}
|
||||
if(isinf(number)) {
|
||||
strcpy(s, "inf");
|
||||
return s;
|
||||
}
|
||||
|
||||
if(number > 4294967040.0 || number < -4294967040.0) {
|
||||
strcpy(s, "ovf");
|
||||
return s;
|
||||
}
|
||||
char* out = s;
|
||||
// Handle negative numbers
|
||||
if(number < 0.0) {
|
||||
*out = '-';
|
||||
++out;
|
||||
number = -number;
|
||||
}
|
||||
if(number > 4294967040.0 || number < -4294967040.0) {
|
||||
strcpy(s, "ovf");
|
||||
return s;
|
||||
}
|
||||
char* out = s;
|
||||
// Handle negative numbers
|
||||
if(number < 0.0) {
|
||||
*out = '-';
|
||||
++out;
|
||||
number = -number;
|
||||
}
|
||||
|
||||
// Round correctly so that print(1.999, 2) prints as "2.00"
|
||||
double rounding = 0.5;
|
||||
for(uint8_t i = 0; i < prec; ++i)
|
||||
rounding /= 10.0;
|
||||
// Round correctly so that print(1.999, 2) prints as "2.00"
|
||||
double rounding = 0.5;
|
||||
for(uint8_t i = 0; i < prec; ++i)
|
||||
rounding /= 10.0;
|
||||
|
||||
number += rounding;
|
||||
number += rounding;
|
||||
|
||||
// Extract the integer part of the number and print it
|
||||
unsigned long int_part = (unsigned long) number;
|
||||
double remainder = number - (double) int_part;
|
||||
out += sprintf(out, "%d", int_part);
|
||||
// Extract the integer part of the number and print it
|
||||
unsigned long int_part = (unsigned long) number;
|
||||
double remainder = number - (double) int_part;
|
||||
out += sprintf(out, "%d", int_part);
|
||||
|
||||
// Print the decimal point, but only if there are digits beyond
|
||||
if(prec > 0) {
|
||||
*out = '.';
|
||||
++out;
|
||||
}
|
||||
// Print the decimal point, but only if there are digits beyond
|
||||
if(prec > 0) {
|
||||
*out = '.';
|
||||
++out;
|
||||
}
|
||||
|
||||
while(prec-- > 0) {
|
||||
remainder *= 10.0;
|
||||
}
|
||||
sprintf(out, "%d", (int) remainder);
|
||||
while(prec-- > 0) {
|
||||
remainder *= 10.0;
|
||||
}
|
||||
sprintf(out, "%d", (int) remainder);
|
||||
|
||||
return s;
|
||||
return s;
|
||||
}
|
||||
|
||||
|
@ -1,24 +1,23 @@
|
||||
/*
|
||||
core_esp8266_wiring.c - implementation of Wiring API for esp8266
|
||||
core_esp8266_wiring.c - implementation of Wiring API for esp8266
|
||||
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
|
||||
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 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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#include "wiring_private.h"
|
||||
#include "ets_sys.h"
|
||||
@ -36,57 +35,45 @@ static uint32_t micros_overflow_count = 0;
|
||||
#define ONCE 0
|
||||
#define REPEAT 1
|
||||
|
||||
|
||||
void delay_end(void* arg)
|
||||
{
|
||||
void delay_end(void* arg) {
|
||||
esp_schedule();
|
||||
}
|
||||
|
||||
void delay(unsigned long ms)
|
||||
{
|
||||
if (ms)
|
||||
{
|
||||
void delay(unsigned long ms) {
|
||||
if(ms) {
|
||||
os_timer_setfn(&delay_timer, (os_timer_func_t*) &delay_end, 0);
|
||||
os_timer_arm(&delay_timer, ms, ONCE);
|
||||
}
|
||||
else
|
||||
{
|
||||
} else {
|
||||
esp_schedule();
|
||||
}
|
||||
esp_yield();
|
||||
if (ms)
|
||||
{
|
||||
if(ms) {
|
||||
os_timer_disarm(&delay_timer);
|
||||
}
|
||||
}
|
||||
|
||||
void micros_overflow_tick(void* arg)
|
||||
{
|
||||
void micros_overflow_tick(void* arg) {
|
||||
uint32_t m = system_get_time();
|
||||
if (m < micros_at_last_overflow_tick)
|
||||
if(m < micros_at_last_overflow_tick)
|
||||
++micros_overflow_count;
|
||||
micros_at_last_overflow_tick = m;
|
||||
}
|
||||
|
||||
unsigned long millis()
|
||||
{
|
||||
unsigned long millis() {
|
||||
uint32_t m = system_get_time();
|
||||
uint32_t c = micros_overflow_count + ((m < micros_at_last_overflow_tick) ? 1 : 0);
|
||||
return c * 4294967 + m / 1000;
|
||||
}
|
||||
|
||||
unsigned long micros()
|
||||
{
|
||||
unsigned long micros() {
|
||||
return system_get_time();
|
||||
}
|
||||
|
||||
void delayMicroseconds(unsigned int us)
|
||||
{
|
||||
void delayMicroseconds(unsigned int us) {
|
||||
os_delay_us(us);
|
||||
}
|
||||
|
||||
void init()
|
||||
{
|
||||
void init() {
|
||||
initPins();
|
||||
os_timer_setfn(µs_overflow_timer, (os_timer_func_t*) µs_overflow_tick, 0);
|
||||
os_timer_arm(µs_overflow_timer, 60000, REPEAT);
|
||||
|
@ -1,39 +1,35 @@
|
||||
/*
|
||||
core_esp8266_analog.c - an interface to the esp8266 ADC
|
||||
core_esp8266_analog.c - an interface to the esp8266 ADC
|
||||
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#include "wiring_private.h"
|
||||
#include "pins_arduino.h"
|
||||
|
||||
|
||||
void analogReference(uint8_t mode)
|
||||
{
|
||||
void analogReference(uint8_t mode) {
|
||||
}
|
||||
|
||||
extern int __analogRead(uint8_t pin)
|
||||
{
|
||||
if (pin == 0)
|
||||
return system_adc_read();
|
||||
extern int __analogRead(uint8_t pin) {
|
||||
if(pin == 0)
|
||||
return system_adc_read();
|
||||
|
||||
return 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
extern int analogRead(uint8_t pin) __attribute__ ((weak, alias("__analogRead")));
|
||||
|
@ -1,23 +1,23 @@
|
||||
/*
|
||||
core_esp8266_wiring_digital.c - implementation of Wiring API for esp8266
|
||||
core_esp8266_wiring_digital.c - implementation of Wiring API for esp8266
|
||||
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#define ARDUINO_MAIN
|
||||
#include "wiring_private.h"
|
||||
@ -31,77 +31,42 @@
|
||||
|
||||
#define PINCOUNT 16
|
||||
|
||||
static const uint32_t g_pin_muxes[PINCOUNT] = {
|
||||
[0] = PERIPHS_IO_MUX_GPIO0_U,
|
||||
[1] = PERIPHS_IO_MUX_U0TXD_U,
|
||||
[2] = PERIPHS_IO_MUX_GPIO2_U,
|
||||
[3] = PERIPHS_IO_MUX_U0RXD_U,
|
||||
[4] = PERIPHS_IO_MUX_GPIO4_U,
|
||||
[5] = PERIPHS_IO_MUX_GPIO5_U,
|
||||
static const uint32_t g_pin_muxes[PINCOUNT] = { [0] = PERIPHS_IO_MUX_GPIO0_U, [1] = PERIPHS_IO_MUX_U0TXD_U, [2] = PERIPHS_IO_MUX_GPIO2_U, [3] = PERIPHS_IO_MUX_U0RXD_U, [4] = PERIPHS_IO_MUX_GPIO4_U, [5] = PERIPHS_IO_MUX_GPIO5_U,
|
||||
|
||||
// These 6 pins are used for SPI flash interface
|
||||
[6] = 0,
|
||||
[7] = 0,
|
||||
[8] = 0,
|
||||
[9] = 0,
|
||||
[10] = 0,
|
||||
[11] = 0,
|
||||
// These 6 pins are used for SPI flash interface
|
||||
[6] = 0, [7] = 0, [8] = 0, [9] = 0, [10] = 0, [11] = 0,
|
||||
|
||||
[12] = PERIPHS_IO_MUX_MTDI_U,
|
||||
[13] = PERIPHS_IO_MUX_MTCK_U,
|
||||
[14] = PERIPHS_IO_MUX_MTMS_U,
|
||||
[15] = PERIPHS_IO_MUX_MTDO_U,
|
||||
};
|
||||
[12] = PERIPHS_IO_MUX_MTDI_U, [13] = PERIPHS_IO_MUX_MTCK_U, [14] = PERIPHS_IO_MUX_MTMS_U, [15] = PERIPHS_IO_MUX_MTDO_U, };
|
||||
|
||||
static const uint32_t g_pin_funcs[PINCOUNT] = {
|
||||
[0] = FUNC_GPIO0,
|
||||
[1] = FUNC_GPIO1,
|
||||
[2] = FUNC_GPIO2,
|
||||
[3] = FUNC_GPIO3,
|
||||
[4] = FUNC_GPIO4,
|
||||
[5] = FUNC_GPIO5,
|
||||
[12] = FUNC_GPIO12,
|
||||
[13] = FUNC_GPIO13,
|
||||
[14] = FUNC_GPIO14,
|
||||
[15] = FUNC_GPIO15,
|
||||
};
|
||||
static const uint32_t g_pin_funcs[PINCOUNT] = { [0] = FUNC_GPIO0, [1] = FUNC_GPIO1, [2] = FUNC_GPIO2, [3] = FUNC_GPIO3, [4] = FUNC_GPIO4, [5] = FUNC_GPIO5, [12] = FUNC_GPIO12, [13] = FUNC_GPIO13, [14] = FUNC_GPIO14, [15] = FUNC_GPIO15, };
|
||||
|
||||
|
||||
uint32_t digitalPinToPort(uint32_t pin)
|
||||
{
|
||||
uint32_t digitalPinToPort(uint32_t pin) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
uint32_t digitalPinToBitMask(uint32_t pin)
|
||||
{
|
||||
uint32_t digitalPinToBitMask(uint32_t pin) {
|
||||
return 1 << pin;
|
||||
}
|
||||
|
||||
volatile uint32_t* portOutputRegister(uint32_t port)
|
||||
{
|
||||
volatile uint32_t* portOutputRegister(uint32_t port) {
|
||||
return (volatile uint32_t*) (PERIPHS_GPIO_BASEADDR + GPIO_OUT_ADDRESS);
|
||||
}
|
||||
|
||||
volatile uint32_t* portInputRegister(uint32_t port)
|
||||
{
|
||||
volatile uint32_t* portInputRegister(uint32_t port) {
|
||||
return (volatile uint32_t*) (PERIPHS_GPIO_BASEADDR + GPIO_IN_ADDRESS);
|
||||
}
|
||||
|
||||
volatile uint32_t* portModeRegister(uint32_t port)
|
||||
{
|
||||
volatile uint32_t* portModeRegister(uint32_t port) {
|
||||
return (volatile uint32_t*) (PERIPHS_GPIO_BASEADDR + GPIO_ENABLE_ADDRESS);
|
||||
}
|
||||
|
||||
|
||||
enum PinFunction { GPIO, PWM };
|
||||
static uint32_t g_gpio_function[PINCOUNT] = {
|
||||
GPIO
|
||||
enum PinFunction {
|
||||
GPIO, PWM
|
||||
};
|
||||
static uint32_t g_gpio_function[PINCOUNT] = { GPIO };
|
||||
|
||||
extern void __pinMode(uint8_t pin, uint8_t mode)
|
||||
{
|
||||
if (pin == 16)
|
||||
{
|
||||
extern void __pinMode(uint8_t pin, uint8_t mode) {
|
||||
if(pin == 16) {
|
||||
uint32_t val = (mode == OUTPUT) ? 1 : 0;
|
||||
|
||||
MODIFY_PERI_REG(PAD_XPD_DCDC_CONF, 0x43, 1);
|
||||
@ -111,115 +76,84 @@ extern void __pinMode(uint8_t pin, uint8_t mode)
|
||||
}
|
||||
|
||||
uint32_t mux = g_pin_muxes[pin];
|
||||
if (mode == INPUT)
|
||||
{
|
||||
if(mode == INPUT) {
|
||||
gpio_output_set(0, 0, 0, 1 << pin);
|
||||
PIN_PULLUP_DIS(mux);
|
||||
}
|
||||
else if (mode == INPUT_PULLUP)
|
||||
{
|
||||
} else if(mode == INPUT_PULLUP) {
|
||||
gpio_output_set(0, 0, 0, 1 << pin);
|
||||
PIN_PULLUP_EN(mux);
|
||||
}
|
||||
else if (mode == OUTPUT)
|
||||
{
|
||||
} else if(mode == OUTPUT) {
|
||||
gpio_output_set(0, 0, 1 << pin, 0);
|
||||
}
|
||||
else if (mode == OUTPUT_OPEN_DRAIN)
|
||||
{
|
||||
GPIO_REG_WRITE(
|
||||
GPIO_PIN_ADDR(GPIO_ID_PIN(pin)),
|
||||
GPIO_REG_READ(GPIO_PIN_ADDR(GPIO_ID_PIN(pin))) |
|
||||
GPIO_PIN_PAD_DRIVER_SET(GPIO_PAD_DRIVER_ENABLE)
|
||||
);
|
||||
} else if(mode == OUTPUT_OPEN_DRAIN) {
|
||||
GPIO_REG_WRITE(GPIO_PIN_ADDR(GPIO_ID_PIN(pin)), GPIO_REG_READ(GPIO_PIN_ADDR(GPIO_ID_PIN(pin))) | GPIO_PIN_PAD_DRIVER_SET(GPIO_PAD_DRIVER_ENABLE));
|
||||
|
||||
GPIO_REG_WRITE(GPIO_ENABLE_ADDRESS, GPIO_REG_READ(GPIO_ENABLE_ADDRESS) | (1 << pin));
|
||||
}
|
||||
}
|
||||
|
||||
extern void __digitalWrite(uint8_t pin, uint8_t val)
|
||||
{
|
||||
if (pin == 16)
|
||||
{
|
||||
extern void __digitalWrite(uint8_t pin, uint8_t val) {
|
||||
if(pin == 16) {
|
||||
MODIFY_PERI_REG(RTC_GPIO_OUT, 1, (val & 1));
|
||||
return;
|
||||
}
|
||||
|
||||
uint32_t mask = 1 << pin;
|
||||
if (val)
|
||||
GPIO_REG_WRITE(GPIO_OUT_W1TS_ADDRESS, mask);
|
||||
if(val)
|
||||
GPIO_REG_WRITE(GPIO_OUT_W1TS_ADDRESS, mask);
|
||||
else
|
||||
GPIO_REG_WRITE(GPIO_OUT_W1TC_ADDRESS, mask);
|
||||
GPIO_REG_WRITE(GPIO_OUT_W1TC_ADDRESS, mask);
|
||||
}
|
||||
|
||||
extern int __digitalRead(uint8_t pin)
|
||||
{
|
||||
if (pin == 16)
|
||||
extern int __digitalRead(uint8_t pin) {
|
||||
if(pin == 16)
|
||||
return (READ_PERI_REG(RTC_GPIO_IN_DATA) & 1);
|
||||
else
|
||||
return ((gpio_input_get() >> pin) & 1);
|
||||
}
|
||||
|
||||
extern void __analogWrite(uint8_t pin, int val)
|
||||
{
|
||||
extern void __analogWrite(uint8_t pin, int val) {
|
||||
}
|
||||
|
||||
typedef void (*voidFuncPtr)(void);
|
||||
static voidFuncPtr g_handlers[PINCOUNT] = { 0 };
|
||||
|
||||
|
||||
void interrupt_handler(void *arg)
|
||||
{
|
||||
void interrupt_handler(void *arg) {
|
||||
uint32_t intr_mask = GPIO_REG_READ(GPIO_STATUS_ADDRESS);
|
||||
for (int pin = 0; intr_mask; intr_mask >>= 1, ++pin)
|
||||
{
|
||||
if ((intr_mask & 1) && g_handlers[pin])
|
||||
{
|
||||
for(int pin = 0; intr_mask; intr_mask >>= 1, ++pin) {
|
||||
if((intr_mask & 1) && g_handlers[pin]) {
|
||||
GPIO_REG_WRITE(GPIO_STATUS_W1TC_ADDRESS, 1 << pin);
|
||||
(*g_handlers[pin])();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
extern void __attachInterrupt(uint8_t pin, voidFuncPtr handler, int mode)
|
||||
{
|
||||
if (pin < 0 || pin > PINCOUNT)
|
||||
extern void __attachInterrupt(uint8_t pin, voidFuncPtr handler, int mode) {
|
||||
if(pin < 0 || pin > PINCOUNT)
|
||||
return;
|
||||
|
||||
g_handlers[pin] = handler;
|
||||
|
||||
if (mode == RISING)
|
||||
{
|
||||
if(mode == RISING) {
|
||||
gpio_pin_intr_state_set(pin, GPIO_PIN_INTR_POSEDGE);
|
||||
}
|
||||
else if (mode == FALLING)
|
||||
{
|
||||
} else if(mode == FALLING) {
|
||||
gpio_pin_intr_state_set(pin, GPIO_PIN_INTR_NEGEDGE);
|
||||
}
|
||||
else if (mode == CHANGE)
|
||||
{
|
||||
} else if(mode == CHANGE) {
|
||||
gpio_pin_intr_state_set(pin, GPIO_PIN_INTR_ANYEDGE);
|
||||
}
|
||||
else
|
||||
{
|
||||
} else {
|
||||
gpio_pin_intr_state_set(pin, GPIO_PIN_INTR_DISABLE);
|
||||
}
|
||||
}
|
||||
|
||||
extern void __detachInterrupt(uint8_t pin)
|
||||
{
|
||||
extern void __detachInterrupt(uint8_t pin) {
|
||||
g_handlers[pin] = 0;
|
||||
gpio_pin_intr_state_set(pin, GPIO_PIN_INTR_DISABLE);
|
||||
}
|
||||
|
||||
void initPins()
|
||||
{
|
||||
void initPins() {
|
||||
gpio_init();
|
||||
for (int i = 0; i < PINCOUNT; ++i)
|
||||
{
|
||||
for(int i = 0; i < PINCOUNT; ++i) {
|
||||
uint32_t mux = g_pin_muxes[i];
|
||||
if (mux)
|
||||
{
|
||||
if(mux) {
|
||||
uint32_t func = g_pin_funcs[i];
|
||||
PIN_FUNC_SELECT(mux, func);
|
||||
}
|
||||
@ -229,7 +163,7 @@ void initPins()
|
||||
|
||||
extern void pinMode(uint8_t pin, uint8_t mode) __attribute__ ((weak, alias("__pinMode")));
|
||||
extern void digitalWrite(uint8_t pin, uint8_t val) __attribute__ ((weak, alias("__digitalWrite")));
|
||||
extern int digitalRead(uint8_t pin) __attribute__ ((weak, alias("__digitalRead")));
|
||||
extern int digitalRead(uint8_t pin) __attribute__ ((weak, alias("__digitalRead")));
|
||||
extern void analogWrite(uint8_t pin, int val) __attribute__ ((weak, alias("__analogWrite")));
|
||||
extern void attachInterrupt(uint8_t pin, voidFuncPtr handler, int mode) __attribute__ ((weak, alias("__attachInterrupt")));
|
||||
extern void detachInterrupt(uint8_t pin) __attribute__ ((weak, alias("__detachInterrupt")));
|
||||
|
@ -1,23 +1,23 @@
|
||||
/*
|
||||
core_esp8266_wiring_pulse.c - implementation of pulseIn function
|
||||
core_esp8266_wiring_pulse.c - implementation of pulseIn function
|
||||
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#include "wiring_private.h"
|
||||
#include "pins_arduino.h"
|
||||
@ -26,7 +26,6 @@
|
||||
* or LOW, the type of pulse to measure. Works on pulses from 2-3 microseconds
|
||||
* to 3 minutes in length, but must be called at least a few dozen microseconds
|
||||
* before the start of the pulse. */
|
||||
unsigned long pulseIn(uint8_t pin, uint8_t state, unsigned long timeout)
|
||||
{
|
||||
return 0;
|
||||
unsigned long pulseIn(uint8_t pin, uint8_t state, unsigned long timeout) {
|
||||
return 0;
|
||||
}
|
||||
|
@ -1,58 +1,57 @@
|
||||
/*
|
||||
wiring_shift.c - shiftOut() function
|
||||
Part of Arduino - http://www.arduino.cc/
|
||||
wiring_shift.c - shiftOut() function
|
||||
Part of Arduino - http://www.arduino.cc/
|
||||
|
||||
Copyright (c) 2005-2006 David A. Mellis
|
||||
Copyright (c) 2005-2006 David A. Mellis
|
||||
|
||||
Note: file renamed with a core_esp8266_ prefix to simplify linker
|
||||
script rules for moving code into irom0_text section.
|
||||
Note: file renamed with a core_esp8266_ prefix to simplify linker
|
||||
script rules for moving code into irom0_text section.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General
|
||||
Public License along with this library; if not, write to the
|
||||
Free Software Foundation, Inc., 59 Temple Place, Suite 330,
|
||||
Boston, MA 02111-1307 USA
|
||||
You should have received a copy of the GNU Lesser General
|
||||
Public License along with this library; if not, write to the
|
||||
Free Software Foundation, Inc., 59 Temple Place, Suite 330,
|
||||
Boston, MA 02111-1307 USA
|
||||
|
||||
$Id: wiring.c 248 2007-02-03 15:36:30Z mellis $
|
||||
*/
|
||||
$Id: wiring.c 248 2007-02-03 15:36:30Z mellis $
|
||||
*/
|
||||
|
||||
#include "wiring_private.h"
|
||||
|
||||
uint8_t shiftIn(uint8_t dataPin, uint8_t clockPin, uint8_t bitOrder) {
|
||||
uint8_t value = 0;
|
||||
uint8_t i;
|
||||
uint8_t value = 0;
|
||||
uint8_t i;
|
||||
|
||||
for (i = 0; i < 8; ++i) {
|
||||
digitalWrite(clockPin, HIGH);
|
||||
if (bitOrder == LSBFIRST)
|
||||
value |= digitalRead(dataPin) << i;
|
||||
else
|
||||
value |= digitalRead(dataPin) << (7 - i);
|
||||
digitalWrite(clockPin, LOW);
|
||||
}
|
||||
return value;
|
||||
for(i = 0; i < 8; ++i) {
|
||||
digitalWrite(clockPin, HIGH);
|
||||
if(bitOrder == LSBFIRST)
|
||||
value |= digitalRead(dataPin) << i;
|
||||
else
|
||||
value |= digitalRead(dataPin) << (7 - i);
|
||||
digitalWrite(clockPin, LOW);
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
void shiftOut(uint8_t dataPin, uint8_t clockPin, uint8_t bitOrder, uint8_t val)
|
||||
{
|
||||
uint8_t i;
|
||||
void shiftOut(uint8_t dataPin, uint8_t clockPin, uint8_t bitOrder, uint8_t val) {
|
||||
uint8_t i;
|
||||
|
||||
for (i = 0; i < 8; i++) {
|
||||
if (bitOrder == LSBFIRST)
|
||||
digitalWrite(dataPin, !!(val & (1 << i)));
|
||||
else
|
||||
digitalWrite(dataPin, !!(val & (1 << (7 - i))));
|
||||
for(i = 0; i < 8; i++) {
|
||||
if(bitOrder == LSBFIRST)
|
||||
digitalWrite(dataPin, !!(val & (1 << i)));
|
||||
else
|
||||
digitalWrite(dataPin, !!(val & (1 << (7 - i))));
|
||||
|
||||
digitalWrite(clockPin, HIGH);
|
||||
digitalWrite(clockPin, LOW);
|
||||
}
|
||||
digitalWrite(clockPin, HIGH);
|
||||
digitalWrite(clockPin, LOW);
|
||||
}
|
||||
}
|
||||
|
@ -1,23 +1,23 @@
|
||||
/*
|
||||
i2c.cpp - esp8266 i2c bit-banging library
|
||||
i2c.cpp - esp8266 i2c bit-banging library
|
||||
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#include <Arduino.h>
|
||||
#include "i2c.h"
|
||||
@ -33,93 +33,78 @@ static uint8_t s_sda_pin = 0;
|
||||
static uint8_t s_scl_pin = 2;
|
||||
static uint32_t s_i2c_delay = 5;
|
||||
|
||||
static inline void i2c_digital_write(int pin, int val)
|
||||
{
|
||||
uint32_t mask = 1 << pin;
|
||||
if (val)
|
||||
GPIO_REG_WRITE(GPIO_OUT_W1TS_ADDRESS, mask);
|
||||
static inline void i2c_digital_write(int pin, int val) {
|
||||
uint32_t mask = 1 << pin;
|
||||
if(val)
|
||||
GPIO_REG_WRITE(GPIO_OUT_W1TS_ADDRESS, mask);
|
||||
else
|
||||
GPIO_REG_WRITE(GPIO_OUT_W1TC_ADDRESS, mask);
|
||||
GPIO_REG_WRITE(GPIO_OUT_W1TC_ADDRESS, mask);
|
||||
}
|
||||
|
||||
static inline void i2c_set(int sda, int scl)
|
||||
{
|
||||
i2c_digital_write(s_sda_pin, sda);
|
||||
i2c_digital_write(s_scl_pin, scl);
|
||||
static inline void i2c_set(int sda, int scl) {
|
||||
i2c_digital_write(s_sda_pin, sda);
|
||||
i2c_digital_write(s_scl_pin, scl);
|
||||
}
|
||||
|
||||
static inline void i2c_set_sda(int sda)
|
||||
{
|
||||
i2c_digital_write(s_sda_pin, sda);
|
||||
static inline void i2c_set_sda(int sda) {
|
||||
i2c_digital_write(s_sda_pin, sda);
|
||||
}
|
||||
|
||||
static inline void i2c_set_scl(int scl)
|
||||
{
|
||||
i2c_digital_write(s_scl_pin, scl);
|
||||
static inline void i2c_set_scl(int scl) {
|
||||
i2c_digital_write(s_scl_pin, scl);
|
||||
}
|
||||
|
||||
static inline uint8_t i2c_get_sda()
|
||||
{
|
||||
return GPIO_INPUT_GET(GPIO_ID_PIN(s_sda_pin));
|
||||
static inline uint8_t i2c_get_sda() {
|
||||
return GPIO_INPUT_GET(GPIO_ID_PIN(s_sda_pin));
|
||||
}
|
||||
|
||||
static inline uint8_t i2c_get_scl()
|
||||
{
|
||||
return GPIO_INPUT_GET(GPIO_ID_PIN(s_scl_pin));
|
||||
static inline uint8_t i2c_get_scl() {
|
||||
return GPIO_INPUT_GET(GPIO_ID_PIN(s_scl_pin));
|
||||
}
|
||||
|
||||
|
||||
static inline void i2c_wait()
|
||||
{
|
||||
delayMicroseconds(s_i2c_delay);
|
||||
static inline void i2c_wait() {
|
||||
delayMicroseconds(s_i2c_delay);
|
||||
}
|
||||
|
||||
void i2c_freq(int freq_hz)
|
||||
{
|
||||
s_i2c_delay = 1000000 / freq_hz / 4 - 1;
|
||||
if (s_i2c_delay < 0)
|
||||
s_i2c_delay = 0;
|
||||
void i2c_freq(int freq_hz) {
|
||||
s_i2c_delay = 1000000 / freq_hz / 4 - 1;
|
||||
if(s_i2c_delay < 0)
|
||||
s_i2c_delay = 0;
|
||||
}
|
||||
|
||||
void i2c_init(int sda_pin, int scl_pin)
|
||||
{
|
||||
s_sda_pin = sda_pin;
|
||||
s_scl_pin = scl_pin;
|
||||
pinMode(ESP_PINS_OFFSET + sda_pin, OUTPUT_OPEN_DRAIN);
|
||||
pinMode(ESP_PINS_OFFSET + scl_pin, OUTPUT_OPEN_DRAIN);
|
||||
i2c_set(1, 1);
|
||||
i2c_wait();
|
||||
void i2c_init(int sda_pin, int scl_pin) {
|
||||
s_sda_pin = sda_pin;
|
||||
s_scl_pin = scl_pin;
|
||||
pinMode(ESP_PINS_OFFSET + sda_pin, OUTPUT_OPEN_DRAIN);
|
||||
pinMode(ESP_PINS_OFFSET + scl_pin, OUTPUT_OPEN_DRAIN);
|
||||
i2c_set(1, 1);
|
||||
i2c_wait();
|
||||
}
|
||||
|
||||
|
||||
void i2c_release()
|
||||
{
|
||||
pinMode(ESP_PINS_OFFSET + s_sda_pin, INPUT);
|
||||
pinMode(ESP_PINS_OFFSET + s_scl_pin, INPUT);
|
||||
void i2c_release() {
|
||||
pinMode(ESP_PINS_OFFSET + s_sda_pin, INPUT);
|
||||
pinMode(ESP_PINS_OFFSET + s_scl_pin, INPUT);
|
||||
}
|
||||
|
||||
void i2c_start()
|
||||
{
|
||||
i2c_set(1, 1);
|
||||
i2c_wait();
|
||||
i2c_set_sda(0);
|
||||
i2c_wait();
|
||||
i2c_wait();
|
||||
i2c_set_scl(0);
|
||||
i2c_wait();
|
||||
void i2c_start() {
|
||||
i2c_set(1, 1);
|
||||
i2c_wait();
|
||||
i2c_set_sda(0);
|
||||
i2c_wait();
|
||||
i2c_wait();
|
||||
i2c_set_scl(0);
|
||||
i2c_wait();
|
||||
}
|
||||
|
||||
void i2c_stop()
|
||||
{
|
||||
i2c_wait();
|
||||
void i2c_stop() {
|
||||
i2c_wait();
|
||||
i2c_set_scl(1);
|
||||
i2c_wait();
|
||||
i2c_set_sda(1);
|
||||
i2c_wait();
|
||||
}
|
||||
|
||||
void i2c_set_ack(int ack)
|
||||
{
|
||||
void i2c_set_ack(int ack) {
|
||||
i2c_set_sda(!ack);
|
||||
i2c_wait();
|
||||
i2c_set_scl(1);
|
||||
@ -130,120 +115,108 @@ void i2c_set_ack(int ack)
|
||||
i2c_wait();
|
||||
}
|
||||
|
||||
int i2c_get_ack()
|
||||
{
|
||||
i2c_set_scl(1);
|
||||
i2c_wait();
|
||||
int result = i2c_get_sda();
|
||||
i2c_set_scl(0);
|
||||
i2c_wait();
|
||||
i2c_set_sda(0);
|
||||
i2c_wait();
|
||||
return result;
|
||||
int i2c_get_ack() {
|
||||
i2c_set_scl(1);
|
||||
i2c_wait();
|
||||
int result = i2c_get_sda();
|
||||
i2c_set_scl(0);
|
||||
i2c_wait();
|
||||
i2c_set_sda(0);
|
||||
i2c_wait();
|
||||
return result;
|
||||
}
|
||||
|
||||
uint8_t i2c_read(void)
|
||||
{
|
||||
uint8_t result = 0;
|
||||
for (int i = 7; i >= 0; --i)
|
||||
{
|
||||
i2c_wait();
|
||||
i2c_set_scl(1);
|
||||
i2c_wait();
|
||||
result <<= 1;
|
||||
result |= i2c_get_sda();
|
||||
i2c_set_scl(0);
|
||||
}
|
||||
return result;
|
||||
uint8_t i2c_read(void) {
|
||||
uint8_t result = 0;
|
||||
for(int i = 7; i >= 0; --i) {
|
||||
i2c_wait();
|
||||
i2c_set_scl(1);
|
||||
i2c_wait();
|
||||
result <<= 1;
|
||||
result |= i2c_get_sda();
|
||||
i2c_set_scl(0);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
void i2c_write(uint8_t val)
|
||||
{
|
||||
for (int i = 7; i >= 0; --i)
|
||||
{
|
||||
i2c_set_sda((val >> i) & 1);
|
||||
i2c_wait();
|
||||
i2c_set_scl(1);
|
||||
i2c_wait();
|
||||
i2c_set_scl(0);
|
||||
}
|
||||
i2c_wait();
|
||||
i2c_set_sda(1);
|
||||
void i2c_write(uint8_t val) {
|
||||
for(int i = 7; i >= 0; --i) {
|
||||
i2c_set_sda((val >> i) & 1);
|
||||
i2c_wait();
|
||||
i2c_set_scl(1);
|
||||
i2c_wait();
|
||||
i2c_set_scl(0);
|
||||
}
|
||||
i2c_wait();
|
||||
i2c_set_sda(1);
|
||||
}
|
||||
|
||||
size_t i2c_master_read_from(int address, uint8_t* data, size_t size, bool sendStop)
|
||||
{
|
||||
i2c_start();
|
||||
i2c_write(address << 1 | 1);
|
||||
int ack = i2c_get_ack();
|
||||
uint8_t* end = data + size;
|
||||
for (;data != end; ++data )
|
||||
{
|
||||
i2c_set_sda(1);
|
||||
pinMode(ESP_PINS_OFFSET + s_sda_pin, INPUT);
|
||||
*data = i2c_read();
|
||||
pinMode(ESP_PINS_OFFSET + s_sda_pin, OUTPUT_OPEN_DRAIN);
|
||||
if (data == end - 1)
|
||||
i2c_set_ack(0);
|
||||
else
|
||||
i2c_set_ack(1);
|
||||
}
|
||||
if (sendStop)
|
||||
i2c_stop();
|
||||
return size;
|
||||
size_t i2c_master_read_from(int address, uint8_t* data, size_t size, bool sendStop) {
|
||||
i2c_start();
|
||||
i2c_write(address << 1 | 1);
|
||||
int ack = i2c_get_ack();
|
||||
uint8_t* end = data + size;
|
||||
for(; data != end; ++data) {
|
||||
i2c_set_sda(1);
|
||||
pinMode(ESP_PINS_OFFSET + s_sda_pin, INPUT);
|
||||
*data = i2c_read();
|
||||
pinMode(ESP_PINS_OFFSET + s_sda_pin, OUTPUT_OPEN_DRAIN);
|
||||
if(data == end - 1)
|
||||
i2c_set_ack(0);
|
||||
else
|
||||
i2c_set_ack(1);
|
||||
}
|
||||
if(sendStop)
|
||||
i2c_stop();
|
||||
return size;
|
||||
}
|
||||
|
||||
size_t i2c_master_write_to(int address, const uint8_t* data, size_t size, bool sendStop)
|
||||
{
|
||||
i2c_start();
|
||||
i2c_write(address << 1);
|
||||
int ack = i2c_get_ack();
|
||||
const uint8_t* end = data + size;
|
||||
for (;data != end; ++data )
|
||||
{
|
||||
i2c_write(*data);
|
||||
ack = i2c_get_ack();
|
||||
}
|
||||
if (sendStop)
|
||||
i2c_stop();
|
||||
return size;
|
||||
size_t i2c_master_write_to(int address, const uint8_t* data, size_t size, bool sendStop) {
|
||||
i2c_start();
|
||||
i2c_write(address << 1);
|
||||
int ack = i2c_get_ack();
|
||||
const uint8_t* end = data + size;
|
||||
for(; data != end; ++data) {
|
||||
i2c_write(*data);
|
||||
ack = i2c_get_ack();
|
||||
}
|
||||
if(sendStop)
|
||||
i2c_stop();
|
||||
return size;
|
||||
}
|
||||
|
||||
// some stubs for libraries that use private twi.h interface
|
||||
extern "C"
|
||||
{
|
||||
void twi_init(void) { }
|
||||
|
||||
void twi_setAddress(uint8_t) { }
|
||||
|
||||
uint8_t twi_readFrom(uint8_t addr, uint8_t* data, uint8_t size, uint8_t sendStop)
|
||||
{
|
||||
return i2c_master_read_from(addr, data, size, sendStop);
|
||||
}
|
||||
|
||||
uint8_t twi_writeTo(uint8_t addr, uint8_t* data, uint8_t size, uint8_t wait, uint8_t sendStop)
|
||||
{
|
||||
return i2c_master_write_to(addr, data, size, sendStop);
|
||||
}
|
||||
|
||||
uint8_t twi_transmit(const uint8_t* data, uint8_t length)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
|
||||
void twi_attachSlaveRxEvent( void (*)(uint8_t*, int) ) { }
|
||||
void twi_attachSlaveTxEvent( void (*)(void) ) { }
|
||||
void twi_reply(uint8_t) { }
|
||||
void twi_stop(void)
|
||||
{
|
||||
i2c_stop();
|
||||
}
|
||||
|
||||
void twi_releaseBus(void)
|
||||
{
|
||||
i2c_set(1, 1);
|
||||
}
|
||||
extern "C" {
|
||||
void twi_init(void) {
|
||||
}
|
||||
|
||||
void twi_setAddress(uint8_t) {
|
||||
}
|
||||
|
||||
uint8_t twi_readFrom(uint8_t addr, uint8_t* data, uint8_t size, uint8_t sendStop) {
|
||||
return i2c_master_read_from(addr, data, size, sendStop);
|
||||
}
|
||||
|
||||
uint8_t twi_writeTo(uint8_t addr, uint8_t* data, uint8_t size, uint8_t wait, uint8_t sendStop) {
|
||||
return i2c_master_write_to(addr, data, size, sendStop);
|
||||
}
|
||||
|
||||
uint8_t twi_transmit(const uint8_t* data, uint8_t length) {
|
||||
|
||||
}
|
||||
|
||||
void twi_attachSlaveRxEvent(void (*)(uint8_t*, int)) {
|
||||
}
|
||||
void twi_attachSlaveTxEvent(void (*)(void)) {
|
||||
}
|
||||
void twi_reply(uint8_t) {
|
||||
}
|
||||
void twi_stop(void) {
|
||||
i2c_stop();
|
||||
}
|
||||
|
||||
void twi_releaseBus(void) {
|
||||
i2c_set(1, 1);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1,23 +1,23 @@
|
||||
/*
|
||||
i2c.h - esp8266 i2c bit-banging library
|
||||
i2c.h - esp8266 i2c bit-banging library
|
||||
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef I2C_H
|
||||
#define I2C_H
|
||||
@ -34,7 +34,6 @@ int i2c_get_ack();
|
||||
uint8_t i2c_read(void);
|
||||
void i2c_write(uint8_t val);
|
||||
|
||||
|
||||
size_t i2c_master_read_from(int address, uint8_t* data, size_t size, bool sendStop);
|
||||
size_t i2c_master_write_to(int address, const uint8_t* data, size_t size, bool sendStop);
|
||||
|
||||
|
@ -36,292 +36,289 @@
|
||||
#include "mem.h"
|
||||
#include "user_interface.h"
|
||||
|
||||
|
||||
void* malloc(size_t size) {
|
||||
return os_malloc(size);
|
||||
return os_malloc(size);
|
||||
}
|
||||
|
||||
void free(void* ptr) {
|
||||
os_free(ptr);
|
||||
os_free(ptr);
|
||||
}
|
||||
|
||||
void* realloc(void* ptr, size_t size) {
|
||||
return os_realloc(ptr, size);
|
||||
return os_realloc(ptr, size);
|
||||
}
|
||||
|
||||
int puts(const char * str){
|
||||
return os_printf("%s", str);
|
||||
int puts(const char * str) {
|
||||
return os_printf("%s", str);
|
||||
}
|
||||
|
||||
int printf(const char* format, ...) {
|
||||
int ret;
|
||||
va_list arglist;
|
||||
va_start(arglist, format);
|
||||
ret = ets_vprintf(format, arglist);
|
||||
va_end(arglist);
|
||||
return ret;
|
||||
int ret;
|
||||
va_list arglist;
|
||||
va_start(arglist, format);
|
||||
ret = ets_vprintf(format, arglist);
|
||||
va_end(arglist);
|
||||
return ret;
|
||||
}
|
||||
|
||||
int sprintf(char* buffer, const char* format, ...) {
|
||||
int ret;
|
||||
va_list arglist;
|
||||
va_start(arglist, format);
|
||||
ret = ets_vsprintf(buffer, format, arglist);
|
||||
va_end(arglist);
|
||||
return ret;
|
||||
int ret;
|
||||
va_list arglist;
|
||||
va_start(arglist, format);
|
||||
ret = ets_vsprintf(buffer, format, arglist);
|
||||
va_end(arglist);
|
||||
return ret;
|
||||
}
|
||||
|
||||
int snprintf(char* buffer, size_t size, const char* format, ...) {
|
||||
int ret;
|
||||
va_list arglist;
|
||||
va_start(arglist, format);
|
||||
ret = ets_vsnprintf(buffer, size, format, arglist);
|
||||
va_end(arglist);
|
||||
return ret;
|
||||
int ret;
|
||||
va_list arglist;
|
||||
va_start(arglist, format);
|
||||
ret = ets_vsnprintf(buffer, size, format, arglist);
|
||||
va_end(arglist);
|
||||
return ret;
|
||||
}
|
||||
|
||||
int vsnprintf(char * buffer, size_t size, const char * format, va_list arg) {
|
||||
return ets_vsnprintf(buffer, size, format, arg);
|
||||
return ets_vsnprintf(buffer, size, format, arg);
|
||||
}
|
||||
|
||||
int memcmp(const void *s1, const void *s2, size_t n) {
|
||||
return ets_memcmp(s1, s2, n);
|
||||
return ets_memcmp(s1, s2, n);
|
||||
}
|
||||
|
||||
void* memcpy(void *dest, const void *src, size_t n) {
|
||||
return ets_memcpy(dest, src, n);
|
||||
return ets_memcpy(dest, src, n);
|
||||
}
|
||||
|
||||
void* memset(void *s, int c, size_t n) {
|
||||
return ets_memset(s, c, n);
|
||||
return ets_memset(s, c, n);
|
||||
}
|
||||
|
||||
int strcmp(const char *s1, const char *s2) {
|
||||
return ets_strcmp(s1, s2);
|
||||
return ets_strcmp(s1, s2);
|
||||
}
|
||||
|
||||
char* strcpy(char *dest, const char *src) {
|
||||
return ets_strcpy(dest, src);
|
||||
return ets_strcpy(dest, src);
|
||||
}
|
||||
|
||||
size_t strlen(const char *s) {
|
||||
return ets_strlen(s);
|
||||
return ets_strlen(s);
|
||||
}
|
||||
|
||||
int strncmp(const char *s1, const char *s2, size_t len) {
|
||||
return ets_strncmp(s1, s2, len);
|
||||
return ets_strncmp(s1, s2, len);
|
||||
}
|
||||
|
||||
char *strncpy(char * dest, const char * src, size_t n) {
|
||||
return ets_strncpy(dest, src, n);
|
||||
return ets_strncpy(dest, src, n);
|
||||
}
|
||||
|
||||
char *ets_strstr(const char *haystack, const char *needle) {
|
||||
return strstr(haystack, needle);
|
||||
return strstr(haystack, needle);
|
||||
}
|
||||
|
||||
char * strchr(const char * str, int character) {
|
||||
while(1) {
|
||||
if(*str == 0x00) {
|
||||
return NULL;
|
||||
}
|
||||
if(*str == (char) character) {
|
||||
return (char *) str;
|
||||
}
|
||||
str++;
|
||||
}
|
||||
while(1) {
|
||||
if(*str == 0x00) {
|
||||
return NULL;
|
||||
}
|
||||
if(*str == (char) character) {
|
||||
return (char *) str;
|
||||
}
|
||||
str++;
|
||||
}
|
||||
}
|
||||
|
||||
char * strrchr(const char * str, int character) {
|
||||
char * ret = NULL;
|
||||
while(1) {
|
||||
if(*str == 0x00) {
|
||||
return ret;
|
||||
}
|
||||
if(*str == (char) character) {
|
||||
ret = (char *) str;
|
||||
}
|
||||
str++;
|
||||
}
|
||||
char * ret = NULL;
|
||||
while(1) {
|
||||
if(*str == 0x00) {
|
||||
return ret;
|
||||
}
|
||||
if(*str == (char) character) {
|
||||
ret = (char *) str;
|
||||
}
|
||||
str++;
|
||||
}
|
||||
}
|
||||
|
||||
char * strcat(char * dest, const char * src) {
|
||||
return strncat(dest, src, strlen(src));
|
||||
return strncat(dest, src, strlen(src));
|
||||
}
|
||||
|
||||
char * strncat(char * dest, const char * src, size_t n) {
|
||||
uint32_t offset = strlen(dest);
|
||||
for(uint32_t i = 0; i < n; i++) {
|
||||
*(dest + i + offset) = *(src + i);
|
||||
if(*(src + i) == 0x00) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
return dest;
|
||||
uint32_t offset = strlen(dest);
|
||||
for(uint32_t i = 0; i < n; i++) {
|
||||
*(dest + i + offset) = *(src + i);
|
||||
if(*(src + i) == 0x00) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
return dest;
|
||||
}
|
||||
|
||||
char * strtok_r(char * str, const char * delimiters, char ** temp) {
|
||||
static char * ret = NULL;
|
||||
char * start = NULL;
|
||||
char * end = NULL;
|
||||
uint32_t size = 0;
|
||||
static char * ret = NULL;
|
||||
char * start = NULL;
|
||||
char * end = NULL;
|
||||
uint32_t size = 0;
|
||||
|
||||
if(str == NULL) {
|
||||
start = *temp;
|
||||
} else {
|
||||
start = str;
|
||||
}
|
||||
if(str == NULL) {
|
||||
start = *temp;
|
||||
} else {
|
||||
start = str;
|
||||
}
|
||||
|
||||
if(start == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
if(start == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
end = start;
|
||||
end = start;
|
||||
|
||||
while(1) {
|
||||
for(uint16_t i = 0; i < strlen(delimiters); i++) {
|
||||
if(*end == *(delimiters + i)) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
end++;
|
||||
if(*end == 0x00) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
while(1) {
|
||||
for(uint16_t i = 0; i < strlen(delimiters); i++) {
|
||||
if(*end == *(delimiters + i)) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
end++;
|
||||
if(*end == 0x00) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
*temp = end;
|
||||
*temp = end;
|
||||
|
||||
if(ret != NULL) {
|
||||
free(ret);
|
||||
}
|
||||
if(ret != NULL) {
|
||||
free(ret);
|
||||
}
|
||||
|
||||
size = (end - start);
|
||||
ret = (char *) malloc(size);
|
||||
strncpy(ret, start, size);
|
||||
return ret;
|
||||
size = (end - start);
|
||||
ret = (char *) malloc(size);
|
||||
strncpy(ret, start, size);
|
||||
return ret;
|
||||
}
|
||||
|
||||
int strcasecmp(const char * str1, const char * str2) {
|
||||
int d = 0;
|
||||
while(1) {
|
||||
int c1 = tolower(*str1++);
|
||||
int c2 = tolower(*str2++);
|
||||
if(((d = c1 - c2) != 0) || (c2 == '\0')) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
return d;
|
||||
int d = 0;
|
||||
while(1) {
|
||||
int c1 = tolower(*str1++);
|
||||
int c2 = tolower(*str2++);
|
||||
if(((d = c1 - c2) != 0) || (c2 == '\0')) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
return d;
|
||||
}
|
||||
|
||||
char * strdup(const char *str) {
|
||||
size_t len = strlen(str) + 1;
|
||||
char *cstr = malloc(len);
|
||||
if(cstr) {
|
||||
memcpy(cstr, str, len);
|
||||
}
|
||||
return cstr;
|
||||
size_t len = strlen(str) + 1;
|
||||
char *cstr = malloc(len);
|
||||
if(cstr) {
|
||||
memcpy(cstr, str, len);
|
||||
}
|
||||
return cstr;
|
||||
}
|
||||
|
||||
|
||||
long int ICACHE_FLASH_ATTR strtol(const char* str, char** endptr, int base) {
|
||||
long int result = 0;
|
||||
int sign = 1;
|
||||
long int result = 0;
|
||||
int sign = 1;
|
||||
|
||||
while(isspace(*str)) {
|
||||
str++;
|
||||
}
|
||||
while(isspace(*str)) {
|
||||
str++;
|
||||
}
|
||||
|
||||
if(*str == 0x00) {
|
||||
// only space in str?
|
||||
*endptr = (char*) str;
|
||||
return result;
|
||||
}
|
||||
if(*str == 0x00) {
|
||||
// only space in str?
|
||||
*endptr = (char*) str;
|
||||
return result;
|
||||
}
|
||||
|
||||
switch(base) {
|
||||
case 10:
|
||||
switch(base) {
|
||||
case 10:
|
||||
|
||||
if(*str == '-') {
|
||||
sign = -1;
|
||||
str++;
|
||||
} else if(*str == '+') {
|
||||
str++;
|
||||
}
|
||||
if(*str == '-') {
|
||||
sign = -1;
|
||||
str++;
|
||||
} else if(*str == '+') {
|
||||
str++;
|
||||
}
|
||||
|
||||
for(uint8_t i = 0; *str; i++, str++) {
|
||||
int x = *str - '0';
|
||||
if(x < 0 || x > 9) {
|
||||
break;
|
||||
}
|
||||
result = result * 10 + x;
|
||||
}
|
||||
break;
|
||||
case 2:
|
||||
for(uint8_t i = 0; *str; i++, str++) {
|
||||
int x = *str - '0';
|
||||
if(x < 0 || x > 1) {
|
||||
break;
|
||||
}
|
||||
result = result * 2 + x;
|
||||
}
|
||||
break;
|
||||
case 16:
|
||||
default:
|
||||
os_printf("fnk: strtol() only supports base 10 and 2 ATM!\n");
|
||||
break;
|
||||
for(uint8_t i = 0; *str; i++, str++) {
|
||||
int x = *str - '0';
|
||||
if(x < 0 || x > 9) {
|
||||
break;
|
||||
}
|
||||
result = result * 10 + x;
|
||||
}
|
||||
break;
|
||||
case 2:
|
||||
for(uint8_t i = 0; *str; i++, str++) {
|
||||
int x = *str - '0';
|
||||
if(x < 0 || x > 1) {
|
||||
break;
|
||||
}
|
||||
result = result * 2 + x;
|
||||
}
|
||||
break;
|
||||
case 16:
|
||||
default:
|
||||
os_printf("fnk: strtol() only supports base 10 and 2 ATM!\n");
|
||||
break;
|
||||
|
||||
}
|
||||
*endptr = (char*) str;
|
||||
return sign * result;
|
||||
}
|
||||
*endptr = (char*) str;
|
||||
return sign * result;
|
||||
}
|
||||
|
||||
|
||||
// based on Source:
|
||||
// https://github.com/anakod/Sming/blob/master/Sming/system/stringconversion.cpp#L93
|
||||
double ICACHE_FLASH_ATTR strtod(const char* str, char** endptr) {
|
||||
double result = 0.0;
|
||||
double factor = 1.0;
|
||||
bool decimals = false;
|
||||
char c;
|
||||
double result = 0.0;
|
||||
double factor = 1.0;
|
||||
bool decimals = false;
|
||||
char c;
|
||||
|
||||
while(isspace(*str)) {
|
||||
str++;
|
||||
}
|
||||
while(isspace(*str)) {
|
||||
str++;
|
||||
}
|
||||
|
||||
if(*str == 0x00) {
|
||||
// only space in str?
|
||||
*endptr = (char*) str;
|
||||
return result;
|
||||
}
|
||||
if(*str == 0x00) {
|
||||
// only space in str?
|
||||
*endptr = (char*) str;
|
||||
return result;
|
||||
}
|
||||
|
||||
if(*str == '-') {
|
||||
factor = -1;
|
||||
str++;
|
||||
} else if(*str == '+') {
|
||||
str++;
|
||||
}
|
||||
if(*str == '-') {
|
||||
factor = -1;
|
||||
str++;
|
||||
} else if(*str == '+') {
|
||||
str++;
|
||||
}
|
||||
|
||||
while((c = *str)) {
|
||||
if(c == '.') {
|
||||
decimals = true;
|
||||
str++;
|
||||
continue;
|
||||
}
|
||||
while((c = *str)) {
|
||||
if(c == '.') {
|
||||
decimals = true;
|
||||
str++;
|
||||
continue;
|
||||
}
|
||||
|
||||
int d = c - '0';
|
||||
if(d < 0 || d > 9) {
|
||||
break;
|
||||
}
|
||||
int d = c - '0';
|
||||
if(d < 0 || d > 9) {
|
||||
break;
|
||||
}
|
||||
|
||||
result = 10.0 * result + d;
|
||||
if(decimals) {
|
||||
factor *= 0.1;
|
||||
}
|
||||
result = 10.0 * result + d;
|
||||
if(decimals) {
|
||||
factor *= 0.1;
|
||||
}
|
||||
|
||||
str++;
|
||||
}
|
||||
*endptr = (char*) str;
|
||||
return result * factor;
|
||||
str++;
|
||||
}
|
||||
*endptr = (char*) str;
|
||||
return result * factor;
|
||||
}
|
||||
|
||||
// ##########################################################################
|
||||
@ -329,115 +326,115 @@ double ICACHE_FLASH_ATTR strtod(const char* str, char** endptr) {
|
||||
// ##########################################################################
|
||||
|
||||
int isalnum(int c) {
|
||||
if(isalpha(c) || isdigit(c)) {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
if(isalpha(c) || isdigit(c)) {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int isalpha(int c) {
|
||||
if(islower(c) || isupper(c)) {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
if(islower(c) || isupper(c)) {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int iscntrl(int c) {
|
||||
if(c <= 0x1F || c == 0x7F) {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
if(c <= 0x1F || c == 0x7F) {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int isdigit(int c) {
|
||||
if(c >= '0' && c <= '9') {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
if(c >= '0' && c <= '9') {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int isgraph(int c) {
|
||||
if(isprint(c) && c != ' ') {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
if(isprint(c) && c != ' ') {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int islower(int c) {
|
||||
if(c >= 'a' && c <= 'z') {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
if(c >= 'a' && c <= 'z') {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int isprint(int c) {
|
||||
if(!iscntrl(c)) {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
if(!iscntrl(c)) {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int ispunct(int c) {
|
||||
if(isgraph(c) && !isalnum(c)) {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
if(isgraph(c) && !isalnum(c)) {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int isspace(int c) {
|
||||
switch(c) {
|
||||
case 0x20: // ' '
|
||||
case 0x09: // '\t'
|
||||
case 0x0a: // '\n'
|
||||
case 0x0b: // '\v'
|
||||
case 0x0c: // '\f'
|
||||
case 0x0d: // '\r'
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
switch(c) {
|
||||
case 0x20: // ' '
|
||||
case 0x09: // '\t'
|
||||
case 0x0a: // '\n'
|
||||
case 0x0b: // '\v'
|
||||
case 0x0c: // '\f'
|
||||
case 0x0d: // '\r'
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int isupper(int c) {
|
||||
if(c >= 'A' && c <= 'Z') {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
if(c >= 'A' && c <= 'Z') {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int isxdigit(int c) {
|
||||
if(c >= 'A' && c <= 'F') {
|
||||
return 1;
|
||||
}
|
||||
if(c >= 'a' && c <= 'f') {
|
||||
return 1;
|
||||
}
|
||||
if(isdigit(c)) {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
if(c >= 'A' && c <= 'F') {
|
||||
return 1;
|
||||
}
|
||||
if(c >= 'a' && c <= 'f') {
|
||||
return 1;
|
||||
}
|
||||
if(isdigit(c)) {
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int tolower(int c) {
|
||||
if(isupper(c)) {
|
||||
c += 0x20;
|
||||
}
|
||||
return c;
|
||||
if(isupper(c)) {
|
||||
c += 0x20;
|
||||
}
|
||||
return c;
|
||||
}
|
||||
|
||||
int toupper(int c) {
|
||||
if(islower(c)) {
|
||||
c -= 0x20;
|
||||
}
|
||||
return c;
|
||||
if(islower(c)) {
|
||||
c -= 0x20;
|
||||
}
|
||||
return c;
|
||||
}
|
||||
|
||||
int isblank(int c) {
|
||||
switch(c) {
|
||||
case 0x20: // ' '
|
||||
case 0x09: // '\t'
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
switch(c) {
|
||||
case 0x20: // ' '
|
||||
case 0x09: // '\t'
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
// ##########################################################################
|
||||
@ -445,8 +442,8 @@ int isblank(int c) {
|
||||
static int errno_var = 0;
|
||||
|
||||
int * __errno(void) {
|
||||
os_printf("__errno is called last error: %d (not current)\n", errno_var);
|
||||
return &errno_var;
|
||||
os_printf("__errno is called last error: %d (not current)\n", errno_var);
|
||||
return &errno_var;
|
||||
}
|
||||
|
||||
// ##########################################################################
|
||||
@ -454,66 +451,66 @@ int * __errno(void) {
|
||||
// ##########################################################################
|
||||
|
||||
double __ieee754_sinh(double x) {
|
||||
return sinh(x);
|
||||
return sinh(x);
|
||||
}
|
||||
|
||||
double __ieee754_hypot(double x, double y) {
|
||||
return hypot(x, y);
|
||||
return hypot(x, y);
|
||||
}
|
||||
|
||||
float __ieee754_hypotf(float x, float y) {
|
||||
return hypotf(x, y);
|
||||
return hypotf(x, y);
|
||||
}
|
||||
|
||||
float __ieee754_logf(float x) {
|
||||
return logf(x);
|
||||
return logf(x);
|
||||
}
|
||||
|
||||
double __ieee754_log10(double x) {
|
||||
return log10(x);
|
||||
return log10(x);
|
||||
}
|
||||
|
||||
double __ieee754_exp(double x) {
|
||||
return exp(x);
|
||||
return exp(x);
|
||||
}
|
||||
|
||||
double __ieee754_cosh(double x) {
|
||||
return cosh(x);
|
||||
return cosh(x);
|
||||
}
|
||||
|
||||
float __ieee754_expf(float x) {
|
||||
return expf(x);
|
||||
return expf(x);
|
||||
}
|
||||
|
||||
float __ieee754_log10f(float x) {
|
||||
return log10f(x);
|
||||
return log10f(x);
|
||||
}
|
||||
|
||||
double __ieee754_atan2(double x, double y) {
|
||||
return atan2(x, y);
|
||||
return atan2(x, y);
|
||||
}
|
||||
|
||||
float __ieee754_sqrtf(float x) {
|
||||
return sqrtf(x);
|
||||
return sqrtf(x);
|
||||
}
|
||||
|
||||
float __ieee754_sinhf(float x) {
|
||||
return sinhf(x);
|
||||
return sinhf(x);
|
||||
}
|
||||
|
||||
double __ieee754_log(double x) {
|
||||
return log(x);
|
||||
return log(x);
|
||||
}
|
||||
|
||||
double __ieee754_sqrt(double x) {
|
||||
return sqrt(x);
|
||||
return sqrt(x);
|
||||
}
|
||||
|
||||
float __ieee754_coshf(float x) {
|
||||
return coshf(x);
|
||||
return coshf(x);
|
||||
}
|
||||
|
||||
float __ieee754_atan2f(float x, float y) {
|
||||
return atan2f(x, y);
|
||||
return atan2f(x, y);
|
||||
}
|
||||
|
||||
|
@ -6,22 +6,21 @@
|
||||
#define PROGMEM
|
||||
#define PGM_P const char *
|
||||
#define PSTR(str) (str)
|
||||
#define F(str) (str)
|
||||
|
||||
#define vsnprintf_P(...) vsnprintf( __VA_ARGS__ )
|
||||
#define snprintf_P(...) snprintf( __VA_ARGS__ )
|
||||
|
||||
#define _SFR_BYTE(n) (n)
|
||||
|
||||
typedef void prog_void;
|
||||
typedef char prog_char;
|
||||
typedef unsigned char prog_uchar;
|
||||
typedef int8_t prog_int8_t;
|
||||
typedef uint8_t prog_uint8_t;
|
||||
typedef int16_t prog_int16_t;
|
||||
typedef uint16_t prog_uint16_t;
|
||||
typedef int32_t prog_int32_t;
|
||||
typedef uint32_t prog_uint32_t;
|
||||
typedef void prog_void;
|
||||
typedef char prog_char;
|
||||
typedef unsigned char prog_uchar;
|
||||
typedef int8_t prog_int8_t;
|
||||
typedef uint8_t prog_uint8_t;
|
||||
typedef int16_t prog_int16_t;
|
||||
typedef uint16_t prog_uint16_t;
|
||||
typedef int32_t prog_int32_t;
|
||||
typedef uint32_t prog_uint32_t;
|
||||
|
||||
#define memcpy_P(dest, src, num) memcpy((dest), (src), (num))
|
||||
#define strcpy_P(dest, src) strcpy((dest), (src))
|
||||
|
@ -1,23 +1,23 @@
|
||||
/*
|
||||
sigma_delta.h - esp8266 sigma-delta source
|
||||
sigma_delta.h - esp8266 sigma-delta source
|
||||
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
|
||||
#ifndef SIGMA_DELTA_H
|
||||
#define SIGMA_DELTA_H
|
||||
|
@ -1,26 +1,26 @@
|
||||
/*
|
||||
wiring_private.h - Internal header file.
|
||||
Part of Arduino - http://www.arduino.cc/
|
||||
wiring_private.h - Internal header file.
|
||||
Part of Arduino - http://www.arduino.cc/
|
||||
|
||||
Copyright (c) 2005-2006 David A. Mellis
|
||||
Copyright (c) 2005-2006 David A. Mellis
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General
|
||||
Public License along with this library; if not, write to the
|
||||
Free Software Foundation, Inc., 59 Temple Place, Suite 330,
|
||||
Boston, MA 02111-1307 USA
|
||||
You should have received a copy of the GNU Lesser General
|
||||
Public License along with this library; if not, write to the
|
||||
Free Software Foundation, Inc., 59 Temple Place, Suite 330,
|
||||
Boston, MA 02111-1307 USA
|
||||
|
||||
$Id: wiring.h 239 2007-01-12 17:58:39Z mellis $
|
||||
*/
|
||||
$Id: wiring.h 239 2007-01-12 17:58:39Z mellis $
|
||||
*/
|
||||
|
||||
#ifndef WiringPrivate_h
|
||||
#define WiringPrivate_h
|
||||
@ -31,7 +31,7 @@
|
||||
#include "Arduino.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C"{
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
typedef void (*voidFuncPtr)(void);
|
||||
|
@ -1,360 +1,301 @@
|
||||
/*
|
||||
ClientContext.h - TCP connection handling on top of lwIP
|
||||
ClientContext.h - TCP connection handling on top of lwIP
|
||||
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
Copyright (c) 2014 Ivan Grokhotkov. All rights reserved.
|
||||
This file is part of the esp8266 core for Arduino environment.
|
||||
|
||||
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 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.
|
||||
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.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with this library; if not, write to the Free Software
|
||||
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*/
|
||||
#ifndef CLIENTCONTEXT_H
|
||||
#define CLIENTCONTEXT_H
|
||||
|
||||
class ClientContext;
|
||||
class WiFiClient;
|
||||
|
||||
typedef void(*discard_cb_t)(void*, ClientContext*);
|
||||
typedef void (*discard_cb_t)(void*, ClientContext*);
|
||||
|
||||
extern "C" void esp_yield();
|
||||
extern "C" void esp_schedule();
|
||||
|
||||
class ClientContext {
|
||||
public:
|
||||
ClientContext(tcp_pcb* pcb, discard_cb_t discard_cb, void* discard_cb_arg) :
|
||||
_pcb(pcb), _rx_buf(0), _rx_buf_offset(0), _discard_cb(discard_cb), _discard_cb_arg(discard_cb_arg), _refcnt(0), _next(0), _send_waiting(false) {
|
||||
tcp_setprio(pcb, TCP_PRIO_MIN);
|
||||
tcp_arg(pcb, this);
|
||||
tcp_recv(pcb, &_s_recv);
|
||||
tcp_sent(pcb, &_s_sent);
|
||||
tcp_err(pcb, &_s_error);
|
||||
}
|
||||
|
||||
class ClientContext
|
||||
{
|
||||
public:
|
||||
ClientContext(tcp_pcb* pcb,
|
||||
discard_cb_t discard_cb, void* discard_cb_arg)
|
||||
: _pcb(pcb)
|
||||
, _rx_buf(0)
|
||||
, _rx_buf_offset(0)
|
||||
, _discard_cb(discard_cb)
|
||||
, _discard_cb_arg(discard_cb_arg)
|
||||
, _refcnt(0)
|
||||
, _next(0)
|
||||
, _send_waiting(false)
|
||||
{
|
||||
tcp_setprio(pcb, TCP_PRIO_MIN);
|
||||
tcp_arg(pcb, this);
|
||||
tcp_recv(pcb, &_s_recv);
|
||||
tcp_sent(pcb, &_s_sent);
|
||||
tcp_err(pcb, &_s_error);
|
||||
}
|
||||
~ClientContext() {
|
||||
}
|
||||
|
||||
~ClientContext()
|
||||
{
|
||||
}
|
||||
ClientContext* next() const {
|
||||
return _next;
|
||||
}
|
||||
|
||||
ClientContext* next() const
|
||||
{
|
||||
return _next;
|
||||
}
|
||||
ClientContext* next(ClientContext* new_next) {
|
||||
_next = new_next;
|
||||
}
|
||||
|
||||
ClientContext* next(ClientContext* new_next)
|
||||
{
|
||||
_next = new_next;
|
||||
}
|
||||
void ref() {
|
||||
++_refcnt;
|
||||
DEBUGV(":ref %d\r\n", _refcnt);
|
||||
}
|
||||
|
||||
void ref()
|
||||
{
|
||||
++_refcnt;
|
||||
DEBUGV(":ref %d\r\n", _refcnt);
|
||||
}
|
||||
void unref() {
|
||||
err_t err;
|
||||
DEBUGV(":ur %d\r\n", _refcnt);
|
||||
if(--_refcnt == 0) {
|
||||
flush();
|
||||
if(_pcb) {
|
||||
tcp_arg(_pcb, NULL);
|
||||
tcp_sent(_pcb, NULL);
|
||||
tcp_recv(_pcb, NULL);
|
||||
tcp_err(_pcb, NULL);
|
||||
err = tcp_close(_pcb);
|
||||
if(err != ERR_OK) {
|
||||
DEBUGV(":tc err %d\r\n", err);
|
||||
tcp_abort(_pcb);
|
||||
}
|
||||
_pcb = 0;
|
||||
}
|
||||
delete this;
|
||||
}
|
||||
}
|
||||
|
||||
void unref()
|
||||
{
|
||||
err_t err;
|
||||
DEBUGV(":ur %d\r\n", _refcnt);
|
||||
if (--_refcnt == 0)
|
||||
{
|
||||
flush();
|
||||
if (_pcb)
|
||||
uint32_t getRemoteAddress() {
|
||||
if(!_pcb) return 0;
|
||||
|
||||
return _pcb->remote_ip.addr;
|
||||
}
|
||||
|
||||
uint16_t getRemotePort() {
|
||||
if(!_pcb) return 0;
|
||||
|
||||
return _pcb->remote_port;
|
||||
}
|
||||
|
||||
size_t getSize() const {
|
||||
if(!_rx_buf) return 0;
|
||||
|
||||
return _rx_buf->tot_len - _rx_buf_offset;
|
||||
}
|
||||
|
||||
char read() {
|
||||
if(!_rx_buf) return 0;
|
||||
|
||||
char c = reinterpret_cast<char*>(_rx_buf->payload)[_rx_buf_offset];
|
||||
_consume(1);
|
||||
return c;
|
||||
}
|
||||
|
||||
size_t read(char* dst, size_t size) {
|
||||
if(!_rx_buf) return 0;
|
||||
|
||||
size_t max_size = _rx_buf->tot_len - _rx_buf_offset;
|
||||
size = (size < max_size) ? size : max_size;
|
||||
|
||||
DEBUGV(":rd %d, %d, %d\r\n", size, _rx_buf->tot_len, _rx_buf_offset);
|
||||
size_t size_read = 0;
|
||||
while(size) {
|
||||
size_t buf_size = _rx_buf->len - _rx_buf_offset;
|
||||
size_t copy_size = (size < buf_size) ? size : buf_size;
|
||||
DEBUGV(":rdi %d, %d\r\n", buf_size, copy_size);
|
||||
os_memcpy(dst, reinterpret_cast<char*>(_rx_buf->payload) + _rx_buf_offset, copy_size);
|
||||
dst += copy_size;
|
||||
_consume(copy_size);
|
||||
size -= copy_size;
|
||||
size_read += copy_size;
|
||||
}
|
||||
return size_read;
|
||||
}
|
||||
|
||||
char peek() {
|
||||
if(!_rx_buf) return 0;
|
||||
|
||||
return reinterpret_cast<char*>(_rx_buf->payload)[_rx_buf_offset];
|
||||
}
|
||||
|
||||
void flush() {
|
||||
if(!_rx_buf) {
|
||||
return;
|
||||
}
|
||||
if(_pcb) {
|
||||
tcp_recved(_pcb, (size_t) _rx_buf->tot_len);
|
||||
}
|
||||
pbuf_free(_rx_buf);
|
||||
_rx_buf = 0;
|
||||
_rx_buf_offset = 0;
|
||||
}
|
||||
|
||||
uint8_t state() const {
|
||||
if(!_pcb) return CLOSED;
|
||||
|
||||
return _pcb->state;
|
||||
}
|
||||
|
||||
size_t write(const char* data, size_t size) {
|
||||
if(!_pcb) {
|
||||
DEBUGV(":wr !_pcb\r\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(size == 0) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
size_t room = tcp_sndbuf(_pcb);
|
||||
size_t will_send = (room < size) ? room : size;
|
||||
err_t err = tcp_write(_pcb, data, will_send, 0);
|
||||
if(err != ERR_OK) {
|
||||
DEBUGV(":wr !ERR_OK\r\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
_size_sent = will_send;
|
||||
DEBUGV(":wr\r\n");
|
||||
_send_waiting = true;
|
||||
delay(5000); // max send timeout
|
||||
_send_waiting = false;
|
||||
DEBUGV(":ww\r\n");
|
||||
return will_send - _size_sent;
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
void _consume(size_t size) {
|
||||
ptrdiff_t left = _rx_buf->len - _rx_buf_offset - size;
|
||||
if(left > 0) {
|
||||
_rx_buf_offset += size;
|
||||
} else if(!_rx_buf->next) {
|
||||
DEBUGV(":c0 %d, %d\r\n", size, _rx_buf->tot_len);
|
||||
if(_pcb) tcp_recved(_pcb, _rx_buf->len);
|
||||
pbuf_free(_rx_buf);
|
||||
_rx_buf = 0;
|
||||
_rx_buf_offset = 0;
|
||||
} else {
|
||||
DEBUGV(":c %d, %d, %d\r\n", size, _rx_buf->len, _rx_buf->tot_len);
|
||||
auto head = _rx_buf;
|
||||
_rx_buf = _rx_buf->next;
|
||||
_rx_buf_offset = 0;
|
||||
pbuf_ref(_rx_buf);
|
||||
if(_pcb) tcp_recved(_pcb, head->len);
|
||||
pbuf_free(head);
|
||||
}
|
||||
}
|
||||
|
||||
err_t _recv(tcp_pcb* pcb, pbuf* pb, err_t err) {
|
||||
|
||||
if(pb == 0) // connection closed
|
||||
{
|
||||
DEBUGV(":rcl\r\n");
|
||||
tcp_arg(pcb, NULL);
|
||||
tcp_sent(pcb, NULL);
|
||||
tcp_recv(pcb, NULL);
|
||||
tcp_err(pcb, NULL);
|
||||
// int error = tcp_close(pcb);
|
||||
// if (error != ERR_OK)
|
||||
{
|
||||
DEBUGV(":rcla\r\n");
|
||||
tcp_abort(pcb);
|
||||
_pcb = 0;
|
||||
return ERR_ABRT;
|
||||
}
|
||||
_pcb = 0;
|
||||
return ERR_OK;
|
||||
}
|
||||
|
||||
if(_rx_buf) {
|
||||
// there is some unread data
|
||||
// chain the new pbuf to the existing one
|
||||
DEBUGV(":rch %d, %d\r\n", _rx_buf->tot_len, pb->tot_len);
|
||||
pbuf_cat(_rx_buf, pb);
|
||||
} else {
|
||||
DEBUGV(":rn %d\r\n", pb->tot_len);
|
||||
_rx_buf = pb;
|
||||
_rx_buf_offset = 0;
|
||||
}
|
||||
// tcp_recved(pcb, received);
|
||||
// pbuf_free(pb);
|
||||
return ERR_OK;
|
||||
}
|
||||
|
||||
void _error(err_t err) {
|
||||
DEBUGV(":er %d\r\n", err);
|
||||
|
||||
if(_pcb) {
|
||||
tcp_arg(_pcb, NULL);
|
||||
tcp_sent(_pcb, NULL);
|
||||
tcp_recv(_pcb, NULL);
|
||||
tcp_err(_pcb, NULL);
|
||||
err = tcp_close(_pcb);
|
||||
if(err != ERR_OK) {
|
||||
DEBUGV(":tc err %d\r\n", err);
|
||||
tcp_abort(_pcb);
|
||||
}
|
||||
_pcb = 0;
|
||||
}
|
||||
delete this;
|
||||
}
|
||||
}
|
||||
|
||||
uint32_t getRemoteAddress()
|
||||
{
|
||||
if (!_pcb)
|
||||
return 0;
|
||||
|
||||
return _pcb->remote_ip.addr;
|
||||
}
|
||||
|
||||
uint16_t getRemotePort()
|
||||
{
|
||||
if (!_pcb)
|
||||
return 0;
|
||||
|
||||
return _pcb->remote_port;
|
||||
}
|
||||
|
||||
size_t getSize() const
|
||||
{
|
||||
if (!_rx_buf)
|
||||
return 0;
|
||||
|
||||
return _rx_buf->tot_len - _rx_buf_offset;
|
||||
}
|
||||
|
||||
char read()
|
||||
{
|
||||
if (!_rx_buf)
|
||||
return 0;
|
||||
|
||||
char c = reinterpret_cast<char*>(_rx_buf->payload)[_rx_buf_offset];
|
||||
_consume(1);
|
||||
return c;
|
||||
}
|
||||
|
||||
size_t read(char* dst, size_t size)
|
||||
{
|
||||
if (!_rx_buf)
|
||||
return 0;
|
||||
|
||||
size_t max_size = _rx_buf->tot_len - _rx_buf_offset;
|
||||
size = (size < max_size) ? size : max_size;
|
||||
|
||||
DEBUGV(":rd %d, %d, %d\r\n", size, _rx_buf->tot_len, _rx_buf_offset);
|
||||
size_t size_read = 0;
|
||||
while(size)
|
||||
{
|
||||
size_t buf_size = _rx_buf->len - _rx_buf_offset;
|
||||
size_t copy_size = (size < buf_size) ? size : buf_size;
|
||||
DEBUGV(":rdi %d, %d\r\n", buf_size, copy_size);
|
||||
os_memcpy(dst, reinterpret_cast<char*>(_rx_buf->payload) + _rx_buf_offset, copy_size);
|
||||
dst += copy_size;
|
||||
_consume(copy_size);
|
||||
size -= copy_size;
|
||||
size_read += copy_size;
|
||||
}
|
||||
return size_read;
|
||||
}
|
||||
|
||||
char peek()
|
||||
{
|
||||
if (!_rx_buf)
|
||||
return 0;
|
||||
|
||||
return reinterpret_cast<char*>(_rx_buf->payload)[_rx_buf_offset];
|
||||
}
|
||||
|
||||
void flush()
|
||||
{
|
||||
if(!_rx_buf) {
|
||||
return;
|
||||
}
|
||||
if(_pcb) {
|
||||
tcp_recved(_pcb, (size_t) _rx_buf->tot_len);
|
||||
}
|
||||
pbuf_free(_rx_buf);
|
||||
_rx_buf = 0;
|
||||
_rx_buf_offset = 0;
|
||||
}
|
||||
|
||||
uint8_t state() const
|
||||
{
|
||||
if (!_pcb)
|
||||
return CLOSED;
|
||||
|
||||
return _pcb->state;
|
||||
}
|
||||
|
||||
size_t write(const char* data, size_t size)
|
||||
{
|
||||
if (!_pcb) {
|
||||
DEBUGV(":wr !_pcb\r\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(size == 0) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
size_t room = tcp_sndbuf(_pcb);
|
||||
size_t will_send = (room < size) ? room : size;
|
||||
err_t err = tcp_write(_pcb, data, will_send, 0);
|
||||
if (err != ERR_OK) {
|
||||
DEBUGV(":wr !ERR_OK\r\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
_size_sent = will_send;
|
||||
DEBUGV(":wr\r\n");
|
||||
_send_waiting = true;
|
||||
delay(5000); // max send timeout
|
||||
_send_waiting = false;
|
||||
DEBUGV(":ww\r\n");
|
||||
return will_send - _size_sent;
|
||||
}
|
||||
|
||||
|
||||
private:
|
||||
|
||||
void _consume(size_t size)
|
||||
{
|
||||
ptrdiff_t left = _rx_buf->len - _rx_buf_offset - size;
|
||||
if (left > 0)
|
||||
{
|
||||
_rx_buf_offset += size;
|
||||
}
|
||||
else if (!_rx_buf->next)
|
||||
{
|
||||
DEBUGV(":c0 %d, %d\r\n", size, _rx_buf->tot_len);
|
||||
if (_pcb)
|
||||
tcp_recved(_pcb, _rx_buf->len);
|
||||
pbuf_free(_rx_buf);
|
||||
_rx_buf = 0;
|
||||
_rx_buf_offset = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
DEBUGV(":c %d, %d, %d\r\n", size, _rx_buf->len, _rx_buf->tot_len);
|
||||
auto head = _rx_buf;
|
||||
_rx_buf = _rx_buf->next;
|
||||
_rx_buf_offset = 0;
|
||||
pbuf_ref(_rx_buf);
|
||||
if (_pcb)
|
||||
tcp_recved(_pcb, head->len);
|
||||
pbuf_free(head);
|
||||
}
|
||||
}
|
||||
|
||||
err_t _recv(tcp_pcb* pcb, pbuf* pb, err_t err)
|
||||
{
|
||||
|
||||
if (pb == 0) // connection closed
|
||||
{
|
||||
DEBUGV(":rcl\r\n");
|
||||
tcp_arg(pcb, NULL);
|
||||
tcp_sent(pcb, NULL);
|
||||
tcp_recv(pcb, NULL);
|
||||
tcp_err(pcb, NULL);
|
||||
// int error = tcp_close(pcb);
|
||||
// if (error != ERR_OK)
|
||||
{
|
||||
DEBUGV(":rcla\r\n");
|
||||
tcp_abort(pcb);
|
||||
_pcb = 0;
|
||||
return ERR_ABRT;
|
||||
if(err != ERR_OK) {
|
||||
DEBUGV(":tc err %d\r\n", err);
|
||||
tcp_abort(_pcb);
|
||||
}
|
||||
}
|
||||
_pcb = 0;
|
||||
|
||||
if(_size_sent && _send_waiting) {
|
||||
esp_schedule();
|
||||
}
|
||||
}
|
||||
|
||||
err_t _poll(tcp_pcb* pcb) {
|
||||
return ERR_OK;
|
||||
}
|
||||
|
||||
if (_rx_buf)
|
||||
{
|
||||
// there is some unread data
|
||||
// chain the new pbuf to the existing one
|
||||
DEBUGV(":rch %d, %d\r\n", _rx_buf->tot_len, pb->tot_len);
|
||||
pbuf_cat(_rx_buf, pb);
|
||||
err_t _sent(tcp_pcb* pcb, uint16_t len) {
|
||||
DEBUGV(":sent %d\r\n", len);
|
||||
_size_sent -= len;
|
||||
if(_size_sent == 0 && _send_waiting) esp_schedule();
|
||||
return ERR_OK;
|
||||
}
|
||||
else
|
||||
{
|
||||
DEBUGV(":rn %d\r\n", pb->tot_len);
|
||||
_rx_buf = pb;
|
||||
_rx_buf_offset = 0;
|
||||
|
||||
static err_t _s_recv(void *arg, struct tcp_pcb *tpcb, struct pbuf *pb, err_t err) {
|
||||
return reinterpret_cast<ClientContext*>(arg)->_recv(tpcb, pb, err);
|
||||
}
|
||||
// tcp_recved(pcb, received);
|
||||
// pbuf_free(pb);
|
||||
return ERR_OK;
|
||||
}
|
||||
|
||||
void _error(err_t err)
|
||||
{
|
||||
DEBUGV(":er %d\r\n", err);
|
||||
|
||||
if(_pcb) {
|
||||
tcp_arg(_pcb, NULL);
|
||||
tcp_sent(_pcb, NULL);
|
||||
tcp_recv(_pcb, NULL);
|
||||
tcp_err(_pcb, NULL);
|
||||
err = tcp_close(_pcb);
|
||||
if(err != ERR_OK) {
|
||||
DEBUGV(":tc err %d\r\n", err);
|
||||
tcp_abort(_pcb);
|
||||
}
|
||||
static void _s_error(void *arg, err_t err) {
|
||||
reinterpret_cast<ClientContext*>(arg)->_error(err);
|
||||
}
|
||||
_pcb = 0;
|
||||
|
||||
if(_size_sent && _send_waiting) {
|
||||
esp_schedule();
|
||||
static err_t _s_poll(void *arg, struct tcp_pcb *tpcb) {
|
||||
return reinterpret_cast<ClientContext*>(arg)->_poll(tpcb);
|
||||
}
|
||||
}
|
||||
|
||||
err_t _poll(tcp_pcb* pcb)
|
||||
{
|
||||
return ERR_OK;
|
||||
}
|
||||
static err_t _s_sent(void *arg, struct tcp_pcb *tpcb, uint16_t len) {
|
||||
return reinterpret_cast<ClientContext*>(arg)->_sent(tpcb, len);
|
||||
}
|
||||
|
||||
err_t _sent(tcp_pcb* pcb, uint16_t len)
|
||||
{
|
||||
DEBUGV(":sent %d\r\n", len);
|
||||
_size_sent -= len;
|
||||
if (_size_sent == 0 && _send_waiting)
|
||||
esp_schedule();
|
||||
return ERR_OK;
|
||||
}
|
||||
private:
|
||||
ClientContext* _next;
|
||||
int _refcnt;
|
||||
|
||||
tcp_pcb* _pcb;
|
||||
|
||||
static err_t _s_recv(void *arg, struct tcp_pcb *tpcb, struct pbuf *pb, err_t err)
|
||||
{
|
||||
return reinterpret_cast<ClientContext*>(arg)->_recv(tpcb, pb, err);
|
||||
}
|
||||
pbuf* _rx_buf;
|
||||
size_t _rx_buf_offset;
|
||||
|
||||
static void _s_error(void *arg, err_t err)
|
||||
{
|
||||
reinterpret_cast<ClientContext*>(arg)->_error(err);
|
||||
}
|
||||
discard_cb_t _discard_cb;
|
||||
void* _discard_cb_arg;
|
||||
|
||||
static err_t _s_poll(void *arg, struct tcp_pcb *tpcb)
|
||||
{
|
||||
return reinterpret_cast<ClientContext*>(arg)->_poll(tpcb);
|
||||
}
|
||||
|
||||
static err_t _s_sent(void *arg, struct tcp_pcb *tpcb, uint16_t len)
|
||||
{
|
||||
return reinterpret_cast<ClientContext*>(arg)->_sent(tpcb, len);
|
||||
}
|
||||
|
||||
private:
|
||||
ClientContext* _next;
|
||||
int _refcnt;
|
||||
|
||||
tcp_pcb* _pcb;
|
||||
|
||||
pbuf* _rx_buf;
|
||||
size_t _rx_buf_offset;
|
||||
|
||||
discard_cb_t _discard_cb;
|
||||
void* _discard_cb_arg;
|
||||
|
||||
size_t _size_sent;
|
||||
bool _send_waiting;
|
||||
size_t _size_sent;
|
||||
bool _send_waiting;
|
||||
};
|
||||
|
||||
|
||||
|
||||
#endif//CLIENTCONTEXT_H
|
||||
|
Loading…
x
Reference in New Issue
Block a user