Update Zephyr to v3.4.0

This commit is contained in:
valeros
2023-09-29 13:40:00 +03:00
parent e74bdd6c8c
commit f7a0f68506
26 changed files with 288 additions and 1025 deletions

View File

@@ -119,6 +119,11 @@ if "nobuild" in COMMAND_LINE_TARGETS:
else:
target_elf = env.BuildProgram()
target_firm = env.ElfToBin(join("$BUILD_DIR", "${PROGNAME}"), target_elf)
if "zephyr" in frameworks and "mcuboot-image" in COMMAND_LINE_TARGETS:
target_firm = env.MCUbootImage(
join("$BUILD_DIR", "${PROGNAME}.mcuboot.bin"), target_firm)
env.Depends(target_firm, "checkprogsize")
AlwaysBuild(env.Alias("nobuild", target_firm))

View File

@@ -4,48 +4,43 @@
* SPDX-License-Identifier: Apache-2.0
*/
#include <zephyr.h>
#include <device.h>
#include <devicetree.h>
#include <drivers/gpio.h>
#include <zephyr/kernel.h>
#include <zephyr/drivers/gpio.h>
/* 1000 msec = 1 sec */
#define SLEEP_TIME_MS 1000
#define SLEEP_TIME_MS 300
/* The devicetree node identifier for the "led0" alias. */
#define LED0_NODE DT_ALIAS(led0)
#if DT_NODE_HAS_STATUS(LED0_NODE, okay)
#define LED0 DT_GPIO_LABEL(LED0_NODE, gpios)
#define PIN DT_GPIO_PIN(LED0_NODE, gpios)
#define FLAGS DT_GPIO_FLAGS(LED0_NODE, gpios)
#else
/* A build error here means your board isn't set up to blink an LED. */
#error "Unsupported board: led0 devicetree alias is not defined"
#define LED0 ""
#define PIN 0
#define FLAGS 0
#endif
/*
* A build error on this line means your board is unsupported.
* See the sample documentation for information on how to fix this.
*/
static const struct gpio_dt_spec led = GPIO_DT_SPEC_GET(LED0_NODE, gpios);
void main(void)
{
const struct device *dev;
bool led_is_on = true;
int ret;
dev = device_get_binding(LED0);
if (dev == NULL) {
if (!gpio_is_ready_dt(&led))
{
return;
}
ret = gpio_pin_configure(dev, PIN, GPIO_OUTPUT_ACTIVE | FLAGS);
if (ret < 0) {
ret = gpio_pin_configure_dt(&led, GPIO_OUTPUT_ACTIVE);
if (ret < 0)
{
return;
}
while (1) {
gpio_pin_set(dev, PIN, (int)led_is_on);
led_is_on = !led_is_on;
while (1)
{
ret = gpio_pin_toggle_dt(&led);
if (ret < 0)
{
return;
}
k_msleep(SLEEP_TIME_MS);
}
}

View File

@@ -1 +1 @@
# nothing here
CONFIG_GPIO=y

View File

@@ -19,9 +19,9 @@
*/
#include <stdio.h>
#include <zephyr.h>
#include <arch/cpu.h>
#include <sys/printk.h>
#include <zephyr/kernel.h>
#include <zephyr/arch/cpu.h>
#include <zephyr/sys/printk.h>
/**
* @class semaphore the basic pure virtual semaphore class
@@ -64,7 +64,7 @@ public:
cpp_semaphore::cpp_semaphore()
{
printk("Create semaphore %p\n", this);
k_sem_init(&_sema_internal, 0, UINT_MAX);
k_sem_init(&_sema_internal, 0, K_SEM_MAX_LIMIT);
}
/*
@@ -98,12 +98,9 @@ int cpp_semaphore::wait(int timeout)
}
/**
*
* @brief Signal a semaphore
*
* This routine signals the specified semaphore.
*
* @return N/A
*/
void cpp_semaphore::give(void)
{

View File

@@ -1,2 +1,2 @@
CONFIG_CPLUSPLUS=y
CONFIG_MINIMAL_LIBC_MALLOC_ARENA_SIZE=128
CONFIG_CPP=y
CONFIG_COMMON_LIBC_MALLOC_ARENA_SIZE=128

View File

@@ -4,13 +4,14 @@
* SPDX-License-Identifier: Apache-2.0
*/
#include <zephyr.h>
#include <kernel.h>
#include <sys/printk.h>
#include <device.h>
#include <drivers/can.h>
#include <drivers/gpio.h>
#include <sys/byteorder.h>
#include <stdio.h>
#include <zephyr/kernel.h>
#include <zephyr/sys/printk.h>
#include <zephyr/device.h>
#include <zephyr/drivers/can.h>
#include <zephyr/drivers/gpio.h>
#include <zephyr/sys/byteorder.h>
#define RX_THREAD_STACK_SIZE 512
#define RX_THREAD_PRIORITY 2
@@ -25,25 +26,34 @@
K_THREAD_STACK_DEFINE(rx_thread_stack, RX_THREAD_STACK_SIZE);
K_THREAD_STACK_DEFINE(poll_state_stack, STATE_POLL_THREAD_STACK_SIZE);
const struct device *can_dev;
const struct device *led_gpio_dev;
const struct device *const can_dev = DEVICE_DT_GET(DT_CHOSEN(zephyr_canbus));
struct gpio_dt_spec led = GPIO_DT_SPEC_GET_OR(DT_ALIAS(led0), gpios, {0});
struct k_thread rx_thread_data;
struct k_thread poll_state_thread_data;
struct zcan_work rx_work;
struct k_work_poll change_led_work;
struct k_work state_change_work;
enum can_state current_state;
struct can_bus_err_cnt current_err_cnt;
CAN_DEFINE_MSGQ(counter_msgq, 2);
CAN_MSGQ_DEFINE(change_led_msgq, 2);
CAN_MSGQ_DEFINE(counter_msgq, 2);
void tx_irq_callback(uint32_t error_flags, void *arg)
static struct k_poll_event change_led_events[1] = {
K_POLL_EVENT_STATIC_INITIALIZER(K_POLL_TYPE_MSGQ_DATA_AVAILABLE,
K_POLL_MODE_NOTIFY_ONLY,
&change_led_msgq, 0)
};
void tx_irq_callback(const struct device *dev, int error, void *arg)
{
char *sender = (char *)arg;
if (error_flags) {
printk("Callback! error-code: %d\nSender: %s\n",
error_flags, sender);
ARG_UNUSED(dev);
if (error != 0) {
printf("Callback! error-code: %d\nSender: %s\n",
error, sender);
}
}
@@ -52,68 +62,63 @@ void rx_thread(void *arg1, void *arg2, void *arg3)
ARG_UNUSED(arg1);
ARG_UNUSED(arg2);
ARG_UNUSED(arg3);
const struct zcan_filter filter = {
.id_type = CAN_EXTENDED_IDENTIFIER,
.rtr = CAN_DATAFRAME,
const struct can_filter filter = {
.flags = CAN_FILTER_DATA | CAN_FILTER_IDE,
.id = COUNTER_MSG_ID,
.rtr_mask = 1,
.id_mask = CAN_EXT_ID_MASK
.mask = CAN_EXT_ID_MASK
};
struct zcan_frame msg;
struct can_frame frame;
int filter_id;
filter_id = can_attach_msgq(can_dev, &counter_msgq, &filter);
printk("Counter filter id: %d\n", filter_id);
filter_id = can_add_rx_filter_msgq(can_dev, &counter_msgq, &filter);
printf("Counter filter id: %d\n", filter_id);
while (1) {
k_msgq_get(&counter_msgq, &msg, K_FOREVER);
k_msgq_get(&counter_msgq, &frame, K_FOREVER);
if (msg.dlc != 2U) {
printk("Wrong data length: %u\n", msg.dlc);
if (frame.dlc != 2U) {
printf("Wrong data length: %u\n", frame.dlc);
continue;
}
printk("Counter received: %u\n",
sys_be16_to_cpu(UNALIGNED_GET((uint16_t *)&msg.data)));
printf("Counter received: %u\n",
sys_be16_to_cpu(UNALIGNED_GET((uint16_t *)&frame.data)));
}
}
void change_led(struct zcan_frame *msg, void *unused)
void change_led_work_handler(struct k_work *work)
{
ARG_UNUSED(unused);
struct can_frame frame;
int ret;
#if DT_PHA_HAS_CELL(DT_ALIAS(led0), gpios, pin) && \
DT_NODE_HAS_PROP(DT_ALIAS(led0), gpios)
if (!led_gpio_dev) {
printk("No LED GPIO device\n");
return;
while (k_msgq_get(&change_led_msgq, &frame, K_NO_WAIT) == 0) {
if (led.port == NULL) {
printf("LED %s\n", frame.data[0] == SET_LED ? "ON" : "OFF");
} else {
gpio_pin_set(led.port, led.pin, frame.data[0] == SET_LED ? 1 : 0);
}
}
switch (msg->data[0]) {
case SET_LED:
gpio_pin_set(led_gpio_dev,
DT_GPIO_PIN(DT_ALIAS(led0), gpios), 1);
break;
case RESET_LED:
gpio_pin_set(led_gpio_dev,
DT_GPIO_PIN(DT_ALIAS(led0), gpios), 0);
break;
ret = k_work_poll_submit(&change_led_work, change_led_events,
ARRAY_SIZE(change_led_events), K_FOREVER);
if (ret != 0) {
printf("Failed to resubmit msgq polling: %d", ret);
}
#else
printk("LED %s\n", msg->data[0] == SET_LED ? "ON" : "OFF");
#endif
}
char *state_to_str(enum can_state state)
{
switch (state) {
case CAN_ERROR_ACTIVE:
case CAN_STATE_ERROR_ACTIVE:
return "error-active";
case CAN_ERROR_PASSIVE:
case CAN_STATE_ERROR_WARNING:
return "error-warning";
case CAN_STATE_ERROR_PASSIVE:
return "error-passive";
case CAN_BUS_OFF:
case CAN_STATE_BUS_OFF:
return "bus-off";
case CAN_STATE_STOPPED:
return "stopped";
default:
return "unknown";
}
@@ -123,11 +128,18 @@ void poll_state_thread(void *unused1, void *unused2, void *unused3)
{
struct can_bus_err_cnt err_cnt = {0, 0};
struct can_bus_err_cnt err_cnt_prev = {0, 0};
enum can_state state_prev = CAN_ERROR_ACTIVE;
enum can_state state_prev = CAN_STATE_ERROR_ACTIVE;
enum can_state state;
int err;
while (1) {
state = can_get_state(can_dev, &err_cnt);
err = can_get_state(can_dev, &state, &err_cnt);
if (err != 0) {
printf("Failed to get CAN controller state: %d", err);
k_sleep(K_MSEC(100));
continue;
}
if (err_cnt.tx_err_cnt != err_cnt_prev.tx_err_cnt ||
err_cnt.rx_err_cnt != err_cnt_prev.rx_err_cnt ||
state_prev != state) {
@@ -135,7 +147,7 @@ void poll_state_thread(void *unused1, void *unused2, void *unused3)
err_cnt_prev.tx_err_cnt = err_cnt.tx_err_cnt;
err_cnt_prev.rx_err_cnt = err_cnt.rx_err_cnt;
state_prev = state;
printk("state: %s\n"
printf("state: %s\n"
"rx error count: %d\n"
"tx error count: %d\n",
state_to_str(state),
@@ -148,48 +160,49 @@ void poll_state_thread(void *unused1, void *unused2, void *unused3)
void state_change_work_handler(struct k_work *work)
{
printk("State Change ISR\nstate: %s\n"
printf("State Change ISR\nstate: %s\n"
"rx error count: %d\n"
"tx error count: %d\n",
state_to_str(current_state),
current_err_cnt.rx_err_cnt, current_err_cnt.tx_err_cnt);
#ifndef CONFIG_CAN_AUTO_BUS_OFF_RECOVERY
if (current_state == CAN_BUS_OFF) {
printk("Recover from bus-off\n");
if (current_state == CAN_STATE_BUS_OFF) {
printf("Recover from bus-off\n");
if (can_recover(can_dev, K_MSEC(100) != 0)) {
printk("Recovery timed out\n");
if (can_recover(can_dev, K_MSEC(100)) != 0) {
printf("Recovery timed out\n");
}
}
#endif /* CONFIG_CAN_AUTO_BUS_OFF_RECOVERY */
}
void state_change_isr(enum can_state state, struct can_bus_err_cnt err_cnt)
void state_change_callback(const struct device *dev, enum can_state state,
struct can_bus_err_cnt err_cnt, void *user_data)
{
struct k_work *work = (struct k_work *)user_data;
ARG_UNUSED(dev);
current_state = state;
current_err_cnt = err_cnt;
k_work_submit(&state_change_work);
k_work_submit(work);
}
void main(void)
int main(void)
{
const struct zcan_filter change_led_filter = {
.id_type = CAN_STANDARD_IDENTIFIER,
.rtr = CAN_DATAFRAME,
const struct can_filter change_led_filter = {
.flags = CAN_FILTER_DATA,
.id = LED_MSG_ID,
.rtr_mask = 1,
.id_mask = CAN_STD_ID_MASK
.mask = CAN_STD_ID_MASK
};
struct zcan_frame change_led_frame = {
.id_type = CAN_STANDARD_IDENTIFIER,
.rtr = CAN_DATAFRAME,
struct can_frame change_led_frame = {
.flags = 0,
.id = LED_MSG_ID,
.dlc = 1
};
struct zcan_frame counter_frame = {
.id_type = CAN_EXTENDED_IDENTIFIER,
.rtr = CAN_DATAFRAME,
struct can_frame counter_frame = {
.flags = CAN_FRAME_IDE,
.id = COUNTER_MSG_ID,
.dlc = 2
};
@@ -198,54 +211,64 @@ void main(void)
k_tid_t rx_tid, get_state_tid;
int ret;
can_dev = device_get_binding(DT_CHOSEN_ZEPHYR_CAN_PRIMARY_LABEL);
if (!can_dev) {
printk("CAN: Device driver not found.\n");
return;
if (!device_is_ready(can_dev)) {
printf("CAN: Device %s not ready.\n", can_dev->name);
return 0;
}
#ifdef CONFIG_LOOPBACK_MODE
can_set_mode(can_dev, CAN_LOOPBACK_MODE);
#endif
#if DT_PHA_HAS_CELL(DT_ALIAS(led0), gpios, pin) && \
DT_NODE_HAS_PROP(DT_ALIAS(led0), gpios)
led_gpio_dev = device_get_binding(DT_GPIO_LABEL(DT_ALIAS(led0), gpios));
if (!led_gpio_dev) {
printk("LED: Device driver not found.\n");
return;
}
ret = gpio_pin_configure(led_gpio_dev,
DT_GPIO_PIN(DT_ALIAS(led0), gpios),
GPIO_OUTPUT_HIGH |
DT_GPIO_FLAGS(DT_ALIAS(led0), gpios));
if (ret < 0) {
printk("Error setting LED pin to output mode [%d]", ret);
ret = can_set_mode(can_dev, CAN_MODE_LOOPBACK);
if (ret != 0) {
printf("Error setting CAN mode [%d]", ret);
return 0;
}
#endif
ret = can_start(can_dev);
if (ret != 0) {
printf("Error starting CAN controller [%d]", ret);
return 0;
}
if (led.port != NULL) {
if (!device_is_ready(led.port)) {
printf("LED: Device %s not ready.\n",
led.port->name);
return 0;
}
ret = gpio_pin_configure_dt(&led, GPIO_OUTPUT_HIGH);
if (ret < 0) {
printf("Error setting LED pin to output mode [%d]",
ret);
led.port = NULL;
}
}
k_work_init(&state_change_work, state_change_work_handler);
k_work_poll_init(&change_led_work, change_led_work_handler);
ret = can_attach_workq(can_dev, &k_sys_work_q, &rx_work, change_led,
NULL, &change_led_filter);
if (ret == CAN_NO_FREE_FILTER) {
printk("Error, no filter available!\n");
return;
ret = can_add_rx_filter_msgq(can_dev, &change_led_msgq, &change_led_filter);
if (ret == -ENOSPC) {
printf("Error, no filter available!\n");
return 0;
}
printk("Change LED filter ID: %d\n", ret);
printf("Change LED filter ID: %d\n", ret);
ret = k_work_poll_submit(&change_led_work, change_led_events,
ARRAY_SIZE(change_led_events), K_FOREVER);
if (ret != 0) {
printf("Failed to submit msgq polling: %d", ret);
return 0;
}
rx_tid = k_thread_create(&rx_thread_data, rx_thread_stack,
K_THREAD_STACK_SIZEOF(rx_thread_stack),
rx_thread, NULL, NULL, NULL,
RX_THREAD_PRIORITY, 0, K_NO_WAIT);
if (!rx_tid) {
printk("ERROR spawning rx thread\n");
printf("ERROR spawning rx thread\n");
}
get_state_tid = k_thread_create(&poll_state_thread_data,
poll_state_stack,
K_THREAD_STACK_SIZEOF(poll_state_stack),
@@ -253,12 +276,12 @@ void main(void)
STATE_POLL_THREAD_PRIORITY, 0,
K_NO_WAIT);
if (!get_state_tid) {
printk("ERROR spawning poll_state_thread\n");
printf("ERROR spawning poll_state_thread\n");
}
can_register_state_change_isr(can_dev, state_change_isr);
can_set_state_change_callback(can_dev, state_change_callback, &state_change_work);
printk("Finished init.\n");
printf("Finished init.\n");
while (1) {
change_led_frame.data[0] = toggle++ & 0x01 ? SET_LED : RESET_LED;

View File

@@ -1,3 +1,4 @@
CONFIG_POLL=y
CONFIG_CAN=y
CONFIG_CAN_INIT_PRIORITY=80
CONFIG_CAN_MAX_FILTER=5
@@ -5,3 +6,9 @@ CONFIG_CAN_MAX_FILTER=5
CONFIG_SHELL=y
CONFIG_CAN_SHELL=y
CONFIG_DEVICE_SHELL=y
CONFIG_GPIO=y
CONFIG_STATS=y
CONFIG_STATS_NAMES=y
CONFIG_STATS_SHELL=y
CONFIG_CAN_STATS=y

View File

@@ -1 +0,0 @@
.pio

View File

@@ -1,33 +0,0 @@
.. Copyright 2019-present PlatformIO <contact@platformio.org>
Licensed 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.
How to build PlatformIO based project
=====================================
1. [Install PlatformIO Core](https://docs.platformio.org/page/core.html)
2. Download [development platform with examples](https://github.com/platformio/platform-ststm32/archive/develop.zip)
3. Extract ZIP archive
4. Change IP configuration in platform-ststm32/examples/zephyr-net-civetweb/zephyr/prj.conf file. Default server IPv4 address: `10.0.0.111`
5. Run these commands:
```shell
# Change directory to example
$ cd platform-ststm32/examples/zephyr-net-civetweb
# Build project
$ pio run
# Upload firmware
$ pio run --target upload
# Clean build files
$ pio run --target clean
```

View File

@@ -1,39 +0,0 @@
This directory is intended for project header files.
A header file is a file containing C declarations and macro definitions
to be shared between several project source files. You request the use of a
header file in your project source file (C, C++, etc) located in `src` folder
by including it, with the C preprocessing directive `#include'.
```src/main.c
#include "header.h"
int main (void)
{
...
}
```
Including a header file produces the same results as copying the header file
into each source file that needs it. Such copying would be time-consuming
and error-prone. With a header file, the related declarations appear
in only one place. If they need to be changed, they can be changed in one
place, and programs that include the header file will automatically use the
new version when next recompiled. The header file eliminates the labor of
finding and changing all the copies as well as the risk that a failure to
find one copy will result in inconsistencies within a program.
In C, the usual convention is to give header files names that end with `.h'.
It is most portable to use only letters, digits, dashes, and underscores in
header file names, and at most one dot.
Read more about using header files in official GCC documentation:
* Include Syntax
* Include Operation
* Once-Only Headers
* Computed Includes
https://gcc.gnu.org/onlinedocs/cpp/Header-Files.html

View File

@@ -1,29 +0,0 @@
/*
* Copyright (c) 2019 Antmicro Ltd
* Copyright (c) 2020 Alexander Kozhinov <AlexanderKozhinov@yandex.com>
*
* SPDX-License-Identifier: Apache-2.0
*/
static void log_access(const struct mg_connection *conn)
{
const struct mg_request_info *ri;
char src_addr[IP_ADDR_STR_LEN];
if (!conn || !conn->dom_ctx) {
return;
}
ri = &conn->request_info;
sockaddr_to_string(src_addr, sizeof(src_addr), &conn->client.rsa);
LOG_DBG("%s - \"%s %s%s%s HTTP/%s\" %d\n",
STR_LOG_ALLOC(src_addr),
STR_LOG_ALLOC(ri->request_method),
STR_LOG_ALLOC(ri->request_uri),
(ri->query_string == NULL) ? log_strdup("?") : log_strdup(""),
STR_LOG_ALLOC(ri->query_string),
STR_LOG_ALLOC(ri->http_version),
conn->status_code);
}

View File

@@ -1,23 +0,0 @@
/*
* Copyright (c) 2019 Antmicro Ltd
* Copyright (c) 2020 Alexander Kozhinov <AlexanderKozhinov@yandex.com>
*
* SPDX-License-Identifier: Apache-2.0
*/
#include <logging/log.h>
LOG_MODULE_REGISTER(mg_cry_internal_impl, LOG_LEVEL_DBG);
#include "helper.h"
static void mg_cry_internal_impl(const struct mg_connection *conn,
const char *func,
unsigned line,
const char *fmt,
va_list ap)
{
(void)conn;
LOG_ERR("%s @ %d in civetweb.c", STR_LOG_ALLOC(func), line);
vprintf(fmt, ap);
}

View File

@@ -1,15 +0,0 @@
/*
* Copyright (c) 2020 Alexander Kozhinov Mail: <AlexanderKozhinov@yandex.com>
*
* SPDX-License-Identifier: Apache-2.0
*/
#ifndef __HELPER__
#define __HELPER__
#include <logging/log.h>
#define STR_LOG_ALLOC(str) ((str == NULL) ? log_strdup("null") :\
log_strdup(str))
#endif /* __HELPER__ */

View File

@@ -1,72 +0,0 @@
/*
* Copyright (c) 2019 Antmicro Ltd
*
* SPDX-License-Identifier: Apache-2.0
*/
#include <zephyr.h>
#include <string.h>
#include <stdio.h>
#include <sys/types.h>
#include <net/socket.h>
#define pollfd zsock_pollfd
#define fcntl zsock_fcntl
#define POLLIN ZSOCK_POLLIN
#define POLLOUT ZSOCK_POLLOUT
#define addrinfo zsock_addrinfo
#define F_SETFD 2
#define FD_CLOEXEC 1
size_t strcspn(const char *s1, const char *s2);
size_t strspn(const char *s1, const char *s2);
int iscntrl(int c);
double atof(const char *str);
long long strtoll(const char *str, char **endptr, int base);
int sscanf(const char *s, const char *format, ...);
char *strerror(int err);
unsigned long long strtoull(const char *str, char **endptr, int base);
time_t time(time_t *t);
struct tm *gmtime(const time_t *ptime);
size_t strftime(char *dst, size_t dst_size, const char *fmt,
const struct tm *tm);
double difftime(time_t end, time_t beg);
struct tm *localtime(const time_t *timer);
int fileno(FILE *stream);
int ferror(FILE *stream);
int fclose(FILE *stream);
int fseeko(FILE *stream, off_t offset, int whence);
FILE *fopen(const char *filename, const char *mode);
char *fgets(char *str, int num, FILE *stream);
size_t fread(void *ptr, size_t size, size_t count, FILE *stream);
int remove(const char *filename);
int getsockname(int sock, struct sockaddr *addr, socklen_t *addrlen);
int poll(struct zsock_pollfd *fds, int nfds, int timeout);
int getnameinfo(const struct sockaddr *addr, socklen_t addrlen,
char *host, socklen_t hostlen,
char *serv, socklen_t servlen, int flags);
ssize_t send(int sock, const void *buf, size_t len, int flags);
ssize_t recv(int sock, void *buf, size_t max_len, int flags);
int socket(int family, int type, int proto);
int getaddrinfo(const char *host, const char *service,
const struct zsock_addrinfo *hints,
struct zsock_addrinfo **res);
void freeaddrinfo(struct zsock_addrinfo *ai);
int connect(int sock, const struct sockaddr *addr, socklen_t addrlen);
int getsockopt(int sock, int level, int optname,
void *optval, socklen_t *optlen);
int setsockopt(int sock, int level, int optname,
const void *optval, socklen_t optlen);
int listen(int sock, int backlog);
int accept(int sock, struct sockaddr *addr, socklen_t *addrlen);
int bind(int sock, const struct sockaddr *addr, socklen_t addrlen);

View File

@@ -1,46 +0,0 @@
This directory is intended for project specific (private) libraries.
PlatformIO will compile them to static libraries and link into executable file.
The source code of each library should be placed in a an own separate directory
("lib/your_library_name/[here are source files]").
For example, see a structure of the following two libraries `Foo` and `Bar`:
|--lib
| |
| |--Bar
| | |--docs
| | |--examples
| | |--src
| | |- Bar.c
| | |- Bar.h
| | |- library.json (optional, custom build options, etc) https://docs.platformio.org/page/librarymanager/config.html
| |
| |--Foo
| | |- Foo.c
| | |- Foo.h
| |
| |- README --> THIS FILE
|
|- platformio.ini
|--src
|- main.c
and a contents of `src/main.c`:
```
#include <Foo.h>
#include <Bar.h>
int main (void)
{
...
}
```
PlatformIO Library Dependency Finder will find automatically dependent
libraries scanning project source files.
More information about PlatformIO Library Dependency Finder
- https://docs.platformio.org/page/librarymanager/ldf.html

View File

@@ -1,13 +0,0 @@
; PlatformIO Project Configuration File
;
; Build options: build flags, source filter, extra scripting
; Upload options: custom port, speed and extra flags
; Library options: dependencies, extra library storages
;
; Please visit documentation for the other options and examples
; https://docs.platformio.org/page/projectconf.html
[env:nucleo_f767zi]
platform = ststm32
framework = zephyr
board = nucleo_f767zi

View File

@@ -1,245 +0,0 @@
/*
* Copyright (c) 2019 Antmicro Ltd
*
* SPDX-License-Identifier: Apache-2.0
*/
#include <logging/log.h>
LOG_MODULE_REGISTER(lib_extensions, LOG_LEVEL_DBG);
#include <zephyr.h>
#include <string.h>
#include <stdio.h>
#include <stdlib.h>
#include "libc_extensions.h"
#define FN_MISSING() LOG_DBG("[IMPLEMENTATION MISSING : %s]\n", __func__)
int iscntrl(int c)
{
/* All the characters placed before the space on the ASCII table
* and the 0x7F character (DEL) are control characters.
*/
return (int)(c < ' ' || c == 0x7F);
}
size_t strftime(char *dst, size_t dst_size,
const char *fmt,
const struct tm *tm)
{
FN_MISSING();
return 0;
}
double difftime(time_t end, time_t beg)
{
return end - beg;
}
struct __strerr_wrap {
int err;
const char *errstr;
};
/* Implementation suggested by @rakons in #16527 */
#define STRERR_DEFINE(e) {e, #e}
static const struct __strerr_wrap error_strings[] = {
STRERR_DEFINE(EILSEQ),
STRERR_DEFINE(EDOM),
STRERR_DEFINE(ERANGE),
STRERR_DEFINE(ENOTTY),
STRERR_DEFINE(EACCES),
STRERR_DEFINE(EPERM),
STRERR_DEFINE(ENOENT),
STRERR_DEFINE(ESRCH),
STRERR_DEFINE(EEXIST),
STRERR_DEFINE(ENOSPC),
STRERR_DEFINE(ENOMEM),
STRERR_DEFINE(EBUSY),
STRERR_DEFINE(EINTR),
STRERR_DEFINE(EAGAIN),
STRERR_DEFINE(ESPIPE),
STRERR_DEFINE(EXDEV),
STRERR_DEFINE(EROFS),
STRERR_DEFINE(ENOTEMPTY),
STRERR_DEFINE(ECONNRESET),
STRERR_DEFINE(ETIMEDOUT),
STRERR_DEFINE(ECONNREFUSED),
STRERR_DEFINE(EHOSTDOWN),
STRERR_DEFINE(EHOSTUNREACH),
STRERR_DEFINE(EADDRINUSE),
STRERR_DEFINE(EPIPE),
STRERR_DEFINE(EIO),
STRERR_DEFINE(ENXIO),
STRERR_DEFINE(ENOTBLK),
STRERR_DEFINE(ENODEV),
STRERR_DEFINE(ENOTDIR),
STRERR_DEFINE(EISDIR),
STRERR_DEFINE(ETXTBSY),
STRERR_DEFINE(ENOEXEC),
STRERR_DEFINE(EINVAL),
STRERR_DEFINE(E2BIG),
STRERR_DEFINE(ELOOP),
STRERR_DEFINE(ENAMETOOLONG),
STRERR_DEFINE(ENFILE),
STRERR_DEFINE(EMFILE),
STRERR_DEFINE(EBADF),
STRERR_DEFINE(ECHILD),
STRERR_DEFINE(EFAULT),
STRERR_DEFINE(EFBIG),
STRERR_DEFINE(EMLINK),
STRERR_DEFINE(ENOLCK),
STRERR_DEFINE(EDEADLK),
STRERR_DEFINE(ECANCELED),
STRERR_DEFINE(ENOSYS),
STRERR_DEFINE(ENOMSG),
STRERR_DEFINE(ENOSTR),
STRERR_DEFINE(ENODATA),
STRERR_DEFINE(ETIME),
STRERR_DEFINE(ENOSR),
STRERR_DEFINE(EPROTO),
STRERR_DEFINE(EBADMSG),
STRERR_DEFINE(ENOTSOCK),
STRERR_DEFINE(EDESTADDRREQ),
STRERR_DEFINE(EMSGSIZE),
STRERR_DEFINE(EPROTOTYPE),
STRERR_DEFINE(ENOPROTOOPT),
STRERR_DEFINE(EPROTONOSUPPORT),
STRERR_DEFINE(ESOCKTNOSUPPORT),
STRERR_DEFINE(ENOTSUP),
STRERR_DEFINE(EPFNOSUPPORT),
STRERR_DEFINE(EAFNOSUPPORT),
STRERR_DEFINE(EADDRNOTAVAIL),
STRERR_DEFINE(ENETDOWN),
STRERR_DEFINE(ENETUNREACH),
STRERR_DEFINE(ENETRESET),
STRERR_DEFINE(ECONNABORTED),
STRERR_DEFINE(ENOBUFS),
STRERR_DEFINE(EISCONN),
STRERR_DEFINE(ENOTCONN),
STRERR_DEFINE(ESHUTDOWN),
STRERR_DEFINE(EALREADY),
STRERR_DEFINE(EINPROGRESS),
};
static char *strerr_unknown = "UNKNOWN";
char *strerror(int err)
{
int i;
for (i = 0; i < ARRAY_SIZE(error_strings); ++i) {
if (error_strings[i].err == err) {
return (char *)error_strings[i].errstr;
}
}
return strerr_unknown;
}
int sscanf(const char *s, const char *format, ...)
{
FN_MISSING();
return 0;
}
double atof(const char *str)
{
/* XXX good enough for civetweb uses */
return (double)atoi(str);
}
long long strtoll(const char *str, char **endptr, int base)
{
/* XXX good enough for civetweb uses */
return (long long)strtol(str, endptr, base);
}
/*
* Most of the wrappers below are copies of the wrappers in net/sockets.h,
* but they are available only if CONFIG_NET_SOCKETS_POSIX_NAMES is enabled
* which is impossible here.
*/
int getsockname(int sock, struct sockaddr *addr,
socklen_t *addrlen)
{
return zsock_getsockname(sock, addr, addrlen);
}
int poll(struct zsock_pollfd *fds, int nfds, int timeout)
{
return zsock_poll(fds, nfds, timeout);
}
int getnameinfo(const struct sockaddr *addr, socklen_t addrlen,
char *host, socklen_t hostlen,
char *serv, socklen_t servlen, int flags)
{
return zsock_getnameinfo(addr, addrlen, host, hostlen,
serv, servlen, flags);
}
ssize_t send(int sock, const void *buf, size_t len, int flags)
{
return zsock_send(sock, buf, len, flags);
}
ssize_t recv(int sock, void *buf, size_t max_len, int flags)
{
return zsock_recv(sock, buf, max_len, flags);
}
int socket(int family, int type, int proto)
{
return zsock_socket(family, type, proto);
}
int getaddrinfo(const char *host, const char *service,
const struct zsock_addrinfo *hints,
struct zsock_addrinfo **res)
{
return zsock_getaddrinfo(host, service, hints, res);
}
void freeaddrinfo(struct zsock_addrinfo *ai)
{
zsock_freeaddrinfo(ai);
}
int connect(int sock, const struct sockaddr *addr,
socklen_t addrlen)
{
return zsock_connect(sock, addr, addrlen);
}
int getsockopt(int sock, int level, int optname,
void *optval, socklen_t *optlen)
{
return zsock_getsockopt(sock, level, optname, optval, optlen);
}
int setsockopt(int sock, int level, int optname,
const void *optval, socklen_t optlen)
{
return zsock_setsockopt(sock, level, optname, optval, optlen);
}
int listen(int sock, int backlog)
{
return zsock_listen(sock, backlog);
}
int bind(int sock, const struct sockaddr *addr, socklen_t addrlen)
{
return zsock_bind(sock, addr, addrlen);
}
int accept(int sock, struct sockaddr *addr, socklen_t *addrlen)
{
return zsock_accept(sock, addr, addrlen);
}

View File

@@ -1,187 +0,0 @@
/*
* Copyright (c) 2019 Antmicro Ltd
*
* SPDX-License-Identifier: Apache-2.0
*/
#include <zephyr.h>
#include <posix/pthread.h>
#include <data/json.h>
#include "civetweb.h"
#define HTTP_PORT 8080
#define HTTPS_PORT 4443
#define CIVETWEB_MAIN_THREAD_STACK_SIZE CONFIG_MAIN_STACK_SIZE
/* Use samllest possible value of 1024 (see the line 18619 of civetweb.c) */
#define MAX_REQUEST_SIZE_BYTES 1024
K_THREAD_STACK_DEFINE(civetweb_stack, CIVETWEB_MAIN_THREAD_STACK_SIZE);
struct civetweb_info {
const char *version;
const char *os;
uint32_t features;
const char *feature_list;
const char *build;
const char *compiler;
const char *data_model;
};
#define FIELD(struct_, member_, type_) { \
.field_name = #member_, \
.field_name_len = sizeof(#member_) - 1, \
.offset = offsetof(struct_, member_), \
.type = type_ \
}
void send_ok(struct mg_connection *conn)
{
mg_printf(conn,
"HTTP/1.1 200 OK\r\n"
"Content-Type: text/html\r\n"
"Connection: close\r\n\r\n");
}
int hello_world_handler(struct mg_connection *conn, void *cbdata)
{
send_ok(conn);
mg_printf(conn, "<html><body>");
mg_printf(conn, "<h3>Hello World from Zephyr!</h3>");
mg_printf(conn, "See also:\n");
mg_printf(conn, "<ul>\n");
mg_printf(conn, "<li><a href=/info>system info</a></li>\n");
mg_printf(conn, "<li><a href=/history>cookie demo</a></li>\n");
mg_printf(conn, "</ul>\n");
mg_printf(conn, "</body></html>\n");
return 200;
}
int system_info_handler(struct mg_connection *conn, void *cbdata)
{
static const struct json_obj_descr descr[] = {
FIELD(struct civetweb_info, version, JSON_TOK_STRING),
FIELD(struct civetweb_info, os, JSON_TOK_STRING),
FIELD(struct civetweb_info, feature_list, JSON_TOK_STRING),
FIELD(struct civetweb_info, build, JSON_TOK_STRING),
FIELD(struct civetweb_info, compiler, JSON_TOK_STRING),
FIELD(struct civetweb_info, data_model, JSON_TOK_STRING),
};
struct civetweb_info info = {};
char info_str[1024] = {};
int ret;
int size;
size = mg_get_system_info(info_str, sizeof(info_str));
ret = json_obj_parse(info_str, size, descr, ARRAY_SIZE(descr), &info);
send_ok(conn);
if (ret < 0) {
mg_printf(conn, "Could not retrieve: %d\n", ret);
return 500;
}
mg_printf(conn, "<html><body>");
mg_printf(conn, "<h3>Server info</h3>");
mg_printf(conn, "<ul>\n");
mg_printf(conn, "<li>host os - %s</li>\n", info.os);
mg_printf(conn, "<li>server - civetweb %s</li>\n", info.version);
mg_printf(conn, "<li>compiler - %s</li>\n", info.compiler);
mg_printf(conn, "<li>board - %s</li>\n", CONFIG_BOARD);
mg_printf(conn, "</ul>\n");
mg_printf(conn, "</body></html>\n");
return 200;
}
int history_handler(struct mg_connection *conn, void *cbdata)
{
const struct mg_request_info *req_info = mg_get_request_info(conn);
const char *cookie = mg_get_header(conn, "Cookie");
char history_str[64];
mg_get_cookie(cookie, "history", history_str, sizeof(history_str));
mg_printf(conn, "HTTP/1.1 200 OK\r\n");
mg_printf(conn, "Connection: close\r\n");
mg_printf(conn, "Set-Cookie: history='%s'\r\n", req_info->local_uri);
mg_printf(conn, "Content-Type: text/html\r\n\r\n");
mg_printf(conn, "<html><body>");
mg_printf(conn, "<h3>Your URI is: %s<h3>\n", req_info->local_uri);
if (history_str[0] == 0) {
mg_printf(conn, "<h5>This is your first visit.</h5>\n");
} else {
mg_printf(conn, "<h5>your last /history visit was: %s</h5>\n",
history_str);
}
mg_printf(conn, "Some cookie-saving links to try:\n");
mg_printf(conn, "<ul>\n");
mg_printf(conn, "<li><a href=/history/first>first</a></li>\n");
mg_printf(conn, "<li><a href=/history/second>second</a></li>\n");
mg_printf(conn, "<li><a href=/history/third>third</a></li>\n");
mg_printf(conn, "<li><a href=/history/fourth>fourth</a></li>\n");
mg_printf(conn, "<li><a href=/history/fifth>fifth</a></li>\n");
mg_printf(conn, "</ul>\n");
mg_printf(conn, "</body></html>\n");
return 200;
}
void *main_pthread(void *arg)
{
static const char * const options[] = {
"listening_ports",
STRINGIFY(HTTP_PORT),
"num_threads",
"1",
"max_request_size",
STRINGIFY(MAX_REQUEST_SIZE_BYTES),
NULL
};
struct mg_callbacks callbacks;
struct mg_context *ctx;
(void)arg;
memset(&callbacks, 0, sizeof(callbacks));
ctx = mg_start(&callbacks, 0, (const char **)options);
if (ctx == NULL) {
printf("Unable to start the server.");
return 0;
}
mg_set_request_handler(ctx, "/$", hello_world_handler, 0);
mg_set_request_handler(ctx, "/info$", system_info_handler, 0);
mg_set_request_handler(ctx, "/history", history_handler, 0);
return 0;
}
void main(void)
{
pthread_attr_t civetweb_attr;
pthread_t civetweb_thread;
(void)pthread_attr_init(&civetweb_attr);
(void)pthread_attr_setstack(&civetweb_attr, &civetweb_stack,
CIVETWEB_MAIN_THREAD_STACK_SIZE);
(void)pthread_create(&civetweb_thread, &civetweb_attr,
&main_pthread, 0);
}

View File

@@ -1,11 +0,0 @@
This directory is intended for PIO Unit Testing and project tests.
Unit Testing is a software testing method by which individual units of
source code, sets of one or more MCU program modules together with associated
control data, usage procedures, and operating procedures, are tested to
determine whether they are fit for use. Unit testing finds problems early
in the development cycle.
More information about PIO Unit Testing:
- https://docs.platformio.org/page/plus/unit-testing.html

View File

@@ -1,15 +0,0 @@
# SPDX-License-Identifier: Apache-2.0
cmake_minimum_required(VERSION 3.13.1)
set (CONF_FILE "prj.conf")
include($ENV{ZEPHYR_BASE}/cmake/app/boilerplate.cmake NO_POLICY_SCOPE)
project(civetweb-server)
FILE(GLOB app_sources ../src/*.c)
target_sources(app PRIVATE ${app_sources})
zephyr_include_directories(../include)
set(gen_dir ${ZEPHYR_BINARY_DIR}/include/generated/)

View File

@@ -1,36 +0,0 @@
# General config
CONFIG_CIVETWEB=y
CONFIG_JSON_LIBRARY=y
# pthreads
CONFIG_POSIX_API=y
CONFIG_PTHREAD_IPC=y
CONFIG_POSIX_MQUEUE=y
# networking
CONFIG_NETWORKING=y
CONFIG_NET_IPV4=y
# CONFIG_NET_IPV6 is not set
CONFIG_NET_TCP=y
CONFIG_NET_SOCKETS=y
CONFIG_MINIMAL_LIBC_MALLOC_ARENA_SIZE=16384
CONFIG_NET_TX_STACK_SIZE=2048
CONFIG_NET_RX_STACK_SIZE=2048
CONFIG_ISR_STACK_SIZE=2048
CONFIG_MAIN_STACK_SIZE=2048
CONFIG_IDLE_STACK_SIZE=1024
CONFIG_DNS_RESOLVER=y
CONFIG_NET_CONFIG_SETTINGS=y
CONFIG_NET_CONFIG_MY_IPV4_ADDR="192.0.2.1"
CONFIG_NET_CONFIG_MY_IPV4_NETMASK="255.255.255.0"
CONFIG_NET_CONFIG_MY_IPV4_GW="192.0.2.2"
CONFIG_NET_CONFIG_PEER_IPV4_ADDR="192.0.2.2"
# logging
CONFIG_NET_LOG=y
# Do not include mbedtls via this option as civetweb does not
# work properly with mbedtls.
CONFIG_NET_TCP_ISN_RFC6528=n

View File

@@ -4,13 +4,13 @@
* SPDX-License-Identifier: Apache-2.0
*/
#include <logging/log.h>
#include <zephyr/logging/log.h>
LOG_MODULE_REGISTER(net_http_client_sample, LOG_LEVEL_DBG);
#include <net/net_ip.h>
#include <net/socket.h>
#include <net/tls_credentials.h>
#include <net/http_client.h>
#include <zephyr/net/net_ip.h>
#include <zephyr/net/socket.h>
#include <zephyr/net/tls_credentials.h>
#include <zephyr/net/http/client.h>
#include "ca_certificate.h"
@@ -356,7 +356,7 @@ static int run_queries(void)
return ret;
}
void main(void)
int main(void)
{
int iterations = CONFIG_NET_SAMPLE_SEND_ITERATIONS;
int i = 0;
@@ -383,4 +383,5 @@ void main(void)
}
exit(0);
return 0;
}

View File

@@ -4,66 +4,52 @@
*
* SPDX-License-Identifier: Apache-2.0
*/
#include <zephyr.h>
#include <device.h>
#include <drivers/gpio.h>
#include <zephyr/kernel.h>
#include <zephyr/device.h>
#include <zephyr/drivers/gpio.h>
#include <usb/usb_device.h>
#include <usb/class/usb_hid.h>
#include <zephyr/usb/usb_device.h>
#include <zephyr/usb/class/usb_hid.h>
#define LOG_LEVEL LOG_LEVEL_DBG
LOG_MODULE_REGISTER(main);
/*
* Devicetree node identifiers for the buttons and LED this sample
* supports.
*/
#define SW0_NODE DT_ALIAS(sw0)
#if DT_NODE_HAS_STATUS(SW0_NODE, okay)
#define PORT0 DT_GPIO_LABEL(SW0_NODE, gpios)
#define PIN0 DT_GPIO_PIN(SW0_NODE, gpios)
#define PIN0_FLAGS DT_GPIO_FLAGS(SW0_NODE, gpios)
#else
#error "Unsupported board: sw0 devicetree alias is not defined"
#define PORT0 ""
#define PIN0 0
#define PIN0_FLAGS 0
#endif
#define SW1_NODE DT_ALIAS(sw1)
#if DT_NODE_HAS_STATUS(SW1_NODE, okay)
#define PORT1 DT_GPIO_LABEL(SW1_NODE, gpios)
#define PIN1 DT_GPIO_PIN(SW1_NODE, gpios)
#define PIN1_FLAGS DT_GPIO_FLAGS(SW1_NODE, gpios)
#endif
#define SW2_NODE DT_ALIAS(sw2)
#if DT_NODE_HAS_STATUS(SW2_NODE, okay)
#define PORT2 DT_GPIO_LABEL(SW2_NODE, gpios)
#define PIN2 DT_GPIO_PIN(SW2_NODE, gpios)
#define PIN2_FLAGS DT_GPIO_FLAGS(SW2_NODE, gpios)
#endif
#define SW3_NODE DT_ALIAS(sw3)
#if DT_NODE_HAS_STATUS(SW3_NODE, okay)
#define PORT3 DT_GPIO_LABEL(SW3_NODE, gpios)
#define PIN3 DT_GPIO_PIN(SW3_NODE, gpios)
#define PIN3_FLAGS DT_GPIO_FLAGS(SW3_NODE, gpios)
#endif
#define LED0_NODE DT_ALIAS(led0)
#if DT_NODE_HAS_STATUS(LED0_NODE, okay)
#define LED_PORT DT_GPIO_LABEL(LED0_NODE, gpios)
#define LED DT_GPIO_PIN(LED0_NODE, gpios)
#define LED_FLAGS DT_GPIO_FLAGS(LED0_NODE, gpios)
#else
#error "Unsupported board: led0 devicetree alias is not defined"
#define LED_PORT ""
#define LED 0
#define LED_FLAGS 0
/*
* Button sw0 and LED led0 are required.
*/
#if !DT_NODE_EXISTS(SW0_NODE)
#error "Unsupported board: sw0 devicetree alias is not defined"
#endif
#if !DT_NODE_EXISTS(LED0_NODE)
#error "Unsupported board: led0 devicetree alias is not defined"
#endif
/*
* Helper macro for initializing a gpio_dt_spec from the devicetree
* with fallback values when the nodes are missing.
*/
#define GPIO_SPEC(node_id) GPIO_DT_SPEC_GET_OR(node_id, gpios, {0})
/*
* Create gpio_dt_spec structures from the devicetree.
*/
static const struct gpio_dt_spec sw0 = GPIO_SPEC(SW0_NODE),
sw1 = GPIO_SPEC(SW1_NODE),
sw2 = GPIO_SPEC(SW2_NODE),
sw3 = GPIO_SPEC(SW3_NODE),
led0 = GPIO_SPEC(LED0_NODE);
static const uint8_t hid_report_desc[] = HID_MOUSE_REPORT_DESC(2);
static uint8_t def_val[4];
@@ -80,8 +66,6 @@ static enum usb_dc_status_code usb_status;
#define MOUSE_BTN_RIGHT BIT(1)
#define MOUSE_BTN_MIDDLE BIT(2)
static void status_cb(enum usb_dc_status_code status, const uint8_t *param)
{
usb_status = status;
@@ -100,10 +84,10 @@ static void left_button(const struct device *gpio, struct gpio_callback *cb,
}
}
ret = gpio_pin_get(gpio, PIN0);
ret = gpio_pin_get(gpio, sw0.pin);
if (ret < 0) {
LOG_ERR("Failed to get the state of pin %u, error: %d",
PIN0, ret);
LOG_ERR("Failed to get the state of port %s pin %u, error: %d",
gpio->name, sw0.pin, ret);
return;
}
@@ -119,7 +103,6 @@ static void left_button(const struct device *gpio, struct gpio_callback *cb,
}
}
#if DT_NODE_HAS_STATUS(SW1_NODE, okay)
static void right_button(const struct device *gpio, struct gpio_callback *cb,
uint32_t pins)
{
@@ -133,10 +116,10 @@ static void right_button(const struct device *gpio, struct gpio_callback *cb,
}
}
ret = gpio_pin_get(gpio, PIN1);
ret = gpio_pin_get(gpio, sw1.pin);
if (ret < 0) {
LOG_ERR("Failed to get the state of pin %u, error: %d",
PIN1, ret);
LOG_ERR("Failed to get the state of port %s pin %u, error: %d",
gpio->name, sw1.pin, ret);
return;
}
@@ -151,19 +134,17 @@ static void right_button(const struct device *gpio, struct gpio_callback *cb,
k_sem_give(&sem);
}
}
#endif
#if DT_NODE_HAS_STATUS(SW2_NODE, okay)
static void x_move(const struct device *gpio, struct gpio_callback *cb,
uint32_t pins)
{
int ret;
uint8_t state = status[MOUSE_X_REPORT_POS];
ret = gpio_pin_get(gpio, PIN2);
ret = gpio_pin_get(gpio, sw2.pin);
if (ret < 0) {
LOG_ERR("Failed to get the state of pin %u, error: %d",
PIN2, ret);
LOG_ERR("Failed to get the state of port %s pin %u, error: %d",
gpio->name, sw2.pin, ret);
return;
}
@@ -176,19 +157,17 @@ static void x_move(const struct device *gpio, struct gpio_callback *cb,
k_sem_give(&sem);
}
}
#endif
#if DT_NODE_HAS_STATUS(SW3_NODE, okay)
static void y_move(const struct device *gpio, struct gpio_callback *cb,
uint32_t pins)
{
int ret;
uint8_t state = status[MOUSE_Y_REPORT_POS];
ret = gpio_pin_get(gpio, PIN3);
ret = gpio_pin_get(gpio, sw3.pin);
if (ret < 0) {
LOG_ERR("Failed to get the state of pin %u, error: %d",
PIN3, ret);
LOG_ERR("Failed to get the state of port %s pin %u, error: %d",
gpio->name, sw3.pin, ret);
return;
}
@@ -201,30 +180,36 @@ static void y_move(const struct device *gpio, struct gpio_callback *cb,
k_sem_give(&sem);
}
}
#endif
int callbacks_configure(const struct device *gpio, uint32_t pin, int flags,
int callbacks_configure(const struct gpio_dt_spec *spec,
gpio_callback_handler_t handler,
struct gpio_callback *callback, uint8_t *val)
{
const struct device *gpio = spec->port;
gpio_pin_t pin = spec->pin;
int ret;
if (!gpio) {
LOG_ERR("Could not find PORT");
return -ENXIO;
if (gpio == NULL) {
/* Optional GPIO is missing. */
return 0;
}
ret = gpio_pin_configure(gpio, pin, GPIO_INPUT | flags);
if (!device_is_ready(gpio)) {
LOG_ERR("GPIO port %s is not ready", gpio->name);
return -ENODEV;
}
ret = gpio_pin_configure_dt(spec, GPIO_INPUT);
if (ret < 0) {
LOG_ERR("Failed to configure pin %u, error: %d",
pin, ret);
LOG_ERR("Failed to configure port %s pin %u, error: %d",
gpio->name, pin, ret);
return ret;
}
ret = gpio_pin_get(gpio, pin);
if (ret < 0) {
LOG_ERR("Failed to get the state of pin %u, error: %d",
pin, ret);
LOG_ERR("Failed to get the state of port %s pin %u, error: %d",
gpio->name, pin, ret);
return ret;
}
@@ -233,74 +218,67 @@ int callbacks_configure(const struct device *gpio, uint32_t pin, int flags,
gpio_init_callback(callback, handler, BIT(pin));
ret = gpio_add_callback(gpio, callback);
if (ret < 0) {
LOG_ERR("Failed to add the callback for pin %u, error: %d",
pin, ret);
LOG_ERR("Failed to add the callback for port %s pin %u, "
"error: %d",
gpio->name, pin, ret);
return ret;
}
ret = gpio_pin_interrupt_configure(gpio, pin, GPIO_INT_EDGE_BOTH);
ret = gpio_pin_interrupt_configure_dt(spec, GPIO_INT_EDGE_BOTH);
if (ret < 0) {
LOG_ERR("Failed to configure interrupt for pin %u, error: %d",
pin, ret);
LOG_ERR("Failed to configure interrupt for port %s pin %u, "
"error: %d",
gpio->name, pin, ret);
return ret;
}
return 0;
}
void main(void)
int main(void)
{
int ret;
uint8_t report[4] = { 0x00 };
const struct device *led_dev, *hid_dev;
const struct device *hid_dev;
led_dev = device_get_binding(LED_PORT);
if (led_dev == NULL) {
LOG_ERR("Cannot get LED");
return;
if (!device_is_ready(led0.port)) {
LOG_ERR("LED device %s is not ready", led0.port->name);
return 0;
}
hid_dev = device_get_binding("HID_0");
if (hid_dev == NULL) {
LOG_ERR("Cannot get USB HID Device");
return;
return 0;
}
ret = gpio_pin_configure(led_dev, LED, GPIO_OUTPUT | LED_FLAGS);
ret = gpio_pin_configure_dt(&led0, GPIO_OUTPUT);
if (ret < 0) {
LOG_ERR("Failed to configure the LED pin, error: %d", ret);
return;
return 0;
}
if (callbacks_configure(device_get_binding(PORT0), PIN0, PIN0_FLAGS,
&left_button, &callback[0], &def_val[0])) {
if (callbacks_configure(&sw0, &left_button, &callback[0],
&def_val[0])) {
LOG_ERR("Failed configuring left button callback.");
return;
return 0;
}
#if DT_NODE_HAS_STATUS(SW1_NODE, okay)
if (callbacks_configure(device_get_binding(PORT1), PIN1, PIN1_FLAGS,
&right_button, &callback[1], &def_val[1])) {
if (callbacks_configure(&sw1, &right_button, &callback[1],
&def_val[1])) {
LOG_ERR("Failed configuring right button callback.");
return;
return 0;
}
#endif
#if DT_NODE_HAS_STATUS(SW2_NODE, okay)
if (callbacks_configure(device_get_binding(PORT2), PIN2, PIN2_FLAGS,
&x_move, &callback[2], &def_val[2])) {
if (callbacks_configure(&sw2, &x_move, &callback[2], &def_val[2])) {
LOG_ERR("Failed configuring X axis movement callback.");
return;
return 0;
}
#endif
#if DT_NODE_HAS_STATUS(SW3_NODE, okay)
if (callbacks_configure(device_get_binding(PORT3), PIN3, PIN3_FLAGS,
&y_move, &callback[3], &def_val[3])) {
if (callbacks_configure(&sw3, &y_move, &callback[3], &def_val[3])) {
LOG_ERR("Failed configuring Y axis movement callback.");
return;
return 0;
}
#endif
usb_hid_register_device(hid_dev,
hid_report_desc, sizeof(hid_report_desc),
@@ -311,7 +289,7 @@ void main(void)
ret = usb_enable(status_cb);
if (ret != 0) {
LOG_ERR("Failed to enable USB");
return;
return 0;
}
while (true) {
@@ -328,9 +306,10 @@ void main(void)
}
/* Toggle LED on sent report */
ret = gpio_pin_toggle(led_dev, LED);
ret = gpio_pin_toggle(led0.port, led0.pin);
if (ret < 0) {
LOG_ERR("Failed to toggle the LED pin, error: %d", ret);
}
}
return 0;
}

View File

@@ -1,6 +1,8 @@
CONFIG_USB_DEVICE_STACK=y
CONFIG_USB_DEVICE_HID=y
CONFIG_USB_DEVICE_PRODUCT="Zephyr HID mouse sample"
CONFIG_USB_DEVICE_PID=0x0007
CONFIG_USB_DEVICE_INITIALIZE_AT_BOOT=n
CONFIG_LOG=y
CONFIG_USB_DRIVER_LOG_LEVEL_ERR=y

View File

@@ -298,7 +298,7 @@
"type": "framework",
"optional": true,
"owner": "platformio",
"version": "~2.20701.0"
"version": "~2.30400.0"
},
"tool-stm32duino": {
"type": "uploader",

View File

@@ -12,15 +12,16 @@
# See the License for the specific language governing permissions and
# limitations under the License.
import json
import os
import sys
import subprocess
from platformio.managers.platform import PlatformBase
IS_WINDOWS = sys.platform.startswith("win")
class Ststm32Platform(PlatformBase):
def configure_default_packages(self, variables, targets):
@@ -89,7 +90,7 @@ class Ststm32Platform(PlatformBase):
for p in self.packages:
if p in ("tool-cmake", "tool-dtc", "tool-ninja"):
self.packages[p]["optional"] = False
self.packages["toolchain-gccarmnoneeabi"]["version"] = "~1.80201.0"
self.packages["toolchain-gccarmnoneeabi"]["version"] = "~1.120301.0"
if not IS_WINDOWS:
self.packages["tool-gperf"]["optional"] = False
@@ -110,6 +111,24 @@ class Ststm32Platform(PlatformBase):
return PlatformBase.configure_default_packages(self, variables,
targets)
def install_package(self, name, *args, **kwargs):
pkg = super().install_package(name, *args, **kwargs)
if name != "framework-zephyr":
return pkg
if not os.path.isfile(os.path.join(pkg.path, "_pio", "state.json")):
self.pm.log.info("Installing Zephyr project dependencies...")
try:
subprocess.run([
os.path.normpath(sys.executable),
os.path.join(pkg.path, "scripts", "platformio", "install-deps.py"),
"--platform", self.name
])
except subprocess.CalledProcessError:
self.pm.log.info("Failed to install Zephyr dependencies!")
return pkg
def get_boards(self, id_=None):
result = PlatformBase.get_boards(self, id_)
if not result: