Merge pull request #2497 from openmv/fs_boot_script
Some checks failed
🔎 Check Code Formatting / formatting-check (push) Has been cancelled
🔥 Firmware Build / build-firmware (ARDUINO_GIGA) (push) Has been cancelled
🔥 Firmware Build / build-firmware (ARDUINO_NANO_33_BLE_SENSE) (push) Has been cancelled
🔥 Firmware Build / build-firmware (ARDUINO_NANO_RP2040_CONNECT) (push) Has been cancelled
🔥 Firmware Build / build-firmware (ARDUINO_NICLA_VISION) (push) Has been cancelled
🔥 Firmware Build / build-firmware (ARDUINO_PORTENTA_H7) (push) Has been cancelled
🔥 Firmware Build / build-firmware (OPENMV2) (push) Has been cancelled
🔥 Firmware Build / build-firmware (OPENMV3) (push) Has been cancelled
🔥 Firmware Build / build-firmware (OPENMV4) (push) Has been cancelled
🔥 Firmware Build / build-firmware (OPENMV4P) (push) Has been cancelled
🔥 Firmware Build / build-firmware (OPENMVPT) (push) Has been cancelled
🔥 Firmware Build / build-firmware (OPENMV_RT1060) (push) Has been cancelled
🔥 Firmware Build / code-size-report (push) Has been cancelled
🔥 Firmware Build / stable-release (push) Has been cancelled
🔥 Firmware Build / development-release (push) Has been cancelled

misc: Add common filesystem boot script.
This commit is contained in:
Ibrahim Abdelkader 2024-11-12 15:15:26 +02:00 committed by GitHub
commit 11caeff9d9
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
43 changed files with 255 additions and 1532 deletions

130
scripts/libraries/_boot.py Normal file
View File

@ -0,0 +1,130 @@
# SPDX-License-Identifier: MIT
#
# Copyright (C) 2024 OpenMV, LLC.
#
# Permission is hereby granted, free of charge, to any person obtaining a copy
# of this software and associated documentation files (the "Software"), to deal
# in the Software without restriction, including without limitation the rights
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
# copies of the Software, and to permit persons to whom the Software is
# furnished to do so, subject to the following conditions:
#
# The above copyright notice and this permission notice shall be included in
# all copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
# THE SOFTWARE.
import os
import sys
import vfs
main_py = """import time
from machine import LED
led = LED("LED_BLUE")
while True:
led.on()
time.sleep_ms(150)
led.off()
time.sleep_ms(100)
led.on()
time.sleep_ms(150)
led.off()
time.sleep_ms(600)
"""
readme_txt = """Thank you for supporting the OpenMV project!
To download the IDE, please visit:
https://openmv.io/pages/download
For tutorials and documentation, please visit:
http://docs.openmv.io/
For technical support and projects, please visit the forums:
http://forums.openmv.io/
Please use github to report bugs and issues:
https://github.com/openmv/openmv
"""
bdev = None
sdcard = None
if bdev is None:
try:
import pyb
bdev = pyb.Flash(start=0)
sdcard = pyb.SDCard()
except Exception:
pass
if bdev is None:
try:
import mimxrt
import machine
bdev = mimxrt.Flash()
sdcard = machine.SDCard(1)
except Exception:
pass
if bdev is None:
try:
import rp2
bdev = rp2.Flash()
except Exception:
pass
def create_file(path, data=None):
with open(path, "w") as f:
if data is not None:
f.write(data)
try:
fat = vfs.VfsFat(bdev)
vfs.mount(fat, "/flash")
except Exception:
vfs.VfsFat.mkfs(bdev)
fat = vfs.VfsFat(bdev)
vfs.mount(fat, "/flash")
create_file("/flash/main.py", main_py)
create_file("/flash/README.txt", readme_txt)
os.chdir("/flash")
sys.path.append("/flash")
sys.path.append("/flash/lib")
try:
os.stat("SKIPSD")
sdcard = None # Skip SD mount
except Exception:
pass
if sdcard is not None:
try:
fat = vfs.VfsFat(sdcard)
vfs.mount(fat, "/sdcard")
os.chdir("/sdcard")
sys.path.append("/sdcard")
sys.path.append("/sdcard/lib")
except Exception:
pass # Fail silently
try:
os.stat(".openmv_disk")
except Exception:
create_file(".openmv_disk")
del fat, bdev, sdcard

@ -1 +1 @@
Subproject commit 12f6d620efcdde76824b6e90c269e0184809c236 Subproject commit a971731624f0d447dfb6f67cd84d187b60626849

View File

@ -17,7 +17,6 @@ SRCS += $(addprefix alloc/, \
SRCS += $(addprefix common/, \ SRCS += $(addprefix common/, \
array.c \ array.c \
ini.c \
ringbuf.c \ ringbuf.c \
trace.c \ trace.c \
mutex.c \ mutex.c \

View File

@ -1,5 +1,8 @@
include("$(MPY_DIR)/extmod/asyncio") include("$(MPY_DIR)/extmod/asyncio")
# Filesystem
freeze ("$(OMV_LIB_DIR)/", "_boot.py")
# Drivers # Drivers
require("onewire") require("onewire")
require("dht") require("dht")

View File

@ -151,7 +151,6 @@
#define OMV_GC_BLOCK1_MEMORY DRAM // Extra GC block 1. #define OMV_GC_BLOCK1_MEMORY DRAM // Extra GC block 1.
#define OMV_GC_BLOCK1_SIZE (2560K) #define OMV_GC_BLOCK1_SIZE (2560K)
#define OMV_MSC_BUF_SIZE (2K) // USB MSC bot data #define OMV_MSC_BUF_SIZE (2K) // USB MSC bot data
#define OMV_VFS_BUF_SIZE (1K) // VFS struct + FATFS file buffer (624 bytes)
#define OMV_SDRAM_SIZE (8 * 1024 * 1024) // This needs to be here for UVC firmware. #define OMV_SDRAM_SIZE (8 * 1024 * 1024) // This needs to be here for UVC firmware.
#define OMV_LINE_BUF_SIZE (11 * 1024) // Image line buffer round(2592 * 2BPP * 2 buffers). #define OMV_LINE_BUF_SIZE (11 * 1024) // Image line buffer round(2592 * 2BPP * 2 buffers).

View File

@ -1,19 +0,0 @@
static const char fresh_readme_txt[] =
"Thank you for supporting Arduino and the OpenMV project!\r\n"
"\r\n"
"To download the OpenMV IDE, please visit:\r\n"
"https://openmv.io/pages/download\r\n"
"\r\n"
"For tutorials and documentation, please visit:\r\n"
"https://docs.arduino.cc/\r\n"
"http://docs.openmv.io/\r\n"
"\r\n"
"For technical OpenMV support and projects, please visit the forums:\r\n"
"http://forums.openmv.io/\r\n"
"\r\n"
"For Arduino related issues, please visit the Arduino help center:\r\n"
"https://support.arduino.cc/\r\n"
"\r\n"
"Please use Github to report bugs and issues:\r\n"
"https://github.com/openmv/openmv\r\n"
;

View File

@ -1,5 +1,8 @@
include("$(MPY_DIR)/extmod/asyncio") include("$(MPY_DIR)/extmod/asyncio")
freeze ("$(PORT_DIR)/modules") freeze ("$(PORT_DIR)/modules", "rp2.py")
# Filesystem
freeze ("$(OMV_LIB_DIR)/", "_boot.py")
# Drivers # Drivers
require("lsm6dsox") require("lsm6dsox")

View File

@ -1,19 +0,0 @@
static const char fresh_readme_txt[] =
"Thank you for supporting Arduino and the OpenMV project!\r\n"
"\r\n"
"To download the OpenMV IDE, please visit:\r\n"
"https://openmv.io/pages/download\r\n"
"\r\n"
"For tutorials and documentation, please visit:\r\n"
"https://docs.arduino.cc/\r\n"
"http://docs.openmv.io/\r\n"
"\r\n"
"For technical OpenMV support and projects, please visit the forums:\r\n"
"http://forums.openmv.io/\r\n"
"\r\n"
"For Arduino related issues, please visit the Arduino help center:\r\n"
"https://support.arduino.cc/\r\n"
"\r\n"
"Please use Github to report bugs and issues:\r\n"
"https://github.com/openmv/openmv\r\n"
;

View File

@ -1,5 +1,8 @@
include("$(MPY_DIR)/extmod/asyncio") include("$(MPY_DIR)/extmod/asyncio")
# Filesystem
freeze ("$(OMV_LIB_DIR)/", "_boot.py")
# Drivers # Drivers
require("lsm6dsox") require("lsm6dsox")
require("onewire") require("onewire")

View File

@ -138,7 +138,6 @@
#define OMV_GC_BLOCK2_MEMORY SRAM1 // Extra GC block 2. #define OMV_GC_BLOCK2_MEMORY SRAM1 // Extra GC block 2.
#define OMV_GC_BLOCK2_SIZE (276K) #define OMV_GC_BLOCK2_SIZE (276K)
#define OMV_MSC_BUF_SIZE (2K) // USB MSC bot data #define OMV_MSC_BUF_SIZE (2K) // USB MSC bot data
#define OMV_VFS_BUF_SIZE (1K) // VFS struct + FATFS file buffer (624 bytes)
#define OMV_LINE_BUF_SIZE (3 * 1024) // Image line buffer round(640 * 2BPP * 2 buffers). #define OMV_LINE_BUF_SIZE (3 * 1024) // Image line buffer round(640 * 2BPP * 2 buffers).
// Memory map. // Memory map.

View File

@ -1,19 +0,0 @@
static const char fresh_readme_txt[] =
"Thank you for supporting Arduino and the OpenMV project!\r\n"
"\r\n"
"To download the OpenMV IDE, please visit:\r\n"
"https://openmv.io/pages/download\r\n"
"\r\n"
"For tutorials and documentation, please visit:\r\n"
"https://docs.arduino.cc/\r\n"
"http://docs.openmv.io/\r\n"
"\r\n"
"For technical OpenMV support and projects, please visit the forums:\r\n"
"http://forums.openmv.io/\r\n"
"\r\n"
"For Arduino related issues, please visit the Arduino help center:\r\n"
"https://support.arduino.cc/\r\n"
"\r\n"
"Please use Github to report bugs and issues:\r\n"
"https://github.com/openmv/openmv\r\n"
;

View File

@ -1,5 +1,8 @@
include("$(MPY_DIR)/extmod/asyncio") include("$(MPY_DIR)/extmod/asyncio")
# Filesystem
freeze ("$(OMV_LIB_DIR)/", "_boot.py")
# Drivers # Drivers
require("onewire") require("onewire")
require("ds18x20") require("ds18x20")

View File

@ -154,7 +154,6 @@
#define OMV_GC_BLOCK1_MEMORY DRAM // Extra GC block 1. #define OMV_GC_BLOCK1_MEMORY DRAM // Extra GC block 1.
#define OMV_GC_BLOCK1_SIZE (2560K) #define OMV_GC_BLOCK1_SIZE (2560K)
#define OMV_MSC_BUF_SIZE (2K) // USB MSC bot data #define OMV_MSC_BUF_SIZE (2K) // USB MSC bot data
#define OMV_VFS_BUF_SIZE (1K) // VFS struct + FATFS file buffer (624 bytes)
#define OMV_SDRAM_SIZE (8 * 1024 * 1024) // This needs to be here for UVC firmware. #define OMV_SDRAM_SIZE (8 * 1024 * 1024) // This needs to be here for UVC firmware.
#define OMV_LINE_BUF_SIZE (11 * 1024) // Image line buffer round(2592 * 2BPP * 2 buffers). #define OMV_LINE_BUF_SIZE (11 * 1024) // Image line buffer round(2592 * 2BPP * 2 buffers).

View File

@ -1,19 +0,0 @@
static const char fresh_readme_txt[] =
"Thank you for supporting Arduino and the OpenMV project!\r\n"
"\r\n"
"To download the OpenMV IDE, please visit:\r\n"
"https://openmv.io/pages/download\r\n"
"\r\n"
"For tutorials and documentation, please visit:\r\n"
"https://docs.arduino.cc/\r\n"
"http://docs.openmv.io/\r\n"
"\r\n"
"For technical OpenMV support and projects, please visit the forums:\r\n"
"http://forums.openmv.io/\r\n"
"\r\n"
"For Arduino related issues, please visit the Arduino help center:\r\n"
"https://support.arduino.cc/\r\n"
"\r\n"
"Please use Github to report bugs and issues:\r\n"
"https://github.com/openmv/openmv\r\n"
;

View File

@ -1,4 +1,5 @@
include("$(MPY_DIR)/extmod/asyncio") include("$(MPY_DIR)/extmod/asyncio")
freeze ("$(OMV_LIB_DIR)/", "_boot.py")
freeze ("$(OMV_LIB_DIR)/", "bno055.py") freeze ("$(OMV_LIB_DIR)/", "bno055.py")
freeze ("$(OMV_LIB_DIR)/", "modbus.py") freeze ("$(OMV_LIB_DIR)/", "modbus.py")
freeze ("$(OMV_LIB_DIR)/", "mqtt.py") freeze ("$(OMV_LIB_DIR)/", "mqtt.py")

View File

@ -91,7 +91,6 @@
#define OMV_GC_BLOCK0_SIZE (46K) #define OMV_GC_BLOCK0_SIZE (46K)
#define OMV_JPEG_SIZE (8K) // IDE JPEG buffer size (header + data). #define OMV_JPEG_SIZE (8K) // IDE JPEG buffer size (header + data).
#define OMV_MSC_BUF_SIZE (2K) // USB MSC bot data #define OMV_MSC_BUF_SIZE (2K) // USB MSC bot data
#define OMV_VFS_BUF_SIZE (1K) // VFS struct + FATFS file buffer (624 bytes)
#define OMV_FFS_BUF_SIZE (16K) // Flash filesystem cache #define OMV_FFS_BUF_SIZE (16K) // Flash filesystem cache
#define OMV_LINE_BUF_SIZE (2 * 1024) // Image line buffer round(320 * 2BPP * 2 buffers). #define OMV_LINE_BUF_SIZE (2 * 1024) // Image line buffer round(320 * 2BPP * 2 buffers).

View File

@ -1,4 +1,5 @@
include("$(MPY_DIR)/extmod/asyncio") include("$(MPY_DIR)/extmod/asyncio")
freeze ("$(OMV_LIB_DIR)/", "_boot.py")
freeze ("$(OMV_LIB_DIR)/", "bno055.py") freeze ("$(OMV_LIB_DIR)/", "bno055.py")
freeze ("$(OMV_LIB_DIR)/", "modbus.py") freeze ("$(OMV_LIB_DIR)/", "modbus.py")
freeze ("$(OMV_LIB_DIR)/", "mqtt.py") freeze ("$(OMV_LIB_DIR)/", "mqtt.py")

View File

@ -90,7 +90,6 @@
#define OMV_GC_BLOCK0_SIZE (53K) #define OMV_GC_BLOCK0_SIZE (53K)
#define OMV_JPEG_SIZE (22K) // IDE JPEG buffer (header + data). #define OMV_JPEG_SIZE (22K) // IDE JPEG buffer (header + data).
#define OMV_MSC_BUF_SIZE (2K) // USB MSC bot data #define OMV_MSC_BUF_SIZE (2K) // USB MSC bot data
#define OMV_VFS_BUF_SIZE (1K) // VFS struct + FATFS file buffer (624 bytes)
#define OMV_FFS_BUF_SIZE (32K) // Flash filesystem cache #define OMV_FFS_BUF_SIZE (32K) // Flash filesystem cache
#define OMV_LINE_BUF_SIZE (3 * 1024) // Image line buffer round(640 * 2BPP * 2 buffers). #define OMV_LINE_BUF_SIZE (3 * 1024) // Image line buffer round(640 * 2BPP * 2 buffers).

View File

@ -1,5 +1,8 @@
include("$(MPY_DIR)/extmod/asyncio") include("$(MPY_DIR)/extmod/asyncio")
# Filesystem
freeze ("$(OMV_LIB_DIR)/", "_boot.py")
# Drivers # Drivers
require("onewire") require("onewire")
require("ds18x20") require("ds18x20")

View File

@ -73,9 +73,6 @@
#define OMV_FIR_AMG8833_ENABLE (1) #define OMV_FIR_AMG8833_ENABLE (1)
#define OMV_FIR_LEPTON_ENABLE (1) #define OMV_FIR_LEPTON_ENABLE (1)
// Debugging configuration.
#define OMV_WIFIDBG_ENABLE (1)
// UMM heap block size // UMM heap block size
#define OMV_UMM_BLOCK_SIZE 16 #define OMV_UMM_BLOCK_SIZE 16
@ -149,7 +146,6 @@
#define OMV_GC_BLOCK1_MEMORY SRAM1 // Extra GC block 0. #define OMV_GC_BLOCK1_MEMORY SRAM1 // Extra GC block 0.
#define OMV_GC_BLOCK1_SIZE (267K) #define OMV_GC_BLOCK1_SIZE (267K)
#define OMV_MSC_BUF_SIZE (2K) // USB MSC bot data #define OMV_MSC_BUF_SIZE (2K) // USB MSC bot data
#define OMV_VFS_BUF_SIZE (1K) // VFS struct + FATFS file buffer (624 bytes)
#define OMV_LINE_BUF_SIZE (3 * 1024) // Image line buffer round(640 * 2BPP * 2 buffers). #define OMV_LINE_BUF_SIZE (3 * 1024) // Image line buffer round(640 * 2BPP * 2 buffers).
// Memory map. // Memory map.

View File

@ -1,5 +1,8 @@
include("$(MPY_DIR)/extmod/asyncio") include("$(MPY_DIR)/extmod/asyncio")
# Filesystem
freeze ("$(OMV_LIB_DIR)/", "_boot.py")
# Drivers # Drivers
require("onewire") require("onewire")
require("ds18x20") require("ds18x20")

View File

@ -60,9 +60,6 @@
#define OMV_FIR_AMG8833_ENABLE (1) #define OMV_FIR_AMG8833_ENABLE (1)
#define OMV_FIR_LEPTON_ENABLE (1) #define OMV_FIR_LEPTON_ENABLE (1)
// Debugging configuration.
#define OMV_WIFIDBG_ENABLE (1)
// UMM heap block size // UMM heap block size
#define OMV_UMM_BLOCK_SIZE 256 #define OMV_UMM_BLOCK_SIZE 256
@ -140,7 +137,6 @@
#define OMV_GC_BLOCK1_MEMORY DRAM // Extra GC block 0. #define OMV_GC_BLOCK1_MEMORY DRAM // Extra GC block 0.
#define OMV_GC_BLOCK1_SIZE (4M) #define OMV_GC_BLOCK1_SIZE (4M)
#define OMV_MSC_BUF_SIZE (2K) // USB MSC bot data #define OMV_MSC_BUF_SIZE (2K) // USB MSC bot data
#define OMV_VFS_BUF_SIZE (1K) // VFS struct + FATFS file buffer (624 bytes)
#define OMV_SDRAM_SIZE (32 * 1024 * 1024) // This needs to be here for UVC firmware. #define OMV_SDRAM_SIZE (32 * 1024 * 1024) // This needs to be here for UVC firmware.
#define OMV_LINE_BUF_SIZE (11 * 1024) // Image line buffer round(2592 * 2BPP * 2 buffers). #define OMV_LINE_BUF_SIZE (11 * 1024) // Image line buffer round(2592 * 2BPP * 2 buffers).

View File

@ -1,5 +1,8 @@
include("$(MPY_DIR)/extmod/asyncio") include("$(MPY_DIR)/extmod/asyncio")
# Filesystem
freeze ("$(OMV_LIB_DIR)/", "_boot.py")
# Drivers # Drivers
require("onewire") require("onewire")
require("ds18x20") require("ds18x20")

View File

@ -45,9 +45,6 @@
#define OMV_FIR_AMG8833_ENABLE (1) #define OMV_FIR_AMG8833_ENABLE (1)
#define OMV_FIR_LEPTON_ENABLE (1) #define OMV_FIR_LEPTON_ENABLE (1)
// Debugging configuration.
#define OMV_WIFIDBG_ENABLE (1)
// UMM heap block size // UMM heap block size
#define OMV_UMM_BLOCK_SIZE 256 #define OMV_UMM_BLOCK_SIZE 256
@ -132,7 +129,6 @@
#define OMV_GC_BLOCK1_SIZE (8M) #define OMV_GC_BLOCK1_SIZE (8M)
#define OMV_SDRAM_SIZE (64 * 1024 * 1024) // This needs to be here for UVC firmware. #define OMV_SDRAM_SIZE (64 * 1024 * 1024) // This needs to be here for UVC firmware.
#define OMV_MSC_BUF_SIZE (2K) // USB MSC bot data #define OMV_MSC_BUF_SIZE (2K) // USB MSC bot data
#define OMV_VFS_BUF_SIZE (1K) // VFS struct + FATFS file buffer (624 bytes)
#define OMV_LINE_BUF_SIZE (11 * 1024) // Image line buffer round(2592 * 2BPP * 2 buffers). #define OMV_LINE_BUF_SIZE (11 * 1024) // Image line buffer round(2592 * 2BPP * 2 buffers).
// Memory map. // Memory map.

View File

@ -1,5 +1,8 @@
include("$(MPY_DIR)/extmod/asyncio") include("$(MPY_DIR)/extmod/asyncio")
# Filesystem
freeze ("$(OMV_LIB_DIR)/", "_boot.py")
# Drivers # Drivers
require("onewire") require("onewire")
require("ds18x20") require("ds18x20")

View File

@ -222,13 +222,6 @@ PROVIDE(__stack = __StackTop);
. = . + OMV_MSC_BUF_SIZE; . = . + OMV_MSC_BUF_SIZE;
#endif #endif
/* VFS + FATFS buffer */
#if defined(OMV_VFS_BUF_SIZE)
. = ALIGN(16);
_vfs_buf = .;
. = . + OMV_VFS_BUF_SIZE;
#endif
#if defined(OMV_JPEG_SIZE) && !defined(OMV_JPEG_MEMORY) #if defined(OMV_JPEG_SIZE) && !defined(OMV_JPEG_MEMORY)
. = ALIGN(16); . = ALIGN(16);
_jpeg_memory_start = .; _jpeg_memory_start = .;

View File

@ -1,542 +0,0 @@
/*
* SPDX-License-Identifier: BSD-3-Clause
*
* Copyright (C) 2009-2020, Ben Hoyt
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*
* Read an INI file into easy-to-access name/value pairs.
* For more info, see: https://github.com/benhoyt/inih
*/
#include <stddef.h>
#include <stdbool.h>
#include <string.h>
#include "ini.h"
#include "file_utils.h"
/*-------------------------------------------------------------------------
_isppace.c - part of ctype.h
Written By - Sandeep Dutta . sandeep.dutta@usa.net (1999)
This library is free software; you can redistribute it and/or modify it
under the terms of the GNU Library General Public License as published by the
Free Software Foundation; either version 2, or (at your option) any
later version.
This library 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 Library General Public License for more details.
You should have received a copy of the GNU Library General Public License
along with this program; if not, write to the Free Software
Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
In other words, you are welcome to use, share and improve this program.
You are forbidden to forbid anyone else to use, share and improve
what you give them. Help stamp out software-hoarding!
-------------------------------------------------------------------------*/
char ini_isspace(unsigned char c) {
if (c == ' '
|| c == '\f'
|| c == '\n'
|| c == '\r'
|| c == '\t'
|| c == '\v') {
return 1;
}
return 0;
}
/*
* atoi.c --
*
* Source code for the "atoi" library procedure.
*
* Copyright 1988 Regents of the University of California
* Permission to use, copy, modify, and distribute this
* software and its documentation for any purpose and without
* fee is hereby granted, provided that the above copyright
* notice appear in all copies. The University of California
* makes no representations about the suitability of this
* software for any purpose. It is provided "as is" without
* express or implied warranty.
*/
/*
*----------------------------------------------------------------------
*
* atoi --
*
* Convert an ASCII string into an integer.
*
* Results:
* The return value is the integer equivalent of string. If there
* are no decimal digits in string, then 0 is returned.
*
* Side effects:
* None.
*
*----------------------------------------------------------------------
*/
int
ini_atoi(string)
const char *string; /* String of ASCII digits, possibly
* preceded by white space. For bases
* greater than 10, either lower- or
* upper-case digits may be used.
*/
{
register int result = 0;
register unsigned int digit;
int sign;
/*
* Skip any leading blanks.
*/
while (ini_isspace(*string)) {
string += 1;
}
/*
* Check for a sign.
*/
if (*string == '-') {
sign = 1;
string += 1;
} else {
sign = 0;
if (*string == '+') {
string += 1;
}
}
for (; *string; string++) {
digit = *string - '0';
if ((digit < 0) || (digit > 9)) {
break;
}
result = (10 * result) + digit;
}
if (sign) {
return -result;
}
return result;
}
bool ini_is_true(const char *value) {
int i = ini_atoi(value);
if (i) {
return true;
}
if (strlen(value) != 4) {
return false;
}
if ((value[0] != 'T') && (value[0] != 't')) {
return false;
}
if ((value[1] != 'R') && (value[1] != 'r')) {
return false;
}
if ((value[2] != 'U') && (value[2] != 'u')) {
return false;
}
if ((value[3] != 'E') && (value[3] != 'e')) {
return false;
}
return true;
}
/*
* Copyright (c) 2000-2002 Opsycon AB (www.opsycon.se)
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by Opsycon AB.
* 4. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
* OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
*/
/** ini_fgetc(fp) -- get char from stream */
int ini_fgetc(FIL *fp) {
char c;
UINT b;
if (file_ll_read(fp, &c, 1, &b) != FR_OK || b != 1) {
return (EOF);
}
return (c);
}
/*
* Copyright (c) 2000-2002 Opsycon AB (www.opsycon.se)
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by Opsycon AB.
* 4. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
* OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
*/
/** char *ini_fgets(dst,max,fp) -- get string from stream */
char *ini_fgets(char *dst, int max, FIL *fp) {
char *p;
int c = EOF;
/* get max bytes or upto a newline */
for (p = dst, max--; max > 0; max--) {
if ((c = ini_fgetc(fp)) == EOF) {
break;
}
*p++ = c;
if (c == '\n') {
break;
}
}
*p = 0;
if (p == dst || c == EOF) {
return NULL;
}
return (p);
}
/* inih -- simple .INI file parser
inih is released under the New BSD license (see LICENSE.txt). Go to the project
home page for more info:
https://github.com/benhoyt/inih
*/
#if defined(_MSC_VER) && !defined(_CRT_SECURE_NO_WARNINGS)
#define _CRT_SECURE_NO_WARNINGS
#endif
#include <ctype.h>
#include <string.h>
#if !INI_USE_STACK
#include <stdlib.h>
#endif
#define MAX_SECTION 50
#define MAX_NAME 50
/* Used by ini_parse_string() to keep track of string parsing state. */
typedef struct {
const char *ptr;
size_t num_left;
} ini_parse_string_ctx;
/* Strip whitespace chars off end of given string, in place. Return s. */
static char *rstrip(char *s) {
char *p = s + strlen(s);
while (p > s && ini_isspace((unsigned char) (*--p))) {
*p = '\0';
}
return s;
}
/* Return pointer to first non-whitespace char in given string. */
static char *lskip(const char *s) {
while (*s && ini_isspace((unsigned char) (*s))) {
s++;
}
return (char *) s;
}
/* Return pointer to first char (of chars) or inline comment in given string,
or pointer to null at end of string if neither found. Inline comment must
be prefixed by a whitespace character to register as a comment. */
static char *find_chars_or_comment(const char *s, const char *chars) {
#if INI_ALLOW_INLINE_COMMENTS
int was_space = 0;
while (*s && (!chars || !strchr(chars, *s)) &&
!(was_space && strchr(INI_INLINE_COMMENT_PREFIXES, *s))) {
was_space = ini_isspace((unsigned char) (*s));
s++;
}
#else
while (*s && (!chars || !strchr(chars, *s))) {
s++;
}
#endif
return (char *) s;
}
/* Version of strncpy that ensures dest (size bytes) is null-terminated. */
static char *strncpy0(char *dest, const char *src, size_t size) {
strncpy(dest, src, size - 1);
dest[size - 1] = '\0';
return dest;
}
/* See documentation in header file. */
int ini_parse_stream(ini_reader reader, void *stream, ini_handler handler,
void *user) {
/* Uses a fair bit of stack (use heap instead if you need to) */
#if INI_USE_STACK
char line[INI_MAX_LINE];
int max_line = INI_MAX_LINE;
#else
char *line;
int max_line = INI_INITIAL_ALLOC;
#endif
#if INI_ALLOW_REALLOC
char *new_line;
int offset;
#endif
char section[MAX_SECTION] = "";
char prev_name[MAX_NAME] = "";
char *start;
char *end;
char *name;
char *value;
int lineno = 0;
int error = 0;
#if !INI_USE_STACK
line = (char *) malloc(INI_INITIAL_ALLOC);
if (!line) {
return -2;
}
#endif
#if INI_HANDLER_LINENO
#define HANDLER(u, s, n, v) handler(u, s, n, v, lineno)
#else
#define HANDLER(u, s, n, v) handler(u, s, n, v)
#endif
/* Scan through stream line by line */
while (reader(line, max_line, stream) != NULL) {
#if INI_ALLOW_REALLOC
offset = strlen(line);
while (offset == max_line - 1 && line[offset - 1] != '\n') {
max_line *= 2;
if (max_line > INI_MAX_LINE) {
max_line = INI_MAX_LINE;
}
new_line = realloc(line, max_line);
if (!new_line) {
free(line);
return -2;
}
line = new_line;
if (reader(line + offset, max_line - offset, stream) == NULL) {
break;
}
if (max_line >= INI_MAX_LINE) {
break;
}
offset += strlen(line + offset);
}
#endif
lineno++;
start = line;
#if INI_ALLOW_BOM
if (lineno == 1 && (unsigned char) start[0] == 0xEF &&
(unsigned char) start[1] == 0xBB &&
(unsigned char) start[2] == 0xBF) {
start += 3;
}
#endif
start = lskip(rstrip(start));
if (*start == ';' || *start == '#') {
/* Per Python configparser, allow both ; and # comments at the
start of a line */
}
#if INI_ALLOW_MULTILINE
else if (*prev_name && *start && start > line) {
/* Non-blank line with leading whitespace, treat as continuation
of previous name's value (as per Python configparser). */
if (!HANDLER(user, section, prev_name, start) && !error) {
error = lineno;
}
}
#endif
else if (*start == '[') {
/* A "[section]" line */
end = find_chars_or_comment(start + 1, "]");
if (*end == ']') {
*end = '\0';
strncpy0(section, start + 1, sizeof(section));
*prev_name = '\0';
} else if (!error) {
/* No ']' found on section line */
error = lineno;
}
} else if (*start) {
/* Not a comment, must be a name[=:]value pair */
end = find_chars_or_comment(start, "=:");
if (*end == '=' || *end == ':') {
*end = '\0';
name = rstrip(start);
value = end + 1;
#if INI_ALLOW_INLINE_COMMENTS
end = find_chars_or_comment(value, NULL);
if (*end) {
*end = '\0';
}
#endif
value = lskip(value);
rstrip(value);
/* Valid name[=:]value pair found, call handler */
strncpy0(prev_name, name, sizeof(prev_name));
if (!HANDLER(user, section, name, value) && !error) {
error = lineno;
}
} else if (!error) {
/* No '=' or ':' found on name[=:]value line */
error = lineno;
}
}
#if INI_STOP_ON_FIRST_ERROR
if (error) {
break;
}
#endif
}
#if !INI_USE_STACK
free(line);
#endif
return error;
}
/* See documentation in header file. */
int ini_parse_file(FIL *file, ini_handler handler, void *user) {
return ini_parse_stream((ini_reader) ini_fgets, file, handler, user);
}
/* See documentation in header file. */
int ini_parse(FATFS *fs, const char *filename, ini_handler handler, void *user) {
FIL file;
int error;
FRESULT res = f_open(fs, &file, filename, FA_READ | FA_OPEN_EXISTING);
if (res != FR_OK) {
return -1;
}
error = ini_parse_file(&file, handler, user);
res = f_close(&file);
if (res != FR_OK) {
return -1;
}
return error;
}
/* An ini_reader function to read the next line from a string buffer. This
is the ini_fgets() equivalent used by ini_parse_string(). */
static char *ini_reader_string(char *str, int num, void *stream) {
ini_parse_string_ctx *ctx = (ini_parse_string_ctx *) stream;
const char *ctx_ptr = ctx->ptr;
size_t ctx_num_left = ctx->num_left;
char *strp = str;
char c;
if (ctx_num_left == 0 || num < 2) {
return NULL;
}
while (num > 1 && ctx_num_left != 0) {
c = *ctx_ptr++;
ctx_num_left--;
*strp++ = c;
if (c == '\n') {
break;
}
num--;
}
*strp = '\0';
ctx->ptr = ctx_ptr;
ctx->num_left = ctx_num_left;
return str;
}
/* See documentation in header file. */
int ini_parse_string(const char *string, ini_handler handler, void *user) {
ini_parse_string_ctx ctx;
ctx.ptr = string;
ctx.num_left = strlen(string);
return ini_parse_stream((ini_reader) ini_reader_string, &ctx, handler,
user);
}

View File

@ -1,145 +0,0 @@
/*
* SPDX-License-Identifier: BSD-3-Clause
*
* Copyright (C) 2009-2020, Ben Hoyt
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*
* Read an INI file into easy-to-access name/value pairs.
* For more info, see: https://github.com/benhoyt/inih
*/
#ifndef __INI_H__
#define __INI_H__
int ini_atoi(const char *string);
bool ini_is_true(const char *value);
/* Make this header file easier to include in C++ code */
#ifdef __cplusplus
extern "C" {
#endif
#include "file_utils.h"
/* Nonzero if ini_handler callback should accept lineno parameter. */
#ifndef INI_HANDLER_LINENO
#define INI_HANDLER_LINENO 0
#endif
/* Typedef for prototype of handler function. */
#if INI_HANDLER_LINENO
typedef int (*ini_handler) (void *user, const char *section,
const char *name, const char *value,
int lineno);
#else
typedef int (*ini_handler) (void *user, const char *section,
const char *name, const char *value);
#endif
/* Typedef for prototype of fgets-style reader function. */
typedef char * (*ini_reader) (char *str, int num, void *stream);
/* Parse given INI-style file. May have [section]s, name=value pairs
(whitespace stripped), and comments starting with ';' (semicolon). Section
is "" if name=value pair parsed before any section heading. name:value
pairs are also supported as a concession to Python's configparser.
For each name=value pair parsed, call handler function with given user
pointer as well as section, name, and value (data only valid for duration
of handler call). Handler should return nonzero on success, zero on error.
Returns 0 on success, line number of first error on parse error (doesn't
stop on first error), -1 on file open error, or -2 on memory allocation
error (only when INI_USE_STACK is zero).
*/
int ini_parse(FATFS *fs, const char *filename, ini_handler handler, void *user);
/* Same as ini_parse(), but takes a FIL* instead of filename. This doesn't
close the file when it's finished -- the caller must do that. */
int ini_parse_file(FIL *file, ini_handler handler, void *user);
/* Same as ini_parse(), but takes an ini_reader function pointer instead of
filename. Used for implementing custom or string-based I/O (see also
ini_parse_string). */
int ini_parse_stream(ini_reader reader, void *stream, ini_handler handler,
void *user);
/* Same as ini_parse(), but takes a zero-terminated string with the INI data
instead of a file. Useful for parsing INI data from a network socket or
already in memory. */
int ini_parse_string(const char *string, ini_handler handler, void *user);
/* Nonzero to allow multi-line value parsing, in the style of Python's
configparser. If allowed, ini_parse() will call the handler with the same
name for each subsequent line parsed. */
#ifndef INI_ALLOW_MULTILINE
#define INI_ALLOW_MULTILINE 1
#endif
/* Nonzero to allow a UTF-8 BOM sequence (0xEF 0xBB 0xBF) at the start of
the file. See http://code.google.com/p/inih/issues/detail?id=21 */
#ifndef INI_ALLOW_BOM
#define INI_ALLOW_BOM 1
#endif
/* Nonzero to allow inline comments (with valid inline comment characters
specified by INI_INLINE_COMMENT_PREFIXES). Set to 0 to turn off and match
Python 3.2+ configparser behaviour. */
#ifndef INI_ALLOW_INLINE_COMMENTS
#define INI_ALLOW_INLINE_COMMENTS 1
#endif
#ifndef INI_INLINE_COMMENT_PREFIXES
#define INI_INLINE_COMMENT_PREFIXES ";"
#endif
/* Nonzero to use stack for line buffer, zero to use heap (malloc/free). */
#ifndef INI_USE_STACK
#define INI_USE_STACK 1
#endif
/* Maximum line length for any line in INI file (stack or heap). Note that
this must be 3 more than the longest line (due to '\r', '\n', and '\0'). */
#ifndef INI_MAX_LINE
#define INI_MAX_LINE 200
#endif
/* Nonzero to allow heap line buffer to grow via realloc(), zero for a
fixed-size buffer of INI_MAX_LINE bytes. Only applies if INI_USE_STACK is
zero. */
#ifndef INI_ALLOW_REALLOC
#define INI_ALLOW_REALLOC 0
#endif
/* Initial size in bytes for heap line buffer. Only applies if INI_USE_STACK
is zero. */
#ifndef INI_INITIAL_ALLOC
#define INI_INITIAL_ALLOC 200
#endif
/* Stop parsing on first error (default is to keep parsing). */
#ifndef INI_STOP_ON_FIRST_ERROR
#define INI_STOP_ON_FIRST_ERROR 0
#endif
#ifdef __cplusplus
}
#endif
#endif /* __INI_H__ */

View File

@ -34,19 +34,8 @@
#include "shared/runtime/gchelper.h" #include "shared/runtime/gchelper.h"
#include "shared/runtime/softtimer.h" #include "shared/runtime/softtimer.h"
#include "shared/runtime/pyexec.h" #include "shared/runtime/pyexec.h"
#if MICROPY_HW_USB_MSC
#include "extmod/vfs.h"
#include "extmod/vfs_fat.h"
// Fresh filesystem templates.
#include "main_py.h"
#include "readme_txt.h"
#endif
#include "omv_boardconfig.h" #include "omv_boardconfig.h"
#include "usbdbg.h" #include "usbdbg.h"
#if OMV_WIFIDBG_ENABLE
#include "wifidbg.h"
#endif
#include "file_utils.h"
#include "mp_utils.h" #include "mp_utils.h"
void __attribute__((weak)) gc_collect(void) { void __attribute__((weak)) gc_collect(void) {
@ -70,37 +59,7 @@ void __attribute__((weak)) gc_collect(void) {
gc_collect_end(); gc_collect_end();
} }
#if MICROPY_VFS_FAT bool mp_exec_bootscript(const char *path, bool interruptible) {
extern void __fatal_error();
int mp_init_filesystem(fs_user_mount_t *vfs) {
FIL fp; UINT n;
uint8_t working_buf[FF_MAX_SS];
if (f_mkfs(&vfs->fatfs, FM_FAT, 0, working_buf, sizeof(working_buf)) != FR_OK) {
__fatal_error("Could not create LFS");
}
// Mark FS as OpenMV disk.
if (f_stat(&vfs->fatfs, "/.openmv_disk", NULL) != FR_OK) {
f_open(&vfs->fatfs, &fp, "/.openmv_disk", FA_WRITE | FA_CREATE_ALWAYS);
f_close(&fp);
}
// Create default main.py
f_open(&vfs->fatfs, &fp, "/main.py", FA_WRITE | FA_CREATE_ALWAYS);
f_write(&fp, fresh_main_py, sizeof(fresh_main_py) - 1 /* don't count null terminator */, &n);
f_close(&fp);
// Create readme file
f_open(&vfs->fatfs, &fp, "/README.txt", FA_WRITE | FA_CREATE_ALWAYS);
f_write(&fp, fresh_readme_txt, sizeof(fresh_readme_txt) - 1 /* don't count null terminator */, &n);
f_close(&fp);
return 0;
}
#endif
bool mp_exec_bootscript(const char *path, bool interruptible, bool wifidbg_enabled) {
nlr_buf_t nlr; nlr_buf_t nlr;
bool interrupted = false; bool interrupted = false;
@ -109,9 +68,6 @@ bool mp_exec_bootscript(const char *path, bool interruptible, bool wifidbg_enabl
if (interruptible) { if (interruptible) {
usbdbg_set_irq_enabled(true); usbdbg_set_irq_enabled(true);
usbdbg_set_script_running(true); usbdbg_set_script_running(true);
#if OMV_WIFIDBG_ENABLE
wifidbg_set_irq_enabled(wifidbg_enabled);
#endif
} }
// Parse, compile and execute the script. // Parse, compile and execute the script.
@ -124,9 +80,6 @@ bool mp_exec_bootscript(const char *path, bool interruptible, bool wifidbg_enabl
// Disable IDE interrupts // Disable IDE interrupts
usbdbg_set_irq_enabled(false); usbdbg_set_irq_enabled(false);
usbdbg_set_script_running(false); usbdbg_set_script_running(false);
#if OMV_WIFIDBG_ENABLE
wifidbg_set_irq_enabled(false);
#endif
if (interrupted) { if (interrupted) {
mp_obj_print_exception(&mp_plat_print, (mp_obj_t) nlr.ret_val); mp_obj_print_exception(&mp_plat_print, (mp_obj_t) nlr.ret_val);

View File

@ -27,6 +27,5 @@
#define __MP_UTILS_H__ #define __MP_UTILS_H__
typedef struct _fs_user_mount_t fs_user_mount_t; typedef struct _fs_user_mount_t fs_user_mount_t;
void mp_init_gc_stack(void *stack_start, void *stack_end, void *heap_start, void *heap_end, size_t stack_limit); void mp_init_gc_stack(void *stack_start, void *stack_end, void *heap_start, void *heap_end, size_t stack_limit);
int mp_init_filesystem(fs_user_mount_t *vfs); bool mp_exec_bootscript(const char *path, bool interruptible);
bool mp_exec_bootscript(const char *path, bool interruptible, bool wifidbg_enabled);
#endif // __MP_UTILS_H__ #endif // __MP_UTILS_H__

View File

@ -77,8 +77,6 @@
#include "mimxrt_hal.h" #include "mimxrt_hal.h"
int main(void) { int main(void) {
bool sdcard_detected = false;
bool sdcard_mounted = false;
bool first_soft_reset = true; bool first_soft_reset = true;
mimxrt_hal_init(); mimxrt_hal_init();
@ -159,43 +157,17 @@ soft_reset:
} }
#endif #endif
// Mount or create a fresh filesystem. // Execute _boot.py to set up the filesystem.
mp_obj_t mount_point = MP_OBJ_NEW_QSTR(MP_QSTR__slash_); pyexec_frozen_module("_boot.py", false);
#if MICROPY_PY_MACHINE_SDCARD
mimxrt_sdcard_obj_t *sdcard = &mimxrt_sdcard_objs[MICROPY_HW_SDCARD_SDMMC - 1];
if (!sdcard->state->initialized) {
mp_hal_pin_input(sdcard->pins->cd_b.pin);
sdcard_detected = !mp_hal_pin_read(sdcard->pins->cd_b.pin);
} else {
sdcard_detected = sdcard_detect(sdcard);
}
if (sdcard_detected) {
mp_obj_t args[] = { MP_OBJ_NEW_SMALL_INT(MICROPY_HW_SDCARD_SDMMC) };
mp_obj_t bdev = MP_OBJ_TYPE_GET_SLOT(&machine_sdcard_type, make_new) (&machine_sdcard_type, 1, 0, args);
if (mp_vfs_mount_and_chdir_protected(bdev, mount_point) == 0) {
mimxrt_msc_medium = &machine_sdcard_type;
sdcard_mounted = true;
}
}
#endif
if (sdcard_mounted == false) { // Set the USB medium to flash block device.
mp_obj_t bdev = MP_OBJ_TYPE_GET_SLOT(&mimxrt_flash_type, make_new) (&mimxrt_flash_type, 0, 0, NULL); mimxrt_msc_medium = &mimxrt_flash_type;
if (mp_vfs_mount_and_chdir_protected(bdev, mount_point) == 0) {
mimxrt_msc_medium = &mimxrt_flash_type;
} else {
// Create a fresh filesystem.
fs_user_mount_t *vfs = MP_OBJ_TYPE_GET_SLOT(&mp_fat_vfs_type, make_new) (&mp_fat_vfs_type, 1, 0, &bdev);
if (mp_init_filesystem(vfs) == 0) {
if (mp_vfs_mount_and_chdir_protected(bdev, mount_point) == 0) {
mimxrt_msc_medium = &mimxrt_flash_type;
}
}
}
}
// Mark the filesystem as an OpenMV storage. const char *path = "/sdcard";
file_ll_touch(".openmv_disk"); // If SD is mounted, set the USB medium to SD.
if (mp_vfs_lookup_path(path, &path) != MP_VFS_NONE) {
mimxrt_msc_medium = &machine_sdcard_type;
}
// Initialize TinyUSB after the filesystem is mounted. // Initialize TinyUSB after the filesystem is mounted.
if (!tusb_inited()) { if (!tusb_inited()) {
@ -203,11 +175,11 @@ soft_reset:
} }
// Run boot.py script. // Run boot.py script.
bool interrupted = mp_exec_bootscript("boot.py", true, false); bool interrupted = mp_exec_bootscript("boot.py", true);
// Run main.py script on first soft-reset. // Run main.py script on first soft-reset.
if (first_soft_reset && !interrupted && mp_vfs_import_stat("main.py")) { if (first_soft_reset && !interrupted && mp_vfs_import_stat("main.py")) {
mp_exec_bootscript("main.py", true, false); mp_exec_bootscript("main.py", true);
goto soft_reset_exit; goto soft_reset_exit;
} }

View File

@ -171,7 +171,6 @@ FIRM_OBJ += $(addprefix $(BUILD)/$(OMV_DIR)/alloc/, \
FIRM_OBJ += $(addprefix $(BUILD)/$(OMV_DIR)/common/, \ FIRM_OBJ += $(addprefix $(BUILD)/$(OMV_DIR)/common/, \
array.o \ array.o \
ini.o \
ringbuf.o \ ringbuf.o \
trace.o \ trace.o \
mutex.o \ mutex.o \

View File

@ -269,11 +269,11 @@ soft_reset:
#if MICROPY_VFS || MICROPY_MBFS || MICROPY_MODULE_FROZEN #if MICROPY_VFS || MICROPY_MBFS || MICROPY_MODULE_FROZEN
// Run boot.py script. // Run boot.py script.
bool interrupted = mp_exec_bootscript("boot.py", true, false); bool interrupted = mp_exec_bootscript("boot.py", true);
// Run main.py script on first soft-reset. // Run main.py script on first soft-reset.
if (first_soft_reset && !interrupted && mp_vfs_import_stat("main.py")) { if (first_soft_reset && !interrupted && mp_vfs_import_stat("main.py")) {
mp_exec_bootscript("main.py", true, false); mp_exec_bootscript("main.py", true);
goto soft_reset_exit; goto soft_reset_exit;
} }
#endif #endif

View File

@ -154,7 +154,6 @@ FIRM_OBJ += $(addprefix $(BUILD)/$(OMV_DIR)/alloc/, \
FIRM_OBJ += $(addprefix $(BUILD)/$(OMV_DIR)/common/, \ FIRM_OBJ += $(addprefix $(BUILD)/$(OMV_DIR)/common/, \
array.o \ array.o \
ini.o \
ringbuf.o \ ringbuf.o \
trace.o \ trace.o \
mutex.o \ mutex.o \

View File

@ -189,14 +189,7 @@ soft_reset:
#endif #endif
// Execute _boot.py to set up the filesystem. // Execute _boot.py to set up the filesystem.
#if MICROPY_VFS_FAT && MICROPY_HW_USB_MSC
pyexec_frozen_module("_boot_fat.py", false);
#else
pyexec_frozen_module("_boot.py", false); pyexec_frozen_module("_boot.py", false);
#endif
// Mark the filesystem as an OpenMV storage.
file_ll_touch(".openmv_disk");
// Initialize TinyUSB after the filesystem has been mounted. // Initialize TinyUSB after the filesystem has been mounted.
if (!tusb_inited()) { if (!tusb_inited()) {
@ -209,11 +202,11 @@ soft_reset:
} }
// Run boot.py script. // Run boot.py script.
bool interrupted = mp_exec_bootscript("boot.py", true, false); bool interrupted = mp_exec_bootscript("boot.py", true);
// Run main.py script on first soft-reset. // Run main.py script on first soft-reset.
if (first_soft_reset && !interrupted && mp_vfs_import_stat("main.py")) { if (first_soft_reset && !interrupted && mp_vfs_import_stat("main.py")) {
mp_exec_bootscript("main.py", true, false); mp_exec_bootscript("main.py", true);
goto soft_reset_exit; goto soft_reset_exit;
} }

View File

@ -122,7 +122,6 @@ target_sources(${MICROPY_TARGET} PRIVATE
${TOP_DIR}/${OMV_DIR}/alloc/unaligned_memcpy.c ${TOP_DIR}/${OMV_DIR}/alloc/unaligned_memcpy.c
${TOP_DIR}/${OMV_DIR}/common/array.c ${TOP_DIR}/${OMV_DIR}/common/array.c
${TOP_DIR}/${OMV_DIR}/common/ini.c
${TOP_DIR}/${OMV_DIR}/common/ringbuf.c ${TOP_DIR}/${OMV_DIR}/common/ringbuf.c
${TOP_DIR}/${OMV_DIR}/common/trace.c ${TOP_DIR}/${OMV_DIR}/common/trace.c
${TOP_DIR}/${OMV_DIR}/common/mutex.c ${TOP_DIR}/${OMV_DIR}/common/mutex.c

View File

@ -21,24 +21,19 @@
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE. * THE SOFTWARE.
* *
* main function. * STM32 main function.
*/ */
#include <stdio.h> #include <stdio.h>
#include <stdbool.h> #include <stdbool.h>
#include <string.h> #include <string.h>
#include STM32_HAL_H #include STM32_HAL_H
#include "mpconfig.h" #include "mpconfig.h"
#include "systick.h" #include "systick.h"
#include "pendsv.h" #include "pendsv.h"
#include "qstr.h"
#include "nlr.h" #include "nlr.h"
#include "lexer.h"
#include "parse.h"
#include "compile.h"
#include "runtime.h" #include "runtime.h"
#include "obj.h" #include "obj.h"
#include "objmodule.h"
#include "objstr.h"
#include "gc.h" #include "gc.h"
#include "stackctrl.h" #include "stackctrl.h"
#include "gccollect.h" #include "gccollect.h"
@ -46,17 +41,6 @@
#include "pin.h" #include "pin.h"
#include "usb.h" #include "usb.h"
#include "rtc.h" #include "rtc.h"
#include "storage.h"
#include "sdcard.h"
#include "modmachine.h"
#include "extmod/modnetwork.h"
#include "extmod/modmachine.h"
#include "extmod/vfs.h"
#include "extmod/vfs_fat.h"
#include "shared/runtime/pyexec.h"
#include "shared/readline/readline.h"
#include "irq.h" #include "irq.h"
#include "rng.h" #include "rng.h"
#include "led.h" #include "led.h"
@ -67,19 +51,41 @@
#include "can.h" #include "can.h"
#include "extint.h" #include "extint.h"
#include "servo.h" #include "servo.h"
#include "sdcard.h"
#include "modmachine.h"
#include "extmod/modmachine.h"
#if MICROPY_PY_NETWORK
#include "extmod/modnetwork.h"
#endif
#if MICROPY_PY_BLUETOOTH
#include "mpbthciport.h"
#include "extmod/modbluetooth.h"
#endif
#if MICROPY_PY_LWIP
#include "lwip/init.h"
#include "lwip/apps/mdns.h"
#if MICROPY_PY_NETWORK_CYW43
#include "lib/cyw43-driver/src/cyw43.h"
#endif
#endif
#include "extmod/vfs.h"
#include "extmod/vfs_fat.h"
#include "shared/runtime/pyexec.h"
#include "shared/readline/readline.h"
#include "omv_boardconfig.h"
#include "omv_gpio.h"
#include "omv_i2c.h"
#include "omv_csi.h"
#include "mp_utils.h"
#include "framebuffer.h"
#include "usbdbg.h" #include "usbdbg.h"
#include "wifidbg.h"
#include "sdram.h" #include "sdram.h"
#include "fb_alloc.h" #include "fb_alloc.h"
#include "dma_alloc.h" #include "dma_alloc.h"
#include "file_utils.h" #include "file_utils.h"
#include "usbd_core.h"
#include "usbd_desc.h"
#include "usbd_cdc_msc_hid.h"
#include "usbd_cdc_interface.h"
#include "py_image.h" #include "py_image.h"
#include "py_fir.h" #include "py_fir.h"
#include "py_tv.h" #include "py_tv.h"
@ -87,32 +93,7 @@
#include "py_imu.h" #include "py_imu.h"
#include "py_audio.h" #include "py_audio.h"
#include "framebuffer.h"
#include "ini.h"
#include "omv_boardconfig.h"
#include "omv_gpio.h"
#include "omv_i2c.h"
#include "omv_csi.h"
#if MICROPY_PY_LWIP
#include "lwip/init.h"
#include "lwip/apps/mdns.h"
#include "lib/cyw43-driver/src/cyw43.h"
#endif
#if MICROPY_PY_BLUETOOTH
#include "extmod/modbluetooth.h"
#include "mpbthciport.h"
#endif
#include "extmod/vfs.h"
#include "extmod/vfs_fat.h"
#include "mp_utils.h"
int errno; int errno;
extern char _vfs_buf[];
static fs_user_mount_t *vfs_fat = (fs_user_mount_t *) &_vfs_buf;
#if MICROPY_PY_THREAD #if MICROPY_PY_THREAD
pyb_thread_t pyb_thread_main; pyb_thread_t pyb_thread_main;
#endif #endif
@ -131,24 +112,6 @@ void flash_error(int n) {
} }
void NORETURN __fatal_error(const char *msg) { void NORETURN __fatal_error(const char *msg) {
// Check if any storage has been initialized
// before attempting to create the error log.
if (pyb_usb_storage_medium) {
FIL fp;
if (f_open(&vfs_fat->fatfs, &fp, "ERROR.LOG",
FA_WRITE | FA_CREATE_ALWAYS) == FR_OK) {
UINT bytes;
const char *hdr = "FATAL ERROR:\n";
file_ll_write(&fp, hdr, strlen(hdr), &bytes);
file_ll_write(&fp, msg, strlen(msg), &bytes);
file_ll_close(&fp);
storage_flush();
// Initialize the USB device if it's not already initialize to allow
// the host to mount the filesystem and access the error log.
pyb_usb_dev_init(pyb_usb_dev_detect(), MICROPY_HW_USB_VID,
MICROPY_HW_USB_PID_CDC_MSC, USBD_MODE_CDC_MSC, 0, NULL, NULL);
}
}
for (uint i = 0;;) { for (uint i = 0;;) {
led_toggle(((i++) & 3)); led_toggle(((i++) & 3));
for (volatile uint delay = 0; delay < 500000; delay++) { for (volatile uint delay = 0; delay < 500000; delay++) {
@ -179,65 +142,10 @@ void NORETURN __stack_chk_fail(void) {
} }
#endif #endif
typedef struct openmv_config {
bool wifidbg;
wifidbg_config_t wifidbg_config;
} openmv_config_t;
int ini_handler_callback(void *user, const char *section, const char *name, const char *value) {
openmv_config_t *openmv_config = (openmv_config_t *) user;
#define MATCH(s, n) ((strcmp(section, (s)) == 0) && (strcmp(name, (n)) == 0))
if (MATCH("BoardConfig", "REPLUart")) {
if (ini_is_true(value)) {
mp_obj_t args[2] = {
MP_OBJ_NEW_SMALL_INT(3), // UART Port
MP_OBJ_NEW_SMALL_INT(115200) // Baud Rate
};
MP_STATE_PORT(pyb_stdio_uart) = MP_OBJ_TYPE_GET_SLOT(&machine_uart_type, make_new) (
(mp_obj_t) &machine_uart_type, MP_ARRAY_SIZE(args), 0, args);
uart_attach_to_repl(MP_STATE_PORT(pyb_stdio_uart), true);
}
} else if (MATCH("BoardConfig", "WiFiDebug")) {
openmv_config->wifidbg = ini_is_true(value);
} else if (MATCH("WiFiConfig", "Mode")) {
openmv_config->wifidbg_config.mode = ini_atoi(value);
} else if (MATCH("WiFiConfig", "ClientSSID")) {
strncpy(openmv_config->wifidbg_config.client_ssid, value, WINC_MAX_SSID_LEN);
} else if (MATCH("WiFiConfig", "ClientKey")) {
strncpy(openmv_config->wifidbg_config.client_key, value, WINC_MAX_PSK_LEN);
} else if (MATCH("WiFiConfig", "ClientSecurity")) {
openmv_config->wifidbg_config.client_security = ini_atoi(value);
} else if (MATCH("WiFiConfig", "ClientChannel")) {
openmv_config->wifidbg_config.client_channel = ini_atoi(value);
} else if (MATCH("WiFiConfig", "AccessPointSSID")) {
strncpy(openmv_config->wifidbg_config.access_point_ssid, value, WINC_MAX_SSID_LEN);
} else if (MATCH("WiFiConfig", "AccessPointKey")) {
strncpy(openmv_config->wifidbg_config.access_point_key, value, WINC_MAX_PSK_LEN);
} else if (MATCH("WiFiConfig", "AccessPointSecurity")) {
openmv_config->wifidbg_config.access_point_security = ini_atoi(value);
} else if (MATCH("WiFiConfig", "AccessPointChannel")) {
openmv_config->wifidbg_config.access_point_channel = ini_atoi(value);
} else if (MATCH("WiFiConfig", "BoardName")) {
strncpy(openmv_config->wifidbg_config.board_name, value, WINC_MAX_BOARD_NAME_LEN);
} else {
return 0;
}
return 1;
#undef MATCH
}
int main(void) { int main(void) {
#if MICROPY_HW_SDRAM_SIZE #if MICROPY_HW_SDRAM_SIZE
bool sdram_ok = false; bool sdram_ok = false;
#endif #endif
#if MICROPY_HW_ENABLE_SDCARD
bool sdcard_mounted = false;
#endif
bool first_soft_reset = true; bool first_soft_reset = true;
#if defined(MICROPY_BOARD_EARLY_INIT) #if defined(MICROPY_BOARD_EARLY_INIT)
@ -274,12 +182,9 @@ int main(void) {
__enable_irq(); __enable_irq();
soft_reset: soft_reset:
#if defined(MICROPY_HW_LED4) for (size_t i = 0; i < 4; i++) {
led_state(LED_IR, 0); led_state(i + 1, 0);
#endif }
led_state(LED_RED, 1);
led_state(LED_GREEN, 1);
led_state(LED_BLUE, 1);
machine_init(); machine_init();
@ -294,8 +199,7 @@ soft_reset:
// Micro Python init // Micro Python init
mp_init(); mp_init();
// Initialise low-level sub-systems. Here we need to do the very basic // Initialise low-level sub-systems.
// things like zeroing out memory and resetting any of the sub-systems.
py_fir_init0(); py_fir_init0();
#if MICROPY_PY_TV #if MICROPY_PY_TV
py_tv_init0(); py_tv_init0();
@ -317,7 +221,9 @@ soft_reset:
fb_alloc_init0(); fb_alloc_init0();
omv_gpio_init0(); omv_gpio_init0();
framebuffer_init0(); framebuffer_init0();
#if MICROPY_PY_CSI
omv_csi_init0(); omv_csi_init0();
#endif
dma_alloc_init0(); dma_alloc_init0();
#ifdef IMLIB_ENABLE_IMAGE_FILE_IO #ifdef IMLIB_ENABLE_IMAGE_FILE_IO
file_buffer_init0(); file_buffer_init0();
@ -359,11 +265,12 @@ soft_reset:
pyb_usb_init0(); pyb_usb_init0();
MP_STATE_PORT(pyb_stdio_uart) = NULL; MP_STATE_PORT(pyb_stdio_uart) = NULL;
// Initialize the csi and check the result after #if MICROPY_PY_CSI
// mounting the file-system to log errors (if any). // Initialize the csi.
if (first_soft_reset) { if (first_soft_reset) {
omv_csi_init(); omv_csi_init();
} }
#endif
#if MICROPY_PY_IMU #if MICROPY_PY_IMU
py_imu_init(); py_imu_init();
@ -373,93 +280,18 @@ soft_reset:
mod_network_init(); mod_network_init();
#endif #endif
#if MICROPY_HW_ENABLE_SDCARD // Execute _boot.py to set up the filesystem.
// Initialize storage pyexec_frozen_module("_boot.py", false);
if (sdcard_is_present()) {
// Init the vfs object
vfs_fat->blockdev.flags = 0;
sdcard_init_vfs(vfs_fat, 0);
// Try to mount the SD card // Set the USB medium to flash block device.
FRESULT res = f_mount(&vfs_fat->fatfs);
if (res != FR_OK) {
sdcard_mounted = false;
} else {
sdcard_mounted = true;
// Set USB medium to SD
pyb_usb_storage_medium = PYB_USB_STORAGE_MEDIUM_SDCARD;
}
}
#endif
#if MICROPY_HW_ENABLE_SDCARD
if (sdcard_mounted == false) {
#endif
storage_init();
// init the vfs object
vfs_fat->blockdev.flags = 0;
pyb_flash_init_vfs(vfs_fat);
// Try to mount the flash
FRESULT res = f_mount(&vfs_fat->fatfs);
if (res == FR_NO_FILESYSTEM) {
// Create a fresh filesystem.
led_state(LED_RED, 1);
mp_init_filesystem(vfs_fat);
led_state(LED_RED, 0);
// Flush storage
storage_flush();
} else if (res != FR_OK) {
__fatal_error("Could not access LFS\n");
}
// Set USB medium to flash
pyb_usb_storage_medium = PYB_USB_STORAGE_MEDIUM_FLASH; pyb_usb_storage_medium = PYB_USB_STORAGE_MEDIUM_FLASH;
#if MICROPY_HW_ENABLE_SDCARD
}
#if MICROPY_HW_HAS_FLASH
else {
// The storage should always be initialized on boards that have
// an external flash, to make sure the flash is memory-mapped.
storage_init();
}
#endif
#endif
// Mount the storage device (there should be no other devices mounted at this point) const char *path = "/sdcard";
// we allocate this structure on the heap because vfs->next is a root pointer. // If SD is mounted, set the USB medium to SD.
mp_vfs_mount_t *vfs = m_new_obj_maybe(mp_vfs_mount_t); if (mp_vfs_lookup_path(path, &path) != MP_VFS_NONE) {
if (vfs == NULL) { pyb_usb_storage_medium = PYB_USB_STORAGE_MEDIUM_SDCARD;
__fatal_error("Failed to alloc memory for vfs mount\n");
} }
vfs->str = "/";
vfs->len = 1;
vfs->obj = MP_OBJ_FROM_PTR(vfs_fat);
vfs->next = NULL;
MP_STATE_VM(vfs_mount_table) = vfs;
MP_STATE_PORT(vfs_cur) = vfs;
// Mark the filesystem as an OpenMV storage.
file_ll_touch("/.openmv_disk");
// Parse OpenMV configuration file.
openmv_config_t openmv_config;
memset(&openmv_config, 0, sizeof(openmv_config));
ini_parse(&vfs_fat->fatfs, "/openmv.config", ini_handler_callback, &openmv_config);
// Init wifi debugging if enabled and on first soft-reset only.
#if OMV_WIFIDBG_ENABLE && MICROPY_PY_WINC1500
if (openmv_config.wifidbg == true &&
wifidbg_init(&openmv_config.wifidbg_config) != 0) {
openmv_config.wifidbg = false;
}
#else
openmv_config.wifidbg = false;
#endif
// Init USB device to default setting if it was not already configured // Init USB device to default setting if it was not already configured
if (!(pyb_usb_flags & PYB_USB_FLAG_USB_MODE_CALLED)) { if (!(pyb_usb_flags & PYB_USB_FLAG_USB_MODE_CALLED)) {
pyb_usb_dev_init(pyb_usb_dev_detect(), MICROPY_HW_USB_VID, pyb_usb_dev_init(pyb_usb_dev_detect(), MICROPY_HW_USB_VID,
@ -473,83 +305,57 @@ else {
} }
#endif #endif
// Turn boot-up LEDs off
led_state(LED_RED, 0);
led_state(LED_GREEN, 0);
led_state(LED_BLUE, 0);
// Run boot.py script. // Run boot.py script.
bool interrupted = mp_exec_bootscript("boot.py", true, false); bool interrupted = mp_exec_bootscript("boot.py", true);
// Run main.py script on first soft-reset. // Run main.py script on first soft-reset.
if (first_soft_reset && !interrupted && mp_vfs_import_stat("main.py")) { if (first_soft_reset && !interrupted && mp_vfs_import_stat("main.py")) {
mp_exec_bootscript("main.py", true, openmv_config.wifidbg); mp_exec_bootscript("main.py", true);
goto soft_reset_exit; goto soft_reset_exit;
} }
do { // If there's no script ready, just re-exec REPL
usbdbg_init(); while (!usbdbg_script_ready()) {
nlr_buf_t nlr;
if (openmv_config.wifidbg == true) { if (nlr_push(&nlr) == 0) {
// Need to reinit imlib in WiFi debug mode. // enable IDE interrupt
imlib_deinit_all(); usbdbg_set_irq_enabled(true);
imlib_init_all();
}
// If there's no script ready, just re-exec REPL // run REPL
while (!usbdbg_script_ready()) { if (pyexec_mode_kind == PYEXEC_MODE_RAW_REPL) {
nlr_buf_t nlr; if (pyexec_raw_repl() != 0) {
break;
if (nlr_push(&nlr) == 0) {
// enable IDE interrupt
usbdbg_set_irq_enabled(true);
#if OMV_WIFIDBG_ENABLE && MICROPY_PY_WINC1500
wifidbg_set_irq_enabled(openmv_config.wifidbg);
#endif
// run REPL
if (pyexec_mode_kind == PYEXEC_MODE_RAW_REPL) {
if (pyexec_raw_repl() != 0) {
break;
}
} else {
if (pyexec_friendly_repl() != 0) {
break;
}
} }
nlr_pop();
}
}
if (usbdbg_script_ready()) {
nlr_buf_t nlr;
if (nlr_push(&nlr) == 0) {
// Enable IDE interrupts
usbdbg_set_irq_enabled(true);
#if OMV_WIFIDBG_ENABLE && MICROPY_PY_WINC1500
wifidbg_set_irq_enabled(openmv_config.wifidbg);
#endif
// Execute the script.
pyexec_str(usbdbg_get_script(), true);
// Disable IDE interrupts
usbdbg_set_irq_enabled(false);
nlr_pop();
} else { } else {
mp_obj_print_exception(MP_PYTHON_PRINTER, (mp_obj_t) nlr.ret_val); if (pyexec_friendly_repl() != 0) {
break;
}
} }
}
} while (openmv_config.wifidbg == true); nlr_pop();
}
}
if (usbdbg_script_ready()) {
nlr_buf_t nlr;
if (nlr_push(&nlr) == 0) {
// Enable IDE interrupts
usbdbg_set_irq_enabled(true);
// Execute the script.
pyexec_str(usbdbg_get_script(), true);
// Disable IDE interrupts
usbdbg_set_irq_enabled(false);
nlr_pop();
} else {
mp_obj_print_exception(MP_PYTHON_PRINTER, (mp_obj_t) nlr.ret_val);
}
}
soft_reset_exit: soft_reset_exit:
// soft reset // soft reset
mp_printf(MP_PYTHON_PRINTER, "MPY: soft reboot\n"); mp_printf(MP_PYTHON_PRINTER, "MPY: soft reboot\n");
// Flush filesystem storage.
storage_flush();
#if MICROPY_PY_LWIP #if MICROPY_PY_LWIP
systick_disable_dispatch(SYSTICK_DISPATCH_LWIP); systick_disable_dispatch(SYSTICK_DISPATCH_LWIP);
#endif #endif

View File

@ -33,5 +33,6 @@
#define MICROPY_ENABLE_VM_ABORT (1) #define MICROPY_ENABLE_VM_ABORT (1)
#define MICROPY_GC_SPLIT_HEAP (1) #define MICROPY_GC_SPLIT_HEAP (1)
#define MICROPY_PY_VFS (1)
#define MICROPY_PY_SOCKET_EXTENDED_STATE (1) #define MICROPY_PY_SOCKET_EXTENDED_STATE (1)
#define MICROPY_BANNER_NAME_AND_VERSION "OpenMV " OPENMV_GIT_TAG "; MicroPython " MICROPY_GIT_TAG #define MICROPY_BANNER_NAME_AND_VERSION "OpenMV " OPENMV_GIT_TAG "; MicroPython " MICROPY_GIT_TAG

View File

@ -113,7 +113,6 @@ OMV_CFLAGS += -I$(TOP_DIR)/$(OMV_DIR)/common/
OMV_CFLAGS += -I$(TOP_DIR)/$(OMV_DIR)/imlib/ OMV_CFLAGS += -I$(TOP_DIR)/$(OMV_DIR)/imlib/
OMV_CFLAGS += -I$(TOP_DIR)/$(OMV_DIR)/modules/ OMV_CFLAGS += -I$(TOP_DIR)/$(OMV_DIR)/modules/
OMV_CFLAGS += -I$(TOP_DIR)/$(OMV_DIR)/sensors/ OMV_CFLAGS += -I$(TOP_DIR)/$(OMV_DIR)/sensors/
OMV_CFLAGS += -I$(TOP_DIR)/$(OMV_DIR)/templates/
OMV_CFLAGS += -I$(TOP_DIR)/$(OMV_DIR)/ports/$(PORT)/ OMV_CFLAGS += -I$(TOP_DIR)/$(OMV_DIR)/ports/$(PORT)/
OMV_CFLAGS += -I$(TOP_DIR)/$(OMV_DIR)/ports/$(PORT)/modules/ OMV_CFLAGS += -I$(TOP_DIR)/$(OMV_DIR)/ports/$(PORT)/modules/
@ -190,7 +189,6 @@ FIRM_OBJ += $(addprefix $(BUILD)/$(OMV_DIR)/alloc/, \
FIRM_OBJ += $(addprefix $(BUILD)/$(OMV_DIR)/common/, \ FIRM_OBJ += $(addprefix $(BUILD)/$(OMV_DIR)/common/, \
array.o \ array.o \
ini.o \
ringbuf.o \ ringbuf.o \
trace.o \ trace.o \
mutex.o \ mutex.o \

View File

@ -1,290 +0,0 @@
/*
* SPDX-License-Identifier: MIT
*
* Copyright (C) 2013-2024 OpenMV, LLC.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*
* WiFi debugger.
*/
#include "omv_boardconfig.h"
#if OMV_WIFIDBG_ENABLE && MICROPY_PY_WINC1500
#include <string.h>
#include <stdint.h>
#include <stdbool.h>
#include <errno.h>
#include "py/mphal.h"
#include "pendsv.h"
#include "systick.h"
#include "usb.h"
#include "winc.h"
#include "socket/include/socket.h"
#include "driver/include/m2m_wifi.h"
#include "usbdbg.h"
#include "omv_csi.h"
#include "framebuffer.h"
#include "wifidbg.h"
#include STM32_HAL_H
#ifndef WIFIDBG_MIN
#define WIFIDBG_MIN(x, y) ((x) < (y) ? (x) : (y))
#endif
#define WIFIDBG_BCAST_ADDR ((uint8_t [4]) {255, 255, 255, 255})
#define WIFIDBG_BCAST_PORT (0xABD1)
#define WIFIDBG_SERVER_ADDR ((uint8_t [4]) {192, 168, 1, 1})
#define WIFIDBG_SERVER_PORT (9000)
#define WIFIDBG_BUFFER_SIZE (SOCKET_BUFFER_MAX_LENGTH)
#define WIFIDBG_BCAST_STRING "%d.%d.%d.%d:%d:%s"
#define WIFIDBG_BCAST_STRING_SIZE 4 + 4 + 4 + 4 + 6 + WINC_MAX_BOARD_NAME_LEN + 1
#define WIFIDBG_BCAST_INTERVAL_MS (1000)
#define WIFIDBG_POLL_INTERVAL_MS (10)
#define WIFIDBG_SOCKET_TIMEOUT(x) (x == -ETIMEDOUT || x == SOCK_ERR_TIMEOUT)
typedef struct wifidbg {
int client_fd;
int server_fd;
int bcast_fd;
uint32_t last_bcast;
uint32_t last_dispatch;
uint8_t ipaddr[WINC_IPV4_ADDR_LEN];
char bcast_packet[WIFIDBG_BCAST_STRING_SIZE];
winc_socket_buf_t sockbuf;
uint8_t *buf;
} wifidbg_t;
static wifidbg_t wifidbg;
void wifidbg_close_sockets(wifidbg_t *wifidbg) {
winc_socket_close(wifidbg->client_fd);
winc_socket_close(wifidbg->server_fd);
winc_socket_close(wifidbg->bcast_fd);
wifidbg->client_fd = -1;
wifidbg->server_fd = -1;
wifidbg->bcast_fd = -1;
}
int wifidbg_broadcast(wifidbg_t *wifidbg) {
if ((systick_current_millis() - wifidbg->last_bcast) > WIFIDBG_BCAST_INTERVAL_MS) {
MAKE_SOCKADDR(bcast_sockaddr, WIFIDBG_BCAST_ADDR, WIFIDBG_BCAST_PORT);
if (winc_socket_sendto(wifidbg->bcast_fd, (uint8_t *) wifidbg->bcast_packet,
strlen(wifidbg->bcast_packet) + 1, &bcast_sockaddr, 10) < 0) {
return -1;
}
wifidbg->last_bcast = systick_current_millis();
}
return 0;
}
static uint32_t dbg_write(const void *buf, uint32_t len) {
memcpy(wifidbg.buf, buf, len);
return len;
}
static uint32_t dbg_read(void *buf, uint32_t len) {
memcpy(buf, wifidbg.buf, len);
return len;
}
void wifidbg_pendsv_callback(void) {
int ret = 0;
uint32_t request = 0;
uint8_t buf[WIFIDBG_BUFFER_SIZE];
// Disable systick dispatch
wifidbg_set_irq_enabled(false);
if (wifidbg.bcast_fd < 0) {
// Create broadcast socket.
MAKE_SOCKADDR(bcast_sockaddr, WIFIDBG_BCAST_ADDR, WIFIDBG_BCAST_PORT);
if ((wifidbg.bcast_fd = winc_socket_socket(SOCK_DGRAM)) < 0) {
goto exit_dispatch_error;
}
if ((ret = winc_socket_bind(wifidbg.bcast_fd, &bcast_sockaddr)) < 0) {
goto exit_dispatch_error;
}
}
if (wifidbg.server_fd < 0) {
// Create server socket
MAKE_SOCKADDR(server_sockaddr, wifidbg.ipaddr, WIFIDBG_SERVER_PORT);
if ((wifidbg.server_fd = winc_socket_socket(SOCK_STREAM)) < 0) {
goto exit_dispatch_error;
}
if ((ret = winc_socket_bind(wifidbg.server_fd, &server_sockaddr)) < 0) {
goto exit_dispatch_error;
}
if ((ret = winc_socket_listen(wifidbg.server_fd, 1)) < 0) {
goto exit_dispatch_error;
}
}
if (wifidbg.client_fd < 0) {
wifidbg.sockbuf.idx = 0;
wifidbg.sockbuf.size = 0;
sockaddr client_sockaddr;
// Try to connect to a client
ret = winc_socket_accept(wifidbg.server_fd, &client_sockaddr, &wifidbg.client_fd, 10);
if (WIFIDBG_SOCKET_TIMEOUT(ret)) {
// Timeout, broadcast another message to the IDE.
wifidbg.client_fd = -1;
ret = wifidbg_broadcast(&wifidbg);
}
if (ret < 0) {
// Error on server socket, close sockets and exit.
goto exit_dispatch_error;
}
goto exit_dispatch;
}
uint8_t cmdbuf[6];
// We have a connected client
ret = winc_socket_recv(wifidbg.client_fd, cmdbuf, 6, &wifidbg.sockbuf, 5);
if (WIFIDBG_SOCKET_TIMEOUT(ret)) {
goto exit_dispatch;
} else if (ret < 0 || ret != 6 || cmdbuf[0] != 0x30) {
goto exit_dispatch_error;
}
// Process the request command.
request = cmdbuf[1];
uint32_t xfer_length = *((uint32_t *) (cmdbuf + 2));
usbdbg_control(NULL, request, xfer_length);
wifidbg.buf = buf;
while (xfer_length) {
if (request & 0x80) {
// Device-to-host data phase
int bytes = WIFIDBG_MIN(xfer_length, WIFIDBG_BUFFER_SIZE);
xfer_length -= bytes;
usbdbg_data_in(bytes, dbg_write);
if ((ret = winc_socket_send(wifidbg.client_fd, wifidbg.buf, bytes, 500)) < 0) {
goto exit_dispatch_error;
}
} else {
// Host-to-device data phase
int bytes = WIFIDBG_MIN(xfer_length, WIFIDBG_BUFFER_SIZE);
if ((ret = winc_socket_recv(wifidbg.client_fd, wifidbg.buf, bytes, &wifidbg.sockbuf, 500)) < 0) {
goto exit_dispatch_error;
}
xfer_length -= ret;
usbdbg_data_out(ret, dbg_read);
}
}
goto exit_dispatch;
exit_dispatch_error:
wifidbg_close_sockets(&wifidbg);
exit_dispatch:
if (usbdbg_get_irq_enabled()) {
// Re-enable Systick dispatch if IDE interrupts are still enabled.
wifidbg_set_irq_enabled(true);
}
return;
}
void wifidbg_systick_callback(uint32_t ticks_ms) {
extern int usb_cdc_debug_mode_enabled();
if (usb_cdc_debug_mode_enabled() == false &&
(ticks_ms - wifidbg.last_dispatch) > WIFIDBG_POLL_INTERVAL_MS) {
pendsv_schedule_dispatch(PENDSV_DISPATCH_WINC, wifidbg_pendsv_callback);
wifidbg.last_dispatch = systick_current_millis();
}
}
int wifidbg_init(wifidbg_config_t *config) {
memset(&wifidbg, 0, sizeof(wifidbg_t));
wifidbg.client_fd = -1;
wifidbg.server_fd = -1;
wifidbg.bcast_fd = -1;
if (!config->mode) {
// STA Mode
// Initialize WiFi in STA mode.
if (winc_init(WINC_MODE_STA) != 0) {
return -1;
}
// Connect to network.
if (winc_connect(config->client_ssid,
config->client_security,
config->client_key,
config->client_channel) != 0) {
return -2;
}
winc_ifconfig_t ifconfig;
if (winc_ifconfig(&ifconfig, false) < 0) {
return -3;
}
memcpy(wifidbg.ipaddr, ifconfig.ip_addr, WINC_IPV4_ADDR_LEN);
} else {
// AP Mode
// Initialize WiFi in AP mode.
if (winc_init(WINC_MODE_AP) != 0) {
return -1;
}
// Start WiFi in AP mode.
if (winc_start_ap(config->access_point_ssid,
config->access_point_security,
config->access_point_key,
config->access_point_channel) != 0) {
return -2;
}
memcpy(wifidbg.ipaddr, WIFIDBG_SERVER_ADDR, WINC_IPV4_ADDR_LEN);
}
snprintf(wifidbg.bcast_packet, WIFIDBG_BCAST_STRING_SIZE, WIFIDBG_BCAST_STRING,
wifidbg.ipaddr[0], wifidbg.ipaddr[1], wifidbg.ipaddr[2], wifidbg.ipaddr[3],
WIFIDBG_SERVER_PORT, config->board_name);
return 0;
}
void wifidbg_set_irq_enabled(bool enable) {
if (enable) {
// Re-enable Systick dispatch.
systick_enable_dispatch(SYSTICK_DISPATCH_WINC, wifidbg_systick_callback);
} else {
systick_disable_dispatch(SYSTICK_DISPATCH_WINC);
}
}
#endif // OMV_WIFIDBG_ENABLE && MICROPY_PY_WINC1500
// Old timer dispatch, will be removed.
void wifidbg_dispatch() {
}

View File

@ -1,44 +0,0 @@
/*
* SPDX-License-Identifier: MIT
*
* Copyright (C) 2013-2024 OpenMV, LLC.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*
* WiFi debugger.
*/
#ifndef __WIFI_DBG_H__
#define __WIFI_DBG_H__
#include "winc.h"
typedef struct wifidbg_config {
winc_mode_t mode;
winc_security_t client_security, access_point_security;
char client_key[WINC_MAX_PSK_LEN + 1], access_point_key[WINC_MAX_PSK_LEN + 1];
char client_ssid[WINC_MAX_SSID_LEN + 1], access_point_ssid[WINC_MAX_SSID_LEN + 1];
uint8_t client_channel, access_point_channel;
char board_name[WINC_MAX_BOARD_NAME_LEN + 1];
} wifidbg_config_t;
void wifidbg_dispatch();
void wifidbg_pendsv_callback(void);
void wifidbg_systick_callback(uint32_t ticks_ms);
int wifidbg_init(wifidbg_config_t *config);
void wifidbg_set_irq_enabled(bool enable);
#endif /* __WIFIDBG_H__ */

View File

@ -1,15 +0,0 @@
static const char fresh_main_py[] =
"# main.py -- put your code here!\n"
"import pyb, time\n"
"led = pyb.LED(3)\n"
"usb = pyb.USB_VCP()\n"
"while (usb.isconnected()==False):\n"
" led.on()\n"
" time.sleep_ms(150)\n"
" led.off()\n"
" time.sleep_ms(100)\n"
" led.on()\n"
" time.sleep_ms(150)\n"
" led.off()\n"
" time.sleep_ms(600)\n"
;

View File

@ -1,15 +0,0 @@
static const char fresh_readme_txt[] =
"Thank you for supporting the OpenMV project!\r\n"
"\r\n"
"To download the IDE, please visit:\r\n"
"https://openmv.io/pages/download\r\n"
"\r\n"
"For tutorials and documentation, please visit:\r\n"
"http://docs.openmv.io/\r\n"
"\r\n"
"For technical support and projects, please visit the forums:\r\n"
"http://forums.openmv.io/\r\n"
"\r\n"
"Please use github to report bugs and issues:\r\n"
"https://github.com/openmv/openmv\r\n"
;