diff --git a/hardware/arduino/sam/cores/arduino/Arduino.h b/hardware/arduino/sam/cores/arduino/Arduino.h index f074d5b27..4fae76a2a 100644 --- a/hardware/arduino/sam/cores/arduino/Arduino.h +++ b/hardware/arduino/sam/cores/arduino/Arduino.h @@ -155,6 +155,16 @@ typedef enum _ETCChannel #define PIN_ATTR_PWM (1UL<<3) #define PIN_ATTR_TIMER (1UL<<4) +#define PIN_STATUS_DIGITAL_INPUT_PULLUP (0x01) +#define PIN_STATUS_DIGITAL_INPUT (0x02) +#define PIN_STATUS_DIGITAL_OUTPUT (0x03) +#define PIN_STATUS_ANALOG (0x04) +#define PIN_STATUS_PWM (0x05) +#define PIN_STATUS_TIMER (0x06) +#define PIN_STATUS_SERIAL (0x07) +#define PIN_STATUS_DW_LOW (0x10) +#define PIN_STATUS_DW_HIGH (0x11) + /* Types used for the tables below */ typedef struct _PinDescription { @@ -170,6 +180,8 @@ typedef struct _PinDescription ETCChannel ulTCChannel ; } PinDescription ; +extern uint8_t g_pinStatus[]; + /* Pins table to be instanciated into variant.cpp */ extern const PinDescription g_APinDescription[] ; diff --git a/hardware/arduino/sam/cores/arduino/wiring_analog.c b/hardware/arduino/sam/cores/arduino/wiring_analog.c index e358d4666..05029782c 100644 --- a/hardware/arduino/sam/cores/arduino/wiring_analog.c +++ b/hardware/arduino/sam/cores/arduino/wiring_analog.c @@ -153,6 +153,7 @@ uint32_t analogRead(uint32_t ulPin) if ( latestSelectedChannel != (uint32_t)-1 && ulChannel != latestSelectedChannel) adc_disable_channel( ADC, latestSelectedChannel ); latestSelectedChannel = ulChannel; + g_pinStatus[ulPin] = (g_pinStatus[ulPin] & 0xF0) | PIN_STATUS_ANALOG; } // Start the ADC @@ -189,13 +190,9 @@ static void TC_SetCMR_ChannelB(Tc *tc, uint32_t chan, uint32_t v) } static uint8_t PWMEnabled = 0; -static uint8_t pinEnabled[PINS_COUNT]; static uint8_t TCChanEnabled[] = {0, 0, 0, 0, 0, 0, 0, 0, 0}; void analogOutputInit(void) { - uint8_t i; - for (i=0; i> 4 ? PIO_OUTPUT_1 : PIO_OUTPUT_0), g_APinDescription[ulPin].ulPin, g_APinDescription[ulPin].ulPinConfiguration ) ; + g_pinStatus[ulPin] = (g_pinStatus[ulPin] & 0xF0) | PIN_STATUS_DIGITAL_OUTPUT; + /* if all pins are output, disable PIO Controller clocking, reduce power consumption */ if ( g_APinDescription[ulPin].pPort->PIO_OSR == 0xffffffff ) { @@ -85,6 +96,12 @@ extern void digitalWrite( uint32_t ulPin, uint32_t ulVal ) return ; } + if ((g_pinStatus[ulPin] & 0xF) == PIN_STATUS_PWM) { + pinMode(ulPin, OUTPUT); + } + + g_pinStatus[ulPin] = (g_pinStatus[ulPin] & 0x0F) | (ulVal << 4) ; + if ( PIO_GetOutputDataStatus( g_APinDescription[ulPin].pPort, g_APinDescription[ulPin].ulPin ) == 0 ) { PIO_PullUp( g_APinDescription[ulPin].pPort, g_APinDescription[ulPin].ulPin, ulVal ) ; @@ -97,6 +114,14 @@ extern void digitalWrite( uint32_t ulPin, uint32_t ulVal ) extern int digitalRead( uint32_t ulPin ) { + if ((g_pinStatus[ulPin] & 0xF) == PIN_STATUS_DIGITAL_OUTPUT) { + return (g_pinStatus[ulPin] & 0xF0) >> 4; + } + + if ((g_pinStatus[ulPin] & 0xF) == PIN_STATUS_ANALOG) { + pinMode(ulPin, INPUT); + } + if ( g_APinDescription[ulPin].ulPinType == PIO_NOT_A_PIN ) { return LOW ; diff --git a/hardware/arduino/sam/variants/arduino_due_x/variant.cpp b/hardware/arduino/sam/variants/arduino_due_x/variant.cpp index f95d85017..7a0de80a9 100644 --- a/hardware/arduino/sam/variants/arduino_due_x/variant.cpp +++ b/hardware/arduino/sam/variants/arduino_due_x/variant.cpp @@ -291,6 +291,9 @@ extern const PinDescription g_APinDescription[]= { NULL, 0, 0, PIO_NOT_A_PIN, PIO_DEFAULT, 0, NO_ADC, NO_ADC, NOT_ON_PWM, NOT_ON_TIMER } } ; + +uint8_t g_pinStatus[PINS_COUNT] = {0}; + #ifdef __cplusplus } #endif