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

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


The following commit(s) were added to refs/heads/master by this push:
     new a369f65f718 boards/thingy52: Wire sensors, RGB LEDs and ADC.
a369f65f718 is described below

commit a369f65f718d223d7c08d3acf810c62355ddf3d6
Author: raiden00pl <[email protected]>
AuthorDate: Sat Sep 23 20:28:16 2023 +0200

    boards/thingy52: Wire sensors, RGB LEDs and ADC.
    
    Register the on-board HTS221, LPS22HB, CCS811 and BH1745NUC uORB
    sensors, the lightwell RGB LED behind the SX1509 and the SAADC battery
    voltage channel, and add the thingy_nimble configuration.
    
    Assisted-by: Claude:claude-fable-5-1
    Signed-off-by: raiden00pl <[email protected]>
---
 .../platforms/arm/nrf52/boards/thingy52/index.rst  |  27 ++-
 .../nrf52/thingy52/configs/thingy_nimble/defconfig |  83 +++++++++
 boards/arm/nrf52/thingy52/include/board.h          |   6 +
 boards/arm/nrf52/thingy52/src/CMakeLists.txt       |  14 ++
 boards/arm/nrf52/thingy52/src/Make.defs            |  16 ++
 boards/arm/nrf52/thingy52/src/nrf52_adc.c          | 137 +++++++++++++++
 boards/arm/nrf52/thingy52/src/nrf52_boot.c         |   4 +
 boards/arm/nrf52/thingy52/src/nrf52_bringup.c      |  35 ++++
 boards/arm/nrf52/thingy52/src/nrf52_rgbled.c       | 192 +++++++++++++++++++++
 boards/arm/nrf52/thingy52/src/nrf52_sensors.c      | 126 ++++++++++++++
 boards/arm/nrf52/thingy52/src/nrf52_sx1509.c       |  80 ++++++++-
 boards/arm/nrf52/thingy52/src/thingy52.h           |  74 ++++++++
 drivers/ioexpander/sx1509.c                        |   3 +-
 13 files changed, 779 insertions(+), 18 deletions(-)

diff --git a/Documentation/platforms/arm/nrf52/boards/thingy52/index.rst 
b/Documentation/platforms/arm/nrf52/boards/thingy52/index.rst
index fea73cfe74d..c607be41425 100644
--- a/Documentation/platforms/arm/nrf52/boards/thingy52/index.rst
+++ b/Documentation/platforms/arm/nrf52/boards/thingy52/index.rst
@@ -10,23 +10,25 @@ is a prototyping platform build around the nRF52832 from 
Nordic.
 Peripheral Support
 ==================
 
-================================== ======= =============
+================================== ======= ==========================
 Peripheral                         Support NOTES
-================================== ======= =============
+================================== ======= ==========================
 UART                               Yes
 Buttons                            No
-LEDs                               No
+LEDs                               Yes     Lightwell RGB LED (SX1509)
 NFC                                No
 IMU (MPU-9250)                     No
 Low power accelerometer (LIS2DH12) No
-Pressure and temperature (LPS22HB) No
-Humidity and temperature (HTS221)  No
-Color sensor (BH1745NUC)           No
-Gas sensor (CCS811)                No
+Pressure and temperature (LPS22HB) Yes     uORB, ``sensor_baro0``
+Humidity and temperature (HTS221)  Yes     uORB, ``sensor_humi0``,
+                                           ``sensor_ambient_temp0``
+Color sensor (BH1745NUC)           Yes     uORB, ``sensor_rgb0``
+Gas sensor (CCS811)                Yes     uORB, ``sensor_co20``,
+                                           ``sensor_tvoc0``
 Microphone (MP34DB02)              No
 Speaker                            No
-Battery monitoring                 No
-================================== ======= =============
+Battery monitoring                 Yes     SAADC AIN4 (P0.28)
+================================== ======= ==========================
 
 Serial Console
 ==============
@@ -67,6 +69,13 @@ nsh
 
 Basic NuttShell configuration (console enabled on Segger RTT channel).
 
+thingy_nimble
+-------------
+
+NuttShell configuration with the nimBLE host stack, the SX1509 IO expander
+and LED driver, the buttons and GPIO examples and the on-board uORB sensors
+(HTS221, LPS22HB, BH1745NUC and CCS811) enabled.
+
 Flash & Debug
 =============
 
diff --git a/boards/arm/nrf52/thingy52/configs/thingy_nimble/defconfig 
b/boards/arm/nrf52/thingy52/configs/thingy_nimble/defconfig
new file mode 100644
index 00000000000..2b22a620e27
--- /dev/null
+++ b/boards/arm/nrf52/thingy52/configs/thingy_nimble/defconfig
@@ -0,0 +1,83 @@
+#
+# 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_ARCH_FPU is not set
+# CONFIG_NET_ETHERNET is not set
+# CONFIG_NET_IPv4 is not set
+# CONFIG_NIMBLE_PORTING_EXAMPLE is not set
+# CONFIG_WIRELESS_BLUETOOTH_HOST is not set
+CONFIG_ALLOW_BSDNORDIC_COMPONENTS=y
+CONFIG_ALLOW_BSD_COMPONENTS=y
+CONFIG_ARCH="arm"
+CONFIG_ARCH_BOARD="thingy52"
+CONFIG_ARCH_BOARD_THINGY52=y
+CONFIG_ARCH_BUTTONS=y
+CONFIG_ARCH_CHIP="nrf52"
+CONFIG_ARCH_CHIP_NRF52832=y
+CONFIG_ARCH_CHIP_NRF52=y
+CONFIG_ARCH_IRQBUTTONS=y
+CONFIG_ARCH_STACKDUMP=y
+CONFIG_ARCH_STDARG_H=y
+CONFIG_BOARD_LOOPSPERMSEC=5500
+CONFIG_BUILTIN=y
+CONFIG_DEBUG_FEATURES=y
+CONFIG_DEBUG_FULLOPT=y
+CONFIG_DEBUG_SYMBOLS=y
+CONFIG_DEV_GPIO=y
+CONFIG_EXAMPLES_BUTTONS=y
+CONFIG_EXAMPLES_GPIO=y
+CONFIG_EXAMPLES_LEDS=y
+CONFIG_EXAMPLES_LEDS_DEVPATH="/dev/leds"
+CONFIG_EXAMPLES_LEDS_LEDSET=0x3f
+CONFIG_EXAMPLES_NIMBLE=y
+CONFIG_FS_PROCFS=y
+CONFIG_GPIO_LOWER_HALF=y
+CONFIG_INIT_ENTRYPOINT="nsh_main"
+CONFIG_INPUT=y
+CONFIG_INPUT_BUTTONS=y
+CONFIG_INPUT_BUTTONS_LOWER=y
+CONFIG_INTELHEX_BINARY=y
+CONFIG_IOEXPANDER=y
+CONFIG_IOEXPANDER_SX1509=y
+CONFIG_MM_REGIONS=2
+CONFIG_NET=y
+CONFIG_NETDEV_LATEINIT=y
+CONFIG_NET_BLUETOOTH=y
+CONFIG_NET_LL_GUARDSIZE=14
+CONFIG_NIMBLE=y
+CONFIG_NIMBLE_ROLE_PERIPHERAL=y
+CONFIG_NRF52_GPIOTE=y
+CONFIG_NRF52_I2C0_MASTER=y
+CONFIG_NRF52_UART0=y
+CONFIG_NSH_BUILTIN_APPS=y
+CONFIG_NSH_DISABLE_IFUPDOWN=y
+CONFIG_NSH_FILEIOSIZE=512
+CONFIG_NSH_READLINE=y
+CONFIG_PREALLOC_MQ_MSGS=32
+CONFIG_PREALLOC_TIMERS=4
+CONFIG_PTHREAD_MUTEX_TYPES=y
+CONFIG_RAM_SIZE=65535
+CONFIG_RAM_START=0x20000000
+CONFIG_RAW_BINARY=y
+CONFIG_RR_INTERVAL=200
+CONFIG_SCHED_WAITPID=y
+CONFIG_SENSORS=y
+CONFIG_SENSORS_BH1745NUC=y
+CONFIG_SENSORS_CCS811=y
+CONFIG_SENSORS_HTS221=y
+CONFIG_SENSORS_LPS22HB=y
+CONFIG_SIG_EVTHREAD=y
+CONFIG_SPI=y
+CONFIG_START_DAY=26
+CONFIG_START_MONTH=3
+CONFIG_SX1509_LED_ENABLE=y
+CONFIG_SYMTAB_ORDEREDBYNAME=y
+CONFIG_SYSTEM_NSH=y
+CONFIG_TASK_NAME_SIZE=32
+CONFIG_UART0_SERIAL_CONSOLE=y
+CONFIG_WIRELESS=y
+CONFIG_WIRELESS_BLUETOOTH=y
diff --git a/boards/arm/nrf52/thingy52/include/board.h 
b/boards/arm/nrf52/thingy52/include/board.h
index cabecb020fc..da75a1f2d2f 100644
--- a/boards/arm/nrf52/thingy52/include/board.h
+++ b/boards/arm/nrf52/thingy52/include/board.h
@@ -71,4 +71,10 @@
 #define BOARD_I2C0_SCL_PIN (GPIO_OUTPUT | GPIO_PORT0 | GPIO_PIN(8))
 #define BOARD_I2C0_SDA_PIN (GPIO_INPUT  | GPIO_PORT0 | GPIO_PIN(7))
 
+/* ADC Pins *****************************************************************/
+
+/* ADC CH0 - P0.28 - AIN4 - BATTERY (voltage divider gated by BAT_MON_EN) */
+
+#define NRF52_ADC_CH0_PIN (GPIO_INPUT | GPIO_PORT0 | GPIO_PIN(28))
+
 #endif /* __BOARDS_ARM_NRF52_THINGY52_INCLUDE_BOARD_H */
diff --git a/boards/arm/nrf52/thingy52/src/CMakeLists.txt 
b/boards/arm/nrf52/thingy52/src/CMakeLists.txt
index 97b6c81f684..76f03c1d8d1 100644
--- a/boards/arm/nrf52/thingy52/src/CMakeLists.txt
+++ b/boards/arm/nrf52/thingy52/src/CMakeLists.txt
@@ -22,6 +22,10 @@
 
 set(SRCS nrf52_boot.c nrf52_bringup.c)
 
+if(CONFIG_NRF52_I2C0_MASTER)
+  list(APPEND SRCS nrf52_sensors.c)
+endif()
+
 if(CONFIG_ARCH_BUTTONS)
   list(APPEND SRCS nrf52_buttons.c)
 endif()
@@ -30,6 +34,16 @@ if(CONFIG_IOEXPANDER_SX1509)
   list(APPEND SRCS nrf52_sx1509.c)
 endif()
 
+if(CONFIG_ADC)
+  list(APPEND SRCS nrf52_adc.c)
+endif()
+
+if(CONFIG_RGBLED
+   AND CONFIG_IOEXPANDER_SX1509
+   AND CONFIG_IOEXPANDER_PWM)
+  list(APPEND SRCS nrf52_rgbled.c)
+endif()
+
 target_sources(board PRIVATE ${SRCS})
 
 if(CONFIG_ARCH_BOARD_COMMON)
diff --git a/boards/arm/nrf52/thingy52/src/Make.defs 
b/boards/arm/nrf52/thingy52/src/Make.defs
index dcf77b4614d..07f09deceeb 100644
--- a/boards/arm/nrf52/thingy52/src/Make.defs
+++ b/boards/arm/nrf52/thingy52/src/Make.defs
@@ -22,6 +22,10 @@
 
 CSRCS = nrf52_boot.c nrf52_bringup.c
 
+ifeq ($(CONFIG_NRF52_I2C0_MASTER),y)
+CSRCS += nrf52_sensors.c
+endif
+
 ifeq ($(CONFIG_ARCH_BUTTONS),y)
 CSRCS += nrf52_buttons.c
 endif
@@ -30,6 +34,18 @@ ifeq ($(CONFIG_IOEXPANDER_SX1509),y)
 CSRCS += nrf52_sx1509.c
 endif
 
+ifeq ($(CONFIG_ADC),y)
+CSRCS += nrf52_adc.c
+endif
+
+ifeq ($(CONFIG_RGBLED),y)
+ifeq ($(CONFIG_IOEXPANDER_SX1509),y)
+ifeq ($(CONFIG_IOEXPANDER_PWM),y)
+CSRCS += nrf52_rgbled.c
+endif
+endif
+endif
+
 DEPPATH += --dep-path board
 VPATH += :board
 CFLAGS += 
${INCDIR_PREFIX}$(TOPDIR)$(DELIM)arch$(DELIM)$(CONFIG_ARCH)$(DELIM)src$(DELIM)board$(DELIM)board
diff --git a/boards/arm/nrf52/thingy52/src/nrf52_adc.c 
b/boards/arm/nrf52/thingy52/src/nrf52_adc.c
new file mode 100644
index 00000000000..a0d5957386f
--- /dev/null
+++ b/boards/arm/nrf52/thingy52/src/nrf52_adc.c
@@ -0,0 +1,137 @@
+/****************************************************************************
+ * boards/arm/nrf52/thingy52/src/nrf52_adc.c
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ *
+ * 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 <errno.h>
+#include <nuttx/debug.h>
+
+#include <nuttx/analog/adc.h>
+#include <arch/board/board.h>
+
+#include "nrf52_gpio.h"
+#include "nrf52_adc.h"
+
+/****************************************************************************
+ * Pre-processor Definitions
+ ****************************************************************************/
+
+#define ADC_NCHANNELS (1)
+
+/****************************************************************************
+ * Private data
+ ****************************************************************************/
+
+/* ADC pins configuration */
+
+static uint32_t g_adc_pins[ADC_NCHANNELS] =
+{
+  NRF52_ADC_CH0_PIN,            /* AIN4 */
+};
+
+/* ADC channels configuration */
+
+static struct nrf52_adc_channel_s g_adc_chanlist[ADC_NCHANNELS] =
+{
+  /* Channel 0 */
+
+  {
+    .p_psel  = NRF52_ADC_IN_IN4,         /* AIN4 / P0.28 - BATTERY */
+    .n_psel  = 0,
+#ifdef CONFIG_NRF52_SAADC_LIMITS
+    .limith = 0,
+    .limitl = 0,
+#endif
+    .resp   = NRF52_ADC_RES_BYPASS,
+    .resn   = NRF52_ADC_RES_BYPASS,
+    .gain   = NRF52_ADC_GAIN_1,
+    .refsel = NRF52_ADC_REFSEL_INTERNAL,
+    .tacq   = NRF52_ADC_TACQ_40US,
+    .mode   = NRF52_ADC_MODE_SE,
+    .burst  = NRF52_ADC_BURST_DISABLE,
+  },
+};
+
+/****************************************************************************
+ * Public Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: nrf52_adc_setup
+ *
+ * Description:
+ *   Initialize ADC and register the ADC device.  The battery voltage
+ *   divider is gated by the SX1509 BAT_MON_EN pin, which is enabled during
+ *   the SX1509 bring-up.
+ *
+ ****************************************************************************/
+
+int nrf52_adc_setup(void)
+{
+  static bool       initialized = false;
+  struct adc_dev_s *adc         = NULL;
+  int               ret         = OK;
+  int               i           = 0;
+
+  /* Have we already initialized? */
+
+  if (!initialized)
+    {
+      /* Configure ADC pins */
+
+      for (i = 0; i < ADC_NCHANNELS; i += 1)
+        {
+          nrf52_gpio_config(g_adc_pins[i]);
+        }
+
+      /* Call nrf52_adcinitialize() to get an instance of the ADC interface */
+
+      adc = nrf52_adcinitialize(g_adc_chanlist, ADC_NCHANNELS);
+      if (!adc)
+        {
+          aerr("ERROR: Failed to get the NRF52 ADC lower half\n");
+          ret = -ENODEV;
+          goto errout;
+        }
+
+      /* Register the ADC driver at "/dev/adc0" */
+
+      ret = adc_register("/dev/adc0", adc);
+      if (ret < 0)
+        {
+          aerr("ERROR: adc_register failed: %d\n", ret);
+          goto errout;
+        }
+
+      /* Now we are initialized */
+
+      initialized = true;
+    }
+
+errout:
+  return ret;
+}
diff --git a/boards/arm/nrf52/thingy52/src/nrf52_boot.c 
b/boards/arm/nrf52/thingy52/src/nrf52_boot.c
index ac4fab0e26a..5ab01c714a2 100644
--- a/boards/arm/nrf52/thingy52/src/nrf52_boot.c
+++ b/boards/arm/nrf52/thingy52/src/nrf52_boot.c
@@ -51,6 +51,10 @@
 
 void nrf52_board_initialize(void)
 {
+  /* Enable the VDD rail that supplies the on-board sensors */
+
+  nrf52_gpio_config(GPIO_VDD_PWR_CTRL);
+
   /* Configure on-board LEDs if LED support has been selected. */
 
 #ifdef CONFIG_ARCH_LEDS
diff --git a/boards/arm/nrf52/thingy52/src/nrf52_bringup.c 
b/boards/arm/nrf52/thingy52/src/nrf52_bringup.c
index 2aa293efee9..a69e59ac380 100644
--- a/boards/arm/nrf52/thingy52/src/nrf52_bringup.c
+++ b/boards/arm/nrf52/thingy52/src/nrf52_bringup.c
@@ -161,6 +161,41 @@ int nrf52_bringup(void)
     }
 #endif
 
+#if defined(CONFIG_RGBLED) && defined(CONFIG_IOEXPANDER_SX1509) && \
+    defined(CONFIG_IOEXPANDER_PWM)
+  /* Register the lightwell RGB LED (behind the SX1509 LED driver) */
+
+  ret = nrf52_rgbled_initialize();
+  if (ret < 0)
+    {
+      syslog(LOG_ERR, "ERROR: nrf52_rgbled_initialize() failed: %d\n", ret);
+    }
+#endif
+
+#ifdef CONFIG_NRF52_I2C0_MASTER
+  /* Initialize on-board sensors */
+
+  ret = nrf52_sensors_init();
+  if (ret < 0)
+    {
+      syslog(LOG_ERR,
+             "ERROR: Failed to initialize sensors: %d\n",
+             ret);
+    }
+#endif
+
+#ifdef CONFIG_ADC
+  /* Register the ADC driver used for battery voltage measurement */
+
+  ret = nrf52_adc_setup();
+  if (ret < 0)
+    {
+      syslog(LOG_ERR,
+             "ERROR: Failed to initialize ADC: %d\n",
+             ret);
+    }
+#endif
+
   UNUSED(ret);
   return OK;
 }
diff --git a/boards/arm/nrf52/thingy52/src/nrf52_rgbled.c 
b/boards/arm/nrf52/thingy52/src/nrf52_rgbled.c
new file mode 100644
index 00000000000..f074e0ed27b
--- /dev/null
+++ b/boards/arm/nrf52/thingy52/src/nrf52_rgbled.c
@@ -0,0 +1,192 @@
+/****************************************************************************
+ * boards/arm/nrf52/thingy52/src/nrf52_rgbled.c
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ *
+ * 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 <sys/types.h>
+#include <errno.h>
+#include <debug.h>
+
+#include <nuttx/timers/pwm.h>
+#include <nuttx/leds/rgbled.h>
+#include <nuttx/ioexpander/ioexpander.h>
+#include <arch/board/board.h>
+
+#include "thingy52.h"
+
+/****************************************************************************
+ * Pre-processor Definitions
+ ****************************************************************************/
+
+/* Lightwell RGB LED on SX1509 LED driver outputs */
+
+#define RGBLED_R_PIN (7)
+#define RGBLED_G_PIN (5)
+#define RGBLED_B_PIN (6)
+
+/****************************************************************************
+ * Private Function Prototypes
+ ****************************************************************************/
+
+static int nrf52_rgb_setup(FAR struct pwm_lowerhalf_s *dev);
+static int nrf52_rgb_shutdown(FAR struct pwm_lowerhalf_s *dev);
+static int nrf52_rgb_start(FAR struct pwm_lowerhalf_s *dev,
+                           FAR const struct pwm_info_s *info);
+static int nrf52_rgb_stop(FAR struct pwm_lowerhalf_s *dev);
+static int nrf52_rgb_ioctl(FAR struct pwm_lowerhalf_s *dev, int cmd,
+                           unsigned long arg);
+
+/****************************************************************************
+ * Private Data
+ ****************************************************************************/
+
+/* The RGB LED is not driven by a real PWM peripheral - the color intensity
+ * is set through the io-expander PWM operation, one channel per lightwell
+ * pin.
+ */
+
+static const struct pwm_ops_s g_rgb_ops =
+{
+  .setup    = nrf52_rgb_setup,
+  .shutdown = nrf52_rgb_shutdown,
+  .start    = nrf52_rgb_start,
+  .stop     = nrf52_rgb_stop,
+  .ioctl    = nrf52_rgb_ioctl,
+};
+
+static struct pwm_lowerhalf_s g_rgb_dev =
+{
+  .ops = &g_rgb_ops,
+};
+
+/****************************************************************************
+ * Private Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: nrf52_rgb_setup
+ ****************************************************************************/
+
+static int nrf52_rgb_setup(FAR struct pwm_lowerhalf_s *dev)
+{
+  return OK;
+}
+
+/****************************************************************************
+ * Name: nrf52_rgb_shutdown
+ ****************************************************************************/
+
+static int nrf52_rgb_shutdown(FAR struct pwm_lowerhalf_s *dev)
+{
+  return OK;
+}
+
+/****************************************************************************
+ * Name: nrf52_rgb_start
+ *
+ * Description:
+ *   Apply the requested duty cycles.  Each channel number is the SX1509 pin
+ *   of one lightwell color.
+ *
+ ****************************************************************************/
+
+static int nrf52_rgb_start(FAR struct pwm_lowerhalf_s *dev,
+                           FAR const struct pwm_info_s *info)
+{
+  FAR struct ioexpander_dev_s *ioe = nrf52_sx1509_get();
+  int pin;
+  int ret;
+  int i;
+
+  if (ioe == NULL)
+    {
+      return -ENODEV;
+    }
+
+  for (i = 0; i < CONFIG_PWM_NCHANNELS; i++)
+    {
+      pin = info->channels[i].channel;
+      if (pin <= 0)
+        {
+          continue;
+        }
+
+      ret = IOEXP_SETPWM(ioe, pin, info->channels[i].duty);
+      if (ret < 0)
+        {
+          return ret;
+        }
+    }
+
+  return OK;
+}
+
+/****************************************************************************
+ * Name: nrf52_rgb_stop
+ ****************************************************************************/
+
+static int nrf52_rgb_stop(FAR struct pwm_lowerhalf_s *dev)
+{
+  return OK;
+}
+
+/****************************************************************************
+ * Name: nrf52_rgb_ioctl
+ ****************************************************************************/
+
+static int nrf52_rgb_ioctl(FAR struct pwm_lowerhalf_s *dev, int cmd,
+                           unsigned long arg)
+{
+  return -ENOTTY;
+}
+
+/****************************************************************************
+ * Public Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: nrf52_rgbled_initialize
+ *
+ * Description:
+ *   Register the lightwell RGB LED as /dev/rgbled0.  Must be called after
+ *   the SX1509 io expander has been initialized.
+ *
+ ****************************************************************************/
+
+int nrf52_rgbled_initialize(void)
+{
+  int ret;
+
+  ret = rgbled_register("/dev/rgbled0", &g_rgb_dev, &g_rgb_dev, &g_rgb_dev,
+                        RGBLED_R_PIN, RGBLED_G_PIN, RGBLED_B_PIN);
+  if (ret < 0)
+    {
+      lederr("ERROR: rgbled_register failed: %d\n", ret);
+      return ret;
+    }
+
+  return OK;
+}
diff --git a/boards/arm/nrf52/thingy52/src/nrf52_sensors.c 
b/boards/arm/nrf52/thingy52/src/nrf52_sensors.c
new file mode 100644
index 00000000000..5a906f2af74
--- /dev/null
+++ b/boards/arm/nrf52/thingy52/src/nrf52_sensors.c
@@ -0,0 +1,126 @@
+/****************************************************************************
+ * boards/arm/nrf52/thingy52/src/nrf52_sensors.c
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ *
+ * 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 <errno.h>
+#include <sys/types.h>
+#include <syslog.h>
+
+#include <nuttx/i2c/i2c_master.h>
+
+#ifdef CONFIG_SENSORS_HTS221
+#  include <nuttx/sensors/hts221.h>
+#endif
+
+#ifdef CONFIG_SENSORS_LPS22HB
+#  include <nuttx/sensors/lps22hb.h>
+#endif
+
+#ifdef CONFIG_SENSORS_CCS811
+#  include <nuttx/sensors/ccs811.h>
+#endif
+
+#ifdef CONFIG_SENSORS_BH1745NUC
+#  include <nuttx/sensors/bh1745nuc.h>
+#endif
+
+#include "nrf52_i2c.h"
+#include "thingy52.h"
+
+/****************************************************************************
+ * Private Data
+ ****************************************************************************/
+
+#ifdef CONFIG_SENSORS_CCS811
+static const struct ccs811_config_s g_ccs811_config =
+{
+  .wake = nrf52_ccs811_wake,
+};
+#endif
+
+/****************************************************************************
+ * Public Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: nrf52_sensors_init
+ *
+ * Description:
+ *   Initialzie on-board sensors
+ *
+ ****************************************************************************/
+
+int nrf52_sensors_init(void)
+{
+  FAR struct i2c_master_s *i2c;
+  int ret = OK;
+
+  UNUSED(ret);
+
+  /* All on-board sensors are connected to the I2C0 bus */
+
+  i2c = nrf52_i2cbus_initialize(0);
+  if (i2c == NULL)
+    {
+      syslog(LOG_ERR, "ERROR: Failed to get I2C0 interface\n");
+      return -ENODEV;
+    }
+
+#ifdef CONFIG_SENSORS_HTS221
+  ret = hts221_register_uorb(0, i2c, HTS221_I2C_ADDR, NULL);
+  if (ret < 0)
+    {
+      syslog(LOG_ERR, "ERROR: hts221_register_uorb() failed: %d\n", ret);
+    }
+#endif
+
+#ifdef CONFIG_SENSORS_LPS22HB
+  ret = lps22hb_register_uorb(0, i2c, LPS22HB_I2C_ADDR);
+  if (ret < 0)
+    {
+      syslog(LOG_ERR, "ERROR: lps22hb_register_uorb() failed: %d\n", ret);
+    }
+#endif
+
+#ifdef CONFIG_SENSORS_CCS811
+  ret = ccs811_register_uorb(0, i2c, CCS811_I2C_ADDR, &g_ccs811_config);
+  if (ret < 0)
+    {
+      syslog(LOG_ERR, "ERROR: ccs811_register_uorb() failed: %d\n", ret);
+    }
+#endif
+
+#ifdef CONFIG_SENSORS_BH1745NUC
+  ret = bh1745nuc_register_uorb(0, i2c, BH1745NUC_I2C_ADDR);
+  if (ret < 0)
+    {
+      syslog(LOG_ERR, "ERROR: bh1745nuc_register_uorb() failed: %d\n", ret);
+    }
+#endif
+
+  return ret;
+}
diff --git a/boards/arm/nrf52/thingy52/src/nrf52_sx1509.c 
b/boards/arm/nrf52/thingy52/src/nrf52_sx1509.c
index 9b7b03b8148..054b7dede46 100644
--- a/boards/arm/nrf52/thingy52/src/nrf52_sx1509.c
+++ b/boards/arm/nrf52/thingy52/src/nrf52_sx1509.c
@@ -26,6 +26,7 @@
 
 #include <nuttx/config.h>
 
+#include <nuttx/arch.h>
 #include <nuttx/irq.h>
 
 #include <errno.h>
@@ -82,6 +83,13 @@ struct sx1509_config_s g_sx1509_cfg =
   .led_pre        = 2,
 #endif
 };
+
+/* Saved io-expander handle, used by nrf52_ccs811_wake() to drive the
+ * CCS811 nWAKE line (SX1509 pin 12) around each I2C transaction and by
+ * nrf52_sx1509_get() to expose the device to other board logic.
+ */
+
+static FAR struct ioexpander_dev_s *g_sx1509_ioe;
 /****************************************************************************
  * Private Functions
  ****************************************************************************/
@@ -153,12 +161,12 @@ static void nrf52_sx1509_pinscfg(struct ioexpander_dev_s 
*ioe)
   IOEXP_WRITEPIN(ioe, 3, false);
   gpio_lower_half(ioe, 3, GPIO_INPUT_PIN, 3);
 
-  /* Pin 4: BAT_MON_EN */
+  /* Pin 4: BAT_MON_EN - drive high to enable the battery voltage divider */
 
   IOEXP_SETDIRECTION(ioe, 4, IOEXPANDER_DIRECTION_OUT);
   IOEXP_SETOPTION(ioe, 4, IOEXPANDER_OPTION_INVERT,
                   (void *)IOEXPANDER_VAL_NORMAL);
-  IOEXP_WRITEPIN(ioe, 4, false);
+  IOEXP_WRITEPIN(ioe, 4, true);
   gpio_lower_half(ioe, 4, GPIO_OUTPUT_PIN, 4);
 
 #ifdef CONFIG_SX1509_LED_ENABLE
@@ -206,30 +214,48 @@ static void nrf52_sx1509_pinscfg(struct ioexpander_dev_s 
*ioe)
   IOEXP_WRITEPIN(ioe, 9, false);
   gpio_lower_half(ioe, 9, GPIO_OUTPUT_PIN, 9);
 
-  /* Pin 10: CSS_PWR_CTRL */
+  /* Pin 10: CSS_PWR_CTRL - drive high to power the CCS811 */
 
   IOEXP_SETDIRECTION(ioe, 10, IOEXPANDER_DIRECTION_OUT);
   IOEXP_SETOPTION(ioe, 10, IOEXPANDER_OPTION_INVERT,
                   (void *)IOEXPANDER_VAL_NORMAL);
-  IOEXP_WRITEPIN(ioe, 10, false);
+  IOEXP_WRITEPIN(ioe, 10, true);
   gpio_lower_half(ioe, 10, GPIO_OUTPUT_PIN, 10);
 
-  /* Pin 11: CSS_RESET */
+  /* Pin 11: CSS_RESET - active low, drive high to release the reset */
 
   IOEXP_SETDIRECTION(ioe, 11, IOEXPANDER_DIRECTION_OUT);
   IOEXP_SETOPTION(ioe, 11, IOEXPANDER_OPTION_INVERT,
                   (void *)IOEXPANDER_VAL_NORMAL);
-  IOEXP_WRITEPIN(ioe, 11, false);
+  IOEXP_WRITEPIN(ioe, 11, true);
   gpio_lower_half(ioe, 11, GPIO_OUTPUT_PIN, 11);
 
-  /* Pin 12: CSS_WAKE */
+  /* Pin 12: CSS_WAKE - active low nWAKE */
 
   IOEXP_SETDIRECTION(ioe, 12, IOEXPANDER_DIRECTION_OUT);
   IOEXP_SETOPTION(ioe, 12, IOEXPANDER_OPTION_INVERT,
                   (void *)IOEXPANDER_VAL_NORMAL);
-  IOEXP_WRITEPIN(ioe, 12, false);
+  IOEXP_WRITEPIN(ioe, 12, true);
   gpio_lower_half(ioe, 12, GPIO_OUTPUT_PIN, 12);
 
+  /* Bring up the CCS811 following its datasheet / the Thingy:52 firmware.
+   * Power-cycle it (its supply is held up by the SX1509 across a SoC reset,
+   * so a warm reset would otherwise leave it running in application mode);
+   * hold it in reset with nWAKE idle-high, re-power it, release the reset
+   * and wait for it to boot.  nWAKE is left idle-high; the driver pulses it
+   * low (a falling edge) around each I2C transaction - a static low does not
+   * keep this part awake.
+   */
+
+  IOEXP_WRITEPIN(ioe, 11, false);   /* CSS_RESET  - assert nRESET       */
+  IOEXP_WRITEPIN(ioe, 12, true);    /* CSS_WAKE   - nWAKE idle (high)   */
+  IOEXP_WRITEPIN(ioe, 10, false);   /* CSS_PWR_CTRL - power off          */
+  up_mdelay(50);                    /* let the supply discharge         */
+  IOEXP_WRITEPIN(ioe, 10, true);    /* CSS_PWR_CTRL - power on           */
+  up_mdelay(5);
+  IOEXP_WRITEPIN(ioe, 11, true);    /* release nRESET                   */
+  up_mdelay(30);                    /* boot time                        */
+
 #ifdef CONFIG_SX1509_LED_ENABLE
   /* Pin 13: SENSE_LED_R */
 
@@ -264,6 +290,40 @@ static void nrf52_sx1509_pinscfg(struct ioexpander_dev_s 
*ioe)
  * Public Functions
  ****************************************************************************/
 
+/****************************************************************************
+ * Name: nrf52_ccs811_wake
+ *
+ * Description:
+ *   Drive the CCS811 nWAKE line (SX1509 pin 12, active low).  Passed to the
+ *   CCS811 driver so it can wake the sensor around each I2C transaction.
+ *
+ * Input Parameters:
+ *   on - true asserts nWAKE (drives it low), false releases it (drives it
+ *        high).
+ *
+ ****************************************************************************/
+
+void nrf52_ccs811_wake(bool on)
+{
+  if (g_sx1509_ioe != NULL)
+    {
+      IOEXP_WRITEPIN(g_sx1509_ioe, 12, !on);
+    }
+}
+
+/****************************************************************************
+ * Name: nrf52_sx1509_get
+ *
+ * Description:
+ *   Return the io-expander device, or NULL if not yet initialized.
+ *
+ ****************************************************************************/
+
+FAR struct ioexpander_dev_s *nrf52_sx1509_get(void)
+{
+  return g_sx1509_ioe;
+}
+
 /****************************************************************************
  * Name: nrf52_sx1509_initialize
  *
@@ -304,6 +364,10 @@ int nrf52_sx1509_initialize(void)
 
   nrf52_sx1509_pinscfg(ioe);
 
+  /* Remember the io-expander so the CCS811 driver can pulse nWAKE. */
+
+  g_sx1509_ioe = ioe;
+
 #ifdef CONFIG_SX1509_LED_ENABLE
   /* Initialize sx1509 LED driver */
 
diff --git a/boards/arm/nrf52/thingy52/src/thingy52.h 
b/boards/arm/nrf52/thingy52/src/thingy52.h
index db1dfd306e2..69bb39f6f1b 100644
--- a/boards/arm/nrf52/thingy52/src/thingy52.h
+++ b/boards/arm/nrf52/thingy52/src/thingy52.h
@@ -30,6 +30,8 @@
 #include <nuttx/config.h>
 #include <nuttx/compiler.h>
 
+#include <stdbool.h>
+
 #include "nrf52_gpio.h"
 
 /****************************************************************************
@@ -52,40 +54,48 @@
 
 #define GPIO_BUTTON1 (GPIO_INPUT | GPIO_PULLUP | GPIO_PORT0 | GPIO_PIN(11))
 
+/* Supported devices ********************************************************/
+
 /* LIS2DH12 (I2C address: 0x19)
  *   INT - P0.12
  */
 
+#define LIS2DH12_I2C_ADDR 0x19
 #define GPIO_LIS2DH12_INT (GPIO_INPUT | GPIO_PORT0 | GPIO_PIN(12))
 
 /* MPU9250 (I2C address: 0x68)
  *   INT - P0.05
  */
 
+#define MPU9250_I2C_ADDR  0x68
 #define GPIO_MPU9250_INT (GPIO_INPUT | GPIO_PORT0 | GPIO_PIN(5))
 
 /* LPS22HB (I2C address: 0x5c)
  *   INT - P0.23
  */
 
+#define LPS22HB_I2C_ADDR  0x5c
 #define GPIO_LPS22HB_INT (GPIO_INPUT | GPIO_PORT0 | GPIO_PIN(23))
 
 /* HTS221 (I2C address: 0x5f)
  *   INT - P0.24
  */
 
+#define HTS221_I2C_ADDR   0x5f
 #define GPIO_HTS221_INT (GPIO_INPUT | GPIO_PORT0 | GPIO_PIN(24))
 
 /* BH1745NUC (I2C address: 0x38)
  *   INT - P0.31
  */
 
+#define BH1745NUC_I2C_ADDR 0x38
 #define GPIO_BH1745NUC_INT (GPIO_INPUT | GPIO_PORT0 | GPIO_PIN(31))
 
 /* CCS811 (I2C address: 0x5a)
  *   INT - P0.22
  */
 
+#define CCS811_I2C_ADDR   0x5a
 #define GPIO_CCS811_INT (GPIO_INPUT | GPIO_PORT0 | GPIO_PIN(22))
 
 /* SX1509 (I2C address: 0x3e)
@@ -95,6 +105,13 @@
 
 #define GPIO_SX1509_RESET (GPIO_OUTPUT | GPIO_VALUE_ONE | GPIO_PORT0 | 
GPIO_PIN(16))
 
+/* VDD_PWR_CTRL - P0.30
+ *   Enables the board VDD rail that supplies all on-board sensors.
+ *   Must be driven high, otherwise the rail floats at a too-low voltage.
+ */
+
+#define GPIO_VDD_PWR_CTRL (GPIO_OUTPUT | GPIO_VALUE_ONE | GPIO_PORT0 | 
GPIO_PIN(30))
+
 /****************************************************************************
  * Public Types
  ****************************************************************************/
@@ -122,6 +139,30 @@
 
 int nrf52_bringup(void);
 
+/****************************************************************************
+ * Name: nrf52_sensors_init
+ *
+ * Description:
+ *   Initialzie on-board sensors
+ *
+ ****************************************************************************/
+
+#ifdef CONFIG_NRF52_I2C0_MASTER
+int nrf52_sensors_init(void);
+#endif
+
+#ifdef CONFIG_ADC
+/****************************************************************************
+ * Name: nrf52_adc_setup
+ *
+ * Description:
+ *   Initialize the ADC used to measure the battery voltage.
+ *
+ ****************************************************************************/
+
+int nrf52_adc_setup(void);
+#endif
+
 #ifdef CONFIG_IOEXPANDER_SX1509
 /****************************************************************************
  * Name: nrf52_sx1509_initialize
@@ -132,6 +173,39 @@ int nrf52_bringup(void);
  ****************************************************************************/
 
 int nrf52_sx1509_initialize(void);
+
+/****************************************************************************
+ * Name: nrf52_ccs811_wake
+ *
+ * Description:
+ *   Drive the CCS811 nWAKE line (SX1509 pin 12, active low).
+ *
+ ****************************************************************************/
+
+void nrf52_ccs811_wake(bool on);
+
+/****************************************************************************
+ * Name: nrf52_sx1509_get
+ *
+ * Description:
+ *   Return the io-expander device, or NULL if not yet initialized.
+ *
+ ****************************************************************************/
+
+FAR struct ioexpander_dev_s *nrf52_sx1509_get(void);
+#endif
+
+#if defined(CONFIG_RGBLED) && defined(CONFIG_IOEXPANDER_SX1509) && \
+    defined(CONFIG_IOEXPANDER_PWM)
+/****************************************************************************
+ * Name: nrf52_rgbled_initialize
+ *
+ * Description:
+ *   Configure the RGB LED.
+ *
+ ****************************************************************************/
+
+int nrf52_rgbled_initialize(void);
 #endif
 
 #endif /* __ASSEMBLY__ */
diff --git a/drivers/ioexpander/sx1509.c b/drivers/ioexpander/sx1509.c
index c1ed2dac606..72c20e20e1c 100644
--- a/drivers/ioexpander/sx1509.c
+++ b/drivers/ioexpander/sx1509.c
@@ -156,7 +156,8 @@ static const struct ioexpander_ops_s g_sx1509_ops =
 #endif
 };
 
-#if defined(CONFIG_SX1509_LED_ENABLE) || defined(CONFIG_IOEXPANDER_PWM)
+#if (defined(CONFIG_SX1509_LED_ENABLE) && defined(CONFIG_USERLED_EFFECTS)) || \
+    defined(CONFIG_IOEXPANDER_PWM)
 /* LED driver registers:
  *   TON, ION, OFF, TRISE, TFALL
  */

Reply via email to