This is an automated email from the ASF dual-hosted git repository.

xiaoxiang pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/incubator-nuttx.git


The following commit(s) were added to refs/heads/master by this push:
     new fafe91cec6 Nucleo Wl55JC board supports E-ink display
fafe91cec6 is described below

commit fafe91cec64ffeaf230f38d5606c1dd1b97c71b4
Author: Adam Kaliszan <akalis...@altimetrik.com>
AuthorDate: Mon Jun 13 11:00:50 2022 +0200

    Nucleo Wl55JC board supports E-ink display
    
    All works
    SPI pinouts is arduino compatibile
    Additional lines for display are configurable using make menuconfig
---
 boards/arm/stm32wl5/nucleo-wl55jc/Kconfig          | 151 ++++++++++++
 .../stm32wl5/nucleo-wl55jc/configs/fb/defconfig    |  44 ++++
 boards/arm/stm32wl5/nucleo-wl55jc/include/board.h  |   8 +
 boards/arm/stm32wl5/nucleo-wl55jc/src/Makefile     |  10 +
 .../arm/stm32wl5/nucleo-wl55jc/src/nucleo-wl55jc.h |  80 +++++++
 boards/arm/stm32wl5/nucleo-wl55jc/src/stm32_boot.c |  24 ++
 boards/arm/stm32wl5/nucleo-wl55jc/src/stm32_spi.c  | 252 +++++++++++++++++++++
 .../arm/stm32wl5/nucleo-wl55jc/src/stm32_ssd1680.c | 190 ++++++++++++++++
 .../src/{nucleo-wl55jc.h => stm32wl5_ssd1680.h}    |  67 ++----
 9 files changed, 781 insertions(+), 45 deletions(-)

diff --git a/boards/arm/stm32wl5/nucleo-wl55jc/Kconfig 
b/boards/arm/stm32wl5/nucleo-wl55jc/Kconfig
index a65425890d..134d59c7ae 100644
--- a/boards/arm/stm32wl5/nucleo-wl55jc/Kconfig
+++ b/boards/arm/stm32wl5/nucleo-wl55jc/Kconfig
@@ -275,4 +275,155 @@ endif # ARCH_BOARD_FLASH_PART4_SIZE > 0
 
 endif # ARCH_BOARD_FLASH_MOUNT
 
+if LCD_SSD1680 && ARCH_BOARD_NUCLEO_WL55JC
+
+menu "E-ink SSD1680 pins config"
+
+choice
+       prompt "Port that handles Chip Select line (output)"
+       default SSD1680_GPIO_CS_PORTA if ARCH_BOARD_NUCLEO_WL55JC
+
+config SSD1680_GPIO_CS_DISABLED
+       bool "Not available"
+
+config SSD1680_GPIO_CS_PORTA
+       bool "Port A"
+
+config SSD1680_GPIO_CS_PORTB
+       bool "Port B"
+
+config SSD1680_GPIO_CS_PORTC
+       bool "Port C"
+
+config SSD1680_GPIO_CS_PORTD
+       bool "Port D"
+
+endchoice
+
+if SSD1680_GPIO_CS_PORTA || SSD1680_GPIO_CS_PORTB || SSD1680_GPIO_CS_PORTC || 
SSD1680_GPIO_CS_PORTD
+config SSD1680_GPIO_PIN_CS
+       int "Pin that select the chip on SPI bus (output)"
+       default "4" if ARCH_BOARD_NUCLEO_WL55JC
+       range 0 15
+endif #SSD1680_GPIO_CS_PORTA || SSD1680_GPIO_CS_PORTB || SSD1680_GPIO_CS_PORTC 
|| SSD1680_GPIO_CS_PORTD
+
+choice
+       prompt "Port that handles Data/!Command line"
+       default SSD1680_GPIO_DTA_CMD_PORTA if ARCH_BOARD_NUCLEO_WL55JC
+
+config SSD1680_GPIO_DTA_CMD_DISABLED
+       bool "Not available"
+
+config SSD1680_GPIO_DTA_CMD_PORTA
+       bool "Port A"
+
+config SSD1680_GPIO_DTA_CMD_PORTB
+       bool "Port B"
+
+config SSD1680_GPIO_DTA_CMD_PORTC
+       bool "Port C"
+
+config SSD1680_GPIO_DTA_CMD_PORTD
+       bool "Port D"
+
+endchoice
+
+if SSD1680_GPIO_DTA_CMD_PORTA || SSD1680_GPIO_DTA_CMD_PORTB || 
SSD1680_GPIO_DTA_CMD_PORTC || SSD1680_GPIO_DTA_CMD_PORTD
+config SSD1680_GPIO_PIN_DTA_CMD
+       int "Pin that switch between command and data on 4-wire SPI bus"
+       default "9" if ARCH_BOARD_NUCLEO_WL55JC
+       range 0 15
+endif #SSD1680_GPIO_DTA_CMD_PORTA || SSD1680_GPIO_DTA_CMD_PORTB || 
SSD1680_GPIO_DTA_CMD_PORTC || SSD1680_GPIO_DTA_CMD_PORTD
+
+choice
+       prompt "Port that handles reset line (output)"
+       default SSD1680_GPIO_RST_PORTC if ARCH_BOARD_NUCLEO_WL55JC
+
+config SSD1680_GPIO_RST_DISABLED
+       bool "Not available"
+
+config SSD1680_GPIO_RST_PORTA
+       bool "Port A"
+
+config SSD1680_GPIO_RST_PORTB
+       bool "Port B"
+
+config SSD1680_GPIO_RST_PORTC
+       bool "Port C"
+
+config SSD1680_GPIO_RST_PORTD
+       bool "Port D"
+endchoice
+
+if SSD1680_GPIO_RST_PORTA || SSD1680_GPIO_RST_PORTB || SSD1680_GPIO_RST_PORTC 
|| SSD1680_GPIO_RST_PORTD
+config SSD1680_GPIO_PIN_RST
+       int "Pin that handles the reset line (output)"
+       default "2" if ARCH_BOARD_NUCLEO_WL55JC
+       range 0 15
+endif #SSD1680_GPIO_RST_PORTA || SSD1680_GPIO_RST_PORTB || 
SSD1680_GPIO_RST_PORTC || SSD1680_GPIO_RST_PORTD
+
+choice
+       prompt "Port that handles busy line (input)"
+       default SSD1680_GPIO_BUSY_PORTC if ARCH_BOARD_NUCLEO_WL55JC
+
+config SSD1680_GPIO_BUSY_DISABLED
+       bool "Not available"
+
+config SSD1680_GPIO_BUSY_PORTA
+       bool "Port A"
+
+config SSD1680_GPIO_BUSY_PORTB
+       bool "Port B"
+
+config SSD1680_GPIO_BUSY_PORTC
+       bool "Port C"
+
+config SSD1680_GPIO_BUSY_PORTD
+       bool "Port D"
+
+endchoice
+
+if SSD1680_GPIO_BUSY_PORTA || SSD1680_GPIO_BUSY_PORTB || 
SSD1680_GPIO_BUSY_PORTC || SSD1680_GPIO_BUSY_PORTD
+config SSD1680_GPIO_PIN_BUSY
+       int "Pin that handles the busy line (input)"
+       default "1" if ARCH_BOARD_NUCLEO_WL55JC
+       range 0 15
+endif #SSD1680_GPIO_BUSY_PORTA || SSD1680_GPIO_BUSY_PORTB || 
SSD1680_GPIO_BUSY_PORTC || SSD1680_GPIO_BUSY_PORTD
+
+choice
+       prompt "Port that handles power line"
+       default SSD1680_GPIO_PWR_DISABLED if ARCH_BOARD_NUCLEO_WL55JC
+
+config SSD1680_GPIO_PWR_DISABLED
+       bool "Not available"
+
+config SSD1680_GPIO_PWR_PORTA
+       bool "Port A"
+
+config SSD1680_GPIO_PWR_PORTB
+       bool "Port B"
+
+config SSD1680_GPIO_PWR_PORTC
+       bool "Port C"
+
+config SSD1680_GPIO_PWR_PORTD
+       bool "Port D"
+
+endchoice
+
+if SSD1680_GPIO_PWR_PORTA || SSD1680_GPIO_PWR_PORTB || SSD1680_GPIO_PWR_PORTC 
|| SSD1680_GPIO_PWR_PORTD
+config SSD1680_GPIO_PIN_PWR
+       int "Pin that handles the pwr on/off line (output)"
+       range 0 31
+endif #SSD1680_GPIO_PWR_PORTA || SSD1680_GPIO_PWR_PORTB || 
SSD1680_GPIO_PWR_PORTC || SSD1680_GPIO_PWR_PORTD
+
+
+config SSD1680_SPI_BUS
+       int "Spi bus no"
+       range 1 2
+       default "1"
+endmenu
+
+endif #LCD_SSD1680
+
 endif # ARCH_BOARD_NUCLEO_WL55JC
diff --git a/boards/arm/stm32wl5/nucleo-wl55jc/configs/fb/defconfig 
b/boards/arm/stm32wl5/nucleo-wl55jc/configs/fb/defconfig
new file mode 100644
index 0000000000..62a6c06261
--- /dev/null
+++ b/boards/arm/stm32wl5/nucleo-wl55jc/configs/fb/defconfig
@@ -0,0 +1,44 @@
+#
+# This file is autogenerated: PLEASE DO NOT EDIT IT.
+#
+# You can use "make menuconfig" to make any modifications to the installed 
.config file.
+# You can then do "make savedefconfig" to generate a new defconfig file that 
includes your
+# modifications.
+#
+# CONFIG_STANDARD_SERIAL is not set
+CONFIG_ARCH="arm"
+CONFIG_ARCH_BOARD="nucleo-wl55jc"
+CONFIG_ARCH_BOARD_COMMON=y
+CONFIG_ARCH_BOARD_NUCLEO_WL55JC=y
+CONFIG_ARCH_BUTTONS=y
+CONFIG_ARCH_CHIP="stm32wl5"
+CONFIG_ARCH_CHIP_STM32WL55JC_CPU1=y
+CONFIG_ARCH_CHIP_STM32WL5=y
+CONFIG_BOARD_LATE_INITIALIZE=y
+CONFIG_BUILTIN=y
+CONFIG_DRIVERS_VIDEO=y
+CONFIG_EXAMPLES_FB=y
+CONFIG_FB_MODULEINFO=y
+CONFIG_INIT_ENTRYNAME="main"
+CONFIG_INIT_ENTRYPOINT="nsh_main"
+CONFIG_LCD=y
+CONFIG_LCD_DEV=y
+CONFIG_LCD_FRAMEBUFFER=y
+CONFIG_LCD_SSD1680=y
+CONFIG_LCD_SSD1680_2_13_V2=y
+CONFIG_LPUART1_SERIAL_CONSOLE=y
+CONFIG_NSH_BUILTIN_APPS=y
+CONFIG_RAM_SIZE=32768
+CONFIG_RAM_START=0x20000000
+CONFIG_RAW_BINARY=y
+CONFIG_SPI=y
+CONFIG_SPI_DRIVER=y
+CONFIG_STM32WL5_LPUART1=y
+CONFIG_STM32WL5_SPI1=y
+CONFIG_STM32WL5_USART1=y
+
+CONFIG_STM32WL5_LPUART1=y
+CONFIG_STM32WL5_SPI1=y
+CONFIG_STM32WL5_SPI2S2=y
+CONFIG_SYSTEM_NSH=y
+CONFIG_VIDEO_FB=y
diff --git a/boards/arm/stm32wl5/nucleo-wl55jc/include/board.h 
b/boards/arm/stm32wl5/nucleo-wl55jc/include/board.h
index 2d841e03fe..d786833bd0 100644
--- a/boards/arm/stm32wl5/nucleo-wl55jc/include/board.h
+++ b/boards/arm/stm32wl5/nucleo-wl55jc/include/board.h
@@ -136,6 +136,14 @@
 #define GPIO_LPUART1_RX GPIO_LPUART1_RX_1  /* PA3  */
 #define GPIO_LPUART1_TX GPIO_LPUART1_TX_1  /* PA2 */
 
+#define GPIO_SPI1_MISO   GPIO_SPI1_MISO_2
+#define GPIO_SPI1_MOSI   GPIO_SPI1_MOSI_2
+#define GPIO_SPI1_SCK    GPIO_SPI1_SCK_2
+
+#define GPIO_SPI2S2_MISO   GPIO_SPI2_MISO_2
+#define GPIO_SPI2S2_MOSI   GPIO_SPI2_MOSI_2
+#define GPIO_SPI2S2_SCK    GPIO_SPI2_SCK_3
+
 /* user buttons
  *
  * There are 3 buttons provided for user to program
diff --git a/boards/arm/stm32wl5/nucleo-wl55jc/src/Makefile 
b/boards/arm/stm32wl5/nucleo-wl55jc/src/Makefile
index 16a184a937..4bbfdf84f5 100644
--- a/boards/arm/stm32wl5/nucleo-wl55jc/src/Makefile
+++ b/boards/arm/stm32wl5/nucleo-wl55jc/src/Makefile
@@ -34,4 +34,14 @@ ifeq ($(CONFIG_ARCH_BOARD_FLASH_MOUNT),y)
 CSRCS += stm32_flash.c
 endif
 
+ifeq ($(CONFIG_SPI_DRIVER),y)
+  CSRCS += stm32_spi.c
+endif
+
+ifeq ($(CONFIG_VIDEO_FB),y)
+ifeq ($(CONFIG_LCD_SSD1680),y)
+  CSRCS += stm32_ssd1680.c
+endif
+endif
+
 include $(TOPDIR)/boards/Board.mk
diff --git a/boards/arm/stm32wl5/nucleo-wl55jc/src/nucleo-wl55jc.h 
b/boards/arm/stm32wl5/nucleo-wl55jc/src/nucleo-wl55jc.h
index e3b7b86338..5a8883af04 100644
--- a/boards/arm/stm32wl5/nucleo-wl55jc/src/nucleo-wl55jc.h
+++ b/boards/arm/stm32wl5/nucleo-wl55jc/src/nucleo-wl55jc.h
@@ -48,6 +48,77 @@
 #  undef HAVE_PROC
 #endif
 
+#if defined(CONFIG_LCD_SSD1680)
+
+/* There is no E-ink display on a board.
+ * It can be connected on many different ways
+ * It is possible to configure pins using make menuconfig
+ */
+
+#  if defined(CONFIG_SSD1680_GPIO_CS_PORTA)
+#    define CONFIG_SSD1680_CS_PORT GPIO_PORTA
+#  elif defined(CONFIG_SSD1680_GPIO_CS_PORTB)
+#    define CONFIG_SSD1680_CS_PORT GPIO_PORTB
+#  elif defined(CONFIG_SSD1680_GPIO_CS_PORTC)
+#    define CONFIG_SSD1680_CS_PORT GPIO_PORTC
+#  elif defined(CONFIG_SSD1680_GPIO_CS_PORTD)
+#    define CONFIG_SSD1680_CS_PORT GPIO_PORTD
+#  endif
+
+#  if defined(CONFIG_SSD1680_GPIO_DTA_CMD_PORTA)
+#    define CONFIG_SSD1680_DC_PORT GPIO_PORTA
+#  elif defined(CONFIG_SSD1680_GPIO_DTA_CMD_PORTB)
+#    define CONFIG_SSD1680_DC_PORT GPIO_PORTB
+#  elif defined(CONFIG_SSD1680_GPIO_DTA_CMD_PORTC)
+#    define CONFIG_SSD1680_DC_PORT GPIO_PORTC
+#  elif defined(CONFIG_SSD1680_GPIO_DTA_CMD_PORTD)
+#    define CONFIG_SSD1680_DC_PORT GPIO_PORTD
+#  endif
+
+#  if defined(CONFIG_SSD1680_GPIO_RST_PORTA)
+#    define CONFIG_SSD1680_RST_PORT GPIO_PORTA
+#  elif defined(CONFIG_SSD1680_GPIO_RST_PORTB)
+#    define CONFIG_SSD1680_RST_PORT GPIO_PORTB
+#  elif defined(CONFIG_SSD1680_GPIO_RST_PORTC)
+#    define CONFIG_SSD1680_RST_PORT GPIO_PORTC
+#  elif defined(CONFIG_SSD1680_GPIO_RST_PORTD)
+#    define CONFIG_SSD1680_RST_PORT GPIO_PORTD
+#  endif
+
+#  if defined(CONFIG_SSD1680_GPIO_BUSY_PORTA)
+#    define CONFIG_SSD1680_BUSY_PORT GPIO_PORTA
+#  elif defined(CONFIG_SSD1680_GPIO_BUSY_PORTB)
+#    define CONFIG_SSD1680_BUSY_PORT GPIO_PORTB
+#  elif defined(CONFIG_SSD1680_GPIO_BUSY_PORTC)
+#    define CONFIG_SSD1680_BUSY_PORT GPIO_PORTC
+#  elif defined(CONFIG_SSD1680_GPIO_BUSY_PORTD)
+#    define CONFIG_SSD1680_BUSY_PORT GPIO_PORTD
+#  endif
+
+#  define GPIO_SSD1680_CS     (GPIO_OUTPUT|GPIO_OTYPER_PP(0)|GPIO_SPEED_2MHz|\
+                               GPIO_OUTPUT_SET|\
+                               CONFIG_SSD1680_CS_PORT|\
+                               CONFIG_SSD1680_GPIO_PIN_CS)
+
+#  define GPIO_SSD1680_CMD    (GPIO_OUTPUT|GPIO_OTYPER_PP(0)|GPIO_OSPEED_2MHz|\
+                               GPIO_OUTPUT_SET|\
+                               CONFIG_SSD1680_DC_PORT|\
+                               CONFIG_SSD1680_GPIO_PIN_DTA_CMD)
+
+#  ifdef CONFIG_SSD1680_RST_PORT
+#    define GPIO_SSD1680_RST  (GPIO_OUTPUT|GPIO_OTYPER_PP(0)|GPIO_SPEED_2MHz|\
+                               GPIO_OUTPUT_SET|\
+                               CONFIG_SSD1680_RST_PORT|\
+                               CONFIG_SSD1680_GPIO_PIN_RST)
+#  endif
+
+#  ifdef CONFIG_SSD1680_BUSY_PORT
+#    define GPIO_SSD1680_BUSY (GPIO_INPUT|GPIO_PULLUP|GPIO_SPEED_2MHz|\
+                               CONFIG_SSD1680_BUSY_PORT|\
+                               CONFIG_SSD1680_GPIO_PIN_BUSY)
+#  endif
+#endif
+
 #define GPIO_LED_GREEN (GPIO_PORTB|GPIO_PIN9 
|GPIO_OUTPUT|GPIO_PULLUP|GPIO_SPEED_50MHz)
 #define GPIO_LED_RED   
(GPIO_PORTB|GPIO_PIN11|GPIO_OUTPUT|GPIO_PULLUP|GPIO_SPEED_50MHz)
 #define GPIO_LED_BLUE  
(GPIO_PORTB|GPIO_PIN15|GPIO_OUTPUT|GPIO_PULLUP|GPIO_SPEED_50MHz)
@@ -84,4 +155,13 @@ void board_leds_initialize(void);
 
 int stm32wl5_flash_init(void);
 
+/* Name: stm32wl5_spidev_initialize
+ *
+ * Description:
+ *   Initialize SPIs
+ *
+ ****************************************************************************/
+
+void stm32wl5_spidev_initialize(void);
+
 #endif /* __BOARDS_ARM_STM32WL5_NUCLEO_WL55JC_SRC_NUCLEO_WL55JC_H */
diff --git a/boards/arm/stm32wl5/nucleo-wl55jc/src/stm32_boot.c 
b/boards/arm/stm32wl5/nucleo-wl55jc/src/stm32_boot.c
index 0073361b1e..cc5ce21a24 100644
--- a/boards/arm/stm32wl5/nucleo-wl55jc/src/stm32_boot.c
+++ b/boards/arm/stm32wl5/nucleo-wl55jc/src/stm32_boot.c
@@ -32,6 +32,10 @@
 
 #include <arch/board/board.h>
 
+#ifdef CONFIG_VIDEO_FB
+#include <nuttx/video/fb.h>
+#endif
+
 #include "arm_internal.h"
 #include "nucleo-wl55jc.h"
 
@@ -81,6 +85,26 @@ void stm32wl5_board_initialize(void)
 #ifdef CONFIG_BOARD_LATE_INITIALIZE
 void board_late_initialize(void)
 {
+#if defined(CONFIG_VIDEO_FB)
+  int ret;
+#endif
+
+#if defined(CONFIG_STM32WL5_SPI1) || defined(CONFIG_STM32WL5_SPI2S2)
+  stm32wl5_spidev_initialize();
+#endif
+
+#if defined(CONFIG_LCD_SSD1680) && !defined(CONFIG_VIDEO_FB)
+  board_lcd_initialize();
+#endif
+
+#ifdef CONFIG_VIDEO_FB
+  ret = fb_register(0, 0);
+  if (ret < 0)
+    {
+      syslog(LOG_ERR, "ERROR: fb_register() failed: %d\n", ret);
+    }
+#endif
+
   /* Perform NSH initialization here instead of from the NSH.  This
    * alternative NSH initialization is necessary when NSH is ran in
    * user-space but the initialization function must run in kernel space.
diff --git a/boards/arm/stm32wl5/nucleo-wl55jc/src/stm32_spi.c 
b/boards/arm/stm32wl5/nucleo-wl55jc/src/stm32_spi.c
new file mode 100644
index 0000000000..cab6b89e03
--- /dev/null
+++ b/boards/arm/stm32wl5/nucleo-wl55jc/src/stm32_spi.c
@@ -0,0 +1,252 @@
+/****************************************************************************
+ * boards/arm/stm32wl5/nucleo-wl55jc/src/stm32_spi.c
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.  The
+ * ASF licenses this file to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance with the
+ * License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ *
+ ****************************************************************************/
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include <nuttx/config.h>
+
+#include <stdint.h>
+#include <stdbool.h>
+#include <debug.h>
+#include <errno.h>
+
+#include <arch/board/board.h>
+#include <nuttx/spi/spi.h>
+
+#include "arm_internal.h"
+#include "chip.h"
+
+#include "stm32wl5.h"
+#include "nucleo-wl55jc.h"
+
+#if defined(CONFIG_STM32WL5_SPI1) || defined(CONFIG_STM32WL5_SPI2S2)
+
+/****************************************************************************
+ * Public Data
+ ****************************************************************************/
+
+/* Global driver instances */
+
+#ifdef CONFIG_STM32WL5_SPI1
+struct spi_dev_s *g_spi1;
+#endif
+#ifdef CONFIG_STM32WL5_SPI2S2
+struct spi_dev_s *g_spi2;
+#endif
+
+/****************************************************************************
+ * Public Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: stm32_spidev_initialize
+ *
+ * Description:
+ *   Called to configure SPI chip select GPIO pins for the Nucleo-wl55JC
+ *   boards.
+ *
+ ****************************************************************************/
+
+void weak_function stm32wl5_spidev_initialize(void)
+{
+#ifdef CONFIG_STM32WL5_SPI1
+  /* Configure SPI-based devices */
+
+  g_spi1 = stm32wl5_spibus_initialize(1);
+  if (!g_spi1)
+    {
+      spierr("ERROR: FAILED to initialize SPI port 1\n");
+      return;
+    }
+
+#ifdef CONFIG_LCD_SSD1680
+  spiinfo("Preparing additional lines for SSD1680 device\n");
+  stm32wl5_configgpio(GPIO_SSD1680_CS);    /* SSD1680 chip select */
+  stm32wl5_configgpio(GPIO_SSD1680_CMD);   /* SSD1680 data/!command */
+  stm32wl5_configgpio(GPIO_SSD1680_RST);   /* SSD1680 reset */
+  stm32wl5_configgpio(GPIO_SSD1680_BUSY);  /* SSD1680 busy */
+#endif
+
+#endif
+
+#ifdef CONFIG_STM32_SPI2S2
+  /* Configure SPI-based devices */
+
+  g_spi2 = stm32_spibus_initialize(2);
+#endif
+}
+
+/****************************************************************************
+ * Name:  stm32_spi1/2s2elect and stm32_spi1/2s2status
+ *
+ * Description:
+ *   The external functions, stm32_spi1/2s2select and stm32_spi1/2s2status
+ *   must be provided by board-specific logic.  They are implementations of
+ *   the select and status methods of the SPI interface defined by struct
+ *   spi_ops_s (see include/nuttx/spi/spi.h). All other methods (including
+ *   stm32wl5_spibus_initialize()) are provided by common STM32 logic.
+ *   To use this common SPI logic on your board:
+ *
+ *   1. Provide logic in stm32_boardinitialize() to configure SPI chip select
+ *      pins.
+ *   2. Provide stm32_spi1/2s2select() and stm32_spi1/2s2status() functions
+ *      in your board-specific logic.  These functions will perform chip
+ *      selection and status operations using GPIOs in the way your board is
+ *      configured.
+ *   3. Add a calls to stm32wl5_spibus_initialize() in your low level
+ *      application initialization logic
+ *   4. The handle returned by stm32wl5_spibus_initialize() may then be used
+ *      to bind the SPI driver to higher level logic (e.g., calling
+ *      mmcsd_spislotinitialize(), for example, will bind the SPI driver to
+ *      the SPI MMC/SD driver).
+ *
+ ****************************************************************************/
+
+#ifdef CONFIG_STM32WL5_SPI1
+void stm32wl5_spi1select(struct spi_dev_s *dev, uint32_t devid,
+                      bool selected)
+{
+  spiinfo("devid: %d CS: %s\n", (int)devid, selected ? "assert" :
+          "de-assert");
+
+#if defined(CONFIG_LCD_SSD1680)
+  if (devid == SPIDEV_DISPLAY(0))
+    {
+      stm32wl5_gpiowrite(GPIO_SSD1680_CS, !selected);
+    }
+#endif
+
+#if defined(CONFIG_CAN_MCP2515)
+  if (devid == SPIDEV_CANBUS(0))
+    {
+      stm32wl5_gpiowrite(GPIO_MCP2515_CS, !selected);
+    }
+#endif
+
+#ifdef HAVE_MMCSD
+  if (devid == SPIDEV_MMCSD(0))
+    {
+      stm32wl5_gpiowrite(GPIO_SPI_CS_SD_CARD, !selected);
+    }
+#endif
+}
+
+uint8_t stm32wl5_spi1status(struct spi_dev_s *dev, uint32_t devid)
+{
+#if defined(CONFIG_LCD_SSD1680)
+  if (devid == SPIDEV_DISPLAY(0))
+    {
+      return SPI_STATUS_PRESENT;
+    }
+#endif
+
+  return 0;
+}
+
+int stm32wl5_spi1cmddata(struct spi_dev_s *dev, uint32_t devid, bool cmd)
+{
+#if defined(CONFIG_LCD_SSD1680)
+  if (devid == SPIDEV_DISPLAY(0))
+    {
+      stm32wl5_gpiowrite(GPIO_SSD1680_CMD, !cmd);
+    }
+#endif
+
+  return OK;
+}
+
+#endif
+
+#ifdef CONFIG_STM32WL5_SPI2S2
+void stm32wl5_spi2s2select(struct spi_dev_s *dev, uint32_t devid,
+                      bool selected)
+{
+  spiinfo("devid: %d CS: %s\n", (int)devid, selected ? "assert" :
+          "de-assert");
+}
+
+uint8_t stm32wl5_spi2s2status(struct spi_dev_s *dev, uint32_t devid)
+{
+  return 0;
+}
+
+int stm32wl5_spi2s2cmddata(struct spi_dev_s *dev, uint32_t devid, bool cmd)
+{
+  return OK;
+}
+
+#endif
+
+/****************************************************************************
+ * Name: stm32_spi1cmddata
+ *
+ * Description:
+ *   Set or clear the SH1101A A0 or SD1306 D/C n bit to select data (true)
+ *   or command (false). This function must be provided by platform-specific
+ *   logic. This is an implementation of the cmddata method of the SPI
+ *   interface defined by struct spi_ops_s (see include/nuttx/spi/spi.h).
+ *
+ * Input Parameters:
+ *
+ *   spi - SPI device that controls the bus the device that requires the CMD/
+ *         DATA selection.
+ *   devid - If there are multiple devices on the bus, this selects which one
+ *         to select cmd or data.  NOTE:  This design restricts, for example,
+ *         one one SPI display per SPI bus.
+ *   cmd - true: select command; false: select data
+ *
+ * Returned Value:
+ *   None
+ *
+ ****************************************************************************/
+
+#ifdef CONFIG_SPI_CMDDATA
+#ifdef CONFIG_STM32_SPI1
+int stm32_spi1cmddata(struct spi_dev_s *dev, uint32_t devid, bool cmd)
+{
+#if defined(CONFIG_LCD_SSD16800)
+  if (devid == SPIDEV_DISPLAY(0))
+    {
+      stm32_gpiowrite(GPIO_SSD1680_CMD, !cmd);
+    }
+#endif
+
+  return OK;
+}
+#endif
+
+#ifdef CONFIG_STM32_SPI2
+int stm32_spi2cmddata(struct spi_dev_s *dev, uint32_t devid, bool cmd)
+{
+  return OK;
+}
+#endif
+
+#ifdef CONFIG_STM32_SPI3
+int stm32_spi3cmddata(struct spi_dev_s *dev, uint32_t devid, bool cmd)
+{
+  return OK;
+}
+#endif
+#endif /* CONFIG_SPI_CMDDATA */
+
+#endif /* CONFIG_STM32_SPI1 || CONFIG_STM32_SPI2 || CONFIG_STM32_SPI3 */
diff --git a/boards/arm/stm32wl5/nucleo-wl55jc/src/stm32_ssd1680.c 
b/boards/arm/stm32wl5/nucleo-wl55jc/src/stm32_ssd1680.c
new file mode 100644
index 0000000000..28adb1ac4f
--- /dev/null
+++ b/boards/arm/stm32wl5/nucleo-wl55jc/src/stm32_ssd1680.c
@@ -0,0 +1,190 @@
+/****************************************************************************
+ * boards/arm/stm32wl5/nucleo-wl55jc/src/stm32_ssd1680.c
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.  The
+ * ASF licenses this file to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance with the
+ * License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ *
+ ****************************************************************************/
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include <nuttx/config.h>
+
+#include <debug.h>
+
+#include <nuttx/board.h>
+#include <nuttx/lcd/lcd.h>
+#include <nuttx/lcd/ssd1680.h>
+#include <nuttx/spi/spi.h>
+
+#include "stm32wl5.h"
+#include "nucleo-wl55jc.h"
+#include "stm32wl5_gpio.h"
+#include "stm32wl5_ssd1680.h"
+
+#if defined(CONFIG_VIDEO_FB) && defined(CONFIG_LCD_FRAMEBUFFER)
+#  include <nuttx/video/fb.h>
+#endif
+
+#ifdef CONFIG_LCD_SSD1680
+
+/****************************************************************************
+ * Private Functions
+ ****************************************************************************/
+
+#if defined(GPIO_SSD1680_PWR)
+static bool ssd1680_set_vcc(bool state)
+{
+  esp32_gpiowrite(GPIO_SSD1680_PWR, state);
+  return true;
+}
+#endif
+
+#if defined(CONFIG_SSD1680_GPIO_PIN_RST)
+static bool ssd1680_set_rst(bool state)
+{
+  stm32wl5_gpiowrite(GPIO_SSD1680_RST, state);
+  return true;
+}
+#endif
+
+#if defined(CONFIG_SSD1680_GPIO_PIN_BUSY)
+static bool ssd1680_check_busy(void)
+{
+  return stm32wl5_gpioread(GPIO_SSD1680_BUSY);
+}
+#endif
+
+/****************************************************************************
+ * Private Data
+ ****************************************************************************/
+
+static struct lcd_dev_s    *g_lcddev;
+struct ssd1680_priv_s g_ssd1680_priv =
+{
+#if defined(CONFIG_SSD1680_GPIO_PIN_PWR) && (CONFIG_SSD1680_GPIO_PIN_PWR >= 0)
+  .set_vcc = ssd1680_set_vcc,
+#endif
+
+#if defined(CONFIG_SSD1680_GPIO_PIN_RST)  && (CONFIG_SSD1680_GPIO_PIN_RST >= 0)
+  .set_rst = ssd1680_set_rst,
+#endif
+
+#if defined(CONFIG_SSD1680_GPIO_PIN_BUSY) && (CONFIG_SSD1680_GPIO_PIN_BUSY >= 
0)
+  .check_busy = ssd1680_check_busy,
+#endif
+};
+
+/****************************************************************************
+ * Public Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: board_lcd_initialize
+ ****************************************************************************/
+
+int board_lcd_initialize(void)
+{
+  struct spi_dev_s *spi;
+
+  /* Initialize additional I/O for e-ink display */
+
+#if defined(GPIO_SSD1680_PWR)
+  stm32wl5_configgpio(GPIO_SSD1680_PWR);   /* SSD1680 pwr */
+  lcdinfo("SSD1680 power line is available (0x%08x)\n", GPIO_SSD1680_PWR);
+#else
+  lcdinfo("PWR control line is disabled\n");
+#endif
+#if defined(GPIO_SSD1680_RST)
+  stm32wl5_configgpio(GPIO_SSD1680_RST);   /* SSD1680 reset */
+  lcdinfo("SSD1680 reset line is available (0x%08x)\n", GPIO_SSD1680_RST);
+#elif
+  lcdinfo("SSD1680 RESET line is disabled\n");
+#endif
+
+#if defined(GPIO_SSD1680_BUSY)
+  stm32wl5_configgpio(GPIO_SSD1680_BUSY);  /* SSD1680 busy */
+  lcdinfo("SSD1680 Line for reading busy state is available (0x%08x)\n",
+          GPIO_SSD1680_BUSY);
+#elif
+  lcdinfo("SSD1680 Read busy line is disabled\n");
+#endif
+
+  /* Initialize SPI */
+
+  spi = stm32wl5_spibus_initialize(CONFIG_SSD1680_SPI_BUS);
+  if (!spi)
+    {
+      lcderr("ERROR: Failed to initialize SPI port %d\n",
+        CONFIG_SSD1680_SPI_BUS);
+      return -ENODEV;
+    }
+  else
+    {
+      lcdinfo("Using SPI bus %d. SPI is initialized\n",
+        CONFIG_SSD1680_SPI_BUS);
+    }
+
+  /* Bind the SPI port to the E-PAPER display */
+
+  g_lcddev = ssd1680_initialize(spi, &g_ssd1680_priv);
+  if (!g_lcddev)
+    {
+      lcderr("ERROR: Failed to bind SPI port %d to E-paper display\n",
+          CONFIG_SSD1680_SPI_BUS);
+      return -ENODEV;
+    }
+  else
+    {
+      lcdinfo("Bound SPI port %d to E-PAPER\n", CONFIG_SSD1680_SPI_BUS);
+
+      /* And turn the OLED on.
+       * Must be because setpower(1) function invokes the chip configuration
+       */
+
+      g_lcddev->setpower(g_lcddev, CONFIG_LCD_MAXPOWER);
+    }
+
+  return OK;
+}
+
+/****************************************************************************
+ * Name: board_ssd1680_getdev
+ *
+ * Description:
+ *   Get the SSD1680 device driver instance
+ *
+ * Returned Value:
+ *   Pointer to the instance
+ *
+ ****************************************************************************/
+
+struct lcd_dev_s *board_ssd1680_getdev(void)
+{
+  return g_lcddev;
+}
+
+void board_lcd_uninitialize(void)
+{
+}
+
+struct lcd_dev_s *board_lcd_getdev(int devno)
+{
+  return board_ssd1680_getdev();
+}
+
+#endif
diff --git a/boards/arm/stm32wl5/nucleo-wl55jc/src/nucleo-wl55jc.h 
b/boards/arm/stm32wl5/nucleo-wl55jc/src/stm32wl5_ssd1680.h
similarity index 50%
copy from boards/arm/stm32wl5/nucleo-wl55jc/src/nucleo-wl55jc.h
copy to boards/arm/stm32wl5/nucleo-wl55jc/src/stm32wl5_ssd1680.h
index e3b7b86338..775901a84d 100644
--- a/boards/arm/stm32wl5/nucleo-wl55jc/src/nucleo-wl55jc.h
+++ b/boards/arm/stm32wl5/nucleo-wl55jc/src/stm32wl5_ssd1680.h
@@ -1,5 +1,5 @@
 /****************************************************************************
- * boards/arm/stm32wl5/nucleo-wl55jc/src/nucleo-wl55jc.h
+ * boards/arm/stm32wl5/nucleo-wl55jc/src/stm32wl5_ssd1680.h
  *
  * Licensed to the Apache Software Foundation (ASF) under one or more
  * contributor license agreements.  See the NOTICE file distributed with
@@ -18,70 +18,47 @@
  *
  ****************************************************************************/
 
-#ifndef __BOARDS_ARM_STM32WL5_NUCLEO_WL55JC_SRC_NUCLEO_WL55JC_H
-#define __BOARDS_ARM_STM32WL5_NUCLEO_WL55JC_SRC_NUCLEO_WL55JC_H
+#ifndef __BOARDS_ARM_STMWL5_NUCLEO_WL55JC_INCLUDE_STM32WL5_SSD1680_H
+#define __BOARDS_ARM_STMWL5_NUCLEO_WL55JC_INCLUDE_STM32WL5_SSD1680_H
 
 /****************************************************************************
  * Included Files
  ****************************************************************************/
 
 #include <nuttx/config.h>
-#include <nuttx/compiler.h>
-
-#include <stdint.h>
-#include <stm32wl5.h>
 
 /****************************************************************************
- * Pre-processor Definitions
+ * Public Data
  ****************************************************************************/
 
-/* Configuration ************************************************************/
-
-#define HAVE_PROC             1
-
-#if !defined(CONFIG_FS_PROCFS)
-#  undef HAVE_PROC
-#endif
-
-#if defined(HAVE_PROC) && defined(CONFIG_DISABLE_MOUNTPOINT)
-#  warning Mountpoints disabled.  No procfs support
-#  undef HAVE_PROC
+#ifdef __cplusplus
+#define EXTERN extern "C"
+extern "C"
+{
+#else
+#define EXTERN extern
 #endif
 
-#define GPIO_LED_GREEN (GPIO_PORTB|GPIO_PIN9 
|GPIO_OUTPUT|GPIO_PULLUP|GPIO_SPEED_50MHz)
-#define GPIO_LED_RED   
(GPIO_PORTB|GPIO_PIN11|GPIO_OUTPUT|GPIO_PULLUP|GPIO_SPEED_50MHz)
-#define GPIO_LED_BLUE  
(GPIO_PORTB|GPIO_PIN15|GPIO_OUTPUT|GPIO_PULLUP|GPIO_SPEED_50MHz)
-
-#define GPIO_BUTTON1  (GPIO_PORTA|GPIO_PIN0|GPIO_INPUT|GPIO_PULLUP)
-#define GPIO_BUTTON2  (GPIO_PORTA|GPIO_PIN1|GPIO_INPUT|GPIO_PULLUP)
-#define GPIO_BUTTON3  (GPIO_PORTC|GPIO_PIN6|GPIO_INPUT|GPIO_PULLUP|GPIO_EXTI)
-
-/****************************************************************************
- * Public Data
- ****************************************************************************/
-
 /****************************************************************************
- * Public Functions Prototypes
+ * Public Function Prototypes
  ****************************************************************************/
 
 /****************************************************************************
- * Name: board_leds_initialize
+ * Name: board_ssd1680_getdev
  *
  * Description:
- *   Initialize LEDs
- *
- ****************************************************************************/
-
-void board_leds_initialize(void);
-
-/****************************************************************************
- * Name: stm32wl5_flash_init
+ *   Get the SSD1680 device driver instance
  *
- * Description:
- *   Initialize on-board FLASH partition table
+ * Returned Value:
+ *   Pointer to the instance
  *
  ****************************************************************************/
 
-int stm32wl5_flash_init(void);
+struct lcd_dev_s *board_ssd1680_getdev(void);
+
+#undef EXTERN
+#ifdef __cplusplus
+}
+#endif
 
-#endif /* __BOARDS_ARM_STM32WL5_NUCLEO_WL55JC_SRC_NUCLEO_WL55JC_H */
+#endif /* __BOARDS_ARM_STMWL5_NUCLEO_WL55JC_INCLUDE_STM32WL5_SSD1680_H */
\ No newline at end of file

Reply via email to