From 5f67a6119dfb1a83c039df81cb4884a3fd18c1dc Mon Sep 17 00:00:00 2001 From: Michael Hope Date: Sat, 17 Mar 2018 12:44:40 +0100 Subject: [PATCH] include: improve compatibility with C++ apps. This patch lets a C++ application use more of Zephyr by adding guards and changeing some constructs to the C++11 equivalent. Changes include: - Adding guards - Switching to static_assert - Switching to a template for ARRAY_SIZE as g++ doesn't have the builtin. - Re-ordering designated initialisers to match the struct field order as G++ only supports simple designated initialisers. Signed-off-by: Michael Hope --- include/crc16.h | 9 ++++++ include/device.h | 2 +- include/gpio.h | 36 +++++++++++++--------- include/kernel.h | 2 +- include/led_strip.h | 14 +++++++-- include/misc/byteorder.h | 11 ++++--- include/misc/util.h | 14 ++++----- include/spi.h | 9 ++++-- include/toolchain/gcc.h | 6 +++- include/uart.h | 60 ++++++++++++++++++++++++------------- include/usb/class/usb_hid.h | 8 +++++ include/usb/usb_device.h | 8 +++++ include/watchdog.h | 15 ++++++---- 13 files changed, 135 insertions(+), 59 deletions(-) diff --git a/include/crc16.h b/include/crc16.h index 9feae3e3a0..a5485e3815 100644 --- a/include/crc16.h +++ b/include/crc16.h @@ -14,6 +14,10 @@ #include #include +#ifdef __cplusplus +extern "C" { +#endif + /** * @defgroup checksum Checksum */ @@ -110,4 +114,9 @@ static inline u16_t crc16_ansi(const u8_t *src, size_t len) /** * @} */ + +#ifdef __cplusplus +} +#endif + #endif diff --git a/include/device.h b/include/device.h index bbf9038ae8..a5f6580659 100644 --- a/include/device.h +++ b/include/device.h @@ -216,7 +216,7 @@ struct device; * @param config_info address of driver instance config information */ struct device_config { - char *name; + const char *name; int (*init)(struct device *device); #ifdef CONFIG_DEVICE_POWER_MANAGEMENT int (*device_pm_control)(struct device *device, u32_t command, diff --git a/include/gpio.h b/include/gpio.h index 76d28c95dc..f8db0d8c9d 100644 --- a/include/gpio.h +++ b/include/gpio.h @@ -20,15 +20,16 @@ #include #include +#ifdef __cplusplus +extern "C" { +#endif + /** * @brief GPIO Driver APIs * @defgroup gpio_interface GPIO Driver APIs * @ingroup io_interfaces * @{ */ -#ifdef __cplusplus -extern "C" { -#endif /** @cond INTERNAL_HIDDEN */ #define GPIO_ACCESS_BY_PIN 0 @@ -269,7 +270,8 @@ __syscall int gpio_config(struct device *port, int access_op, u32_t pin, static inline int _impl_gpio_config(struct device *port, int access_op, u32_t pin, int flags) { - const struct gpio_driver_api *api = port->driver_api; + const struct gpio_driver_api *api = + (const struct gpio_driver_api *)port->driver_api; return api->config(port, access_op, pin, flags); } @@ -280,7 +282,8 @@ __syscall int gpio_write(struct device *port, int access_op, u32_t pin, static inline int _impl_gpio_write(struct device *port, int access_op, u32_t pin, u32_t value) { - const struct gpio_driver_api *api = port->driver_api; + const struct gpio_driver_api *api = + (const struct gpio_driver_api *)port->driver_api; return api->write(port, access_op, pin, value); } @@ -291,7 +294,8 @@ __syscall int gpio_read(struct device *port, int access_op, u32_t pin, static inline int _impl_gpio_read(struct device *port, int access_op, u32_t pin, u32_t *value) { - const struct gpio_driver_api *api = port->driver_api; + const struct gpio_driver_api *api = + (const struct gpio_driver_api *)port->driver_api; return api->read(port, access_op, pin, value); } @@ -302,7 +306,8 @@ __syscall int gpio_enable_callback(struct device *port, int access_op, static inline int _impl_gpio_enable_callback(struct device *port, int access_op, u32_t pin) { - const struct gpio_driver_api *api = port->driver_api; + const struct gpio_driver_api *api = + (const struct gpio_driver_api *)port->driver_api; return api->enable_callback(port, access_op, pin); } @@ -313,7 +318,8 @@ __syscall int gpio_disable_callback(struct device *port, int access_op, static inline int _impl_gpio_disable_callback(struct device *port, int access_op, u32_t pin) { - const struct gpio_driver_api *api = port->driver_api; + const struct gpio_driver_api *api = + (const struct gpio_driver_api *)port->driver_api; return api->disable_callback(port, access_op, pin); } @@ -391,7 +397,8 @@ static inline void gpio_init_callback(struct gpio_callback *callback, static inline int gpio_add_callback(struct device *port, struct gpio_callback *callback) { - const struct gpio_driver_api *api = port->driver_api; + const struct gpio_driver_api *api = + (const struct gpio_driver_api *)port->driver_api; __ASSERT(callback, "Callback pointer should not be NULL"); @@ -410,7 +417,8 @@ static inline int gpio_add_callback(struct device *port, static inline int gpio_remove_callback(struct device *port, struct gpio_callback *callback) { - const struct gpio_driver_api *api = port->driver_api; + const struct gpio_driver_api *api = + (const struct gpio_driver_api *)port->driver_api; __ASSERT(callback, "Callback pointer should not be NULL"); @@ -569,14 +577,14 @@ struct gpio_pin_config { #define GPIO_GET_CONTROLLER(_conf) GPIO_GET_CONTROLLER_IDX(, _conf) #define GPIO_GET_PIN(_conf) GPIO_GET_PIN_IDX(, _conf) -#ifdef __cplusplus -} -#endif - /** * @} */ #include +#ifdef __cplusplus +} +#endif + #endif /* __GPIO_H__ */ diff --git a/include/kernel.h b/include/kernel.h index 92a0ceeb06..3d8ffa4191 100644 --- a/include/kernel.h +++ b/include/kernel.h @@ -1549,8 +1549,8 @@ struct k_queue { #define _K_QUEUE_INITIALIZER(obj) \ { \ - .wait_q = SYS_DLIST_STATIC_INIT(&obj.wait_q), \ .data_q = SYS_SLIST_STATIC_INIT(&obj.data_q), \ + .wait_q = SYS_DLIST_STATIC_INIT(&obj.wait_q), \ _POLL_EVENT_OBJ_INIT(obj) \ _OBJECT_TRACING_INIT \ } diff --git a/include/led_strip.h b/include/led_strip.h index f4fd9e8fc5..56743e7a49 100644 --- a/include/led_strip.h +++ b/include/led_strip.h @@ -18,6 +18,10 @@ #include #include +#ifdef __cplusplus +extern "C" { +#endif + /** * @brief Color value for a single RGB LED. * @@ -86,7 +90,8 @@ struct led_strip_driver_api { static inline int led_strip_update_rgb(struct device *dev, struct led_rgb *pixels, size_t num_pixels) { - const struct led_strip_driver_api *api = dev->driver_api; + const struct led_strip_driver_api *api = + (const struct led_strip_driver_api *)dev->driver_api; return api->update_rgb(dev, pixels, num_pixels); } @@ -111,9 +116,14 @@ static inline int led_strip_update_rgb(struct device *dev, static inline int led_strip_update_channels(struct device *dev, u8_t *channels, size_t num_channels) { - const struct led_strip_driver_api *api = dev->driver_api; + const struct led_strip_driver_api *api = + (const struct led_strip_driver_api *)dev->driver_api; return api->update_channels(dev, channels, num_channels); } +#ifdef __cplusplus +} +#endif + #endif /* _ZEPHYR_LED_STRIP_H */ diff --git a/include/misc/byteorder.h b/include/misc/byteorder.h index fc10852bb9..d48200d50b 100644 --- a/include/misc/byteorder.h +++ b/include/misc/byteorder.h @@ -289,14 +289,17 @@ static inline u64_t sys_get_le64(const u8_t src[8]) */ static inline void sys_memcpy_swap(void *dst, const void *src, size_t length) { - __ASSERT(((src < dst && (src + length) <= dst) || - (src > dst && (dst + length) <= src)), + u8_t *pdst = (u8_t *)dst; + const u8_t *psrc = (const u8_t *)src; + + __ASSERT(((psrc < pdst && (psrc + length) <= pdst) || + (psrc > pdst && (pdst + length) <= psrc)), "Source and destination buffers must not overlap"); - src += length - 1; + psrc += length - 1; for (; length > 0; length--) { - *((u8_t *)dst++) = *((u8_t *)src--); + *pdst++ = *psrc--; } } diff --git a/include/misc/util.h b/include/misc/util.h index c38d5bde87..9b16498ceb 100644 --- a/include/misc/util.h +++ b/include/misc/util.h @@ -14,10 +14,6 @@ #ifndef _UTIL__H_ #define _UTIL__H_ -#ifdef __cplusplus -extern "C" { -#endif - #ifndef _ASMLANGUAGE #include @@ -41,12 +37,18 @@ extern "C" { !__builtin_types_compatible_p(__typeof__(array), \ __typeof__(&(array)[0]))) +#if defined(__cplusplus) +template < class T, size_t N > +constexpr size_t ARRAY_SIZE(T(&)[N]) { return N; } + +#else /* Evaluates to number of elements in an array; compile error if not * an array (e.g. pointer) */ #define ARRAY_SIZE(array) \ ((unsigned long) (IS_ARRAY(array) + \ (sizeof(array) / sizeof((array)[0])))) +#endif /* Evaluates to 1 if ptr is part of array, 0 otherwise; compile error if * "array" argument is not an array (e.g. "ptr" and "array" mixed up) @@ -302,8 +304,4 @@ static inline s64_t arithmetic_shift_right(s64_t value, u8_t shift) */ #define UTIL_LISTIFY(LEN, F, F_ARG) UTIL_EVAL(UTIL_REPEAT(LEN, F, F_ARG)) -#ifdef __cplusplus -} -#endif - #endif /* _UTIL__H_ */ diff --git a/include/spi.h b/include/spi.h index f89110ef66..486e95b1b7 100644 --- a/include/spi.h +++ b/include/spi.h @@ -258,7 +258,8 @@ static inline int _impl_spi_transceive(struct device *dev, const struct spi_buf_set *tx_bufs, const struct spi_buf_set *rx_bufs) { - const struct spi_driver_api *api = dev->driver_api; + const struct spi_driver_api *api = + (const struct spi_driver_api *)dev->driver_api; return api->transceive(dev, config, tx_bufs, rx_bufs); } @@ -330,7 +331,8 @@ static inline int spi_transceive_async(struct device *dev, const struct spi_buf_set *rx_bufs, struct k_poll_signal *async) { - const struct spi_driver_api *api = dev->driver_api; + const struct spi_driver_api *api = + (const struct spi_driver_api *)dev->driver_api; return api->transceive_async(dev, config, tx_bufs, rx_bufs, async); } @@ -405,7 +407,8 @@ __syscall int spi_release(struct device *dev, static inline int _impl_spi_release(struct device *dev, const struct spi_config *config) { - const struct spi_driver_api *api = dev->driver_api; + const struct spi_driver_api *api = + (const struct spi_driver_api *)dev->driver_api; return api->release(dev, config); } diff --git a/include/toolchain/gcc.h b/include/toolchain/gcc.h index 31c9aa27b0..4140548b20 100644 --- a/include/toolchain/gcc.h +++ b/include/toolchain/gcc.h @@ -13,11 +13,15 @@ * Macros to abstract compiler capabilities for GCC toolchain. */ +/* C++11 has static_assert built in */ +#ifdef __cplusplus +#define BUILD_ASSERT(EXPR) static_assert(EXPR, "") +#define BUILD_ASSERT_MSG(EXPR, MSG) static_assert(EXPR, MSG) /* * GCC 4.6 and higher have _Static_assert built in, and its output is * easier to understand than the common BUILD_ASSERT macros. */ -#if __GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 6) +#elif (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 6)) #define BUILD_ASSERT(EXPR) _Static_assert(EXPR, "") #define BUILD_ASSERT_MSG(EXPR, MSG) _Static_assert(EXPR, MSG) #endif diff --git a/include/uart.h b/include/uart.h index 4804d30cfc..b412bd4d3b 100644 --- a/include/uart.h +++ b/include/uart.h @@ -187,7 +187,8 @@ __syscall int uart_err_check(struct device *dev); static inline int _impl_uart_err_check(struct device *dev) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if (api->err_check) { return api->err_check(dev); @@ -211,7 +212,8 @@ __syscall int uart_poll_in(struct device *dev, unsigned char *p_char); static inline int _impl_uart_poll_in(struct device *dev, unsigned char *p_char) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; return api->poll_in(dev, p_char); } @@ -237,7 +239,8 @@ __syscall unsigned char uart_poll_out(struct device *dev, static inline unsigned char _impl_uart_poll_out(struct device *dev, unsigned char out_char) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; return api->poll_out(dev, out_char); } @@ -266,7 +269,8 @@ static inline unsigned char _impl_uart_poll_out(struct device *dev, static inline int uart_fifo_fill(struct device *dev, const u8_t *tx_data, int size) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if (api->fifo_fill) { return api->fifo_fill(dev, tx_data, size); @@ -297,7 +301,8 @@ static inline int uart_fifo_fill(struct device *dev, const u8_t *tx_data, static inline int uart_fifo_read(struct device *dev, u8_t *rx_data, const int size) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if (api->fifo_read) { return api->fifo_read(dev, rx_data, size); @@ -317,7 +322,8 @@ __syscall void uart_irq_tx_enable(struct device *dev); static inline void _impl_uart_irq_tx_enable(struct device *dev) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if (api->irq_tx_enable) { api->irq_tx_enable(dev); @@ -334,7 +340,8 @@ __syscall void uart_irq_tx_disable(struct device *dev); static inline void _impl_uart_irq_tx_disable(struct device *dev) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if (api->irq_tx_disable) { api->irq_tx_disable(dev); @@ -358,7 +365,8 @@ static inline void _impl_uart_irq_tx_disable(struct device *dev) */ static inline int uart_irq_tx_ready(struct device *dev) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if (api->irq_tx_ready) { return api->irq_tx_ready(dev); @@ -378,7 +386,8 @@ __syscall void uart_irq_rx_enable(struct device *dev); static inline void _impl_uart_irq_rx_enable(struct device *dev) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if (api->irq_rx_enable) { api->irq_rx_enable(dev); @@ -396,7 +405,8 @@ __syscall void uart_irq_rx_disable(struct device *dev); static inline void _impl_uart_irq_rx_disable(struct device *dev) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if (api->irq_rx_disable) { api->irq_rx_disable(dev); @@ -422,7 +432,8 @@ static inline void _impl_uart_irq_rx_disable(struct device *dev) */ static inline int uart_irq_tx_complete(struct device *dev) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if (api->irq_tx_complete) { return api->irq_tx_complete(dev); @@ -459,7 +470,8 @@ static inline int __deprecated uart_irq_tx_empty(struct device *dev) */ static inline int uart_irq_rx_ready(struct device *dev) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if (api->irq_rx_ready) { return api->irq_rx_ready(dev); @@ -478,7 +490,8 @@ __syscall void uart_irq_err_enable(struct device *dev); static inline void _impl_uart_irq_err_enable(struct device *dev) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if (api->irq_err_enable) { api->irq_err_enable(dev); @@ -497,7 +510,8 @@ __syscall void uart_irq_err_disable(struct device *dev); static inline void _impl_uart_irq_err_disable(struct device *dev) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if (api->irq_err_disable) { api->irq_err_disable(dev); @@ -516,7 +530,8 @@ __syscall int uart_irq_is_pending(struct device *dev); static inline int _impl_uart_irq_is_pending(struct device *dev) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if (api->irq_is_pending) { return api->irq_is_pending(dev); @@ -536,7 +551,8 @@ __syscall int uart_irq_update(struct device *dev); static inline int _impl_uart_irq_update(struct device *dev) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if (api->irq_update) { return api->irq_update(dev); @@ -559,7 +575,8 @@ static inline int _impl_uart_irq_update(struct device *dev) static inline void uart_irq_callback_set(struct device *dev, uart_irq_callback_t cb) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if ((api != NULL) && (api->irq_callback_set != NULL)) { api->irq_callback_set(dev, cb); @@ -586,7 +603,8 @@ __syscall int uart_line_ctrl_set(struct device *dev, static inline int _impl_uart_line_ctrl_set(struct device *dev, u32_t ctrl, u32_t val) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if (api->line_ctrl_set) { return api->line_ctrl_set(dev, ctrl, val); @@ -610,7 +628,8 @@ __syscall int uart_line_ctrl_get(struct device *dev, u32_t ctrl, u32_t *val); static inline int _impl_uart_line_ctrl_get(struct device *dev, u32_t ctrl, u32_t *val) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if (api && api->line_ctrl_get) { return api->line_ctrl_get(dev, ctrl, val); @@ -640,7 +659,8 @@ __syscall int uart_drv_cmd(struct device *dev, u32_t cmd, u32_t p); static inline int _impl_uart_drv_cmd(struct device *dev, u32_t cmd, u32_t p) { - const struct uart_driver_api *api = dev->driver_api; + const struct uart_driver_api *api = + (const struct uart_driver_api *)dev->driver_api; if (api->drv_cmd) { return api->drv_cmd(dev, cmd, p); diff --git a/include/usb/class/usb_hid.h b/include/usb/class/usb_hid.h index 1a92d51aad..b063dcf722 100644 --- a/include/usb/class/usb_hid.h +++ b/include/usb/class/usb_hid.h @@ -17,6 +17,10 @@ #ifndef __USB_HID_H__ #define __USB_HID_H__ +#ifdef __cplusplus +extern "C" { +#endif + struct usb_hid_class_subdescriptor { u8_t bDescriptorType; u16_t wDescriptorLength; @@ -153,4 +157,8 @@ void usb_hid_register_device(const u8_t *desc, size_t size, /* Initialize USB HID */ int usb_hid_init(void); +#ifdef __cplusplus +} +#endif + #endif /* __USB_HID_H__ */ diff --git a/include/usb/usb_device.h b/include/usb/usb_device.h index 25066d0c97..cab97f4975 100644 --- a/include/usb/usb_device.h +++ b/include/usb/usb_device.h @@ -39,6 +39,10 @@ #include #include +#ifdef __cplusplus +extern "C" { +#endif + /************************************************************************* * USB configuration **************************************************************************/ @@ -363,4 +367,8 @@ int usb_transfer_sync(u8_t ep, u8_t *data, size_t dlen, unsigned int flags); */ void usb_cancel_transfer(u8_t ep); +#ifdef __cplusplus +} +#endif + #endif /* USB_DEVICE_H_ */ diff --git a/include/watchdog.h b/include/watchdog.h index b2d8e906f0..94de0ae561 100644 --- a/include/watchdog.h +++ b/include/watchdog.h @@ -74,14 +74,16 @@ struct wdt_driver_api { static inline void wdt_enable(struct device *dev) { - const struct wdt_driver_api *api = dev->driver_api; + const struct wdt_driver_api *api = + (const struct wdt_driver_api *)dev->driver_api; api->enable(dev); } static inline void wdt_disable(struct device *dev) { - const struct wdt_driver_api *api = dev->driver_api; + const struct wdt_driver_api *api = + (const struct wdt_driver_api *)dev->driver_api; api->disable(dev); } @@ -89,7 +91,8 @@ static inline void wdt_disable(struct device *dev) static inline void wdt_get_config(struct device *dev, struct wdt_config *config) { - const struct wdt_driver_api *api = dev->driver_api; + const struct wdt_driver_api *api = + (const struct wdt_driver_api *)dev->driver_api; api->get_config(dev, config); } @@ -97,14 +100,16 @@ static inline void wdt_get_config(struct device *dev, static inline int wdt_set_config(struct device *dev, struct wdt_config *config) { - const struct wdt_driver_api *api = dev->driver_api; + const struct wdt_driver_api *api = + (const struct wdt_driver_api *)dev->driver_api; return api->set_config(dev, config); } static inline void wdt_reload(struct device *dev) { - const struct wdt_driver_api *api = dev->driver_api; + const struct wdt_driver_api *api = + (const struct wdt_driver_api *)dev->driver_api; api->reload(dev); }