Merge pull request #491 from wolfSSL/devin/1740502756-add-freertos-fullstack-example

Add FreeRTOS + wolfIP + wolfSSL HTTPS example
pull/495/head
Reda Chouk 2025-03-03 16:58:43 +01:00 committed by GitHub
commit dc36abdfd4
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
14 changed files with 1020 additions and 0 deletions

View File

@ -0,0 +1,33 @@
# FreeRTOS directories managed by setup script
freertos/FreeRTOS/
freertos/FreeRTOS-Kernel/
# Certificate files
certs/
# Build directory
build/
# Object files
*.o
*.ko
*.obj
*.elf
# Libraries
*.lib
*.a
*.la
*.lo
# Executables
*.exe
*.out
*.app
*.i*86
*.x86_64
*.hex
# Debug files
*.dSYM/

View File

@ -0,0 +1,61 @@
cmake_minimum_required(VERSION 3.13)
project(freertos_wolfssl_demo C)
# Set C standard
set(CMAKE_C_STANDARD 11)
set(CMAKE_C_STANDARD_REQUIRED ON)
# wolfSSL configuration
add_definitions(-DWOLFSSL_USER_SETTINGS)
add_definitions(-DWOLFSSL_WOLFIP)
# FreeRTOS Kernel source files for POSIX port
set(FREERTOS_PORT_DIR ${CMAKE_CURRENT_SOURCE_DIR}/freertos/FreeRTOS-Kernel/portable/ThirdParty/GCC/Posix)
set(FREERTOS_HEAP_DIR ${CMAKE_CURRENT_SOURCE_DIR}/freertos/FreeRTOS-Kernel/portable/MemMang)
# Include directories
include_directories(
${CMAKE_CURRENT_SOURCE_DIR}/include
${CMAKE_CURRENT_SOURCE_DIR}/freertos/FreeRTOS-Kernel/include
${FREERTOS_PORT_DIR}
${CMAKE_CURRENT_SOURCE_DIR}/../../../wolfip/src
${CMAKE_CURRENT_SOURCE_DIR}/../../../wolfip
${CMAKE_CURRENT_SOURCE_DIR}/../../../wolfip/src/http
${CMAKE_CURRENT_SOURCE_DIR}/../../../wolfip/src/port
${CMAKE_CURRENT_SOURCE_DIR}/../../../wolfssl
${CMAKE_CURRENT_SOURCE_DIR}/../../../wolfssl/include
)
# FreeRTOS source files
set(FREERTOS_SOURCES
${CMAKE_CURRENT_SOURCE_DIR}/freertos/FreeRTOS-Kernel/tasks.c
${CMAKE_CURRENT_SOURCE_DIR}/freertos/FreeRTOS-Kernel/queue.c
${CMAKE_CURRENT_SOURCE_DIR}/freertos/FreeRTOS-Kernel/list.c
${CMAKE_CURRENT_SOURCE_DIR}/freertos/FreeRTOS-Kernel/timers.c
${CMAKE_CURRENT_SOURCE_DIR}/freertos/FreeRTOS-Kernel/event_groups.c
${CMAKE_CURRENT_SOURCE_DIR}/freertos/FreeRTOS-Kernel/stream_buffer.c
${FREERTOS_PORT_DIR}/port.c
${FREERTOS_HEAP_DIR}/heap_3.c
${CMAKE_CURRENT_SOURCE_DIR}/freertos/utils/utils.c
)
# Add wolfIP library
add_library(wolfip STATIC
${CMAKE_CURRENT_SOURCE_DIR}/../../../wolfip/src/wolfip.c
${CMAKE_CURRENT_SOURCE_DIR}/../../../wolfip/src/http/httpd.c
${CMAKE_CURRENT_SOURCE_DIR}/../../../wolfip/src/port/wolfssl_io.c
)
# Add the main application
add_executable(freertos_sim
${FREERTOS_SOURCES}
src/main.c
src/wolfip_freertos.c
src/https_server.c
)
target_link_libraries(freertos_sim
pthread
wolfip
wolfssl
)

View File

@ -0,0 +1,85 @@
# FreeRTOS + wolfIP + wolfSSL HTTPS Example
This example demonstrates a full-stack embedded networking application using FreeRTOS, wolfIP, and wolfSSL. It implements a secure HTTPS server running on a simulated FreeRTOS environment with TLS 1.3 support.
## Stack Components
The example integrates the following components:
- FreeRTOS (POSIX port) - Real-time operating system
- wolfIP - TCP/IP networking stack
- wolfSSL - TLS 1.3 security layer
- TAP interface - Virtual network interface
## Building and Running
### Prerequisites
- wolfSSL library
- wolfIP library
- CMake (>= 3.13)
- GCC
- Linux with TUN/TAP support
### Setup
1. Run the setup script to clone FreeRTOS repositories:
```bash
./setup.sh
```
2. Configure the network interface (requires root):
```bash
sudo ./setup_network.sh
```
3. Build the example:
```bash
cd build && cmake .. && make
```
4. Run the example (requires root):
```bash
sudo ./freertos_sim
```
### Testing
Test the HTTPS server using curl:
```bash
sudo ./test_https.sh
```
Or manually:
```bash
curl -v --cacert /path/to/wolfssl/certs/ca-cert.pem \
--tlsv1.3 --insecure https://10.10.0.10:443/
```
## Software Bill of Materials (SBOM)
| Component | Version | License | Source |
|-----------|---------|----------|---------|
| FreeRTOS | Latest | MIT | https://github.com/FreeRTOS/FreeRTOS |
| FreeRTOS-Kernel | Latest | MIT | https://github.com/FreeRTOS/FreeRTOS-Kernel |
| wolfSSL | Latest | GPLv2 | https://github.com/wolfSSL/wolfssl |
| wolfIP | Latest | GPLv2 | https://github.com/wolfSSL/wolfip |
## Features
- TLS 1.3 support with wolfSSL
- Zero dynamic memory allocation networking with wolfIP
- Virtual networking through TAP interface
- UDP echo server for testing
- HTTPS server with demo page
- FreeRTOS task management and scheduling
## Network Configuration
- TAP Interface: 10.10.0.1/24 (Host)
- FreeRTOS IP: 10.10.0.10/24
- Default Gateway: 10.10.0.1
## Security Features
- TLS 1.3 with modern cipher suites
- Certificate-based authentication
- Support for various cryptographic algorithms:
- AES (ECB, CBC, GCM)
- ChaCha20-Poly1305
- Curve25519
- ED25519
- SHA-2 and SHA-3 family

View File

@ -0,0 +1,50 @@
#include <errno.h>
#include <pthread.h>
#include <signal.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
typedef struct event_t {
pthread_mutex_t mutex;
pthread_cond_t cond;
int value;
} event_t;
event_t *event_create(void) {
event_t *event = malloc(sizeof(event_t));
if (event != NULL) {
pthread_mutex_init(&event->mutex, NULL);
pthread_cond_init(&event->cond, NULL);
event->value = 0;
}
return event;
}
void event_delete(event_t *event) {
if (event != NULL) {
pthread_mutex_destroy(&event->mutex);
pthread_cond_destroy(&event->cond);
free(event);
}
}
void event_signal(event_t *event) {
if (event != NULL) {
pthread_mutex_lock(&event->mutex);
event->value = 1;
pthread_cond_signal(&event->cond);
pthread_mutex_unlock(&event->mutex);
}
}
void event_wait(event_t *event) {
if (event != NULL) {
pthread_mutex_lock(&event->mutex);
while (event->value == 0) {
pthread_cond_wait(&event->cond, &event->mutex);
}
event->value = 0;
pthread_mutex_unlock(&event->mutex);
}
}

View File

@ -0,0 +1,102 @@
/* FreeRTOSConfig.h
*
* Copyright (C) 2006-2024 wolfSSL Inc.
*
* This file is part of wolfSSL.
*
* wolfSSL is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* wolfSSL is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#ifndef FREERTOS_CONFIG_H
#define FREERTOS_CONFIG_H
/* Scheduler Related */
#define configUSE_PREEMPTION 1
#define configUSE_PORT_OPTIMISED_TASK_SELECTION 0
#define configUSE_TICKLESS_IDLE 0
#define configCPU_CLOCK_HZ ( ( unsigned long ) 60000000 )
#define configTICK_RATE_HZ ( ( TickType_t ) 1000 )
#define configMAX_PRIORITIES 5
#define configMINIMAL_STACK_SIZE ( ( unsigned short ) 4096 )
#define configMAX_TASK_NAME_LEN 16
#define configUSE_16_BIT_TICKS 0
#define configIDLE_SHOULD_YIELD 1
#define configUSE_TASK_NOTIFICATIONS 1
#define configTASK_NOTIFICATION_ARRAY_ENTRIES 3
#define configUSE_MUTEXES 1
#define configUSE_RECURSIVE_MUTEXES 1
#define configUSE_COUNTING_SEMAPHORES 1
#define configQUEUE_REGISTRY_SIZE 10
#define configUSE_QUEUE_SETS 0
#define configUSE_TIME_SLICING 1
#define configUSE_NEWLIB_REENTRANT 0
#define configENABLE_BACKWARD_COMPATIBILITY 0
#define configNUM_THREAD_LOCAL_STORAGE_POINTERS 5
#define configUSE_MINI_LIST_ITEM 1
/* Memory allocation related definitions. */
#define configSUPPORT_STATIC_ALLOCATION 0
#define configSUPPORT_DYNAMIC_ALLOCATION 1
#define configTOTAL_HEAP_SIZE ( ( size_t ) ( 60 * 1024 ) )
#define configAPPLICATION_ALLOCATED_HEAP 0
/* Hook function related definitions. */
#define configUSE_IDLE_HOOK 0
#define configUSE_TICK_HOOK 0
#define configCHECK_FOR_STACK_OVERFLOW 0
#define configUSE_MALLOC_FAILED_HOOK 0
#define configUSE_DAEMON_TASK_STARTUP_HOOK 0
/* Run time and task stats gathering related definitions. */
#define configGENERATE_RUN_TIME_STATS 0
#define configUSE_TRACE_FACILITY 0
#define configUSE_STATS_FORMATTING_FUNCTIONS 0
/* Co-routine related definitions. */
#define configUSE_CO_ROUTINES 0
#define configMAX_CO_ROUTINE_PRIORITIES 1
/* Software timer related definitions. */
#define configUSE_TIMERS 1
#define configTIMER_TASK_PRIORITY ( configMAX_PRIORITIES - 1 )
#define configTIMER_QUEUE_LENGTH 10
#define configTIMER_TASK_STACK_DEPTH configMINIMAL_STACK_SIZE
/* Define to trap errors during development. */
#define configASSERT( x )
/* Optional functions - most linkers will remove unused functions anyway. */
#define INCLUDE_vTaskPrioritySet 1
#define INCLUDE_uxTaskPriorityGet 1
#define INCLUDE_vTaskDelete 1
#define INCLUDE_vTaskSuspend 1
#define INCLUDE_xResumeFromISR 1
#define INCLUDE_vTaskDelayUntil 1
#define INCLUDE_vTaskDelay 1
#define INCLUDE_xTaskGetSchedulerState 1
#define INCLUDE_xTaskGetCurrentTaskHandle 1
#define INCLUDE_uxTaskGetStackHighWaterMark 0
#define INCLUDE_xTaskGetIdleTaskHandle 0
#define INCLUDE_eTaskGetState 0
#define INCLUDE_xEventGroupSetBitFromISR 1
#define INCLUDE_xTimerPendFunctionCall 0
#define INCLUDE_xTaskAbortDelay 0
#define INCLUDE_xTaskGetHandle 0
#define INCLUDE_xTaskResumeFromISR 1
/* POSIX Port specific definitions. */
#define configPOSIX_STACK_SIZE ( ( unsigned short ) 8192 )
#endif /* FREERTOS_CONFIG_H */

View File

@ -0,0 +1,48 @@
/* user_settings.h
*
* Copyright (C) 2006-2024 wolfSSL Inc.
*
* This file is part of wolfSSL.
*
* wolfSSL is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* wolfSSL is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
/* wolfSSL configuration */
#ifndef USER_SETTINGS_H
#define USER_SETTINGS_H
#define WOLFSSL_TLS13
#define HAVE_TLS_EXTENSIONS
#define HAVE_SUPPORTED_CURVES
#define HAVE_FFDHE_2048
#define HAVE_HKDF
#define HAVE_AEAD
#define HAVE_CHACHA
#define HAVE_POLY1305
#define WOLFSSL_AES_COUNTER
#define WOLFSSL_AES_DIRECT
#define HAVE_AES_ECB
#define HAVE_AES_CBC
#define HAVE_AES_GCM
#define HAVE_AESGCM
#define HAVE_CURVE25519
#define HAVE_ED25519
#define WOLFSSL_SHA384
#define WOLFSSL_SHA512
#define WOLFSSL_SHA224
#define WOLFSSL_SHA3
#define WOLFSSL_SHAKE256
#endif /* USER_SETTINGS_H */

View File

@ -0,0 +1,50 @@
#!/bin/bash
# Script to setup FreeRTOS environment for wolfSSL examples
set -e
FREERTOS_REPO="https://github.com/FreeRTOS/FreeRTOS.git"
FREERTOS_KERNEL_REPO="https://github.com/FreeRTOS/FreeRTOS-Kernel.git"
echo "Setting up FreeRTOS simulation environment..."
# Create directories if they don't exist
mkdir -p freertos
cd freertos
# Clone FreeRTOS repositories if they don't exist
if [ ! -d "FreeRTOS" ]; then
git clone --depth=1 $FREERTOS_REPO
fi
# Clone wolfSSL and wolfIP if they don't exist
cd ../../../../
if [ ! -d "wolfssl" ]; then
git clone --depth=1 https://github.com/wolfSSL/wolfssl.git
cd wolfssl
make
sudo make install
cd ..
fi
if [ ! -d "wolfip" ]; then
git clone --depth=1 https://github.com/wolfSSL/wolfip.git
cd wolfip
make
cd ..
fi
cd wolfssl-examples/fullstack/freertos-wolfip-wolfssl-https/freertos
if [ ! -d "FreeRTOS-Kernel" ]; then
git clone --depth=1 $FREERTOS_KERNEL_REPO
fi
echo "FreeRTOS repositories cloned successfully"
# Create basic directory structure for our project
mkdir -p ../src
mkdir -p ../include
mkdir -p ../build
echo "Directory structure created"
echo "Setup complete!"

View File

@ -0,0 +1,21 @@
#!/bin/bash
# Configure host TAP interface for wolfSSL embedded testing
# Creates a TAP interface for virtual networking between host and FreeRTOS
# Check if running as root
if [ "$EUID" -ne 0 ]; then
echo "Please run as root (sudo)"
exit 1
fi
# Remove existing interface if present
ip link show wtap0 >/dev/null 2>&1 && ip link delete wtap0
# Create new TAP interface and configure it
ip tuntap add dev wtap0 mode tap
ip link set wtap0 down
ip addr flush dev wtap0
ip addr add 10.10.0.1/24 dev wtap0
ip link set wtap0 up
echo "TAP interface wtap0 configured with IP 10.10.0.1/24"

View File

@ -0,0 +1,106 @@
/* https_server.c
*
* Copyright (C) 2006-2024 wolfSSL Inc.
*
* This file is part of wolfSSL.
*
* wolfSSL is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* wolfSSL is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "https_server.h"
#include "httpd.h"
#include <wolfssl/ssl.h>
#include <wolfssl/wolfcrypt/error-crypt.h>
static WOLFSSL_CTX *g_ssl_ctx = NULL;
static struct httpd g_httpd;
/* Root page handler */
static int handle_root(struct httpd *httpd, struct http_client *hc, struct http_request *req) {
const char *response = "<html><body><h1>wolfSSL HTTPS Demo</h1>"
"<p>TLS 1.3 + FreeRTOS + wolfIP</p></body></html>";
http_send_response_headers(hc, HTTP_STATUS_OK, "OK", "text/html", strlen(response));
http_send_response_body(hc, response, strlen(response));
return 0;
}
int https_server_init(struct wolfIP *ipstack) {
int ret;
/* Initialize wolfSSL */
if ((ret = wolfSSL_Init()) != WOLFSSL_SUCCESS) {
printf("Failed to initialize wolfSSL\n");
return -1;
}
/* Create and initialize WOLFSSL_CTX */
if ((g_ssl_ctx = wolfSSL_CTX_new(wolfTLSv1_3_server_method())) == NULL) {
printf("Failed to create WOLFSSL_CTX\n");
return -1;
}
/* Load server certificates */
if ((ret = wolfSSL_CTX_use_certificate_file(g_ssl_ctx, CERT_FILE,
WOLFSSL_FILETYPE_PEM)) != WOLFSSL_SUCCESS) {
printf("Failed to load %s\n", CERT_FILE);
return -1;
}
/* Load server key */
if ((ret = wolfSSL_CTX_use_PrivateKey_file(g_ssl_ctx, KEY_FILE,
WOLFSSL_FILETYPE_PEM)) != WOLFSSL_SUCCESS) {
printf("Failed to load %s\n", KEY_FILE);
return -1;
}
/* Initialize HTTP server with SSL context */
if (httpd_init(&g_httpd, ipstack, HTTPS_PORT, g_ssl_ctx) != 0) {
printf("Failed to initialize HTTPS server\n");
return -1;
}
/* Register handlers */
if (httpd_register_handler(&g_httpd, "/", handle_root) != 0) {
printf("Failed to register root handler\n");
return -1;
}
printf("HTTPS server initialized on port %d\n", HTTPS_PORT);
return 0;
}
static void https_server_task(void* pvParameters) {
const TickType_t xDelay = pdMS_TO_TICKS(100);
printf("HTTPS server task started\n");
/* Task main loop - wolfIP handles connections in callbacks */
for(;;) {
vTaskDelay(xDelay);
}
}
int https_server_start(void) {
BaseType_t ret;
ret = xTaskCreate(https_server_task,
"HTTPS_Server",
HTTPS_TASK_STACK_SIZE,
NULL,
HTTPS_TASK_PRIORITY,
NULL);
return (ret == pdPASS) ? 0 : -1;
}

View File

@ -0,0 +1,47 @@
/* https_server.h
*
* Copyright (C) 2006-2024 wolfSSL Inc.
*
* This file is part of wolfSSL.
*
* wolfSSL is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* wolfSSL is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#ifndef HTTPS_SERVER_H
#define HTTPS_SERVER_H
#include "FreeRTOS.h"
#include "task.h"
#include "wolfip.h"
#include "httpd.h"
#include <wolfssl/ssl.h>
/* HTTPS server configuration */
#define HTTPS_PORT 443
#define HTTPS_TASK_STACK_SIZE (16 * 1024)
#define HTTPS_TASK_PRIORITY (tskIDLE_PRIORITY + 2)
/* Certificate paths */
#define CERT_FILE "../../../../wolfssl/certs/server-cert.pem"
#define KEY_FILE "../../../../wolfssl/certs/server-key.pem"
#define CA_FILE "../../../../wolfssl/certs/ca-cert.pem"
/* Initialize HTTPS server with wolfSSL and wolfIP */
int https_server_init(struct wolfIP *ipstack);
/* Start HTTPS server task */
int https_server_start(void);
#endif /* HTTPS_SERVER_H */

View File

@ -0,0 +1,83 @@
/* main.c
*
* Copyright (C) 2006-2024 wolfSSL Inc.
*
* This file is part of wolfSSL.
*
* wolfSSL is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* wolfSSL is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include <stdio.h>
#include "FreeRTOS.h"
#include "task.h"
#include "wolfip_freertos.h"
#include "https_server.h"
static void testTask(void* pvParameters) {
const TickType_t xDelay = 1000 / portTICK_PERIOD_MS;
int ret;
printf("Initializing wolfIP...\n");
ret = wolfIP_FreeRTOS_Init();
if (ret != 0) {
printf("Failed to initialize wolfIP\n");
return;
}
printf("Starting wolfIP network task...\n");
ret = wolfIP_FreeRTOS_Start();
if (ret != 0) {
printf("Failed to start wolfIP network task\n");
return;
}
printf("Starting UDP echo server...\n");
ret = wolfIP_Start_UDP_Echo();
if (ret != 0) {
printf("Failed to start UDP echo server\n");
return;
}
printf("Starting HTTPS server...\n");
ret = https_server_init(g_wolfip);
if (ret != 0) {
printf("Failed to initialize HTTPS server\n");
return;
}
ret = https_server_start();
if (ret != 0) {
printf("Failed to start HTTPS server\n");
return;
}
printf("Network stack, UDP echo server, and HTTPS server running...\n");
for(;;) {
vTaskDelay(xDelay);
}
}
int main(void) {
printf("Starting FreeRTOS with wolfIP...\n");
/* Create the test task */
xTaskCreate(testTask, "TestTask", configMINIMAL_STACK_SIZE,
NULL, tskIDLE_PRIORITY + 1, NULL);
/* Start the scheduler */
vTaskStartScheduler();
/* Should never reach here */
return 0;
}

View File

@ -0,0 +1,260 @@
/* wolfip_freertos.c
*
* Copyright (C) 2006-2024 wolfSSL Inc.
*
* This file is part of wolfSSL.
*
* wolfSSL is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* wolfSSL is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include "wolfip_freertos.h"
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/ioctl.h>
#include <linux/if.h>
#include <linux/if_tun.h>
#include <arpa/inet.h>
#include <sys/time.h>
#include <poll.h>
#include <sys/socket.h>
#include <sys/random.h>
#include <errno.h>
/* Implementation of wolfIP's required random number generator */
uint32_t wolfIP_getrandom(void) {
uint32_t ret;
getrandom(&ret, sizeof(ret), 0);
return ret;
}
struct wolfIP *g_wolfip = NULL;
static TaskHandle_t g_network_task = NULL;
static int tap_fd = -1;
/* TUN/TAP device functions */
static int tap_init(struct ll *dev, const char *ifname) {
struct ifreq ifr;
int sock_fd;
if ((tap_fd = open("/dev/net/tun", O_RDWR)) < 0) {
perror("Error opening /dev/net/tun");
return -1;
}
memset(&ifr, 0, sizeof(ifr));
ifr.ifr_flags = IFF_TAP | IFF_NO_PI;
strncpy(ifr.ifr_name, ifname, IFNAMSIZ);
if (ioctl(tap_fd, TUNSETIFF, (void *)&ifr) < 0) {
perror("ioctl TUNSETIFF");
close(tap_fd);
return -1;
}
/* Get MAC address */
if (ioctl(tap_fd, SIOCGIFHWADDR, &ifr) < 0) {
perror("ioctl SIOCGIFHWADDR");
close(tap_fd);
return -1;
}
strncpy(dev->ifname, ifname, sizeof(dev->ifname) - 1);
memcpy(dev->mac, ifr.ifr_hwaddr.sa_data, 6);
dev->mac[5] ^= 1; /* Make MAC unique */
/* Configure network interface */
sock_fd = socket(AF_INET, SOCK_DGRAM, 0);
if (sock_fd < 0) {
perror("socket");
close(tap_fd);
return -1;
}
/* Set interface UP */
if (ioctl(sock_fd, SIOCGIFFLAGS, &ifr) < 0) {
perror("ioctl SIOCGIFFLAGS");
close(sock_fd);
return -1;
}
ifr.ifr_flags |= IFF_UP | IFF_RUNNING;
if (ioctl(sock_fd, SIOCSIFFLAGS, &ifr) < 0) {
perror("ioctl SIOCSIFFLAGS");
close(sock_fd);
return -1;
}
close(sock_fd);
return 0;
}
static int tap_poll(struct ll *ll, void *buf, uint32_t len) {
struct pollfd pfd;
int ret;
pfd.fd = tap_fd;
pfd.events = POLLIN;
do {
ret = poll(&pfd, 1, 1); /* Short timeout */
} while (ret < 0 && errno == EINTR);
if (ret < 0) {
perror("poll");
return -1;
}
if (ret == 0) {
return 0;
}
do {
ret = read(tap_fd, buf, len);
} while (ret < 0 && errno == EINTR);
return ret;
}
static int tap_send(struct ll *ll, void *buf, uint32_t len) {
return write(tap_fd, buf, len);
}
/* Network task implementation */
static void wolfIP_NetworkTask(void *pvParameters) {
TickType_t last_wake_time;
const TickType_t frequency = pdMS_TO_TICKS(WOLFIP_POLL_INTERVAL_MS);
struct timeval tv;
last_wake_time = xTaskGetTickCount();
while (1) {
gettimeofday(&tv, NULL);
wolfIP_poll(g_wolfip, tv.tv_sec * 1000 + tv.tv_usec / 1000);
vTaskDelayUntil(&last_wake_time, frequency);
}
}
int wolfIP_FreeRTOS_Init(void) {
struct ll *tapdev;
/* Initialize wolfIP */
wolfIP_init_static(&g_wolfip);
if (!g_wolfip) {
printf("Failed to initialize wolfIP\n");
return -1;
}
/* Setup TUN/TAP interface */
tapdev = wolfIP_getdev(g_wolfip);
if (!tapdev) {
printf("Failed to get device from wolfIP\n");
return -1;
}
/* Initialize TAP device */
if (tap_init(tapdev, "wtap0") < 0) {
printf("Failed to initialize TAP device\n");
return -1;
}
/* Set device callbacks */
tapdev->poll = tap_poll;
tapdev->send = tap_send;
/* Configure IP settings */
wolfIP_ipconfig_set(g_wolfip,
atoip4("10.10.0.10"), /* IP */
atoip4("255.255.255.0"), /* Netmask */
atoip4("10.10.0.1")); /* Gateway */
return 0;
}
static void UDP_Echo_Task(void* pvParameters) {
int sockfd;
uint8_t buf[1024];
int ret;
struct wolfIP_sockaddr_in addr;
struct wolfIP_sockaddr_in client_addr;
socklen_t client_len;
sockfd = wolfIP_sock_socket(g_wolfip, AF_INET, SOCK_DGRAM, 0);
if (sockfd < 0) {
printf("Failed to create UDP socket\n");
return;
}
memset(&addr, 0, sizeof(addr));
addr.sin_family = AF_INET;
addr.sin_port = htons(UDP_TEST_PORT);
addr.sin_addr.s_addr = htonl(INADDR_ANY);
if (wolfIP_sock_bind(g_wolfip, sockfd, (struct wolfIP_sockaddr*)&addr, sizeof(addr)) < 0) {
printf("Failed to bind UDP socket\n");
wolfIP_sock_close(g_wolfip, sockfd);
return;
}
printf("UDP Echo Server running on port %d\n", UDP_TEST_PORT);
while (1) {
client_len = sizeof(client_addr);
ret = wolfIP_sock_recvfrom(g_wolfip, sockfd, buf, sizeof(buf), 0,
(struct wolfIP_sockaddr*)&client_addr, &client_len);
if (ret > 0) {
uint32_t ip = ntohl(client_addr.sin_addr.s_addr);
printf("Received %d bytes from %d.%d.%d.%d:%d\n", ret,
(ip >> 24) & 0xFF,
(ip >> 16) & 0xFF,
(ip >> 8) & 0xFF,
ip & 0xFF,
ntohs(client_addr.sin_port));
wolfIP_sock_sendto(g_wolfip, sockfd, buf, ret, 0,
(struct wolfIP_sockaddr*)&client_addr, client_len);
}
vTaskDelay(pdMS_TO_TICKS(10));
}
}
int wolfIP_Start_UDP_Echo(void) {
BaseType_t ret;
ret = xTaskCreate(UDP_Echo_Task,
"UDP_Echo",
WOLFIP_TASK_STACK_SIZE,
NULL,
tskIDLE_PRIORITY + 1,
NULL);
return (ret == pdPASS) ? 0 : -1;
}
int wolfIP_FreeRTOS_Start(void) {
BaseType_t ret;
if (!g_wolfip) {
printf("wolfIP not initialized\n");
return -1;
}
ret = xTaskCreate(wolfIP_NetworkTask,
"WolfIP_Net",
WOLFIP_TASK_STACK_SIZE,
NULL,
WOLFIP_TASK_PRIORITY,
&g_network_task);
return (ret == pdPASS) ? 0 : -1;
}

View File

@ -0,0 +1,47 @@
/* wolfip_freertos.h
*
* Copyright (C) 2006-2024 wolfSSL Inc.
*
* This file is part of wolfSSL.
*
* wolfSSL is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* wolfSSL is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#ifndef WOLFIP_FREERTOS_H
#define WOLFIP_FREERTOS_H
#include "FreeRTOS.h"
#include "task.h"
#include "wolfip.h"
/* Global wolfIP instance */
extern struct wolfIP *g_wolfip;
/* Network task configuration */
#define WOLFIP_TASK_PRIORITY (tskIDLE_PRIORITY + 2)
#define WOLFIP_TASK_STACK_SIZE (8 * 1024)
#define WOLFIP_POLL_INTERVAL_MS 10
#define UDP_TEST_PORT 7777
/* Initialize wolfIP with FreeRTOS */
int wolfIP_FreeRTOS_Init(void);
/* Start wolfIP network task */
int wolfIP_FreeRTOS_Start(void);
/* Start UDP echo server task */
int wolfIP_Start_UDP_Echo(void);
#endif /* WOLFIP_FREERTOS_H */

View File

@ -0,0 +1,27 @@
#!/bin/bash
# Test HTTPS server with curl using wolfSSL test certificates
# Check if running as root
if [ "$EUID" -ne 0 ]; then
echo "Please run as root (sudo)"
exit 1
fi
# Ensure TAP interface is up
if ! ip link show wtap0 >/dev/null 2>&1; then
echo "TAP interface wtap0 not found. Please run setup_network.sh first."
exit 1
fi
echo "Testing HTTPS server with curl..."
curl -v --cacert ./certs/ca-cert.pem \
--tlsv1.3 --insecure https://10.10.0.10:443/
# Check if curl command succeeded
if [ $? -eq 0 ]; then
echo "HTTPS test successful!"
else
echo "HTTPS test failed!"
exit 1
fi