Merge branch 'master' into telescience-v0.2
authorKeith Packard <keithp@keithp.com>
Wed, 16 Jan 2013 23:22:46 +0000 (15:22 -0800)
committerKeith Packard <keithp@keithp.com>
Wed, 16 Jan 2013 23:22:46 +0000 (15:22 -0800)
15 files changed:
src/Makefile
src/avr/ao_spi_slave.c
src/core/ao.h
src/drivers/ao_cc1120.c
src/megadongle-v0.1/ao_pins.h
src/megametrum-v0.1/ao_pins.h
src/stm-demo/ao_pins.h
src/stm/ao_arch_funcs.h
src/stm/ao_spi_stm.c
src/stm/ao_spi_stm_slave.c [new file with mode: 0644]
src/telelco-v0.1/ao_pins.h
src/telescience-v0.2/.gitignore [new file with mode: 0644]
src/telescience-v0.2/Makefile [new file with mode: 0644]
src/telescience-v0.2/ao_pins.h [new file with mode: 0644]
src/telescience-v0.2/ao_telescience.c [new file with mode: 0644]

index 67ad97d1b7e54500ad153b467f73723b4fc6357b..e4b110390c2cb5b6e4221136d3dc8ac60da23654 100644 (file)
@@ -23,7 +23,7 @@ SDCCDIRS=\
        telelaunch-v0.1 tidongle test \
        teleterra-v0.2 teleshield-v0.1 \
        telefire-v0.1 \
-       spiradio-v0.1
+       spiradio-v0.1 telescience-v0.2
 
 AVRDIRS=\
        telescience-v0.1 telescience-pwm telepyro-v0.1 micropeak
index a400b8a0a929f0485b8d8da894f43c17ec098f79..15e9924da5d6f20c4b1b454a3393d3fea9d23c31 100644 (file)
 #include "ao.h"
 
 uint8_t
-ao_spi_slave_recv(uint8_t *buf, uint8_t len)
+ao_spi_slave_recv(void *buf, uint16_t len)
 {
+       uint8_t *b = buf;
        while (len--) {
                while (!(SPSR & (1 << SPIF)))
                        if ((PINB & (1 << PINB0)))
                                return 0;
-               *buf++ = SPDR;
+               *b++ = SPDR;
        }
        return 1;
 }
 
 void
-ao_spi_slave_send(uint8_t *buf, uint8_t len)
+ao_spi_slave_send(void *buf, uint16_t len)
 {
+       uint8_t *b = buf;
        while (len--) {
-               SPDR = *buf++;
+               SPDR = *b++;
                while (!(SPSR & (1 << SPIF)))
                        if ((PINB & (1 << PINB0)))
                                return;
index df5bbf487e2469702421b27a25d7ac9378351d03..ce0bf5d14289007dff1b602e750cdc7b23dec7f4 100644 (file)
@@ -299,10 +299,10 @@ ao_altitude_to_pa(alt_t alt);
  */
 
 uint8_t
-ao_spi_slave_recv(uint8_t *buf, uint8_t len);
+ao_spi_slave_recv(void *buf, uint16_t len);
 
 void
-ao_spi_slave_send(uint8_t *buf, uint8_t len);
+ao_spi_slave_send(void *buf, uint16_t len);
 
 void
 ao_spi_slave_init(void);
index 8068740f91782483e6f83329a4f439d2c778b5a5..53bb5a62f5621bedb4c94d48d76b660b5213ea46 100644 (file)
@@ -38,7 +38,7 @@ extern const uint32_t ao_radio_cal;
 
 #define FOSC   32000000
 
-#define ao_radio_select()      ao_spi_get_mask(AO_CC1120_SPI_CS_PORT,(1 << AO_CC1120_SPI_CS_PIN),AO_CC1120_SPI_BUS,AO_SPI_SPEED_1MHz)
+#define ao_radio_select()      ao_spi_get_mask(AO_CC1120_SPI_CS_PORT,(1 << AO_CC1120_SPI_CS_PIN),AO_CC1120_SPI_BUS,AO_SPI_SPEED_4MHz)
 #define ao_radio_deselect()    ao_spi_put_mask(AO_CC1120_SPI_CS_PORT,(1 << AO_CC1120_SPI_CS_PIN),AO_CC1120_SPI_BUS)
 #define ao_radio_spi_send(d,l) ao_spi_send((d), (l), AO_CC1120_SPI_BUS)
 #define ao_radio_spi_send_fixed(d,l) ao_spi_send_fixed((d), (l), AO_CC1120_SPI_BUS)
index c766a48c6d24b46d91fb698a6d4bb0d6a309042c..d460a49095b9a38fdd3fd93cb05cdbf122f91f37 100644 (file)
@@ -78,6 +78,7 @@
 #define HAS_SPI_2              1
 #define SPI_2_PB13_PB14_PB15   1       /* Flash, Companion */
 #define SPI_2_PD1_PD3_PD4      0
+#define SPI_2_OSPEEDR          STM_OSPEEDR_10MHz
 
 #define SPI_2_PORT             (&stm_gpiob)
 #define SPI_2_SCK_PIN          13
index 64da41a915304f618b6aa0547969701d0dcd2b55..4c645871fe758d6f6159da4aa49e38ef2823e936 100644 (file)
 #define SPI_1_PA5_PA6_PA7      1       /* Barometer */
 #define SPI_1_PB3_PB4_PB5      0
 #define SPI_1_PE13_PE14_PE15   1       /* Accelerometer */
+#define SPI_1_OSPEEDR          STM_OSPEEDR_10MHz
 
 #define HAS_SPI_2              1
 #define SPI_2_PB13_PB14_PB15   1       /* Flash, Companion */
 #define SPI_2_PD1_PD3_PD4      0
+#define SPI_2_OSPEEDR          STM_OSPEEDR_10MHz
 
 #define SPI_2_PORT             (&stm_gpiob)
 #define SPI_2_SCK_PIN          13
index c9c7446e4e21d489aa1ff80fe25a9c2e1fce3779..07b4a19d919a78c989bd2d48bc53307809cdd463 100644 (file)
@@ -60,6 +60,7 @@
 
 #define HAS_SPI_1              1
 #define SPI_1_PB3_PB4_PB5      1
+#define SPI_1_OSPEEDR          STM_OSPEEDR_10MHz
 
 #define HAS_SPI_2              0
 
index 87bbe73e3b926a6b964d181f6dc5a60926cb4305..d17793076f38ca177e60f66082288c607044d1b5 100644 (file)
@@ -23,7 +23,7 @@
 
 /* PCLK is set to 16MHz (HCLK 32MHz, APB prescaler 2) */
 
-#define AO_SPI_SPEED_8MHz      STM_SPI_CR1_BR_PCLK_2   /* This doesn't appear to work */
+#define AO_SPI_SPEED_8MHz      STM_SPI_CR1_BR_PCLK_2
 #define AO_SPI_SPEED_4MHz      STM_SPI_CR1_BR_PCLK_4
 #define AO_SPI_SPEED_2MHz      STM_SPI_CR1_BR_PCLK_8
 #define AO_SPI_SPEED_1MHz      STM_SPI_CR1_BR_PCLK_16
@@ -32,7 +32,7 @@
 #define AO_SPI_SPEED_125kHz    STM_SPI_CR1_BR_PCLK_128
 #define AO_SPI_SPEED_62500Hz   STM_SPI_CR1_BR_PCLK_256
 
-#define AO_SPI_SPEED_FAST      AO_SPI_SPEED_4MHz
+#define AO_SPI_SPEED_FAST      AO_SPI_SPEED_8MHz
 
 /* Companion bus wants something no faster than 200kHz */
 
index 599d7ee09981694ac4dabea3e695028ec30718be..7b4af96443f28af949669e2d1cf18c2a49d2db49 100644 (file)
@@ -425,12 +425,21 @@ ao_spi_init(void)
 #if HAS_SPI_1
 # if SPI_1_PA5_PA6_PA7
        stm_rcc.ahbenr |= (1 << STM_RCC_AHBENR_GPIOAEN);
+       stm_ospeedr_set(&stm_gpioa, 5, SPI_1_OSPEEDR);
+       stm_ospeedr_set(&stm_gpioa, 6, SPI_1_OSPEEDR);
+       stm_ospeedr_set(&stm_gpioa, 7, SPI_1_OSPEEDR);
 # endif
 # if SPI_1_PB3_PB4_PB5
        stm_rcc.ahbenr |= (1 << STM_RCC_AHBENR_GPIOBEN);
+       stm_ospeedr_set(&stm_gpiob, 3, SPI_1_OSPEEDR);
+       stm_ospeedr_set(&stm_gpiob, 4, SPI_1_OSPEEDR);
+       stm_ospeedr_set(&stm_gpiob, 5, SPI_1_OSPEEDR);
 # endif
 # if SPI_1_PE13_PE14_PE15
        stm_rcc.ahbenr |= (1 << STM_RCC_AHBENR_GPIOEEN);
+       stm_ospeedr_set(&stm_gpioe, 13, SPI_1_OSPEEDR);
+       stm_ospeedr_set(&stm_gpioe, 14, SPI_1_OSPEEDR);
+       stm_ospeedr_set(&stm_gpioe, 15, SPI_1_OSPEEDR);
 # endif
        stm_rcc.apb2enr |= (1 << STM_RCC_APB2ENR_SPI1EN);
        ao_spi_index[0] = AO_SPI_CONFIG_NONE;
@@ -440,9 +449,15 @@ ao_spi_init(void)
 #if HAS_SPI_2
 # if SPI_2_PB13_PB14_PB15
        stm_rcc.ahbenr |= (1 << STM_RCC_AHBENR_GPIOBEN);
+       stm_ospeedr_set(&stm_gpiob, 13, SPI_2_OSPEEDR);
+       stm_ospeedr_set(&stm_gpiob, 14, SPI_2_OSPEEDR);
+       stm_ospeedr_set(&stm_gpiob, 15, SPI_2_OSPEEDR);
 # endif
 # if SPI_2_PD1_PD3_PD4
        stm_rcc.ahbenr |= (1 << STM_RCC_AHBENR_GPIODEN);
+       stm_ospeedr_set(&stm_gpiod, 1, SPI_2_OSPEEDR);
+       stm_ospeedr_set(&stm_gpiod, 3, SPI_2_OSPEEDR);
+       stm_ospeedr_set(&stm_gpiod, 4, SPI_2_OSPEEDR);
 # endif
        stm_rcc.apb1enr |= (1 << STM_RCC_APB1ENR_SPI2EN);
        ao_spi_index[1] = AO_SPI_CONFIG_NONE;
diff --git a/src/stm/ao_spi_stm_slave.c b/src/stm/ao_spi_stm_slave.c
new file mode 100644 (file)
index 0000000..9802244
--- /dev/null
@@ -0,0 +1,339 @@
+/*
+ * Copyright © 2012 Keith Packard <keithp@keithp.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; version 2 of the License.
+ *
+ * This program 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
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+#include <ao.h>
+
+struct ao_spi_stm_slave_info {
+       uint8_t miso_dma_index;
+       uint8_t mosi_dma_index;
+       struct stm_spi *stm_spi;
+};
+
+static uint8_t         ao_spi_slave_mutex[STM_NUM_SPI];
+static uint8_t         ao_spi_slave_index[STM_NUM_SPI];
+
+static const struct ao_spi_stm_slave_info ao_spi_stm_slave_info[STM_NUM_SPI] = {
+       {
+               .miso_dma_index = STM_DMA_INDEX(STM_DMA_CHANNEL_SPI1_RX),
+               .mosi_dma_index = STM_DMA_INDEX(STM_DMA_CHANNEL_SPI1_TX),
+               &stm_spi1
+       },
+       {
+               .miso_dma_index = STM_DMA_INDEX(STM_DMA_CHANNEL_SPI2_RX),
+               .mosi_dma_index = STM_DMA_INDEX(STM_DMA_CHANNEL_SPI2_TX),
+               &stm_spi2
+       }
+};
+
+static uint8_t spi_dev_null;
+
+void
+ao_spi_slave_send(void *block, uint16_t len)
+{
+       struct stm_spi *stm_spi = ao_spi_stm_slave_info[AO_SPI_INDEX(SPI_SLAVE_INDEX)].stm_spi;
+       uint8_t mosi_dma_index = ao_spi_stm_slave_info[AO_SPI_INDEX(SPI_SLAVE_INDEX)].mosi_dma_index;
+       uint8_t miso_dma_index = ao_spi_stm_slave_info[AO_SPI_INDEX(SPI_SLAVE_INDEX)].miso_dma_index;
+
+       /* Set up the transmit DMA to deliver data */
+       ao_dma_set_transfer(mosi_dma_index,
+                           &stm_spi->dr,
+                           block,
+                           len,
+                           (0 << STM_DMA_CCR_MEM2MEM) |
+                           (STM_DMA_CCR_PL_MEDIUM << STM_DMA_CCR_PL) |
+                           (STM_DMA_CCR_MSIZE_8 << STM_DMA_CCR_MSIZE) |
+                           (STM_DMA_CCR_PSIZE_8 << STM_DMA_CCR_PSIZE) |
+                           (1 << STM_DMA_CCR_MINC) |
+                           (0 << STM_DMA_CCR_PINC) |
+                           (0 << STM_DMA_CCR_CIRC) |
+                           (STM_DMA_CCR_DIR_MEM_TO_PER << STM_DMA_CCR_DIR));
+
+       /* Clear RXNE */
+       (void) stm_spi->dr;
+
+       /* Set up the receive DMA -- when this is done, we know the SPI unit
+        * is idle. Without this, we'd have to poll waiting for the BSY bit to
+        * be cleared
+        */
+       ao_dma_set_transfer(miso_dma_index,
+                           &stm_spi->dr,
+                           &spi_dev_null,
+                           len,
+                           (0 << STM_DMA_CCR_MEM2MEM) |
+                           (STM_DMA_CCR_PL_MEDIUM << STM_DMA_CCR_PL) |
+                           (STM_DMA_CCR_MSIZE_8 << STM_DMA_CCR_MSIZE) |
+                           (STM_DMA_CCR_PSIZE_8 << STM_DMA_CCR_PSIZE) |
+                           (0 << STM_DMA_CCR_MINC) |
+                           (0 << STM_DMA_CCR_PINC) |
+                           (0 << STM_DMA_CCR_CIRC) |
+                           (STM_DMA_CCR_DIR_PER_TO_MEM << STM_DMA_CCR_DIR));
+       stm_spi->cr2 = ((0 << STM_SPI_CR2_TXEIE) |
+                       (0 << STM_SPI_CR2_RXNEIE) |
+                       (0 << STM_SPI_CR2_ERRIE) |
+                       (0 << STM_SPI_CR2_SSOE) |
+                       (1 << STM_SPI_CR2_TXDMAEN) |
+                       (1 << STM_SPI_CR2_RXDMAEN));
+       ao_dma_start(miso_dma_index);
+       ao_dma_start(mosi_dma_index);
+       ao_arch_critical(
+               while (!ao_dma_done[miso_dma_index])
+                       ao_sleep(&ao_dma_done[miso_dma_index]);
+               );
+       ao_dma_done_transfer(mosi_dma_index);
+       ao_dma_done_transfer(miso_dma_index);
+}
+
+
+uint8_t
+ao_spi_slave_recv(void *block, uint16_t len)
+{
+       struct stm_spi *stm_spi = ao_spi_stm_slave_info[AO_SPI_INDEX(SPI_SLAVE_INDEX)].stm_spi;
+       uint8_t mosi_dma_index = ao_spi_stm_slave_info[AO_SPI_INDEX(SPI_SLAVE_INDEX)].mosi_dma_index;
+       uint8_t miso_dma_index = ao_spi_stm_slave_info[AO_SPI_INDEX(SPI_SLAVE_INDEX)].miso_dma_index;
+
+       /* Set up transmit DMA to make the SPI hardware actually run */
+       ao_dma_set_transfer(mosi_dma_index,
+                           &stm_spi->dr,
+                           &spi_dev_null,
+                           len,
+                           (0 << STM_DMA_CCR_MEM2MEM) |
+                           (STM_DMA_CCR_PL_MEDIUM << STM_DMA_CCR_PL) |
+                           (STM_DMA_CCR_MSIZE_8 << STM_DMA_CCR_MSIZE) |
+                           (STM_DMA_CCR_PSIZE_8 << STM_DMA_CCR_PSIZE) |
+                           (0 << STM_DMA_CCR_MINC) |
+                           (0 << STM_DMA_CCR_PINC) |
+                           (0 << STM_DMA_CCR_CIRC) |
+                           (STM_DMA_CCR_DIR_MEM_TO_PER << STM_DMA_CCR_DIR));
+
+       /* Clear RXNE */
+       (void) stm_spi->dr;
+
+       /* Set up the receive DMA to capture data */
+       ao_dma_set_transfer(miso_dma_index,
+                           &stm_spi->dr,
+                           block,
+                           len,
+                           (0 << STM_DMA_CCR_MEM2MEM) |
+                           (STM_DMA_CCR_PL_MEDIUM << STM_DMA_CCR_PL) |
+                           (STM_DMA_CCR_MSIZE_8 << STM_DMA_CCR_MSIZE) |
+                           (STM_DMA_CCR_PSIZE_8 << STM_DMA_CCR_PSIZE) |
+                           (1 << STM_DMA_CCR_MINC) |
+                           (0 << STM_DMA_CCR_PINC) |
+                           (0 << STM_DMA_CCR_CIRC) |
+                           (STM_DMA_CCR_DIR_PER_TO_MEM << STM_DMA_CCR_DIR));
+
+       stm_spi->cr2 = ((0 << STM_SPI_CR2_TXEIE) |
+                       (0 << STM_SPI_CR2_RXNEIE) |
+                       (0 << STM_SPI_CR2_ERRIE) |
+                       (0 << STM_SPI_CR2_SSOE) |
+                       (1 << STM_SPI_CR2_TXDMAEN) |
+                       (1 << STM_SPI_CR2_RXDMAEN));
+       ao_dma_start(miso_dma_index);
+       ao_dma_start(mosi_dma_index);
+
+       /* Wait until the SPI unit is done */
+       ao_arch_critical(
+               while (!ao_dma_done[miso_dma_index])
+                       ao_sleep(&ao_dma_done[miso_dma_index]);
+               );
+
+       ao_dma_done_transfer(mosi_dma_index);
+       ao_dma_done_transfer(miso_dma_index);
+}
+
+static void
+ao_spi_slave_disable_index(uint8_t spi_index)
+{
+       /* Disable current config
+        */
+       switch (AO_SPI_INDEX(spi_index)) {
+       case STM_SPI_INDEX(1):
+               switch (spi_index) {
+               case AO_SPI_1_PA5_PA6_PA7:
+                       stm_gpio_set(&stm_gpioa, 5, 1);
+                       stm_moder_set(&stm_gpioa, 5, STM_MODER_OUTPUT);
+                       stm_moder_set(&stm_gpioa, 6, STM_MODER_INPUT);
+                       stm_moder_set(&stm_gpioa, 7, STM_MODER_OUTPUT);
+                       break;
+               case AO_SPI_1_PB3_PB4_PB5:
+                       stm_gpio_set(&stm_gpiob, 3, 1);
+                       stm_moder_set(&stm_gpiob, 3, STM_MODER_OUTPUT);
+                       stm_moder_set(&stm_gpiob, 4, STM_MODER_INPUT);
+                       stm_moder_set(&stm_gpiob, 5, STM_MODER_OUTPUT);
+                       break;
+               case AO_SPI_1_PE13_PE14_PE15:
+                       stm_gpio_set(&stm_gpioe, 13, 1);
+                       stm_moder_set(&stm_gpioe, 13, STM_MODER_OUTPUT);
+                       stm_moder_set(&stm_gpioe, 14, STM_MODER_INPUT);
+                       stm_moder_set(&stm_gpioe, 15, STM_MODER_OUTPUT);
+                       break;
+               }
+               break;
+       case STM_SPI_INDEX(2):
+               switch (spi_index) {
+               case AO_SPI_2_PB13_PB14_PB15:
+                       stm_gpio_set(&stm_gpiob, 13, 1);
+                       stm_moder_set(&stm_gpiob, 13, STM_MODER_OUTPUT);
+                       stm_moder_set(&stm_gpiob, 14, STM_MODER_INPUT);
+                       stm_moder_set(&stm_gpiob, 15, STM_MODER_OUTPUT);
+                       break;
+               case AO_SPI_2_PD1_PD3_PD4:
+                       stm_gpio_set(&stm_gpiod, 1, 1);
+                       stm_moder_set(&stm_gpiod, 1, STM_MODER_OUTPUT);
+                       stm_moder_set(&stm_gpiod, 3, STM_MODER_INPUT);
+                       stm_moder_set(&stm_gpiod, 4, STM_MODER_OUTPUT);
+                       break;
+               }
+               break;
+       }
+}
+
+static void
+ao_spi_slave_enable_index(uint8_t spi_index)
+{
+       switch (AO_SPI_INDEX(spi_index)) {
+       case STM_SPI_INDEX(1):
+               switch (spi_index) {
+               case AO_SPI_1_PA5_PA6_PA7:
+                       stm_afr_set(&stm_gpioa, 5, STM_AFR_AF5);
+                       stm_afr_set(&stm_gpioa, 6, STM_AFR_AF5);
+                       stm_afr_set(&stm_gpioa, 7, STM_AFR_AF5);
+                       break;
+               case AO_SPI_1_PB3_PB4_PB5:
+                       stm_afr_set(&stm_gpiob, 3, STM_AFR_AF5);
+                       stm_afr_set(&stm_gpiob, 4, STM_AFR_AF5);
+                       stm_afr_set(&stm_gpiob, 5, STM_AFR_AF5);
+                       break;
+               case AO_SPI_1_PE13_PE14_PE15:
+                       stm_afr_set(&stm_gpioe, 13, STM_AFR_AF5);
+                       stm_afr_set(&stm_gpioe, 14, STM_AFR_AF5);
+                       stm_afr_set(&stm_gpioe, 15, STM_AFR_AF5);
+                       break;
+               }
+               break;
+       case STM_SPI_INDEX(2):
+               switch (spi_index) {
+               case AO_SPI_2_PB13_PB14_PB15:
+                       stm_afr_set(&stm_gpiob, 13, STM_AFR_AF5);
+                       stm_afr_set(&stm_gpiob, 14, STM_AFR_AF5);
+                       stm_afr_set(&stm_gpiob, 15, STM_AFR_AF5);
+                       break;
+               case AO_SPI_2_PD1_PD3_PD4:
+                       stm_afr_set(&stm_gpiod, 1, STM_AFR_AF5);
+                       stm_afr_set(&stm_gpiod, 3, STM_AFR_AF5);
+                       stm_afr_set(&stm_gpiod, 4, STM_AFR_AF5);
+                       break;
+               }
+               break;
+       }
+}
+
+void
+ao_spi_slave_get(uint8_t spi_index, uint32_t speed)
+{
+       uint8_t         id = AO_SPI_INDEX(spi_index);
+       struct stm_spi  *stm_spi = ao_spi_stm_slave_info[id].stm_spi;
+
+       ao_mutex_get(&ao_spi_slave_mutex[id]);
+       stm_spi->cr1 = ((0 << STM_SPI_CR1_BIDIMODE) |                   /* Three wire mode */
+                       (0 << STM_SPI_CR1_BIDIOE) |
+                       (0 << STM_SPI_CR1_CRCEN) |                      /* CRC disabled */
+                       (0 << STM_SPI_CR1_CRCNEXT) |
+                       (0 << STM_SPI_CR1_DFF) |
+                       (0 << STM_SPI_CR1_RXONLY) |
+                       (1 << STM_SPI_CR1_SSM) |                        /* Software SS handling */
+                       (1 << STM_SPI_CR1_SSI) |                        /*  ... */
+                       (0 << STM_SPI_CR1_LSBFIRST) |                   /* Big endian */
+                       (1 << STM_SPI_CR1_SPE) |                        /* Enable SPI unit */
+                       (speed << STM_SPI_CR1_BR) |     /* baud rate to pclk/4 */
+                       (1 << STM_SPI_CR1_MSTR) |
+                       (0 << STM_SPI_CR1_CPOL) |                       /* Format 0 */
+                       (0 << STM_SPI_CR1_CPHA));
+       if (spi_index != ao_spi_slave_index[id]) {
+               
+               /* Disable old config
+                */
+               ao_spi_slave_disable_index(ao_spi_slave_index[id]);
+
+               /* Enable new config
+                */
+               ao_spi_slave_enable_index(spi_index);
+               
+               /* Remember current config
+                */
+               ao_spi_slave_index[id] = spi_index;
+       }
+}
+
+void
+ao_spi_slave_put(uint8_t spi_index)
+{
+       uint8_t         id = AO_SPI_INDEX(spi_index);
+       struct stm_spi  *stm_spi = ao_spi_stm_slave_info[id].stm_spi;
+
+       stm_spi->cr1 = 0;
+       ao_mutex_put(&ao_spi_slave_mutex[id]);
+}
+
+static void
+ao_spi_channel_init(uint8_t spi_index)
+{
+       uint8_t         id = AO_SPI_INDEX(spi_index);
+       struct stm_spi  *stm_spi = ao_spi_stm_slave_info[id].stm_spi;
+
+       ao_spi_slave_disable_index(spi_index);
+
+       stm_spi->cr1 = 0;
+       (void) stm_spi->sr;
+       stm_spi->cr2 = ((0 << STM_SPI_CR2_TXEIE) |
+                       (0 << STM_SPI_CR2_RXNEIE) |
+                       (0 << STM_SPI_CR2_ERRIE) |
+                       (0 << STM_SPI_CR2_SSOE) |
+                       (0 << STM_SPI_CR2_TXDMAEN) |
+                       (0 << STM_SPI_CR2_RXDMAEN));
+}
+
+void
+ao_spi_slave_init(void)
+{
+#if HAS_SPI_SLAVE_1
+# if SPI_1_PA5_PA6_PA7
+       stm_rcc.ahbenr |= (1 << STM_RCC_AHBENR_GPIOAEN);
+# endif
+# if SPI_1_PB3_PB4_PB5
+       stm_rcc.ahbenr |= (1 << STM_RCC_AHBENR_GPIOBEN);
+# endif
+# if SPI_1_PE13_PE14_PE15
+       stm_rcc.ahbenr |= (1 << STM_RCC_AHBENR_GPIOEEN);
+# endif
+       stm_rcc.apb2enr |= (1 << STM_RCC_APB2ENR_SPI1EN);
+       ao_spi_slave_index[0] = AO_SPI_CONFIG_NONE;
+       ao_spi_channel_init(0);
+#endif
+
+#if HAS_SPI_SLAVE_2
+# if SPI_2_PB13_PB14_PB15
+       stm_rcc.ahbenr |= (1 << STM_RCC_AHBENR_GPIOBEN);
+# endif
+# if SPI_2_PD1_PD3_PD4
+       stm_rcc.ahbenr |= (1 << STM_RCC_AHBENR_GPIODEN);
+# endif
+       stm_rcc.apb1enr |= (1 << STM_RCC_APB1ENR_SPI2EN);
+       ao_spi_slave_index[1] = AO_SPI_CONFIG_NONE;
+       ao_spi_channel_init(1);
+#endif
+}
index 60cf018f4f315e0efc1e06ce52e01ef8a91734e4..970f9bd1799d678060a79ff40ae347c262801b8f 100644 (file)
 #define HAS_TELEMETRY          0
 #define HAS_AES                        1
 
-#define HAS_SPI_1              1
-#define SPI_1_PA5_PA6_PA7      1
+#define HAS_SPI_1              0
+#define SPI_1_PA5_PA6_PA7      0
 #define SPI_1_PB3_PB4_PB5      0
 #define SPI_1_PE13_PE14_PE15   0
 
-#define HAS_SPI_2              1
+#define HAS_SPI_2              1       /* CC1111 */
 #define SPI_2_PB13_PB14_PB15   1
 #define SPI_2_PD1_PD3_PD4      0
 #define SPI_2_GPIO             (&stm_gpiob)
 #define SPI_2_SCK              13
 #define SPI_2_MISO             14
 #define SPI_2_MOSI             15
+#define SPI_2_OSPEEDR          STM_OSPEEDR_10MHz
 
 #define HAS_I2C_1              0
 
diff --git a/src/telescience-v0.2/.gitignore b/src/telescience-v0.2/.gitignore
new file mode 100644 (file)
index 0000000..cc1f8b7
--- /dev/null
@@ -0,0 +1,2 @@
+ao_product.h
+telescience-*.elf
diff --git a/src/telescience-v0.2/Makefile b/src/telescience-v0.2/Makefile
new file mode 100644 (file)
index 0000000..fbeeb75
--- /dev/null
@@ -0,0 +1,85 @@
+#
+# AltOS build
+#
+#
+
+include ../stm/Makefile.defs
+
+INC = \
+       ao.h \
+       ao_arch.h \
+       ao_arch_funcs.h \
+       ao_pins.h \
+       ao_product.h \
+       ao_cc1120_CC1120.h \
+       ao_task.h \
+       ao_whiten.h \
+       stm32l.h \
+       Makefile
+
+#PROFILE=ao_profile.c
+#PROFILE_DEF=-DAO_PROFILE=1
+
+#SAMPLE_PROFILE=ao_sample_profile.c \
+#      ao_sample_profile_timer.c
+#SAMPLE_PROFILE_DEF=-DHAS_SAMPLE_PROFILE=1
+
+#STACK_GUARD=ao_mpu_stm.c
+#STACK_GUARD_DEF=-DHAS_STACK_GUARD=1
+
+ALTOS_SRC = \
+       ao_interrupt.c \
+       ao_product.c \
+       ao_romconfig.c \
+       ao_cmd.c \
+       ao_config.c \
+       ao_task.c \
+       ao_led.c \
+       ao_stdio.c \
+       ao_panic.c \
+       ao_timer.c \
+       ao_mutex.c \
+       ao_dma_stm.c \
+       ao_spi_stm.c \
+       ao_usb_stm.c \
+       ao_adc_stm.c \
+       ao_data.c \
+       ao_exti_stm.c \
+       ao_storage.c \
+       ao_m25.c \
+       ao_science_slave.c \
+       ao_spi_stm_slave.c \
+       ao_log_telescience.c \
+       ao_log_single.c
+
+PRODUCT=TeleScience-v0.2
+PRODUCT_DEF=-DTELESCIENCE
+IDPRODUCT=0x0011
+
+CFLAGS = $(PRODUCT_DEF) $(STM_CFLAGS) $(PROFILE_DEF) $(SAMPLE_PROFILE_DEF) $(STACK_GUARD_DEF) -Os -g
+
+PROGNAME=telescience-v0.2
+PROG=$(PROGNAME)-$(VERSION).elf
+
+SRC=$(ALTOS_SRC) ao_telescience.c
+OBJ=$(SRC:.c=.o)
+
+all: $(PROG)
+
+$(PROG): Makefile $(OBJ) altos.ld
+       $(call quiet,CC) $(LDFLAGS) $(CFLAGS) -o $(PROG) $(OBJ) $(SAT_CLIB) -lgcc
+
+$(OBJ): $(INC)
+
+ao_product.h: ao-make-product.5c ../Version
+       $(call quiet,NICKLE,$<) $< -m altusmetrum.org -i $(IDPRODUCT) -p $(PRODUCT) -v $(VERSION) > $@
+
+distclean:     clean
+
+clean:
+       rm -f *.o $(PROGNAME)-*.elf
+       rm -f ao_product.h
+
+install:
+
+uninstall:
diff --git a/src/telescience-v0.2/ao_pins.h b/src/telescience-v0.2/ao_pins.h
new file mode 100644 (file)
index 0000000..7b97450
--- /dev/null
@@ -0,0 +1,144 @@
+/*
+ * Copyright © 2012 Keith Packard <keithp@keithp.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; version 2 of the License.
+ *
+ * This program 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
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+#ifndef _AO_PINS_H_
+#define _AO_PINS_H_
+
+#define HAS_TASK_QUEUE         1
+
+/* 8MHz High speed external crystal */
+#define AO_HSE                 8000000
+
+/* PLLVCO = 96MHz (so that USB will work) */
+#define AO_PLLMUL              12
+#define AO_RCC_CFGR_PLLMUL     (STM_RCC_CFGR_PLLMUL_12)
+
+/* SYSCLK = 32MHz (no need to go faster than CPU) */
+#define AO_PLLDIV              3
+#define AO_RCC_CFGR_PLLDIV     (STM_RCC_CFGR_PLLDIV_3)
+
+/* HCLK = 32MHz (CPU clock) */
+#define AO_AHB_PRESCALER       1
+#define AO_RCC_CFGR_HPRE_DIV   STM_RCC_CFGR_HPRE_DIV_1
+
+/* Run APB1 at 16MHz (HCLK/2) */
+#define AO_APB1_PRESCALER      2
+#define AO_RCC_CFGR_PPRE1_DIV  STM_RCC_CFGR_PPRE2_DIV_2
+
+/* Run APB2 at 16MHz (HCLK/2) */
+#define AO_APB2_PRESCALER      2
+#define AO_RCC_CFGR_PPRE2_DIV  STM_RCC_CFGR_PPRE2_DIV_2
+
+#define HAS_SERIAL_1           0
+#define USE_SERIAL_1_STDIN     0
+#define SERIAL_1_PB6_PB7       0
+#define SERIAL_1_PA9_PA10      1
+
+#define HAS_SERIAL_2           0
+#define USE_SERIAL_2_STDIN     0
+#define SERIAL_2_PA2_PA3       0
+#define SERIAL_2_PD5_PD6       0
+
+#define HAS_SERIAL_3           0
+#define USE_SERIAL_3_STDIN     0
+#define SERIAL_3_PB10_PB11     0
+#define SERIAL_3_PC10_PC11     1
+#define SERIAL_3_PD8_PD9       0
+
+#define HAS_EEPROM             1
+#define USE_INTERNAL_FLASH     0
+#define HAS_USB                        1
+#define HAS_BEEP               0
+#define HAS_RADIO              0
+#define HAS_TELEMETRY          0
+#define PACKET_HAS_SLAVE       0
+
+#define HAS_SPI_1              0
+#define HAS_SPI_SLAVE_1                1
+#define SPI_1_PA5_PA6_PA7      1       
+#define SPI_1_PB3_PB4_PB5      0
+#define SPI_1_PE13_PE14_PE15   0
+#define SPI_1_OSPEEDR          STM_OSPEEDR_10MHz
+
+#define HAS_SPI_2              1
+#define SPI_2_PB13_PB14_PB15   1
+#define SPI_2_PD1_PD3_PD4      0
+#define SPI_2_OSPEEDR          STM_OSPEEDR_10MHz
+
+#define SPI_2_PORT             (&stm_gpiob)
+#define SPI_2_SCK_PIN          13
+#define SPI_2_MISO_PIN         14
+#define SPI_2_MOSI_PIN         15
+#define SPI_SLAVE_INDEX                1
+
+#define HAS_I2C_1              0
+#define I2C_1_PB8_PB9          0
+
+#define HAS_I2C_2              0
+#define I2C_2_PB10_PB11                0
+
+#define LOW_LEVEL_DEBUG                0
+
+#define LED_PORT_0_ENABLE      STM_RCC_AHBENR_GPIOAEN
+
+#define LED_PORT_0             (&stm_gpioa)
+#define LED_PORT_0_MASK                (0xff)
+#define LED_PORT_0_SHIFT       0
+#define LED_PIN_RED            8
+#define LED_PIN_GREEN          9
+#define AO_LED_RED             (1 << LED_PIN_RED)
+#define AO_LED_GREEN           (1 << LED_PIN_GREEN)
+
+#define LEDS_AVAILABLE         (AO_LED_RED | AO_LED_GREEN)
+
+#define HAS_GPS                        0
+#define HAS_FLIGHT             0
+#define HAS_ADC                        1
+#define HAS_LOG                        1
+
+/*
+ * SPI Flash memory
+ */
+
+#define M25_MAX_CHIPS          1
+#define AO_M25_SPI_CS_PORT     (&stm_gpioa)
+#define AO_M25_SPI_CS_MASK     (1 << 3)
+#define AO_M25_SPI_BUS         AO_SPI_2_PB13_PB14_PB15
+
+/*
+ * ADC
+ */
+
+#define AO_DATA_RING           32
+#define AO_ADC_NUM             1
+
+struct ao_adc {
+       int16_t                 adc[AO_ADC_NUM];
+};
+
+#define AO_ADC_TEMP            16
+
+#define AO_ADC_RCC_AHBENR      0
+
+#define AO_NUM_ADC_PIN         0
+
+#define AO_NUM_ADC             1
+
+#define AO_ADC_SQ1             AO_ADC_TEMP
+
+
+#endif /* _AO_PINS_H_ */
diff --git a/src/telescience-v0.2/ao_telescience.c b/src/telescience-v0.2/ao_telescience.c
new file mode 100644 (file)
index 0000000..2fb3186
--- /dev/null
@@ -0,0 +1,51 @@
+/*
+ * Copyright © 2012 Keith Packard <keithp@keithp.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; version 2 of the License.
+ *
+ * This program 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
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+#include <ao.h>
+#include <ao_exti.h>
+#include <ao_packet.h>
+#include <ao_send_packet.h>
+
+int
+main(void)
+{
+       ao_clock_init();
+       
+#if HAS_STACK_GUARD
+       ao_mpu_init();
+#endif
+
+       ao_task_init();
+       ao_led_init(LEDS_AVAILABLE);
+       ao_led_on(AO_LED_GREEN);
+       ao_timer_init();
+
+       ao_spi_init();
+       ao_spi_slave_init();
+       ao_dma_init();
+       ao_exti_init();
+
+       ao_cmd_init();
+
+       ao_usb_init();
+       ao_config_init();
+       
+       ao_storage_init();
+
+       ao_start_scheduler();
+       return 0;
+}