samd21: Add ability to use arbitrary pin configs with SPI
authorKeith Packard <keithp@keithp.com>
Mon, 7 Nov 2022 01:46:56 +0000 (17:46 -0800)
committerKeith Packard <keithp@keithp.com>
Mon, 7 Nov 2022 01:46:56 +0000 (17:46 -0800)
This embeds the DOPO and DIPO configs in the address

Signed-off-by: Keith Packard <keithp@keithp.com>
src/samd21/ao_arch_funcs.h
src/samd21/ao_spi_samd21.c
src/samd21/samd21.h

index e9fd3216855bc2500eeb4f768f208fbb54eb3f0e..47656551c00305a17d4fe15a30325452d67329e0 100644 (file)
@@ -125,35 +125,77 @@ ao_enable_cs(struct samd21_port *port, uint8_t pin)
 
 /* ao_spi_samd21.c */
 
+#define AO_SPI_INDEX_BIT       0
+#define AO_SPI_INDEX_MASK      0x07
+
+#define AO_SPI_CONFIG_BIT      4
+#define AO_SPI_CONFIG_MASK     (3 << AO_SPI_CONFIG_BIT)
+
 #define AO_SPI_CPOL_BIT                6
 #define AO_SPI_CPHA_BIT                7
 
-#define AO_SPI_CONFIG_1                0x00
+#define AO_SPI_DOPO_BIT                8
+#define  AO_SPI_DOPO_MOSI_0_SCLK_1     (0 << AO_SPI_DOPO_BIT)
+#define  AO_SPI_DOPO_MOSI_2_SCLK_3     (1 << AO_SPI_DOPO_BIT)
+#define  AO_SPI_DOPO_MOSI_3_SCLK_1     (2 << AO_SPI_DOPO_BIT)
+#define  AO_SPI_DOPO_MOSI_0_SCLK_3     (3 << AO_SPI_DOPO_BIT)
+#define  AO_SPI_DOPO_MASK              (3 << AO_SPI_DOPO_BIT)
+
+#define AO_SPI_DIPO_BIT                10
+#define  AO_SPI_DIPO_MISO_0            (0 << AO_SPI_DIPO_BIT)
+#define  AO_SPI_DIPO_MISO_1            (1 << AO_SPI_DIPO_BIT)
+#define  AO_SPI_DIPO_MISO_2            (2 << AO_SPI_DIPO_BIT)
+#define  AO_SPI_DIPO_MISO_3            (3 << AO_SPI_DIPO_BIT)
+#define  AO_SPI_DIPO_MASK              (3 << AO_SPI_DIPO_MASK)
+
+#define AO_SPI_CONFIG_0                (0 << AO_SPI_CONFIG_BIT)
+#define AO_SPI_CONFIG_1                (1 << AO_SPI_CONFIG_BIT)
+#define AO_SPI_CONFIG_2                (2 << AO_SPI_CONFIG_BIT)
+#define AO_SPI_CONFIG_3                (3 << AO_SPI_CONFIG_BIT)
+
 /*
  * PA08 SERCOM0.0 -> MOSI      (DOPO 0)
  * PA09 SERCOM0.1 -> SCLK      (DOPO 0)
  * PA10 SERCOM0.2 -> MISO      (DIPO 2)
  */
-#define AO_SPI_0_CONFIG_PA08_PA09_PA10 AO_SPI_CONFIG_1
+#define AO_SPI_0_CONFIG_PA08_PA09_PA10 (AO_SPI_CONFIG_0 | \
+                                        AO_SPI_DOPO_MOSI_0_SCLK_1 | \
+                                        AO_SPI_DIPO_MISO_2)
 
-#define AO_SPI_CONFIG_2                0x08
 /*
  * PA04 SERCOM0.0 -> MOSI      (DOPO 0)
  * PA05 SERCOM0.1 -> SCLK      (DOPO 0)
  * PA16 SERCOM0.2 -> MISO      (DIPO 2)
  */
-#define AO_SPI_0_CONFIG_PA04_PA05_PA06 AO_SPI_CONFIG_2
+#define AO_SPI_0_CONFIG_PA04_PA05_PA06 (AO_SPI_CONFIG_1 |              \
+                                        AO_SPI_DOPO_MOSI_0_SCLK_1 |    \
+                                        AO_SPI_DIPO_MISO_2)
 
-#define AO_SPI_CONFIG_NONE     0x0c
+/*
+ * PB10 SERCOM4.2 -> MOSI      (DOPO 1)
+ * PB11 SERCOM4.3 -> SCLK      (DOPO 1)
+ * PA12        SERCOM4.0 -> MISO       (DIPO 0)
+ */
+#define AO_SPI_4_CONFIG_PB10_PB11_PA12 (AO_SPI_CONFIG_0 |              \
+                                        AO_SPI_DOPO_MOSI_2_SCLK_3 |    \
+                                        AO_SPI_DIPO_MISO_0)
 
-#define AO_SPI_INDEX_MASK      0x07
-#define AO_SPI_CONFIG_MASK     0x18
+/*
+ * PB22 SERCOM5.2 -> MOSI      (DOPO 1)
+ * PB23 SERCOM5.3 -> SCLK      (DOPO 1)
+ * PB03 SERCOM5.1 -> MISO      (DIPO 1)
+ */
+#define AO_SPI_5_CONFIG_PB22_PB23_PB03 (AO_SPI_CONFIG_3 |              \
+                                        AO_SPI_DOPO_MOSI_2_SCLK_3 |    \
+                                        AO_SPI_DIPO_MISO_1)
 
-#define AO_SPI_INDEX(id)       ((id) & AO_SPI_INDEX_MASK)
+#define AO_SPI_INDEX(id)       ((uint8_t) ((id) & AO_SPI_INDEX_MASK))
 #define AO_SPI_CONFIG(id)      ((id) & AO_SPI_CONFIG_MASK)
 #define AO_SPI_PIN_CONFIG(id)  ((id) & (AO_SPI_INDEX_MASK | AO_SPI_CONFIG_MASK))
 #define AO_SPI_CPOL(id)                ((uint32_t) (((id) >> AO_SPI_CPOL_BIT) & 1))
 #define AO_SPI_CPHA(id)                ((uint32_t) (((id) >> AO_SPI_CPHA_BIT) & 1))
+#define AO_SPI_DOPO(id)                ((uint32_t) (((id) >> AO_SPI_DOPO_BIT) & 3))
+#define AO_SPI_DIPO(id)                ((uint32_t) (((id) >> AO_SPI_DIPO_BIT) & 3))
 
 /*
  * We're not going to do any fancy SPI pin remapping, just use the first
@@ -167,46 +209,58 @@ ao_enable_cs(struct samd21_port *port, uint8_t pin)
 #define AO_SPI_0_PA08_PA09_PA10        (0 | AO_SPI_0_CONFIG_PA08_PA09_PA10)
 #define AO_SPI_0_PA04_PA05_PA06        (0 | AO_SPI_0_CONFIG_PA04_PA05_PA06)
 
+#define AO_SPI_4_PB10_PB11_PA12 (4 | AO_SPI_4_CONFIG_PB10_PB11_PA12)
+
+#define AO_SPI_5_PB22_PB23_PB03        (5 | AO_SPI_5_CONFIG_PB22_PB23_PB03)
+
 void
-ao_spi_send(const void *block, uint16_t len, uint8_t spi_index);
+ao_spi_send(const void *block, uint16_t len, uint16_t spi_index);
 
 void
-ao_spi_recv(void *block, uint16_t len, uint8_t spi_index);
+ao_spi_recv(void *block, uint16_t len, uint16_t spi_index);
 
 void
-ao_spi_duplex(const void *out, void *in, uint16_t len, uint8_t spi_index);
+ao_spi_duplex(const void *out, void *in, uint16_t len, uint16_t spi_index);
 
 void
-ao_spi_get(uint8_t spi_index, uint32_t speed);
+ao_spi_get(uint16_t spi_index, uint32_t speed);
 
 void
-ao_spi_put(uint8_t spi_index);
+ao_spi_put(uint16_t spi_index);
 
 void
 ao_spi_init(void);
 
-#define ao_spi_get_mask(reg,mask,bus, speed) do {              \
-               ao_spi_get(bus, speed);                         \
+#define ao_spi_set_cs(reg,mask) do {           \
+               reg->outclr = mask;             \
+       } while(0)
+
+#define ao_spi_clr_cs(reg,mask) do {           \
+               reg->outset = mask;             \
+       } while(0)
+
+#define ao_spi_get_mask(reg,mask,spi_index, speed) do {                \
+               ao_spi_get(spi_index, speed);                           \
                ao_spi_set_cs(reg,mask);                        \
        } while (0)
 
-#define ao_spi_put_mask(reg,mask,bus) do {     \
+#define ao_spi_put_mask(reg,mask,spi_index) do {       \
                ao_spi_clr_cs(reg,mask);        \
-               ao_spi_put(bus);                \
+               ao_spi_put(spi_index);          \
        } while (0)
 
 static inline void
-ao_spi_get_bit(struct samd21_port *port, uint8_t bit, uint8_t bus, uint32_t speed)
+ao_spi_get_bit(struct samd21_port *port, uint8_t bit, uint16_t spi_index, uint32_t speed)
 {
-       ao_spi_get(bus, speed);
+       ao_spi_get(spi_index, speed);
        ao_gpio_set(port, bit, 0);
 }
 
 static inline void
-ao_spi_put_bit(struct samd21_port *port, uint8_t bit, uint8_t bus)
+ao_spi_put_bit(struct samd21_port *port, uint8_t bit, uint16_t spi_index)
 {
        ao_gpio_set(port, bit, 1);
-       ao_spi_put(bus);
+       ao_spi_put(spi_index);
 }
 
 static inline uint8_t
index 6e49884b69248f9f8299fc9454d7d720abfd5b96..f62426497f96cab921d91b59ed57c21a2ac360c2 100644 (file)
 #include <ao_dma_samd21.h>
 
 static uint8_t         ao_spi_mutex[SAMD21_NUM_SERCOM];
-static uint8_t         ao_spi_pin_config[SAMD21_NUM_SERCOM];
+static uint16_t                ao_spi_pin_config[SAMD21_NUM_SERCOM];
+
+#define SPI_DEBUG      0
+#define SPI_USE_DMA    1
+
+/*
+ * DMA is only used for USARTs in altos, which makes assigning DMA IDs
+ * pretty easy
+ */
+
+#define MISO_DMA_ID(id)                ((uint8_t) ((id) * 2U + 0U))
+#define MOSI_DMA_ID(id)                ((uint8_t) ((id) * 2U + 1U))
 
 struct ao_spi_samd21_info {
        struct samd21_sercom    *sercom;
@@ -45,12 +56,7 @@ static const struct ao_spi_samd21_info ao_spi_samd21_info[SAMD21_NUM_SERCOM] = {
 
 static uint8_t spi_dev_null;
 
-#define USE_DMA        1
-
-#if USE_DMA
-
-#define AO_SAMD21_SPI_MISO_DMA_ID      0
-#define AO_SAMD21_SPI_MOSI_DMA_ID      1
+#if SPI_USE_DMA
 
 static uint8_t ao_spi_done[SAMD21_NUM_SERCOM];
 
@@ -63,7 +69,6 @@ _ao_spi_recv_dma_done(uint8_t dma_id, void *closure)
        ao_spi_done[id] = 1;
        ao_wakeup(&ao_spi_done[id]);
 }
-#endif
 
 static inline uint32_t
 dma_chctrlb(uint8_t id, bool tx)
@@ -99,7 +104,7 @@ dma_chctrlb(uint8_t id, bool tx)
 }
 
 static inline uint16_t
-dma_btctrl(bool tx, bool step)
+dma_btctrl(bool step, bool tx)
 {
        uint16_t        btctrl = 0;
 
@@ -148,33 +153,46 @@ dma_btctrl(bool tx, bool step)
        return btctrl;
 }
 
-void
-ao_spi_send(const void *block, uint16_t len, uint8_t spi_index)
+static void
+spi_run(const void *out, void *in, uint16_t len, uint16_t spi_index, bool step_out, bool step_in)
 {
+       const uint8_t           *o = out;
+       uint8_t                 *i = in;
        uint8_t                 id = AO_SPI_INDEX(spi_index);
        struct samd21_sercom    *sercom = ao_spi_samd21_info[id].sercom;
-#if USE_DMA
 
        ao_arch_block_interrupts();
        ao_spi_done[id] = 0;
 
-       _ao_dma_start_transfer(AO_SAMD21_SPI_MISO_DMA_ID,
+       /*
+        * Stepped addresses to the DMA engine point past the end of
+        * the block
+        */
+       if (step_out)
+               o += len;
+       if (step_in)
+               i += len;
+
+       /* read any stuck data */
+       (void) sercom->data;
+
+       _ao_dma_start_transfer(MISO_DMA_ID(id),
                               (void *) &sercom->data,
-                              &spi_dev_null,
+                              i,
                               len,
                               dma_chctrlb(id, false),
-                              dma_btctrl(false, false),
+                              dma_btctrl(step_in, false),
 
                               _ao_spi_recv_dma_done,
                               (void *) (uintptr_t) id
                );
 
-       _ao_dma_start_transfer(AO_SAMD21_SPI_MOSI_DMA_ID,
-                              (uint8_t *) block + len, /* must point past the end of the block */
+       _ao_dma_start_transfer(MOSI_DMA_ID(id),
+                              o,
                               (void *) &sercom->data,
                               len,
                               dma_chctrlb(id, true),
-                              dma_btctrl(true, true),
+                              dma_btctrl(step_out, true),
                               NULL,
                               NULL
                );
@@ -182,104 +200,146 @@ ao_spi_send(const void *block, uint16_t len, uint8_t spi_index)
        while (ao_spi_done[id] == 0)
                ao_sleep(&ao_spi_done[id]);
 
-       _ao_dma_done_transfer(AO_SAMD21_SPI_MOSI_DMA_ID);
-       _ao_dma_done_transfer(AO_SAMD21_SPI_MISO_DMA_ID);
+       _ao_dma_done_transfer(MOSI_DMA_ID(id));
+       _ao_dma_done_transfer(MISO_DMA_ID(id));
        ao_arch_release_interrupts();
-#else
-       const uint8_t *b = block;
-
-       while (len--) {
-               sercom->data = *b++;
-               while ((sercom->intflag & (1 << SAMD21_SERCOM_INTFLAG_RXC)) == 0)
-                       ;
-               (void) sercom->data;
-       }
-#endif
 }
 
+#else
 
-void
-ao_spi_recv(void *block, uint16_t len, uint8_t spi_index)
+static void
+spi_run(const void *out, void *in, uint16_t len, uint16_t spi_index, bool step_out, bool step_in)
 {
        uint8_t                 id = AO_SPI_INDEX(spi_index);
        struct samd21_sercom    *sercom = ao_spi_samd21_info[id].sercom;
-
-       uint8_t *b = block;
+       const uint8_t           *o = out;
+       uint8_t                 *i = in;
 
        while (len--) {
-               sercom->data = 0xff;
+#if SPI_DEBUG
+               printf("%02x", *o);
+#endif
+               sercom->data = *o;
                while ((sercom->intflag & (1 << SAMD21_SERCOM_INTFLAG_RXC)) == 0)
                        ;
-               *b++ = (uint8_t) sercom->data;
+               *i = (uint8_t) sercom->data;
+#if SPI_DEBUG
+               printf("\t%02x\n", *i);
+#endif
+               if (step_out)
+                       o++;
+               if (step_in)
+                       i++;
        }
 }
 
+#endif
 
 void
-ao_spi_duplex(const void *out, void *in, uint16_t len, uint8_t spi_index)
+ao_spi_send(const void *block, uint16_t len, uint16_t spi_index)
 {
-       uint8_t                 id = AO_SPI_INDEX(spi_index);
-       struct samd21_sercom    *sercom = ao_spi_samd21_info[id].sercom;
+       spi_run(block, &spi_dev_null, len, spi_index, true, false);
+}
 
-       const uint8_t *o = out;
-       uint8_t *i = in;
 
-       while (len--) {
-               sercom->data = *o++;
-               while ((sercom->intflag & (1 << SAMD21_SERCOM_INTFLAG_RXC)) == 0)
-                       ;
-               *i++ = (uint8_t) sercom->data;
-       }
+void
+ao_spi_recv(void *block, uint16_t len, uint16_t spi_index)
+{
+       spi_dev_null = 0xff;
+       spi_run(&spi_dev_null, block, len, spi_index, false, true);
+}
+
+
+void
+ao_spi_duplex(const void *out, void *in, uint16_t len, uint16_t spi_index)
+{
+       spi_run(out, in, len, spi_index, true, true);
 }
 
 static void
-ao_spi_disable_pin_config(uint8_t spi_pin_config)
+ao_spi_disable_pin_config(uint16_t spi_pin_config)
 {
        switch (spi_pin_config) {
 #if HAS_SPI_0
-       case AO_SPI_0_PA08_PA09_PA10:
+       case AO_SPI_PIN_CONFIG(AO_SPI_0_PA08_PA09_PA10):
                samd21_port_pmux_clr(&samd21_port_a, 8);        /* MOSI */
                samd21_port_pmux_clr(&samd21_port_a, 9);        /* SCLK */
                samd21_port_pmux_clr(&samd21_port_a, 10);       /* MISO */
                break;
-       case AO_SPI_0_PA04_PA05_PA06:
+       case AO_SPI_PIN_CONFIG(AO_SPI_0_PA04_PA05_PA06):
                samd21_port_pmux_clr(&samd21_port_a, 4);        /* MOSI */
                samd21_port_pmux_clr(&samd21_port_a, 5);        /* SCLK */
                samd21_port_pmux_clr(&samd21_port_a, 6);        /* MISO */
                break;
 #endif
+#if HAS_SPI_5
+       case AO_SPI_PIN_CONFIG(AO_SPI_5_PB22_PB23_PB03):
+               samd21_port_pmux_clr(&samd21_port_b, 22);       /* MOSI */
+               samd21_port_pmux_clr(&samd21_port_b, 23);       /* SCLK */
+               samd21_port_pmux_clr(&samd21_port_b, 3);        /* MISO */
+               break;
+#endif
+       case 0xffff:
+               break;
        }
 }
 
 static void
-ao_spi_enable_pin_config(uint8_t spi_pin_config)
+ao_spi_enable_pin_config(uint16_t spi_pin_config)
 {
        switch (spi_pin_config) {
 #if HAS_SPI_0
-       case AO_SPI_0_PA08_PA09_PA10:
+       case AO_SPI_PIN_CONFIG(AO_SPI_0_PA08_PA09_PA10):
                ao_enable_output(&samd21_port_a, 8, 1);
                ao_enable_output(&samd21_port_a, 9, 1);
                ao_enable_input(&samd21_port_a, 10, AO_MODE_PULL_NONE);
+
                samd21_port_pmux_set(&samd21_port_a, 8, SAMD21_PORT_PMUX_FUNC_C);       /* MOSI */
                samd21_port_pmux_set(&samd21_port_a, 9, SAMD21_PORT_PMUX_FUNC_C);       /* SCLK */
                samd21_port_pmux_set(&samd21_port_a, 10, SAMD21_PORT_PMUX_FUNC_C);      /* MISO */
                break;
-       case AO_SPI_0_PA04_PA05_PA06:
+       case AO_SPI_PIN_CONFIG(AO_SPI_0_PA04_PA05_PA06):
                ao_enable_output(&samd21_port_a, 4, 1);
                ao_enable_output(&samd21_port_a, 5, 1);
                ao_enable_input(&samd21_port_a, 6, AO_MODE_PULL_NONE);
+
                samd21_port_pmux_set(&samd21_port_a, 4, SAMD21_PORT_PMUX_FUNC_C);       /* MOSI */
                samd21_port_pmux_set(&samd21_port_a, 5, SAMD21_PORT_PMUX_FUNC_C);       /* SCLK */
                samd21_port_pmux_set(&samd21_port_a, 6, SAMD21_PORT_PMUX_FUNC_C);       /* MISO */
                break;
 #endif
+#if HAS_SPI_4
+       case AO_SPI_PIN_CONFIG(AO_SPI_4_PB10_PB11_PA12):
+               ao_enable_output(&samd21_port_b, 10, 1);
+               ao_enable_output(&samd21_port_b, 11, 1);
+               ao_enable_input(&samd21_port_a, 12, AO_MODE_PULL_NONE);
+
+               samd21_port_pmux_set(&samd21_port_b, 10, SAMD21_PORT_PMUX_FUNC_D);      /* MOSI */
+               samd21_port_pmux_set(&samd21_port_b, 11, SAMD21_PORT_PMUX_FUNC_D);      /* SCLK */
+               samd21_port_pmux_set(&samd21_port_a, 12, SAMD21_PORT_PMUX_FUNC_D);      /* MISO */
+               break;
+#endif
+#if HAS_SPI_5
+       case AO_SPI_PIN_CONFIG(AO_SPI_5_PB22_PB23_PB03):
+               ao_enable_output(&samd21_port_b, 22, 1);
+               ao_enable_output(&samd21_port_b, 23, 1);
+               ao_enable_input(&samd21_port_b, 3, AO_MODE_PULL_NONE);
+
+               samd21_port_pmux_set(&samd21_port_b, 22, SAMD21_PORT_PMUX_FUNC_D);      /* 5.2 MOSI */
+               samd21_port_pmux_set(&samd21_port_b, 23, SAMD21_PORT_PMUX_FUNC_D);      /* 5.3 SCLK */
+               samd21_port_pmux_set(&samd21_port_b, 3, SAMD21_PORT_PMUX_FUNC_D);       /* 5.1 MISO */
+               break;
+#endif
+       default:
+               ao_panic(AO_PANIC_SPI);
+               break;
        }
 }
 
 static void
-ao_spi_config(uint8_t spi_index, uint32_t baud)
+ao_spi_config(uint16_t spi_index, uint32_t baud)
 {
-       uint8_t                 spi_pin_config = AO_SPI_PIN_CONFIG(spi_index);
+       uint16_t                spi_pin_config = AO_SPI_PIN_CONFIG(spi_index);
        uint8_t                 id = AO_SPI_INDEX(spi_index);
        struct samd21_sercom    *sercom = ao_spi_samd21_info[id].sercom;
 
@@ -294,13 +354,21 @@ ao_spi_config(uint8_t spi_index, uint32_t baud)
        /* Set spi mode */
        uint32_t ctrla = sercom->ctrla;
        ctrla &= ~((1UL << SAMD21_SERCOM_CTRLA_CPOL) |
-                  (1UL << SAMD21_SERCOM_CTRLA_CPHA));
+                  (1UL << SAMD21_SERCOM_CTRLA_CPHA) |
+                  (SAMD21_SERCOM_CTRLA_DOPO_MASK << SAMD21_SERCOM_CTRLA_DOPO) |
+                  (SAMD21_SERCOM_CTRLA_DIPO_MASK << SAMD21_SERCOM_CTRLA_DIPO));
        ctrla |= ((AO_SPI_CPOL(spi_index) << SAMD21_SERCOM_CTRLA_CPOL) |
-                 (AO_SPI_CPHA(spi_index) << SAMD21_SERCOM_CTRLA_CPHA));
+                 (AO_SPI_CPHA(spi_index) << SAMD21_SERCOM_CTRLA_CPHA) |
+                 (AO_SPI_DOPO(spi_index) << SAMD21_SERCOM_CTRLA_DOPO) |
+                 (AO_SPI_DIPO(spi_index) << SAMD21_SERCOM_CTRLA_DIPO));
 
        /* finish setup and enable the hardware */
        ctrla |= (1 << SAMD21_SERCOM_CTRLA_ENABLE);
 
+#if SPI_DEBUG
+       printf("ctrla %08lx\n", ctrla);
+#endif
+
        sercom->ctrla = ctrla;
 
        while (sercom->syncbusy & (1 << SAMD21_SERCOM_SYNCBUSY_ENABLE))
@@ -308,7 +376,7 @@ ao_spi_config(uint8_t spi_index, uint32_t baud)
 }
 
 void
-ao_spi_get(uint8_t spi_index, uint32_t speed)
+ao_spi_get(uint16_t spi_index, uint32_t speed)
 {
        uint8_t         id = AO_SPI_INDEX(spi_index);
 
@@ -317,7 +385,7 @@ ao_spi_get(uint8_t spi_index, uint32_t speed)
 }
 
 void
-ao_spi_put(uint8_t spi_index)
+ao_spi_put(uint16_t spi_index)
 {
        uint8_t                 id = AO_SPI_INDEX(spi_index);
        struct samd21_sercom    *sercom = ao_spi_samd21_info[id].sercom;
@@ -369,8 +437,7 @@ ao_spi_init_sercom(uint8_t id)
                         (0 << SAMD21_SERCOM_CTRLB_PLOADEN) |
                         (SAMD21_SERCOM_CTRLB_CHSIZE_8 << SAMD21_SERCOM_CTRLB_CHSIZE));
 
-
-       ao_spi_enable_pin_config(id);
+       ao_spi_pin_config[id] = 0xffff;
 }
 
 void
index f65c117fc2b61df9c22e71d3051fff88041a0a41..cd9d2d3464f296d2f3fcd7263eb106505995086a 100644 (file)
@@ -1467,7 +1467,19 @@ extern struct samd21_sercom samd21_sercom5;
 
 /* SPI controller mode */
 #define SAMD21_SERCOM_CTRLA_DOPO       16
+#define  SAMD21_SERCOM_CTRLA_DOPO_MOSI_0_SCLK_1        0UL
+#define  SAMD21_SERCOM_CTRLA_DOPO_MOSI_2_SCLK_3        1UL
+#define  SAMD21_SERCOM_CTRLA_DOPO_MOSI_3_SCLK_1        2UL
+#define  SAMD21_SERCOM_CTRLA_DOPO_MOSI_0_SCLK_3        3UL
+#define  SAMD21_SERCOM_CTRLA_DOPO_MASK         3UL
+
 #define SAMD21_SERCOM_CTRLA_DIPO       20
+#define  SAMD21_SERCOM_CTRLA_DIPO_MISO_0       0UL
+#define  SAMD21_SERCOM_CTRLA_DIPO_MISO_1       1UL
+#define  SAMD21_SERCOM_CTRLA_DIPO_MISO_2       2UL
+#define  SAMD21_SERCOM_CTRLA_DIPO_MISO_3       3UL
+#define  SAMD21_SERCOM_CTRLA_DIPO_MASK         3UL
+
 #define SAMD21_SERCOM_CTRLA_FORM       24
 #define SAMD21_SERCOM_CTRLA_CPHA       28
 #define SAMD21_SERCOM_CTRLA_CPOL       29