예제 #1
0
파일: stm32_lcd.c 프로젝트: dagar/NuttX
FAR int board_lcd_initialize(void)
{
  lcdinfo("Initializing lcd\n");

  lcdinfo("init spi1\n");
  spi = stm32_spibus_initialize(1);
  DEBUGASSERT(spi);

  lcdinfo("configure related io\n");
  stm32_configgpio(GPIO_MEMLCD_EXTCOMIN);
  stm32_configgpio(GPIO_MEMLCD_DISP);

  lcdinfo("configure EXTCOMIN timer\n");
  if (tim == NULL)
    {
      tim = stm32_tim_init(2);
      DEBUGASSERT(tim);
      STM32_TIM_SETPERIOD(tim, TIMER_FREQ / EXTCOMIN_FREQ);
      STM32_TIM_SETCLOCK(tim, TIMER_FREQ);
      STM32_TIM_SETMODE(tim, STM32_TIM_MODE_UP);
    }

  lcdinfo("init lcd\n");
  l_lcddev = memlcd_initialize(spi, &memlcd_priv, 0);
  DEBUGASSERT(l_lcddev);

  return OK;
}
예제 #2
0
int stm32_w25initialize(int minor)
{
#ifdef HAVE_W25
  FAR struct spi_dev_s *spi;
  FAR struct mtd_dev_s *mtd;
#ifdef CONFIG_FS_NXFFS
  char devname[12];
#endif
  int ret;

  /* Get the SPI port */

  spi = stm32_spibus_initialize(1);
  if (!spi)
    {
      ferr("ERROR: Failed to initialize SPI port 2\n");
      return -ENODEV;
    }

  /* Now bind the SPI interface to the W25 SPI FLASH driver */

  mtd = w25_initialize(spi);
  if (!mtd)
    {
      ferr("ERROR: Failed to bind SPI port 2 to the SST 25 FLASH driver\n");
      return -ENODEV;
    }

#ifndef CONFIG_FS_NXFFS
  /* And finally, use the FTL layer to wrap the MTD driver as a block driver */

  ret = ftl_initialize(minor, mtd);
  if (ret < 0)
    {
      ferr("ERROR: Initialize the FTL layer\n");
      return ret;
    }
#else
  /* Initialize to provide NXFFS on the MTD interface */

  ret = nxffs_initialize(mtd);
  if (ret < 0)
    {
      ferr("ERROR: NXFFS initialization failed: %d\n", -ret);
      return ret;
    }

  /* Mount the file system at /mnt/w25 */

  snprintf(devname, 12, "/mnt/w25%c", 'a' + minor);
  ret = mount(NULL, devname, "nxffs", 0, NULL);
  if (ret < 0)
    {
      ferr("ERROR: Failed to mount the NXFFS volume: %d\n", errno);
      return ret;
    }
#endif
#endif
  return OK;
}
예제 #3
0
void stm32_wlinitialize(void)
{
#  ifndef CONFIG_STM32_SPI2
#   error "STM32_SPI2 is required to support nRF24L01 module on this board"
#  endif

  int result;
  FAR struct spi_dev_s *spidev;

  /* Setup CE & IRQ line IOs */

  stm32_configgpio(GPIO_NRF24L01_CE);
  stm32_configgpio(GPIO_NRF24L01_IRQ);

  /* Init SPI bus */

  spidev = stm32_spibus_initialize(2);
  if (!spidev)
    {
      _err("ERROR: Failed to initialize SPI bus\n");
      return;
    }

  result = nrf24l01_register(spidev, &nrf_cfg);
  if (result != OK)
    {
      _err("ERROR: Failed to register initialize SPI bus\n");
      return;
    }
}
예제 #4
0
파일: stm32_spi.c 프로젝트: a1ien/nuttx
FAR struct spi_dev_s *stm32_spi5initialize(void)
{
  if (!g_spidev5)
    {
      g_spidev5 = stm32_spibus_initialize(5);
    }

  return g_spidev5;
}
예제 #5
0
int board_lcd_initialize(void)
{
  g_spidev = stm32_spibus_initialize(LCD_SPI_PORTNO);

  if (!g_spidev)
    {
      lcderr("ERROR: Failed to initialize SPI port %d\n", LCD_SPI_PORTNO);
      return 0;
    }

  return 1;
}
예제 #6
0
void weak_function stm32_spidev_initialize(void)
{
#ifdef CONFIG_STM32_SPI1
  /* Configure SPI-based devices */

  g_spi1 = stm32_spibus_initialize(1);
  if (!g_spi1)
    {
      spierr("ERROR: FAILED to initialize SPI port 1\n");
    }

#ifdef HAVE_MMCSD
  stm32_configgpio(GPIO_SPI_CS_SD_CARD);
#endif
#endif

#ifdef CONFIG_STM32_SPI2
  /* Configure SPI-based devices */

  g_spi2 = stm32_spibus_initialize(2);
#endif
}
예제 #7
0
int usbmsc_archinitialize(void)
{
  /* If system/usbmsc is built as an NSH command, then SD slot should
   * already have been initialized in board_app_initialize() (see stm32_appinit.c).
   * In this case, there is nothing further to be done here.
   */

  FAR struct spi_dev_s *spi;
  int ret;

  /* First, get an instance of the SPI interface */

  syslog(LOG_INFO, "Initializing SPI port %d\n",
      OLIMEXINO_STM32_MMCSDSPIPORTNO);

  spi = stm32_spibus_initialize(OLIMEXINO_STM32_MMCSDSPIPORTNO);
  if (!spi)
    {
      syslog(LOG_ERR, "ERROR: Failed to initialize SPI port %d\n",
          OLIMEXINO_STM32_MMCSDSPIPORTNO);
      return -ENODEV;
    }

  syslog(LOG_INFO, "Successfully initialized SPI port %d\n",
      OLIMEXINO_STM32_MMCSDSPIPORTNO);

  /* Now bind the SPI interface to the MMC/SD driver */

  syslog(LOG_INFO, "Bind SPI to the MMC/SD driver, minor=%d slot=%d\n",
      CONFIG_SYSTEM_USBMSC_DEVMINOR1, OLIMEXINO_STM32_MMCSDSLOTNO);

  ret = mmcsd_spislotinitialize(CONFIG_SYSTEM_USBMSC_DEVMINOR1,
                                OLIMEXINO_STM32_MMCSDSLOTNO, spi);
  if (ret < 0)
    {
      syslog(LOG_ERR,
             "ERROR: Failed to bind SPI port %d to MMC/SD minor=%d slot=%d %d\n",
             OLIMEXINO_STM32_MMCSDSPIPORTNO, CONFIG_SYSTEM_USBMSC_DEVMINOR1,
             OLIMEXINO_STM32_MMCSDSLOTNO, ret);
      return ret;
    }

  syslog(LOG_INFO, "Successfully bound SPI to the MMC/SD driver\n");

  return OK;

}
예제 #8
0
FAR struct lcd_dev_s *board_graphics_setup(unsigned int devno)
{
    FAR struct spi_dev_s *spi;
    FAR struct lcd_dev_s *dev;

    /* Configure the OLED GPIOs. This initial configuration is RESET low,
     * putting the OLED into reset state.
     */

    (void)stm32_configgpio(GPIO_OLED_RESET);

    /* Wait a bit then release the OLED from the reset state */

    up_mdelay(20);
    stm32_gpiowrite(GPIO_OLED_RESET, true);

    /* Get the SPI1 port interface */

    spi = stm32_spibus_initialize(1);
    if (spi == NULL)
    {
        lcddbg("Failed to initialize SPI port 1\n");
    }
    else
    {
        /* Bind the SPI port to the OLED */

        dev = ssd1351_initialize(spi, devno);
        if (dev == NULL)
        {
            lcddbg("Failed to bind SPI port 1 to OLED %d: %d\n", devno);
        }
        else
        {
            lcdvdbg("Bound SPI port 1 to OLED %d\n", devno);

            /* And turn the OLED on */

            (void)dev->setpower(dev, LCD_FULL_ON);
            return dev;
        }
    }

    return NULL;
}
예제 #9
0
파일: stm32_max6675.c 프로젝트: a1ien/nuttx
int stm32_max6675initialize(FAR const char *devpath)
{
  FAR struct spi_dev_s *spi;
  int ret;

  spi = stm32_spibus_initialize(MAX6675_SPI_PORTNO);

  if (!spi)
    {
      return -ENODEV;
    }

  /* Then register the barometer sensor */
  
  ret = max6675_register(devpath, spi);
  if (ret < 0)
    {
      snerr("ERROR: Error registering MAX6675\n");
    }

  return ret;
}
예제 #10
0
int stm32_sdinitialize(int minor)
{
#ifdef HAVE_MMCSD
  FAR struct spi_dev_s *spi;
  int ret;

  /* Get the SPI port */

  finfo("Initializing SPI port %d\n", STM32_MMCSDSPIPORTNO);

  spi = stm32_spibus_initialize(STM32_MMCSDSPIPORTNO);
  if (!spi)
    {
      ferr("ERROR: Failed to initialize SPI port %d\n", STM32_MMCSDSPIPORTNO);
      return -ENODEV;
    }

  finfo("Successfully initialized SPI port %d\n", STM32_MMCSDSPIPORTNO);

  /* Bind the SPI port to the slot */

  finfo("Binding SPI port %d to MMC/SD slot %d\n",
          STM32_MMCSDSPIPORTNO, STM32_MMCSDSLOTNO);

  ret = mmcsd_spislotinitialize(minor, STM32_MMCSDSLOTNO, spi);
  if (ret < 0)
    {
      ferr("ERROR: Failed to bind SPI port %d to MMC/SD slot %d: %d\n",
            STM32_MMCSDSPIPORTNO, STM32_MMCSDSLOTNO, ret);
      return ret;
    }

  finfo("Successfuly bound SPI port %d to MMC/SD slot %d\n",
        STM32_MMCSDSPIPORTNO, STM32_MMCSDSLOTNO);
#endif
  return OK;
}
예제 #11
0
int board_app_initialize(void)
{
#if defined(CONFIG_STM32_SPI4)
  FAR struct spi_dev_s *spi;
  FAR struct mtd_dev_s *mtd;
  FAR struct mtd_geometry_s geo;
#endif

#if defined(CONFIG_MTD_PARTITION_NAMES)
  FAR const char *partname = CONFIG_STM32F429I_DISCO_FLASH_PART_NAMES;
#endif

#if defined(CONFIG_MTD) && defined(CONFIG_MTD_SST25XX)
  int ret;
#elif defined(HAVE_USBHOST) || defined(HAVE_USBMONITOR)
  int ret;
#endif

  /* Configure SPI-based devices */

#ifdef CONFIG_STM32_SPI4
  /* Get the SPI port */

  syslog(LOG_INFO, "Initializing SPI port 4\n");

  spi = stm32_spibus_initialize(4);
  if (!spi)
    {
      syslog(LOG_ERR, "ERROR: Failed to initialize SPI port 4\n");
      return -ENODEV;
    }

  syslog(LOG_INFO, "Successfully initialized SPI port 4\n");

  /* Now bind the SPI interface to the SST25F064 SPI FLASH driver.  This
   * is a FLASH device that has been added external to the board (i.e.
   * the board does not ship from STM with any on-board FLASH.
   */

#if defined(CONFIG_MTD) && defined(CONFIG_MTD_SST25XX)
  syslog(LOG_INFO, "Bind SPI to the SPI flash driver\n");

  mtd = sst25xx_initialize(spi);
  if (!mtd)
    {
      syslog(LOG_ERR, "ERROR: Failed to bind SPI port 4 to the SPI FLASH driver\n");
    }
  else
    {
      syslog(LOG_INFO, "Successfully bound SPI port 4 to the SPI FLASH driver\n");

      /* Get the geometry of the FLASH device */

      ret = mtd->ioctl(mtd, MTDIOC_GEOMETRY, (unsigned long)((uintptr_t)&geo));
      if (ret < 0)
        {
          fdbg("ERROR: mtd->ioctl failed: %d\n", ret);
          return ret;
        }

#ifdef CONFIG_STM32F429I_DISCO_FLASH_PART
      {
        int partno;
        int partsize;
        int partoffset;
        int partszbytes;
        int erasesize;
        const char *partstring = CONFIG_STM32F429I_DISCO_FLASH_PART_LIST;
        const char *ptr;
        FAR struct mtd_dev_s *mtd_part;
        char  partref[4];

        /* Now create a partition on the FLASH device */

        partno = 0;
        ptr = partstring;
        partoffset = 0;

        /* Get the Flash erase size */

        erasesize = geo.erasesize;

        while (*ptr != '\0')
          {
            /* Get the partition size */

            partsize = atoi(ptr);
            partszbytes = (partsize << 10); /* partsize is defined in KB */

            /* Check if partition size is bigger then erase block */

            if (partszbytes < erasesize)
              {
                fdbg("ERROR: Partition size is lesser than erasesize!\n");
                return -1;
              }

            /* Check if partition size is multiple of erase block */

            if ((partszbytes % erasesize) != 0)
              {
                fdbg("ERROR: Partition size is not multiple of erasesize!\n");
                return -1;
              }

            mtd_part    = mtd_partition(mtd, partoffset, partszbytes / erasesize);
            partoffset += partszbytes / erasesize;

#ifdef CONFIG_STM32F429I_DISCO_FLASH_CONFIG_PART
            /* Test if this is the config partition */

            if (CONFIG_STM32F429I_DISCO_FLASH_CONFIG_PART_NUMBER == partno)
              {
                /* Register the partition as the config device */

                mtdconfig_register(mtd_part);
              }
            else
#endif
              {
                /* Now initialize a SMART Flash block device and bind it
                 * to the MTD device.
                 */

#if defined(CONFIG_MTD_SMART) && defined(CONFIG_FS_SMARTFS)
                sprintf(partref, "p%d", partno);
                smart_initialize(CONFIG_STM32F429I_DISCO_FLASH_MINOR, mtd_part, partref);
#endif
              }

#if defined(CONFIG_MTD_PARTITION_NAMES)
            /* Set the partition name */

            if (mtd_part == NULL)
              {
                dbg("Error: failed to create partition %s\n", partname);
                return -1;
              }

            mtd_setpartitionname(mtd_part, partname);

            /* Now skip to next name.  We don't need to split the string here
             * because the MTD partition logic will only display names up to
             * the comma, thus allowing us to use a single static name
             * in the code.
             */

            while (*partname != ',' && *partname != '\0')
              {
                /* Skip to next ',' */

                partname++;
              }

            if (*partname == ',')
              {
                partname++;
              }
#endif

            /* Update the pointer to point to the next size in the list */

            while ((*ptr >= '0') && (*ptr <= '9'))
              {
                ptr++;
              }

            if (*ptr == ',')
              {
                ptr++;
              }

            /* Increment the part number */

            partno++;
          }
      }
#else /* CONFIG_STM32F429I_DISCO_FLASH_PART */

      /* Configure the device with no partition support */

      smart_initialize(CONFIG_STM32F429I_DISCO_FLASH_MINOR, mtd, NULL);

#endif /* CONFIG_STM32F429I_DISCO_FLASH_PART */
    }

#endif /* CONFIG_MTD */
#endif /* CONFIG_STM32_SPI4 */

  /* Create a RAM MTD device if configured */

#if defined(CONFIG_RAMMTD) && defined(CONFIG_STM32F429I_DISCO_RAMMTD)
  {
    uint8_t *start = (uint8_t *) kmm_malloc(CONFIG_STM32F429I_DISCO_RAMMTD_SIZE * 1024);
    mtd = rammtd_initialize(start, CONFIG_STM32F429I_DISCO_RAMMTD_SIZE * 1024);
    mtd->ioctl(mtd, MTDIOC_BULKERASE, 0);

    /* Now initialize a SMART Flash block device and bind it to the MTD device */

#if defined(CONFIG_MTD_SMART) && defined(CONFIG_FS_SMARTFS)
    smart_initialize(CONFIG_STM32F429I_DISCO_RAMMTD_MINOR, mtd, NULL);
#endif
  }

#endif /* CONFIG_RAMMTD && CONFIG_STM32F429I_DISCO_RAMMTD */

#ifdef HAVE_USBHOST
  /* Initialize USB host operation.  stm32_usbhost_initialize() starts a thread
   * will monitor for USB connection and disconnection events.
   */

  ret = stm32_usbhost_initialize();
  if (ret != OK)
    {
      syslog(LOG_ERR, "ERROR: Failed to initialize USB host: %d\n", ret);
      return ret;
    }
#endif

#ifdef HAVE_USBMONITOR
  /* Start the USB Monitor */

  ret = usbmonitor_start(0, NULL);
  if (ret != OK)
    {
      syslog(LOG_ERR, "ERROR: Failed to start USB monitor: %d\n", ret);
    }
#endif

  return OK;
}
예제 #12
0
파일: stm32_appinit.c 프로젝트: a1ien/nuttx
int board_app_initialize(uintptr_t arg)
{
#ifdef CONFIG_STM32_SPI1
  FAR struct spi_dev_s *spi;
  FAR struct mtd_dev_s *mtd;
#endif
#ifdef NSH_HAVEMMCSD
  FAR struct sdio_dev_s *sdio;
#endif
  int ret;

  /* Register I2C drivers on behalf of the I2C tool */

  stm32_i2ctool();

  /* Configure SPI-based devices */

#ifdef CONFIG_STM32_SPI1
  /* Get the SPI port */

  syslog(LOG_INFO, "Initializing SPI port 1\n");
  spi = stm32_spibus_initialize(1);
  if (!spi)
    {
      syslog(LOG_ERR, "ERROR: Failed to initialize SPI port 0\n");
      return -ENODEV;
    }
  syslog(LOG_INFO, "Successfully initialized SPI port 0\n");

  /* Now bind the SPI interface to the M25P64/128 SPI FLASH driver */

  syslog(LOG_INFO, "Bind SPI to the SPI flash driver\n");

  mtd = m25p_initialize(spi);
  if (!mtd)
    {
      syslog(LOG_ERR, "ERROR: Failed to bind SPI port 0 to the SPI FLASH driver\n");
      return -ENODEV;
    }

  syslog(LOG_INFO, "Successfully bound SPI port 0 to the SPI FLASH driver\n");
#warning "Now what are we going to do with this SPI FLASH driver?"
#endif

  /* Create the SPI FLASH MTD instance */
  /* The M25Pxx is not a give media to implement a file system..
   * its block sizes are too large
   */

  /* Mount the SDIO-based MMC/SD block driver */

#ifdef NSH_HAVEMMCSD
  /* First, get an instance of the SDIO interface */

  syslog(LOG_INFO, "Initializing SDIO slot %d\n",
         CONFIG_NSH_MMCSDSLOTNO);

  sdio = sdio_initialize(CONFIG_NSH_MMCSDSLOTNO);
  if (!sdio)
    {
      syslog(LOG_ERR, "ERROR: Failed to initialize SDIO slot %d\n",
             CONFIG_NSH_MMCSDSLOTNO);
      return -ENODEV;
    }

  /* Now bind the SDIO interface to the MMC/SD driver */

  syslog(LOG_INFO, "Bind SDIO to the MMC/SD driver, minor=%d\n",
         CONFIG_NSH_MMCSDMINOR);

  ret = mmcsd_slotinitialize(CONFIG_NSH_MMCSDMINOR, sdio);
  if (ret != OK)
    {
      syslog(LOG_ERR, "ERROR: Failed to bind SDIO to the MMC/SD driver: %d\n", ret);
      return ret;
    }

  syslog(LOG_INFO, "Successfully bound SDIO to the MMC/SD driver\n");

  /* Then let's guess and say that there is a card in the slot.  I need to check to
   * see if the STM3210E-EVAL board supports a GPIO to detect if there is a card in
   * the slot.
   */

   sdio_mediachange(sdio, true);
#endif

#ifdef CONFIG_ADC
  /* Initialize ADC and register the ADC driver. */

  ret = stm32_adc_setup();
  if (ret < 0)
    {
      syslog(LOG_ERR, "ERROR: stm32_adc_setup failed: %d\n", ret);
    }
#endif

#ifdef CONFIG_CAN
  /* Initialize CAN and register the CAN driver. */

  ret = stm32_can_setup();
  if (ret < 0)
    {
      syslog(LOG_ERR, "ERROR: stm32_can_setup failed: %d\n", ret);
    }
#endif

#ifdef CONFIG_DJOYSTICK
  /* Initialize and register the joystick driver */

  ret = stm32_djoy_initialization();
  if (ret != OK)
    {
      syslog(LOG_ERR, "ERROR: Failed to register the joystick driver: %d\n", ret);
      return ret;
    }

  syslog(LOG_INFO, "Successfully registered the joystick driver\n");
#endif

  UNUSED(ret);
  return OK;
}
예제 #13
0
파일: init.c 프로젝트: vivienJ/Firmware
__EXPORT int board_app_initialize(uintptr_t arg)
{
	/* Ensure the power is on 1 ms before we drive the GPIO pins */
	usleep(1000);

	if (OK == determin_hw_version(&hw_version, & hw_revision)) {
		switch (hw_version) {
		case HW_VER_FMUV2_STATE:
			break;

		case HW_VER_FMUV3_STATE:
			hw_type[1]++;
			hw_type[2] = '0';

			/* Has CAN2 transceiver Remove pull up */

			stm32_configgpio(GPIO_CAN2_RX);

			break;

		case HW_VER_FMUV2MINI_STATE:

			/* Detection for a Pixhack3 */

			stm32_configgpio(HW_VER_PA8);
			up_udelay(10);
			bool isph3 = stm32_gpioread(HW_VER_PA8);
			stm32_configgpio(HW_VER_PA8_INIT);


			if (isph3) {

				/* Pixhack3 looks like a FMuV3 Cube */

				hw_version = HW_VER_FMUV3_STATE;
				hw_type[1]++;
				hw_type[2] = '0';
				message("\nPixhack V3 detected, forcing to fmu-v3");

			} else {

				/* It is a mini */

				hw_type[2] = 'M';
			}

			break;

		default:

			/* questionable px4_fmu-v2 hardware, try forcing regular FMUv2 (not much else we can do) */

			message("\nbad version detected, forcing to fmu-v2");
			hw_version = HW_VER_FMUV2_STATE;
			break;
		}

		message("\nFMUv2 ver 0x%1X : Rev %x %s\n", hw_version, hw_revision, hw_type);
	}

	/* configure SPI interfaces */
	stm32_spiinitialize();

	px4_platform_init();

	/* configure the DMA allocator */

	if (board_dma_alloc_init() < 0) {
		message("DMA alloc FAILED");
	}

	/* set up the serial DMA polling */
	static struct hrt_call serial_dma_call;
	struct timespec ts;

	/*
	 * Poll at 1ms intervals for received bytes that have not triggered
	 * a DMA event.
	 */
	ts.tv_sec = 0;
	ts.tv_nsec = 1000000;

	hrt_call_every(&serial_dma_call,
		       ts_to_abstime(&ts),
		       ts_to_abstime(&ts),
		       (hrt_callout)stm32_serial_dma_poll,
		       NULL);

	/* initial LED state */
	drv_led_start();
	led_off(LED_AMBER);

	if (board_hardfault_init(2, true) != 0) {
		led_on(LED_AMBER);
	}

	/* Configure SPI-based devices */

	spi1 = stm32_spibus_initialize(PX4_SPI_BUS_SENSORS);

	if (!spi1) {
		message("[boot] FAILED to initialize SPI port %d\n", PX4_SPI_BUS_SENSORS);
		led_on(LED_AMBER);
		return -ENODEV;
	}

	/* Default SPI1 to 1MHz and de-assert the known chip selects. */
	SPI_SETFREQUENCY(spi1, 10000000);
	SPI_SETBITS(spi1, 8);
	SPI_SETMODE(spi1, SPIDEV_MODE3);
	up_udelay(20);

	/* Get the SPI port for the FRAM */

	spi2 = stm32_spibus_initialize(PX4_SPI_BUS_RAMTRON);

	if (!spi2) {
		message("[boot] FAILED to initialize SPI port %d\n", PX4_SPI_BUS_RAMTRON);
		led_on(LED_AMBER);
		return -ENODEV;
	}

	/* Default SPI2 to 37.5 MHz (40 MHz rounded to nearest valid divider, F4 max)
	 * and de-assert the known chip selects. */

	// XXX start with 10.4 MHz in FRAM usage and go up to 37.5 once validated
	SPI_SETFREQUENCY(spi2, 12 * 1000 * 1000);
	SPI_SETBITS(spi2, 8);
	SPI_SETMODE(spi2, SPIDEV_MODE3);

	spi4 = stm32_spibus_initialize(PX4_SPI_BUS_EXT);

	if (!spi4) {
		message("[boot] FAILED to initialize SPI port %d\n", PX4_SPI_BUS_EXT);
		led_on(LED_AMBER);
		return -ENODEV;
	}

	/* Default SPI4 to 1MHz and de-assert the known chip selects. */
	SPI_SETFREQUENCY(spi4, 10000000);
	SPI_SETBITS(spi4, 8);
	SPI_SETMODE(spi4, SPIDEV_MODE3);

#ifdef CONFIG_MMCSD
	/* First, get an instance of the SDIO interface */

	sdio = sdio_initialize(CONFIG_NSH_MMCSDSLOTNO);

	if (!sdio) {
		led_on(LED_AMBER);
		message("[boot] Failed to initialize SDIO slot %d\n", CONFIG_NSH_MMCSDSLOTNO);
		return -ENODEV;
	}

	/* Now bind the SDIO interface to the MMC/SD driver */
	int ret = mmcsd_slotinitialize(CONFIG_NSH_MMCSDMINOR, sdio);

	if (ret != OK) {
		led_on(LED_AMBER);
		message("[boot] Failed to bind SDIO to the MMC/SD driver: %d\n", ret);
		return ret;
	}

	/* Then let's guess and say that there is a card in the slot. There is no card detect GPIO. */
	sdio_mediachange(sdio, true);

#endif

	return OK;
}
예제 #14
0
int board_app_initialize(void)
{
#ifdef HAVE_SST25
  FAR struct spi_dev_s *spi;
  FAR struct mtd_dev_s *mtd;
  int ret;

  /* Configure SPI-based devices */

  /* Get the SPI port */

  syslog(LOG_INFO, "Initializing SPI port %d\n",
         CONFIG_SPARK_FLASH_SPI);

  spi = stm32_spibus_initialize(CONFIG_SPARK_FLASH_SPI);
  if (!spi)
    {
      syslog(LOG_ERR, "ERROR: Failed to initialize SPI port %d\n",
             CONFIG_SPARK_FLASH_SPI);
      return -ENODEV;
    }

  syslog(LOG_INFO, "Successfully initialized SPI port %d\n",
         CONFIG_SPARK_FLASH_SPI);

  /* Now bind the SPI interface to the SST25 SPI FLASH driver */

  syslog(LOG_INFO, "Bind SPI to the SPI flash driver\n");

  mtd = sst25_initialize(spi);
  if (!mtd)
    {
      syslog(LOG_ERR, "ERROR: Failed to bind SPI port %d to the SPI FLASH driver\n",
             CONFIG_SPARK_FLASH_SPI);
    }
  else
    {
      syslog(LOG_INFO, "Successfully bound SPI port %d to the SPI FLASH driver\n",
             CONFIG_SPARK_FLASH_SPI);
    }

#ifndef CONFIG_SPARK_FLASH_PART

  /* Use the FTL layer to wrap the MTD driver as a block driver */

  ret = ftl_initialize(CONFIG_SPARK_FLASH_MINOR, mtd);
  if (ret < 0)
    {
      fdbg("ERROR: Initialize the FTL layer\n");
      return ret;
    }

#ifdef CONFIG_SPARK_MOUNT_FLASH
  char  partname[16];
  char  mntpoint[16];

  /* mount -t vfat /dev/mtdblock0 /mnt/p0 */

  snprintf(partname, sizeof(partname), "/dev/mtdblock%d",
           CONFIG_SPARK_FLASH_MINOR);
  snprintf(mntpoint, sizeof(mntpoint)-1, CONFIG_SPARK_FLASH_MOUNT_POINT,
           CONFIG_SPARK_FLASH_MINOR);

  /* Mount the file system at /mnt/pn  */

  ret = mount(partname, mntpoint, "vfat", 0, NULL);
  if (ret < 0)
    {
      fdbg("ERROR: Failed to mount the FAT volume: %d\n", errno);
      return ret;
    }

#endif
#else
    {
      int partno;
      int partsize;
      int partoffset;
      const char *partstring = CONFIG_SPARK_FLASH_PART_LIST;
      const char *ptr;
      FAR struct mtd_dev_s *mtd_part;
      char  partname[16];
      char  mntpoint[16];

      /* Now create a partition on the FLASH device */

      partno = CONFIG_SPARK_FLASH_MINOR;
      ptr = partstring;
      partoffset = 0;
      while (*ptr != '\0')
        {
          /* Get the partition size */

          partsize = atoi(ptr);
          mtd_part = mtd_partition(mtd, partoffset, (partsize >> 2) * 16);
          partoffset += (partsize >> 2) * 16;

          /* Use the FTL layer to wrap the MTD driver as a block driver */

          ret = ftl_initialize(partno, mtd_part);
          if (ret < 0)
            {
              fdbg("ERROR: Initialize the FTL layer\n");
              return ret;
            }

          snprintf(partname,sizeof(partname), "/dev/mtdblock%d", partno);
          snprintf(mntpoint,sizeof(mntpoint)-1, CONFIG_SPARK_FLASH_MOUNT_POINT,
                   partno);

          /* Mount the file system at /mnt/pn  */

          ret = mount(partname, mntpoint, "vfat", 0, NULL);
          if (ret < 0)
            {
              fdbg("ERROR: Failed to mount the FAT volume: %d\n", errno);
              return ret;
            }

          /* Update the pointer to point to the next size in the list */

          while ((*ptr >= '0') && (*ptr <= '9'))
            {
              ptr++;
            }

          if (*ptr == ',')
            {
              ptr++;
            }

          /* Increment the part number */

          partno++;
        }
    }
#endif /* CONFIG_SPARK_FLASH_PART */

#endif /* HAVE_SST25 */

#ifdef HAVE_USBMONITOR
  /* Start the USB Monitor */

  ret = usbmonitor_start(0, NULL);
  if (ret != OK)
    {
      syslog(LOG_ERR, "ERROR: Failed to start USB monitor: %d\n", ret);
    }
#endif

  return OK;
}
예제 #15
0
파일: stm32_appinit.c 프로젝트: a1ien/nuttx
int board_app_initialize(uintptr_t arg)
{
#ifdef HAVE_RTC_DRIVER
  FAR struct rtc_lowerhalf_s *lower;
#endif
#ifdef CONFIG_STM32_SPI1
  FAR struct spi_dev_s *spi;
  FAR struct mtd_dev_s *mtd;
#endif
#ifdef HAVE_MMCSD
  FAR struct sdio_dev_s *sdio;
#endif
  int ret;

  /* Register I2C drivers on behalf of the I2C tool */

  stm32_i2ctool();

#ifdef HAVE_RTC_DRIVER
  /* Instantiate the STM32 lower-half RTC driver */

  lower = stm32_rtc_lowerhalf();
  if (!lower)
    {
      syslog(LOG_ERR,
             "ERROR: Failed to instantiate the RTC lower-half driver\n");
      return -ENOMEM;
    }
  else
    {
      /* Bind the lower half driver and register the combined RTC driver
       * as /dev/rtc0
       */

      ret = rtc_initialize(0, lower);
      if (ret < 0)
        {
          syslog(LOG_ERR,
                 "ERROR: Failed to bind/register the RTC driver: %d\n",
                 ret);
          return ret;
        }
    }
#endif

  /* Configure SPI-based devices */

#ifdef CONFIG_STM32_SPI1
  /* Get the SPI port */

  spi = stm32_spibus_initialize(1);
  if (!spi)
    {
      syslog(LOG_ERR, "ERROR: Failed to initialize SPI port 0\n");
      return -ENODEV;
    }

  /* Now bind the SPI interface to the M25P64/128 SPI FLASH driver */

  mtd = m25p_initialize(spi);
  if (!mtd)
    {
      syslog(LOG_ERR,
             "ERROR: Failed to bind SPI port 0 to the SPI FLASH driver\n");
      return -ENODEV;
    }
#warning "Now what are we going to do with this SPI FLASH driver?"
#endif

  /* Mount the SDIO-based MMC/SD block driver */

#ifdef HAVE_MMCSD
  /* First, get an instance of the SDIO interface */

  sdio = sdio_initialize(CONFIG_NSH_MMCSDSLOTNO);
  if (!sdio)
    {
      syslog(LOG_ERR,
             "ERROR: Failed to initialize SDIO slot %d\n",
             CONFIG_NSH_MMCSDSLOTNO);
      return -ENODEV;
    }

  /* Now bind the SDIO interface to the MMC/SD driver */

  ret = mmcsd_slotinitialize(CONFIG_NSH_MMCSDMINOR, sdio);
  if (ret != OK)
    {
      syslog(LOG_ERR,
             "ERROR: Failed to bind SDIO to the MMC/SD driver: %d\n",
             ret);
      return ret;
    }

  /* Then let's guess and say that there is a card in the slot.  I need to check to
   * see if the STM3240G-EVAL board supports a GPIO to detect if there is a card in
   * the slot.
   */

   sdio_mediachange(sdio, true);
#endif

#ifdef HAVE_USBHOST
  /* Initialize USB host operation.  stm32_usbhost_initialize() starts a thread
   * will monitor for USB connection and disconnection events.
   */

  ret = stm32_usbhost_initialize();
  if (ret != OK)
    {
      syslog(LOG_ERR, "ERROR: Failed to initialize USB host: %d\n", ret);
      return ret;
    }
#endif

#ifdef CONFIG_PWM
  /* Initialize PWM and register the PWM device. */

  ret = stm32_pwm_setup();
  if (ret < 0)
    {
      syslog(LOG_ERR, "ERROR: stm32_pwm_setup() failed: %d\n", ret);
    }
#endif

#ifdef CONFIG_ADC
  /* Initialize ADC and register the ADC driver. */

  ret = stm32_adc_setup();
  if (ret < 0)
    {
      syslog(LOG_ERR, "ERROR: stm32_adc_setup failed: %d\n", ret);
    }
#endif

#ifdef CONFIG_CAN
  /* Initialize CAN and register the CAN driver. */

  ret = stm32_can_setup();
  if (ret < 0)
    {
      syslog(LOG_ERR, "ERROR: stm32_can_setup failed: %d\n", ret);
    }
#endif

  UNUSED(ret);
  return OK;
}
예제 #16
0
__EXPORT int stm32_spi_bus_initialize(void)
{
	/* Configure SPI-based devices */

	/* Get the SPI port for the Sensors */

	spi_sensors = stm32_spibus_initialize(PX4_SPI_BUS_SENSORS);

	if (!spi_sensors) {
		message("[boot] FAILED to initialize SPI port %d\n", PX4_SPI_BUS_SENSORS);
		return -ENODEV;
	}

	/* Default PX4_SPI_BUS_SENSORS to 1MHz and de-assert the known chip selects. */

	SPI_SETFREQUENCY(spi_sensors, 10000000);
	SPI_SETBITS(spi_sensors, 8);
	SPI_SETMODE(spi_sensors, SPIDEV_MODE3);

	for (int cs = PX4_SENSORS_BUS_FIRST_CS; cs <= PX4_SENSORS_BUS_LAST_CS; cs++) {
		SPI_SELECT(spi_sensors, cs, false);
	}

	/* Get the SPI port for the Memory */

	spi_memory = stm32_spibus_initialize(PX4_SPI_BUS_MEMORY);

	if (!spi_memory) {
		message("[boot] FAILED to initialize SPI port %d\n", PX4_SPI_BUS_MEMORY);
		return -ENODEV;
	}

	/* Default PX4_SPI_BUS_MEMORY to 12MHz and de-assert the known chip selects.
	 */

	SPI_SETFREQUENCY(spi_memory, 12 * 1000 * 1000);
	SPI_SETBITS(spi_memory, 8);
	SPI_SETMODE(spi_memory, SPIDEV_MODE3);

	for (int cs = PX4_MEMORY_BUS_FIRST_CS; cs <= PX4_MEMORY_BUS_LAST_CS; cs++) {
		SPI_SELECT(spi_memory, cs, false);
	}

	/* Get the SPI port for the BARO */

	spi_baro = stm32_spibus_initialize(PX4_SPI_BUS_BARO);

	if (!spi_baro) {
		message("[boot] FAILED to initialize SPI port %d\n", PX4_SPI_BUS_BARO);
		return -ENODEV;
	}

	/* MS5611 has max SPI clock speed of 20MHz
	 */

	SPI_SETFREQUENCY(spi_baro, 20 * 1000 * 1000);
	SPI_SETBITS(spi_baro, 8);
	SPI_SETMODE(spi_baro, SPIDEV_MODE3);

	for (int cs = PX4_BARO_BUS_FIRST_CS; cs <= PX4_BARO_BUS_LAST_CS; cs++) {
		SPI_SELECT(spi_baro, cs, false);
	}

	/* Get the SPI port for the PX4_SPI_EXTERNAL */

	spi_ext = stm32_spibus_initialize(PX4_SPI_BUS_EXTERNAL);

	if (!spi_ext) {
		message("[boot] FAILED to initialize SPI port %d\n", PX4_SPI_BUS_EXTERNAL);
		return -ENODEV;
	}

	SPI_SETFREQUENCY(spi_ext, 8 * 1000 * 1000);
	SPI_SETBITS(spi_ext, 8);
	SPI_SETMODE(spi_ext, SPIDEV_MODE3);

	for (int cs = PX4_EXTERNAL_BUS_FIRST_CS; cs <= PX4_EXTERNAL_BUS_LAST_CS; cs++) {
		SPI_SELECT(spi_ext, cs, false);
	}

	return OK;

}
예제 #17
0
__EXPORT int board_app_initialize(uintptr_t arg)
{

	int result;

	/* IN12 and IN13 further below */

#if defined(CONFIG_HAVE_CXX) && defined(CONFIG_HAVE_CXXINITIALIZE)

	/* run C++ ctors before we go any further */

	up_cxxinitialize();

#	if defined(CONFIG_EXAMPLES_NSH_CXXINITIALIZE)
#  		error CONFIG_EXAMPLES_NSH_CXXINITIALIZE Must not be defined! Use CONFIG_HAVE_CXX and CONFIG_HAVE_CXXINITIALIZE.
#	endif

#else
#  error platform is dependent on c++ both CONFIG_HAVE_CXX and CONFIG_HAVE_CXXINITIALIZE must be defined.
#endif

	/* configure the high-resolution time/callout interface */
	hrt_init();

	/* configure CPU load estimation */
#ifdef CONFIG_SCHED_INSTRUMENTATION
	cpuload_initialize_once();
#endif

	/* set up the serial DMA polling */
	static struct hrt_call serial_dma_call;
	struct timespec ts;

	/*
	 * Poll at 1ms intervals for received bytes that have not triggered
	 * a DMA event.
	 */
	ts.tv_sec = 0;
	ts.tv_nsec = 1000000;

	hrt_call_every(&serial_dma_call,
		       ts_to_abstime(&ts),
		       ts_to_abstime(&ts),
		       (hrt_callout)stm32_serial_dma_poll,
		       NULL);

	/* initial LED state */
	drv_led_start();
	led_off(LED_AMBER);
	led_off(LED_BLUE);


	/* Configure SPI-based devices */

	spi1 = stm32_spibus_initialize(1);

	if (!spi1) {
		message("[boot] FAILED to initialize SPI port 1\r\n");
		board_autoled_on(LED_AMBER);
		return -ENODEV;
	}

	/* Default SPI1 to 1MHz and de-assert the known chip selects. */
	SPI_SETFREQUENCY(spi1, 10000000);
	SPI_SETBITS(spi1, 8);
	SPI_SETMODE(spi1, SPIDEV_MODE3);
	SPI_SELECT(spi1, PX4_SPIDEV_GYRO, false);
	SPI_SELECT(spi1, PX4_SPIDEV_ACCEL, false);
	SPI_SELECT(spi1, PX4_SPIDEV_MPU, false);
	up_udelay(20);

	/*
	 * If SPI2 is enabled in the defconfig, we loose some ADC pins as chip selects.
	 * Keep the SPI2 init optional and conditionally initialize the ADC pins
	 */

#ifdef CONFIG_STM32_SPI2
	spi2 = stm32_spibus_initialize(2);
	/* Default SPI2 to 1MHz and de-assert the known chip selects. */
	SPI_SETFREQUENCY(spi2, 10000000);
	SPI_SETBITS(spi2, 8);
	SPI_SETMODE(spi2, SPIDEV_MODE3);
	SPI_SELECT(spi2, PX4_SPIDEV_GYRO, false);
	SPI_SELECT(spi2, PX4_SPIDEV_ACCEL_MAG, false);

	message("[boot] Initialized SPI port2 (ADC IN12/13 blocked)\n");
#else
	spi2 = NULL;
	message("[boot] Enabling IN12/13 instead of SPI2\n");
	/* no SPI2, use pins for ADC */
	stm32_configgpio(GPIO_ADC1_IN12);
	stm32_configgpio(GPIO_ADC1_IN13);	// jumperable to MPU6000 DRDY on some boards
#endif

	/* Get the SPI port for the microSD slot */

	spi3 = stm32_spibus_initialize(3);

	if (!spi3) {
		message("[boot] FAILED to initialize SPI port 3\n");
		board_autoled_on(LED_AMBER);
		return -ENODEV;
	}

	/* Now bind the SPI interface to the MMCSD driver */
	result = mmcsd_spislotinitialize(CONFIG_NSH_MMCSDMINOR, CONFIG_NSH_MMCSDSLOTNO, spi3);

	if (result != OK) {
		message("[boot] FAILED to bind SPI port 3 to the MMCSD driver\n");
		board_autoled_on(LED_AMBER);
		return -ENODEV;
	}

	return OK;
}
예제 #18
0
__EXPORT int board_app_initialize(uintptr_t arg)
{

#if defined(CONFIG_HAVE_CXX) && defined(CONFIG_HAVE_CXXINITIALIZE)

	/* run C++ ctors before we go any further */

	up_cxxinitialize();

#	if defined(CONFIG_EXAMPLES_NSH_CXXINITIALIZE)
#  		error CONFIG_EXAMPLES_NSH_CXXINITIALIZE Must not be defined! Use CONFIG_HAVE_CXX and CONFIG_HAVE_CXXINITIALIZE.
#	endif

#else
#  error platform is dependent on c++ both CONFIG_HAVE_CXX and CONFIG_HAVE_CXXINITIALIZE must be defined.
#endif

	/* configure the high-resolution time/callout interface */
	hrt_init();

	/* configure the DMA allocator */

	if (board_dma_alloc_init() < 0) {
		message("DMA alloc FAILED");
	}

	/* configure CPU load estimation */
#ifdef CONFIG_SCHED_INSTRUMENTATION
	cpuload_initialize_once();
#endif

	/* set up the serial DMA polling */
	static struct hrt_call serial_dma_call;
	struct timespec ts;

	/*
	 * Poll at 1ms intervals for received bytes that have not triggered
	 * a DMA event.
	 */
	ts.tv_sec = 0;
	ts.tv_nsec = 1000000;

	hrt_call_every(&serial_dma_call,
		       ts_to_abstime(&ts),
		       ts_to_abstime(&ts),
		       (hrt_callout)stm32_serial_dma_poll,
		       NULL);

#if defined(CONFIG_STM32_BBSRAM)

	/* NB. the use of the console requires the hrt running
	 * to poll the DMA
	 */

	/* Using Battery Backed Up SRAM */

	int filesizes[CONFIG_STM32_BBSRAM_FILES + 1] = BSRAM_FILE_SIZES;

	stm32_bbsraminitialize(BBSRAM_PATH, filesizes);

#if defined(CONFIG_STM32_SAVE_CRASHDUMP)

	/* Panic Logging in Battery Backed Up Files */

	/*
	 * In an ideal world, if a fault happens in flight the
	 * system save it to BBSRAM will then reboot. Upon
	 * rebooting, the system will log the fault to disk, recover
	 * the flight state and continue to fly.  But if there is
	 * a fault on the bench or in the air that prohibit the recovery
	 * or committing the log to disk, the things are too broken to
	 * fly. So the question is:
	 *
	 * Did we have a hard fault and not make it far enough
	 * through the boot sequence to commit the fault data to
	 * the SD card?
	 */

	/* Do we have an uncommitted hard fault in BBSRAM?
	 *  - this will be reset after a successful commit to SD
	 */
	int hadCrash = hardfault_check_status("boot");

	if (hadCrash == OK) {

		message("[boot] There is a hard fault logged. Hold down the SPACE BAR," \
			" while booting to halt the system!\n");

		/* Yes. So add one to the boot count - this will be reset after a successful
		 * commit to SD
		 */

		int reboots = hardfault_increment_reboot("boot", false);

		/* Also end the misery for a user that holds for a key down on the console */

		int bytesWaiting;
		ioctl(fileno(stdin), FIONREAD, (unsigned long)((uintptr_t) &bytesWaiting));

		if (reboots > 2 || bytesWaiting != 0) {

			/* Since we can not commit the fault dump to disk. Display it
			 * to the console.
			 */

			hardfault_write("boot", fileno(stdout), HARDFAULT_DISPLAY_FORMAT, false);

			message("[boot] There were %d reboots with Hard fault that were not committed to disk - System halted %s\n",
				reboots,
				(bytesWaiting == 0 ? "" : " Due to Key Press\n"));


			/* For those of you with a debugger set a break point on up_assert and
			 * then set dbgContinue = 1 and go.
			 */

			/* Clear any key press that got us here */

			static volatile bool dbgContinue = false;
			int c = '>';

			while (!dbgContinue) {

				switch (c) {

				case EOF:


				case '\n':
				case '\r':
				case ' ':
					continue;

				default:

					putchar(c);
					putchar('\n');

					switch (c) {

					case 'D':
					case 'd':
						hardfault_write("boot", fileno(stdout), HARDFAULT_DISPLAY_FORMAT, false);
						break;

					case 'C':
					case 'c':
						hardfault_rearm("boot");
						hardfault_increment_reboot("boot", true);
						break;

					case 'B':
					case 'b':
						dbgContinue = true;
						break;

					default:
						break;
					} // Inner Switch

					message("\nEnter B - Continue booting\n" \
						"Enter C - Clear the fault log\n" \
						"Enter D - Dump fault log\n\n?>");
					fflush(stdout);

					if (!dbgContinue) {
						c = getchar();
					}

					break;

				} // outer switch
			} // for

		} // inner if
	} // outer if

#endif // CONFIG_STM32_SAVE_CRASHDUMP
#endif // CONFIG_STM32_BBSRAM

	/* initial LED state */
	drv_led_start();
	led_off(LED_RED);
	led_off(LED_GREEN);
	led_off(LED_BLUE);

	/* Configure SPI-based devices */

	spi1 = stm32_spibus_initialize(1);

	if (!spi1) {
		message("[boot] FAILED to initialize SPI port 1\n");
		board_autoled_on(LED_RED);
		return -ENODEV;
	}

	/* Default SPI1 to 1MHz and de-assert the known chip selects. */
	SPI_SETFREQUENCY(spi1, 10000000);
	SPI_SETBITS(spi1, 8);
	SPI_SETMODE(spi1, SPIDEV_MODE3);
	SPI_SELECT(spi1, PX4_SPIDEV_GYRO, false);
	SPI_SELECT(spi1, PX4_SPIDEV_HMC, false);
	SPI_SELECT(spi1, PX4_SPIDEV_MPU, false);
	up_udelay(20);

	/* Get the SPI port for the FRAM */

	spi2 = stm32_spibus_initialize(2);

	if (!spi2) {
		message("[boot] FAILED to initialize SPI port 2\n");
		board_autoled_on(LED_RED);
		return -ENODEV;
	}

	/* Default SPI2 to 12MHz and de-assert the known chip selects.
	 * MS5611 has max SPI clock speed of 20MHz
	 */

	// XXX start with 10.4 MHz and go up to 20 once validated
	SPI_SETFREQUENCY(spi2, 20 * 1000 * 1000);
	SPI_SETBITS(spi2, 8);
	SPI_SETMODE(spi2, SPIDEV_MODE3);
	SPI_SELECT(spi2, SPIDEV_FLASH, false);
	SPI_SELECT(spi2, PX4_SPIDEV_BARO, false);

#ifdef CONFIG_MMCSD
	/* First, get an instance of the SDIO interface */

	sdio = sdio_initialize(CONFIG_NSH_MMCSDSLOTNO);

	if (!sdio) {
		message("[boot] Failed to initialize SDIO slot %d\n",
			CONFIG_NSH_MMCSDSLOTNO);
		return -ENODEV;
	}

	/* Now bind the SDIO interface to the MMC/SD driver */
	int ret = mmcsd_slotinitialize(CONFIG_NSH_MMCSDMINOR, sdio);

	if (ret != OK) {
		message("[boot] Failed to bind SDIO to the MMC/SD driver: %d\n", ret);
		return ret;
	}

	/* Then let's guess and say that there is a card in the slot. There is no card detect GPIO. */
	sdio_mediachange(sdio, true);

#endif

	return OK;
}
예제 #19
0
파일: stm32_appinit.c 프로젝트: dagar/NuttX
int board_app_initialize(uintptr_t arg)
{
#ifdef CONFIG_STM32_SPI3
  FAR struct spi_dev_s *spi;
  FAR struct mtd_dev_s *mtd;
#endif
  int ret = OK;

  /* Configure SPI-based devices */

#ifdef CONFIG_STM32_SPI3
  /* Get the SPI port */

  syslog(LOG_INFO, "Initializing SPI port 3\n");
  spi = stm32_spibus_initialize(3);
  if (!spi)
    {
      syslog(LOG_ERR, "ERROR: Failed to initialize SPI port 3\n");
      return -ENODEV;
    }

  syslog(LOG_INFO, "Successfully initialized SPI port 3\n");

  /* Now bind the SPI interface to the M25P8 SPI FLASH driver */

#if defined(CONFIG_MTD) && defined(CONFIG_MIKROE_FLASH)
  syslog(LOG_INFO, "Bind SPI to the SPI flash driver\n");

  mtd = m25p_initialize(spi);
  if (!mtd)
    {
      syslog(LOG_ERR, "ERROR: Failed to bind SPI port 3 to the SPI FLASH driver\n");
    }
  else
    {
      syslog(LOG_INFO, "Successfully bound SPI port 3 to the SPI FLASH driver\n");

#ifdef CONFIG_MIKROE_FLASH_PART
      {
        int partno;
        int partsize;
        int partoffset;
        const char *partstring = CONFIG_MIKROE_FLASH_PART_LIST;
        const char *ptr;
        FAR struct mtd_dev_s *mtd_part;
        char  partname[4];

        /* Now create a partition on the FLASH device */

        partno = 0;
        ptr = partstring;
        partoffset = 0;

        while (*ptr != '\0')
          {
            /* Get the partition size */

            partsize = atoi(ptr);
            mtd_part = mtd_partition(mtd, partoffset, (partsize>>2)*16);
            partoffset += (partsize >> 2) * 16;

#ifdef CONFIG_MIKROE_FLASH_CONFIG_PART
            /* Test if this is the config partition */

            if (CONFIG_MIKROE_FLASH_CONFIG_PART_NUMBER == partno)
              {
                /* Register the partition as the config device */

                mtdconfig_register(mtd_part);
              }
            else
#endif
              {
                /* Now initialize a SMART Flash block device and bind it
                 * to the MTD device.
                 */

#if defined(CONFIG_MTD_SMART) && defined(CONFIG_FS_SMARTFS)
                sprintf(partname, "p%d", partno);
                smart_initialize(CONFIG_MIKROE_FLASH_MINOR, mtd_part, partname);
#endif
              }

            /* Update the pointer to point to the next size in the list */

            while ((*ptr >= '0') && (*ptr <= '9'))
              {
                ptr++;
              }

            if (*ptr == ',')
              {
                ptr++;
              }

            /* Increment the part number */

            partno++;
          }
      }
#else /* CONFIG_MIKROE_FLASH_PART */

      /* Configure the device with no partition support */

      smart_initialize(CONFIG_MIKROE_FLASH_MINOR, mtd, NULL);

#endif /* CONFIG_MIKROE_FLASH_PART */
    }

  /* Create a RAM MTD device if configured */

#if defined(CONFIG_RAMMTD) && defined(CONFIG_MIKROE_RAMMTD)
  {
    uint8_t *start = (uint8_t *) kmm_malloc(CONFIG_MIKROE_RAMMTD_SIZE * 1024);
    mtd = rammtd_initialize(start, CONFIG_MIKROE_RAMMTD_SIZE * 1024);
    mtd->ioctl(mtd, MTDIOC_BULKERASE, 0);

    /* Now initialize a SMART Flash block device and bind it to the MTD device */

#if defined(CONFIG_MTD_SMART) && defined(CONFIG_FS_SMARTFS)
    smart_initialize(CONFIG_MIKROE_RAMMTD_MINOR, mtd, NULL);
#endif
  }

#endif /* CONFIG_RAMMTD && CONFIG_MIKROE_RAMMTD */

#endif /* CONFIG_MTD */
#endif /* CONFIG_STM32_SPI3 */

  /* Create the SPI FLASH MTD instance */
  /* The M25Pxx is not a good media to implement a file system..
   * its block sizes are too large
   */

  /* Mount the SDIO-based MMC/SD block driver */

#ifdef NSH_HAVEMMCSD
  /* Bind the spi interface to the MMC/SD driver */

  syslog(LOG_INFO, "Bind SDIO to the MMC/SD driver, minor=%d\n",
         CONFIG_NSH_MMCSDMINOR);

  ret = mmcsd_spislotinitialize(CONFIG_NSH_MMCSDMINOR, CONFIG_NSH_MMCSDSLOTNO, spi);
  if (ret != OK)
    {
      syslog(LOG_ERR, "ERROR: Failed to bind SPI to the MMC/SD driver: %d\n", ret);
    }
  else
    {
      syslog(LOG_INFO, "Successfully bound SPI to the MMC/SD driver\n");
    }
#endif

#ifdef HAVE_USBHOST
  /* Initialize USB host operation.  stm32_usbhost_initialize() starts a thread
   * will monitor for USB connection and disconnection events.
   */

  ret = stm32_usbhost_initialize();
  if (ret != OK)
    {
      syslog(LOG_ERR, "ERROR: Failed to initialize USB host: %d\n", ret);
      return ret;
    }
#endif

#ifdef HAVE_USBMONITOR
  /* Start the USB Monitor */

  ret = usbmonitor_start();
  if (ret != OK)
    {
      syslog(LOG_ERR, "ERROR: Failed to start USB monitor: %d\n", ret);
    }
#endif

#ifdef CONFIG_INPUT
  /* Initialize the touchscreen */

  ret = stm32_tsc_setup(0);
  if (ret < 0)
    {
      syslog(LOG_ERR, "ERROR: stm32_tsc_setup failed: %d\n", ret);
    }
#endif

#ifdef CONFIG_PWM
  /* Initialize PWM and register the PWM device. */

  ret = stm32_pwm_setup();
  if (ret < 0)
    {
      syslog(LOG_ERR, "ERROR: stm32_pwm_setup() failed: %d\n", ret);
    }
#endif

#if defined(CONFIG_LCD_MIO283QT2) || defined(CONFIG_LCD_MIO283QT9A)
  /* Configure the TFT LCD module */

  syslog(LOG_INFO, "Initializing TFT LCD module\n");

  ret = board_lcd_initialize();
  if (ret < 0)
    {
      syslog(LOG_ERR, "ERROR: Failed to initialize TFT LCD module\n");
    }
#endif

#ifdef CONFIG_SENSORS_QENCODER
  /* Initialize and register the qencoder driver */

  ret = stm32_qencoder_initialize("/dev/qe0", CONFIG_MIKROE_QETIMER);
  if (ret != OK)
    {
      syslog(LOG_ERR,
             "ERROR: Failed to register the qencoder: %d\n",
             ret);
      return ret;
    }
#endif

#ifdef CONFIG_AUDIO
  /* Configure the Audio sub-system if enabled and bind it to SPI 3 */

  up_vs1053initialize(spi);
#endif

  return ret;
}