mirror of
https://github.com/mytechnotalent/Embedded-Hacking.git
synced 2026-10-09 17:34:04 +02:00
Initial commit
This commit is contained in:
commit
ea7fa10403
499 files changed
+172655
No files matched your search
@@ -0,0 +1,12 @@
|
|||||||
|
*.c linguist-detectable=true
|
||||||
|
*.cmake linguist-detectable=false
|
||||||
|
*.py linguist-detectable=false
|
||||||
|
*.txt linguist-detectable=false
|
||||||
|
*.json linguist-detectable=false
|
||||||
|
*.ps1 linguist-detectable=false
|
||||||
|
|
||||||
|
# Line endings: store LF in the repository; check out LF everywhere except the
|
||||||
|
# Windows PowerShell scripts, which stay CRLF. Prevents CRLF<->LF churn.
|
||||||
|
* text=auto eol=lf
|
||||||
|
*.ps1 text eol=crlf
|
||||||
|
|
||||||
+83
@@ -0,0 +1,83 @@
|
|||||||
|
# Prerequisites
|
||||||
|
*.d
|
||||||
|
|
||||||
|
# Object files
|
||||||
|
*.o
|
||||||
|
*.ko
|
||||||
|
*.obj
|
||||||
|
*.elf
|
||||||
|
|
||||||
|
# Linker output
|
||||||
|
*.ilk
|
||||||
|
*.map
|
||||||
|
*.exp
|
||||||
|
|
||||||
|
# Precompiled Headers
|
||||||
|
*.gch
|
||||||
|
*.pch
|
||||||
|
|
||||||
|
# Libraries
|
||||||
|
*.lib
|
||||||
|
*.a
|
||||||
|
*.la
|
||||||
|
*.lo
|
||||||
|
|
||||||
|
# Shared objects (inc. Windows DLLs)
|
||||||
|
*.dll
|
||||||
|
*.so
|
||||||
|
*.so.*
|
||||||
|
*.dylib
|
||||||
|
|
||||||
|
# Executables
|
||||||
|
*.exe
|
||||||
|
*.out
|
||||||
|
*.app
|
||||||
|
*.i*86
|
||||||
|
*.x86_64
|
||||||
|
*.hex
|
||||||
|
|
||||||
|
# Debug files
|
||||||
|
*.dSYM/
|
||||||
|
*.su
|
||||||
|
*.idb
|
||||||
|
*.pdb
|
||||||
|
*.rep
|
||||||
|
*.gpr
|
||||||
|
|
||||||
|
# Kernel Module Compile Results
|
||||||
|
*.mod*
|
||||||
|
*.cmd
|
||||||
|
.tmp_versions/
|
||||||
|
modules.order
|
||||||
|
Module.symvers
|
||||||
|
Mkfile.old
|
||||||
|
dkms.conf
|
||||||
|
|
||||||
|
# Build output
|
||||||
|
build/
|
||||||
|
target/
|
||||||
|
|
||||||
|
# Node.js and PDF generation script
|
||||||
|
node_modules/
|
||||||
|
package-lock.json
|
||||||
|
package.json
|
||||||
|
svg-to-pdf.ps1
|
||||||
|
|
||||||
|
# Operating System Files
|
||||||
|
.DS_Store
|
||||||
|
.DS_Store?
|
||||||
|
._*
|
||||||
|
.Spotlight-V100
|
||||||
|
.Trashes
|
||||||
|
ehthumbs.db
|
||||||
|
Thumbs.db
|
||||||
|
|
||||||
|
# Logs written by the Binary Ninja console helpers (build / flash / OpenOCD)
|
||||||
|
openocd.log
|
||||||
|
flash.log
|
||||||
|
build.log
|
||||||
|
build-flash.log
|
||||||
|
|
||||||
|
# Nested repositories
|
||||||
|
eCTF/
|
||||||
|
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
build
|
||||||
|
!.vscode/*
|
||||||
@@ -0,0 +1,22 @@
|
|||||||
|
{
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Pico",
|
||||||
|
"includePath": [
|
||||||
|
"${workspaceFolder}/**",
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.2.0/**"
|
||||||
|
],
|
||||||
|
"forcedInclude": [
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.2.0/src/common/pico_base_headers/include/pico.h",
|
||||||
|
"${workspaceFolder}/build/generated/pico_base/pico/config_autogen.h"
|
||||||
|
],
|
||||||
|
"defines": [],
|
||||||
|
"compilerPath": "${userHome}/.pico-sdk/toolchain/14_2_Rel1/bin/arm-none-eabi-gcc.exe",
|
||||||
|
"compileCommands": "${workspaceFolder}/build/compile_commands.json",
|
||||||
|
"cStandard": "c17",
|
||||||
|
"cppStandard": "c++14",
|
||||||
|
"intelliSenseMode": "linux-gcc-arm"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"version": 4
|
||||||
|
}
|
||||||
+15
@@ -0,0 +1,15 @@
|
|||||||
|
[
|
||||||
|
{
|
||||||
|
"name": "Pico",
|
||||||
|
"compilers": {
|
||||||
|
"C": "${command:raspberry-pi-pico.getCompilerPath}",
|
||||||
|
"CXX": "${command:raspberry-pi-pico.getCxxCompilerPath}"
|
||||||
|
},
|
||||||
|
"environmentVariables": {
|
||||||
|
"PATH": "${command:raspberry-pi-pico.getEnvPath};${env:PATH}"
|
||||||
|
},
|
||||||
|
"cmakeSettings": {
|
||||||
|
"Python3_EXECUTABLE": "${command:raspberry-pi-pico.getPythonPath}"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
+9
@@ -0,0 +1,9 @@
|
|||||||
|
{
|
||||||
|
"recommendations": [
|
||||||
|
"marus25.cortex-debug",
|
||||||
|
"ms-vscode.cpptools",
|
||||||
|
"ms-vscode.cpptools-extension-pack",
|
||||||
|
"ms-vscode.vscode-serial-monitor",
|
||||||
|
"raspberry-pi.raspberry-pi-pico"
|
||||||
|
]
|
||||||
|
}
|
||||||
+50
@@ -0,0 +1,50 @@
|
|||||||
|
{
|
||||||
|
"version": "0.2.0",
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Pico Debug (Cortex-Debug)",
|
||||||
|
"cwd": "${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"executable": "${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"request": "launch",
|
||||||
|
"type": "cortex-debug",
|
||||||
|
"servertype": "openocd",
|
||||||
|
"serverpath": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"gdbPath": "${command:raspberry-pi-pico.getGDBPath}",
|
||||||
|
"device": "${command:raspberry-pi-pico.getChipUppercase}",
|
||||||
|
"configFiles": [
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"target/${command:raspberry-pi-pico.getTarget}.cfg"
|
||||||
|
],
|
||||||
|
"svdFile": "${userHome}/.pico-sdk/sdk/2.2.0/src/${command:raspberry-pi-pico.getChip}/hardware_regs/${command:raspberry-pi-pico.getChipUppercase}.svd",
|
||||||
|
"runToEntryPoint": "main",
|
||||||
|
// Fix for no_flash binaries, where monitor reset halt doesn't do what is expected
|
||||||
|
// Also works fine for flash binaries
|
||||||
|
"overrideLaunchCommands": [
|
||||||
|
"monitor reset init",
|
||||||
|
"load \"${command:raspberry-pi-pico.launchTargetPath}\""
|
||||||
|
],
|
||||||
|
"openOCDLaunchCommands": [
|
||||||
|
"adapter speed 5000"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Pico Debug (Cortex-Debug with external OpenOCD)",
|
||||||
|
"cwd": "${workspaceRoot}",
|
||||||
|
"executable": "${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"request": "launch",
|
||||||
|
"type": "cortex-debug",
|
||||||
|
"servertype": "external",
|
||||||
|
"gdbTarget": "localhost:3333",
|
||||||
|
"gdbPath": "${command:raspberry-pi-pico.getGDBPath}",
|
||||||
|
"device": "${command:raspberry-pi-pico.getChipUppercase}",
|
||||||
|
"svdFile": "${userHome}/.pico-sdk/sdk/2.2.0/src/${command:raspberry-pi-pico.getChip}/hardware_regs/${command:raspberry-pi-pico.getChipUppercase}.svd",
|
||||||
|
"runToEntryPoint": "main",
|
||||||
|
// Fix for no_flash binaries, where monitor reset halt doesn't do what is expected
|
||||||
|
// Also works fine for flash binaries
|
||||||
|
"overrideLaunchCommands": [
|
||||||
|
"monitor reset init",
|
||||||
|
"load \"${command:raspberry-pi-pico.launchTargetPath}\""
|
||||||
|
]
|
||||||
|
},
|
||||||
|
]
|
||||||
|
}
|
||||||
+43
@@ -0,0 +1,43 @@
|
|||||||
|
{
|
||||||
|
"cmake.showSystemKits": false,
|
||||||
|
"cmake.options.statusBarVisibility": "hidden",
|
||||||
|
"cmake.options.advanced": {
|
||||||
|
"build": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"launch": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"debug": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"cmake.configureOnEdit": false,
|
||||||
|
"cmake.automaticReconfigure": false,
|
||||||
|
"cmake.configureOnOpen": false,
|
||||||
|
"cmake.generator": "Ninja",
|
||||||
|
"cmake.cmakePath": "${userHome}/.pico-sdk/cmake/v3.31.5/bin/cmake",
|
||||||
|
"C_Cpp.debugShortcut": false,
|
||||||
|
"terminal.integrated.env.windows": {
|
||||||
|
"PICO_SDK_PATH": "${env:USERPROFILE}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:USERPROFILE}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"Path": "${env:USERPROFILE}/.pico-sdk/toolchain/14_2_Rel1/bin;${env:USERPROFILE}/.pico-sdk/picotool/2.2.0/picotool;${env:USERPROFILE}/.pico-sdk/cmake/v3.31.5/bin;${env:USERPROFILE}/.pico-sdk/ninja/v1.12.1;${env:PATH}"
|
||||||
|
},
|
||||||
|
"terminal.integrated.env.osx": {
|
||||||
|
"PICO_SDK_PATH": "${env:HOME}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1/bin:${env:HOME}/.pico-sdk/picotool/2.2.0/picotool:${env:HOME}/.pico-sdk/cmake/v3.31.5/bin:${env:HOME}/.pico-sdk/ninja/v1.12.1:${env:PATH}"
|
||||||
|
},
|
||||||
|
"terminal.integrated.env.linux": {
|
||||||
|
"PICO_SDK_PATH": "${env:HOME}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1/bin:${env:HOME}/.pico-sdk/picotool/2.2.0/picotool:${env:HOME}/.pico-sdk/cmake/v3.31.5/bin:${env:HOME}/.pico-sdk/ninja/v1.12.1:${env:PATH}"
|
||||||
|
},
|
||||||
|
"raspberry-pi-pico.cmakeAutoConfigure": true,
|
||||||
|
"raspberry-pi-pico.useCmakeTools": false,
|
||||||
|
"raspberry-pi-pico.cmakePath": "${HOME}/.pico-sdk/cmake/v3.31.5/bin/cmake",
|
||||||
|
"raspberry-pi-pico.ninjaPath": "${HOME}/.pico-sdk/ninja/v1.12.1/ninja",
|
||||||
|
"files.associations": {
|
||||||
|
"stdlib.h": "c"
|
||||||
|
}
|
||||||
|
}
|
||||||
+102
@@ -0,0 +1,102 @@
|
|||||||
|
{
|
||||||
|
"version": "2.0.0",
|
||||||
|
"tasks": [
|
||||||
|
{
|
||||||
|
"label": "Compile Project",
|
||||||
|
"type": "process",
|
||||||
|
"isBuildCommand": true,
|
||||||
|
"command": "${userHome}/.pico-sdk/ninja/v1.12.1/ninja",
|
||||||
|
"args": ["-C", "${workspaceFolder}/build"],
|
||||||
|
"group": "build",
|
||||||
|
"presentation": {
|
||||||
|
"reveal": "always",
|
||||||
|
"panel": "dedicated"
|
||||||
|
},
|
||||||
|
"problemMatcher": "$gcc",
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/ninja/v1.12.1/ninja.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Run Project",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${env:HOME}/.pico-sdk/picotool/2.2.0/picotool/picotool",
|
||||||
|
"args": [
|
||||||
|
"load",
|
||||||
|
"${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"-fx"
|
||||||
|
],
|
||||||
|
"presentation": {
|
||||||
|
"reveal": "always",
|
||||||
|
"panel": "dedicated"
|
||||||
|
},
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/picotool/2.2.0/picotool/picotool.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Flash",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/${command:raspberry-pi-pico.getTarget}.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; program \"${command:raspberry-pi-pico.launchTargetPath}\" verify reset exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Rescue Reset",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/${command:raspberry-pi-pico.getChip}-rescue.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; reset halt; exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Risc-V Reset (RP2350)",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-c",
|
||||||
|
"set USE_CORE { rv0 rv1 cm0 cm1 }",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/rp2350.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; init;",
|
||||||
|
"-c",
|
||||||
|
"write_memory 0x40120158 8 { 0x3 }; echo [format \"Info : ARCHSEL 0x%02x\" [read_memory 0x40120158 8 1]];",
|
||||||
|
"-c",
|
||||||
|
"reset halt; targets rp2350.rv0; echo [format \"Info : ARCHSEL_STATUS 0x%02x\" [read_memory 0x4012015C 8 1]]; exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -0,0 +1,46 @@
|
|||||||
|
/**
|
||||||
|
* @file 0x0001_hello-world.c
|
||||||
|
* @brief Hello World: print a greeting over UART in an infinite loop
|
||||||
|
* @author Kevin Thomas
|
||||||
|
* @date 2025
|
||||||
|
*
|
||||||
|
* MIT License
|
||||||
|
*
|
||||||
|
* Copyright (c) 2025 Kevin Thomas
|
||||||
|
*
|
||||||
|
* 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.
|
||||||
|
*
|
||||||
|
* -----------------------------------------------------------------------------
|
||||||
|
*
|
||||||
|
* Demonstrates the minimal "hello, world" program on the Raspberry Pi Pico 2.
|
||||||
|
* Initializes stdio over UART and prints a greeting in an infinite loop.
|
||||||
|
*
|
||||||
|
* Wiring:
|
||||||
|
* No external wiring required (USB serial).
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
#include "pico/stdlib.h"
|
||||||
|
|
||||||
|
int main(void) {
|
||||||
|
stdio_init_all();
|
||||||
|
while (true) {
|
||||||
|
printf("hello, world\r\n");
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,57 @@
|
|||||||
|
# Generated Cmake Pico project file
|
||||||
|
|
||||||
|
cmake_minimum_required(VERSION 3.13)
|
||||||
|
|
||||||
|
set(CMAKE_C_STANDARD 11)
|
||||||
|
set(CMAKE_CXX_STANDARD 17)
|
||||||
|
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
|
||||||
|
|
||||||
|
# Initialise pico_sdk from installed location
|
||||||
|
# (note this can come from environment, CMake cache etc)
|
||||||
|
|
||||||
|
# == DO NOT EDIT THE FOLLOWING LINES for the Raspberry Pi Pico VS Code Extension to work ==
|
||||||
|
if(WIN32)
|
||||||
|
set(USERHOME $ENV{USERPROFILE})
|
||||||
|
else()
|
||||||
|
set(USERHOME $ENV{HOME})
|
||||||
|
endif()
|
||||||
|
set(sdkVersion 2.2.0)
|
||||||
|
set(toolchainVersion 14_2_Rel1)
|
||||||
|
set(picotoolVersion 2.2.0)
|
||||||
|
set(picoVscode ${USERHOME}/.pico-sdk/cmake/pico-vscode.cmake)
|
||||||
|
if (EXISTS ${picoVscode})
|
||||||
|
include(${picoVscode})
|
||||||
|
endif()
|
||||||
|
# ====================================================================================
|
||||||
|
set(PICO_BOARD pico2 CACHE STRING "Board type")
|
||||||
|
|
||||||
|
# Pull in Raspberry Pi Pico SDK (must be before project)
|
||||||
|
include(pico_sdk_import.cmake)
|
||||||
|
|
||||||
|
project(0x0001_hello-world C CXX ASM)
|
||||||
|
|
||||||
|
# Initialise the Raspberry Pi Pico SDK
|
||||||
|
pico_sdk_init()
|
||||||
|
|
||||||
|
# Add executable. Default name is the project name, version 0.1
|
||||||
|
|
||||||
|
add_executable(0x0001_hello-world 0x0001_hello-world.c )
|
||||||
|
|
||||||
|
pico_set_program_name(0x0001_hello-world "0x0001_hello-world")
|
||||||
|
pico_set_program_version(0x0001_hello-world "0.1")
|
||||||
|
|
||||||
|
# Modify the below lines to enable/disable output over UART/USB
|
||||||
|
pico_enable_stdio_uart(0x0001_hello-world 1)
|
||||||
|
pico_enable_stdio_usb(0x0001_hello-world 0)
|
||||||
|
|
||||||
|
# Add the standard library to the build
|
||||||
|
target_link_libraries(0x0001_hello-world
|
||||||
|
pico_stdlib)
|
||||||
|
|
||||||
|
# Add the standard include files to the build
|
||||||
|
target_include_directories(0x0001_hello-world PRIVATE
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}
|
||||||
|
)
|
||||||
|
|
||||||
|
pico_add_extra_outputs(0x0001_hello-world)
|
||||||
|
|
||||||
@@ -0,0 +1,121 @@
|
|||||||
|
# This is a copy of <PICO_SDK_PATH>/external/pico_sdk_import.cmake
|
||||||
|
|
||||||
|
# This can be dropped into an external project to help locate this SDK
|
||||||
|
# It should be include()ed prior to project()
|
||||||
|
|
||||||
|
# Copyright 2020 (c) 2020 Raspberry Pi (Trading) Ltd.
|
||||||
|
#
|
||||||
|
# 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. Neither the name of the copyright holder nor the names of its contributors may be used to endorse or promote products
|
||||||
|
# derived from this software without specific prior written permission.
|
||||||
|
#
|
||||||
|
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "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 COPYRIGHT HOLDER OR CONTRIBUTORS 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.
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_PATH} AND (NOT PICO_SDK_PATH))
|
||||||
|
set(PICO_SDK_PATH $ENV{PICO_SDK_PATH})
|
||||||
|
message("Using PICO_SDK_PATH from environment ('${PICO_SDK_PATH}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT} AND (NOT PICO_SDK_FETCH_FROM_GIT))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT $ENV{PICO_SDK_FETCH_FROM_GIT})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT from environment ('${PICO_SDK_FETCH_FROM_GIT}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT_PATH} AND (NOT PICO_SDK_FETCH_FROM_GIT_PATH))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_PATH $ENV{PICO_SDK_FETCH_FROM_GIT_PATH})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT_PATH from environment ('${PICO_SDK_FETCH_FROM_GIT_PATH}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT_TAG} AND (NOT PICO_SDK_FETCH_FROM_GIT_TAG))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG $ENV{PICO_SDK_FETCH_FROM_GIT_TAG})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT_TAG from environment ('${PICO_SDK_FETCH_FROM_GIT_TAG}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT AND NOT PICO_SDK_FETCH_FROM_GIT_TAG)
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG "master")
|
||||||
|
message("Using master as default value for PICO_SDK_FETCH_FROM_GIT_TAG")
|
||||||
|
endif()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH "${PICO_SDK_PATH}" CACHE PATH "Path to the Raspberry Pi Pico SDK")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT "${PICO_SDK_FETCH_FROM_GIT}" CACHE BOOL "Set to ON to fetch copy of SDK from git if not otherwise locatable")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_PATH "${PICO_SDK_FETCH_FROM_GIT_PATH}" CACHE FILEPATH "location to download SDK")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG "${PICO_SDK_FETCH_FROM_GIT_TAG}" CACHE FILEPATH "release tag for SDK")
|
||||||
|
|
||||||
|
if (NOT PICO_SDK_PATH)
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT)
|
||||||
|
include(FetchContent)
|
||||||
|
set(FETCHCONTENT_BASE_DIR_SAVE ${FETCHCONTENT_BASE_DIR})
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT_PATH)
|
||||||
|
get_filename_component(FETCHCONTENT_BASE_DIR "${PICO_SDK_FETCH_FROM_GIT_PATH}" REALPATH BASE_DIR "${CMAKE_SOURCE_DIR}")
|
||||||
|
endif ()
|
||||||
|
FetchContent_Declare(
|
||||||
|
pico_sdk
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
)
|
||||||
|
|
||||||
|
if (NOT pico_sdk)
|
||||||
|
message("Downloading Raspberry Pi Pico SDK")
|
||||||
|
# GIT_SUBMODULES_RECURSE was added in 3.17
|
||||||
|
if (${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.17.0")
|
||||||
|
FetchContent_Populate(
|
||||||
|
pico_sdk
|
||||||
|
QUIET
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
GIT_SUBMODULES_RECURSE FALSE
|
||||||
|
|
||||||
|
SOURCE_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-src
|
||||||
|
BINARY_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-build
|
||||||
|
SUBBUILD_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-subbuild
|
||||||
|
)
|
||||||
|
else ()
|
||||||
|
FetchContent_Populate(
|
||||||
|
pico_sdk
|
||||||
|
QUIET
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
|
||||||
|
SOURCE_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-src
|
||||||
|
BINARY_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-build
|
||||||
|
SUBBUILD_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-subbuild
|
||||||
|
)
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH ${pico_sdk_SOURCE_DIR})
|
||||||
|
endif ()
|
||||||
|
set(FETCHCONTENT_BASE_DIR ${FETCHCONTENT_BASE_DIR_SAVE})
|
||||||
|
else ()
|
||||||
|
message(FATAL_ERROR
|
||||||
|
"SDK location was not specified. Please set PICO_SDK_PATH or set PICO_SDK_FETCH_FROM_GIT to on to fetch from git."
|
||||||
|
)
|
||||||
|
endif ()
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
get_filename_component(PICO_SDK_PATH "${PICO_SDK_PATH}" REALPATH BASE_DIR "${CMAKE_BINARY_DIR}")
|
||||||
|
if (NOT EXISTS ${PICO_SDK_PATH})
|
||||||
|
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' not found")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_INIT_CMAKE_FILE ${PICO_SDK_PATH}/pico_sdk_init.cmake)
|
||||||
|
if (NOT EXISTS ${PICO_SDK_INIT_CMAKE_FILE})
|
||||||
|
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' does not appear to contain the Raspberry Pi Pico SDK")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH ${PICO_SDK_PATH} CACHE PATH "Path to the Raspberry Pi Pico SDK" FORCE)
|
||||||
|
|
||||||
|
include(${PICO_SDK_INIT_CMAKE_FILE})
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
build
|
||||||
|
!.vscode/*
|
||||||
+22
@@ -0,0 +1,22 @@
|
|||||||
|
{
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Pico",
|
||||||
|
"includePath": [
|
||||||
|
"${workspaceFolder}/**",
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.3.0/**"
|
||||||
|
],
|
||||||
|
"forcedInclude": [
|
||||||
|
"${workspaceFolder}/build/generated/pico_base/pico/config_autogen.h",
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.3.0/src/common/pico_base_headers/include/pico.h"
|
||||||
|
],
|
||||||
|
"defines": [],
|
||||||
|
"compilerPath": "${userHome}/.pico-sdk/toolchain/15_2_Rel1/bin/arm-none-eabi-gcc.exe",
|
||||||
|
"compileCommands": "${workspaceFolder}/build/compile_commands.json",
|
||||||
|
"cStandard": "c17",
|
||||||
|
"cppStandard": "c++14",
|
||||||
|
"intelliSenseMode": "linux-gcc-arm"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"version": 4
|
||||||
|
}
|
||||||
+15
@@ -0,0 +1,15 @@
|
|||||||
|
[
|
||||||
|
{
|
||||||
|
"name": "Pico",
|
||||||
|
"compilers": {
|
||||||
|
"C": "${command:raspberry-pi-pico.getCompilerPath}",
|
||||||
|
"CXX": "${command:raspberry-pi-pico.getCxxCompilerPath}"
|
||||||
|
},
|
||||||
|
"environmentVariables": {
|
||||||
|
"PATH": "${command:raspberry-pi-pico.getEnvPath};${env:PATH}"
|
||||||
|
},
|
||||||
|
"cmakeSettings": {
|
||||||
|
"Python3_EXECUTABLE": "${command:raspberry-pi-pico.getPythonPath}"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
+9
@@ -0,0 +1,9 @@
|
|||||||
|
{
|
||||||
|
"recommendations": [
|
||||||
|
"marus25.cortex-debug",
|
||||||
|
"ms-vscode.cpptools",
|
||||||
|
"ms-vscode.cpptools-extension-pack",
|
||||||
|
"ms-vscode.vscode-serial-monitor",
|
||||||
|
"raspberry-pi.raspberry-pi-pico"
|
||||||
|
]
|
||||||
|
}
|
||||||
Vendored
+52
@@ -0,0 +1,52 @@
|
|||||||
|
{
|
||||||
|
"version": "0.2.0",
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Pico Debug (Cortex-Debug)",
|
||||||
|
"cwd": "${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"executable": "${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"request": "launch",
|
||||||
|
"type": "cortex-debug",
|
||||||
|
"servertype": "openocd",
|
||||||
|
"serverpath": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"gdbPath": "${command:raspberry-pi-pico.getGDBPath}",
|
||||||
|
"debuggerArgs": ["-ex", "set debug-file-directory /debug"],
|
||||||
|
"device": "${command:raspberry-pi-pico.getChipUppercase}",
|
||||||
|
"configFiles": [
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"target/${command:raspberry-pi-pico.getTarget}.cfg"
|
||||||
|
],
|
||||||
|
"svdFile": "${userHome}/.pico-sdk/sdk/2.3.0/src/${command:raspberry-pi-pico.getChip}/hardware_regs/${command:raspberry-pi-pico.getChipUppercase}.svd",
|
||||||
|
"runToEntryPoint": "main",
|
||||||
|
// Fix for no_flash binaries, where monitor reset halt doesn't do what is expected
|
||||||
|
// Also works fine for flash binaries
|
||||||
|
"overrideLaunchCommands": [
|
||||||
|
"monitor reset init",
|
||||||
|
"load \"${command:raspberry-pi-pico.launchTargetPath}\""
|
||||||
|
],
|
||||||
|
"openOCDLaunchCommands": [
|
||||||
|
"adapter speed 5000"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Pico Debug (Cortex-Debug with external OpenOCD)",
|
||||||
|
"cwd": "${workspaceRoot}",
|
||||||
|
"executable": "${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"request": "launch",
|
||||||
|
"type": "cortex-debug",
|
||||||
|
"servertype": "external",
|
||||||
|
"gdbTarget": "localhost:3333",
|
||||||
|
"gdbPath": "${command:raspberry-pi-pico.getGDBPath}",
|
||||||
|
"debuggerArgs": ["-ex", "set debug-file-directory /debug"],
|
||||||
|
"device": "${command:raspberry-pi-pico.getChipUppercase}",
|
||||||
|
"svdFile": "${userHome}/.pico-sdk/sdk/2.3.0/src/${command:raspberry-pi-pico.getChip}/hardware_regs/${command:raspberry-pi-pico.getChipUppercase}.svd",
|
||||||
|
"runToEntryPoint": "main",
|
||||||
|
// Fix for no_flash binaries, where monitor reset halt doesn't do what is expected
|
||||||
|
// Also works fine for flash binaries
|
||||||
|
"overrideLaunchCommands": [
|
||||||
|
"monitor reset init",
|
||||||
|
"load \"${command:raspberry-pi-pico.launchTargetPath}\""
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
Vendored
+46
@@ -0,0 +1,46 @@
|
|||||||
|
{
|
||||||
|
"cmake.showSystemKits": false,
|
||||||
|
"cmake.options.statusBarVisibility": "hidden",
|
||||||
|
"cmake.options.advanced": {
|
||||||
|
"build": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"launch": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"debug": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"variant": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"buildTarget": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"cmake.configureOnEdit": false,
|
||||||
|
"cmake.automaticReconfigure": false,
|
||||||
|
"cmake.configureOnOpen": false,
|
||||||
|
"cmake.generator": "Ninja",
|
||||||
|
"cmake.cmakePath": "${userHome}/.pico-sdk/cmake/v4.3.4/bin/cmake",
|
||||||
|
"C_Cpp.debugShortcut": false,
|
||||||
|
"terminal.integrated.env.windows": {
|
||||||
|
"PICO_SDK_PATH": "${env:USERPROFILE}/.pico-sdk/sdk/2.3.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:USERPROFILE}/.pico-sdk/toolchain/15_2_Rel1",
|
||||||
|
"Path": "${env:USERPROFILE}/.pico-sdk/toolchain/15_2_Rel1/bin;${env:USERPROFILE}/.pico-sdk/picotool/2.3.0/picotool;${env:USERPROFILE}/.pico-sdk/cmake/v4.3.4/bin;${env:USERPROFILE}/.pico-sdk/ninja/v1.13.2;${env:PATH}"
|
||||||
|
},
|
||||||
|
"terminal.integrated.env.osx": {
|
||||||
|
"PICO_SDK_PATH": "${env:HOME}/.pico-sdk/sdk/2.3.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:HOME}/.pico-sdk/toolchain/15_2_Rel1",
|
||||||
|
"PATH": "${env:HOME}/.pico-sdk/toolchain/15_2_Rel1/bin:${env:HOME}/.pico-sdk/picotool/2.3.0/picotool:${env:HOME}/.pico-sdk/cmake/v4.3.4/bin:${env:HOME}/.pico-sdk/ninja/v1.13.2:${env:PATH}"
|
||||||
|
},
|
||||||
|
"terminal.integrated.env.linux": {
|
||||||
|
"PICO_SDK_PATH": "${env:HOME}/.pico-sdk/sdk/2.3.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:HOME}/.pico-sdk/toolchain/15_2_Rel1",
|
||||||
|
"PATH": "${env:HOME}/.pico-sdk/toolchain/15_2_Rel1/bin:${env:HOME}/.pico-sdk/picotool/2.3.0/picotool:${env:HOME}/.pico-sdk/cmake/v4.3.4/bin:${env:HOME}/.pico-sdk/ninja/v1.13.2:${env:PATH}"
|
||||||
|
},
|
||||||
|
"raspberry-pi-pico.cmakeAutoConfigure": true,
|
||||||
|
"raspberry-pi-pico.useCmakeTools": false,
|
||||||
|
"raspberry-pi-pico.cmakePath": "${HOME}/.pico-sdk/cmake/v4.3.4/bin/cmake",
|
||||||
|
"raspberry-pi-pico.ninjaPath": "${HOME}/.pico-sdk/ninja/v1.13.2/ninja"
|
||||||
|
}
|
||||||
Vendored
+102
@@ -0,0 +1,102 @@
|
|||||||
|
{
|
||||||
|
"version": "2.0.0",
|
||||||
|
"tasks": [
|
||||||
|
{
|
||||||
|
"label": "Compile Project",
|
||||||
|
"type": "process",
|
||||||
|
"isBuildCommand": true,
|
||||||
|
"command": "${userHome}/.pico-sdk/ninja/v1.13.2/ninja",
|
||||||
|
"args": ["-C", "${workspaceFolder}/build"],
|
||||||
|
"group": "build",
|
||||||
|
"presentation": {
|
||||||
|
"reveal": "always",
|
||||||
|
"panel": "dedicated"
|
||||||
|
},
|
||||||
|
"problemMatcher": "$gcc",
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/ninja/v1.13.2/ninja.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Run Project",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${env:HOME}/.pico-sdk/picotool/2.3.0/picotool/picotool",
|
||||||
|
"args": [
|
||||||
|
"load",
|
||||||
|
"${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"-fx"
|
||||||
|
],
|
||||||
|
"presentation": {
|
||||||
|
"reveal": "always",
|
||||||
|
"panel": "dedicated"
|
||||||
|
},
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/picotool/2.3.0/picotool/picotool.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Flash",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/${command:raspberry-pi-pico.getTarget}.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; program \"${command:raspberry-pi-pico.launchTargetPath}\" verify reset exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Rescue Reset",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/${command:raspberry-pi-pico.getChip}-rescue.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; reset halt; exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "RISC-V Reset (RP2350)",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-c",
|
||||||
|
"set USE_CORE { rv0 rv1 cm0 cm1 }",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/rp2350.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; init;",
|
||||||
|
"-c",
|
||||||
|
"write_memory 0x40120158 8 { 0x3 }; echo [format \"Info : ARCHSEL 0x%02x\" [read_memory 0x40120158 8 1]];",
|
||||||
|
"-c",
|
||||||
|
"reset halt; targets rp2350.rv0; echo [format \"Info : ARCHSEL_STATUS 0x%02x\" [read_memory 0x4012015C 8 1]]; exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -0,0 +1,23 @@
|
|||||||
|
#include <stdio.h>
|
||||||
|
#include "pico/stdlib.h"
|
||||||
|
|
||||||
|
|
||||||
|
int main()
|
||||||
|
{
|
||||||
|
stdio_init_all();
|
||||||
|
|
||||||
|
while (true) {
|
||||||
|
__asm volatile(
|
||||||
|
// Save a low register and the link register.
|
||||||
|
"push {r4, lr}\n"
|
||||||
|
// Intentionally unordered: the encoded list is still r2, r3, r6.
|
||||||
|
"push {r3, r2, r6}\n"
|
||||||
|
// Thumb PUSH cannot encode high registers r8-r12.
|
||||||
|
"stmdb sp!, {r9, r10}\n"
|
||||||
|
// Restore each group in reverse order to return SP to its start.
|
||||||
|
"ldmia sp!, {r9, r10}\n"
|
||||||
|
"pop {r2, r3, r6}\n"
|
||||||
|
"pop {r4, lr}\n"
|
||||||
|
::: "memory");
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,57 @@
|
|||||||
|
# Generated Cmake Pico project file
|
||||||
|
|
||||||
|
cmake_minimum_required(VERSION 3.13)
|
||||||
|
|
||||||
|
set(CMAKE_C_STANDARD 11)
|
||||||
|
set(CMAKE_CXX_STANDARD 17)
|
||||||
|
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
|
||||||
|
|
||||||
|
# Initialise pico_sdk from installed location
|
||||||
|
# (note this can come from environment, CMake cache etc)
|
||||||
|
|
||||||
|
# == DO NOT EDIT THE FOLLOWING LINES for the Raspberry Pi Pico VS Code Extension to work ==
|
||||||
|
if(WIN32)
|
||||||
|
set(USERHOME $ENV{USERPROFILE})
|
||||||
|
else()
|
||||||
|
set(USERHOME $ENV{HOME})
|
||||||
|
endif()
|
||||||
|
set(sdkVersion 2.3.0)
|
||||||
|
set(toolchainVersion 15_2_Rel1)
|
||||||
|
set(picotoolVersion 2.3.0)
|
||||||
|
set(picoVscode ${USERHOME}/.pico-sdk/cmake/pico-vscode.cmake)
|
||||||
|
if (EXISTS ${picoVscode})
|
||||||
|
include(${picoVscode})
|
||||||
|
endif()
|
||||||
|
# ====================================================================================
|
||||||
|
set(PICO_BOARD pico2 CACHE STRING "Board type")
|
||||||
|
|
||||||
|
# Pull in Raspberry Pi Pico SDK (must be before project)
|
||||||
|
include(pico_sdk_import.cmake)
|
||||||
|
|
||||||
|
project(0x0001a_stack C CXX ASM)
|
||||||
|
|
||||||
|
# Initialise the Raspberry Pi Pico SDK
|
||||||
|
pico_sdk_init()
|
||||||
|
|
||||||
|
# Add executable. Default name is the project name, version 0.1
|
||||||
|
|
||||||
|
add_executable(0x0001a_stack 0x0001a_stack.c )
|
||||||
|
|
||||||
|
pico_set_program_name(0x0001a_stack "0x0001a_stack")
|
||||||
|
pico_set_program_version(0x0001a_stack "0.1")
|
||||||
|
|
||||||
|
# Modify the below lines to enable/disable output over UART/USB
|
||||||
|
pico_enable_stdio_uart(0x0001a_stack 1)
|
||||||
|
pico_enable_stdio_usb(0x0001a_stack 0)
|
||||||
|
|
||||||
|
# Add the standard library to the build
|
||||||
|
target_link_libraries(0x0001a_stack
|
||||||
|
pico_stdlib)
|
||||||
|
|
||||||
|
# Add the standard include files to the build
|
||||||
|
target_include_directories(0x0001a_stack PRIVATE
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}
|
||||||
|
)
|
||||||
|
|
||||||
|
pico_add_extra_outputs(0x0001a_stack)
|
||||||
|
|
||||||
@@ -0,0 +1,121 @@
|
|||||||
|
# This is a copy of <PICO_SDK_PATH>/external/pico_sdk_import.cmake
|
||||||
|
|
||||||
|
# This can be dropped into an external project to help locate this SDK
|
||||||
|
# It should be include()ed prior to project()
|
||||||
|
|
||||||
|
# Copyright 2020 (c) 2020 Raspberry Pi (Trading) Ltd.
|
||||||
|
#
|
||||||
|
# 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. Neither the name of the copyright holder nor the names of its contributors may be used to endorse or promote products
|
||||||
|
# derived from this software without specific prior written permission.
|
||||||
|
#
|
||||||
|
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "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 COPYRIGHT HOLDER OR CONTRIBUTORS 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.
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_PATH} AND (NOT PICO_SDK_PATH))
|
||||||
|
set(PICO_SDK_PATH $ENV{PICO_SDK_PATH})
|
||||||
|
message("Using PICO_SDK_PATH from environment ('${PICO_SDK_PATH}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT} AND (NOT PICO_SDK_FETCH_FROM_GIT))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT $ENV{PICO_SDK_FETCH_FROM_GIT})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT from environment ('${PICO_SDK_FETCH_FROM_GIT}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT_PATH} AND (NOT PICO_SDK_FETCH_FROM_GIT_PATH))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_PATH $ENV{PICO_SDK_FETCH_FROM_GIT_PATH})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT_PATH from environment ('${PICO_SDK_FETCH_FROM_GIT_PATH}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT_TAG} AND (NOT PICO_SDK_FETCH_FROM_GIT_TAG))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG $ENV{PICO_SDK_FETCH_FROM_GIT_TAG})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT_TAG from environment ('${PICO_SDK_FETCH_FROM_GIT_TAG}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT AND NOT PICO_SDK_FETCH_FROM_GIT_TAG)
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG "master")
|
||||||
|
message("Using master as default value for PICO_SDK_FETCH_FROM_GIT_TAG")
|
||||||
|
endif()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH "${PICO_SDK_PATH}" CACHE PATH "Path to the Raspberry Pi Pico SDK")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT "${PICO_SDK_FETCH_FROM_GIT}" CACHE BOOL "Set to ON to fetch copy of SDK from git if not otherwise locatable")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_PATH "${PICO_SDK_FETCH_FROM_GIT_PATH}" CACHE FILEPATH "location to download SDK")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG "${PICO_SDK_FETCH_FROM_GIT_TAG}" CACHE FILEPATH "release tag for SDK")
|
||||||
|
|
||||||
|
if (NOT PICO_SDK_PATH)
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT)
|
||||||
|
include(FetchContent)
|
||||||
|
set(FETCHCONTENT_BASE_DIR_SAVE ${FETCHCONTENT_BASE_DIR})
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT_PATH)
|
||||||
|
get_filename_component(FETCHCONTENT_BASE_DIR "${PICO_SDK_FETCH_FROM_GIT_PATH}" REALPATH BASE_DIR "${CMAKE_SOURCE_DIR}")
|
||||||
|
endif ()
|
||||||
|
FetchContent_Declare(
|
||||||
|
pico_sdk
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
)
|
||||||
|
|
||||||
|
if (NOT pico_sdk)
|
||||||
|
message("Downloading Raspberry Pi Pico SDK")
|
||||||
|
# GIT_SUBMODULES_RECURSE was added in 3.17
|
||||||
|
if (${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.17.0")
|
||||||
|
FetchContent_Populate(
|
||||||
|
pico_sdk
|
||||||
|
QUIET
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
GIT_SUBMODULES_RECURSE FALSE
|
||||||
|
|
||||||
|
SOURCE_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-src
|
||||||
|
BINARY_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-build
|
||||||
|
SUBBUILD_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-subbuild
|
||||||
|
)
|
||||||
|
else ()
|
||||||
|
FetchContent_Populate(
|
||||||
|
pico_sdk
|
||||||
|
QUIET
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
|
||||||
|
SOURCE_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-src
|
||||||
|
BINARY_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-build
|
||||||
|
SUBBUILD_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-subbuild
|
||||||
|
)
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH ${pico_sdk_SOURCE_DIR})
|
||||||
|
endif ()
|
||||||
|
set(FETCHCONTENT_BASE_DIR ${FETCHCONTENT_BASE_DIR_SAVE})
|
||||||
|
else ()
|
||||||
|
message(FATAL_ERROR
|
||||||
|
"SDK location was not specified. Please set PICO_SDK_PATH or set PICO_SDK_FETCH_FROM_GIT to on to fetch from git."
|
||||||
|
)
|
||||||
|
endif ()
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
get_filename_component(PICO_SDK_PATH "${PICO_SDK_PATH}" REALPATH BASE_DIR "${CMAKE_BINARY_DIR}")
|
||||||
|
if (NOT EXISTS ${PICO_SDK_PATH})
|
||||||
|
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' not found")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_INIT_CMAKE_FILE ${PICO_SDK_PATH}/pico_sdk_init.cmake)
|
||||||
|
if (NOT EXISTS ${PICO_SDK_INIT_CMAKE_FILE})
|
||||||
|
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' does not appear to contain the Raspberry Pi Pico SDK")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH ${PICO_SDK_PATH} CACHE PATH "Path to the Raspberry Pi Pico SDK" FORCE)
|
||||||
|
|
||||||
|
include(${PICO_SDK_INIT_CMAKE_FILE})
|
||||||
@@ -0,0 +1,4 @@
|
|||||||
|
build
|
||||||
|
!.vscode/*
|
||||||
|
!build-ctf/0x0001b_ctf.bin
|
||||||
|
!CTF-01.bin
|
||||||
+22
@@ -0,0 +1,22 @@
|
|||||||
|
{
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Pico",
|
||||||
|
"includePath": [
|
||||||
|
"${workspaceFolder}/**",
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.3.1/**"
|
||||||
|
],
|
||||||
|
"forcedInclude": [
|
||||||
|
"${workspaceFolder}/build/generated/pico_base/pico/config_autogen.h",
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.3.1/src/common/pico_base_headers/include/pico.h"
|
||||||
|
],
|
||||||
|
"defines": [],
|
||||||
|
"compilerPath": "${userHome}/.pico-sdk/toolchain/15_2_Rel1/bin/arm-none-eabi-gcc.exe",
|
||||||
|
"compileCommands": "${workspaceFolder}/build/compile_commands.json",
|
||||||
|
"cStandard": "c17",
|
||||||
|
"cppStandard": "c++14",
|
||||||
|
"intelliSenseMode": "linux-gcc-arm"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"version": 4
|
||||||
|
}
|
||||||
Vendored
+15
@@ -0,0 +1,15 @@
|
|||||||
|
[
|
||||||
|
{
|
||||||
|
"name": "Pico",
|
||||||
|
"compilers": {
|
||||||
|
"C": "${command:raspberry-pi-pico.getCompilerPath}",
|
||||||
|
"CXX": "${command:raspberry-pi-pico.getCxxCompilerPath}"
|
||||||
|
},
|
||||||
|
"environmentVariables": {
|
||||||
|
"PATH": "${command:raspberry-pi-pico.getEnvPath};${env:PATH}"
|
||||||
|
},
|
||||||
|
"cmakeSettings": {
|
||||||
|
"Python3_EXECUTABLE": "${command:raspberry-pi-pico.getPythonPath}"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
Vendored
+9
@@ -0,0 +1,9 @@
|
|||||||
|
{
|
||||||
|
"recommendations": [
|
||||||
|
"marus25.cortex-debug",
|
||||||
|
"ms-vscode.cpptools",
|
||||||
|
"ms-vscode.cpptools-extension-pack",
|
||||||
|
"ms-vscode.vscode-serial-monitor",
|
||||||
|
"raspberry-pi.raspberry-pi-pico"
|
||||||
|
]
|
||||||
|
}
|
||||||
Vendored
+52
@@ -0,0 +1,52 @@
|
|||||||
|
{
|
||||||
|
"version": "0.2.0",
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Pico Debug (Cortex-Debug)",
|
||||||
|
"cwd": "${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"executable": "${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"request": "launch",
|
||||||
|
"type": "cortex-debug",
|
||||||
|
"servertype": "openocd",
|
||||||
|
"serverpath": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"gdbPath": "${command:raspberry-pi-pico.getGDBPath}",
|
||||||
|
"debuggerArgs": ["-ex", "set debug-file-directory /debug"],
|
||||||
|
"device": "${command:raspberry-pi-pico.getChipUppercase}",
|
||||||
|
"configFiles": [
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"target/${command:raspberry-pi-pico.getTarget}.cfg"
|
||||||
|
],
|
||||||
|
"svdFile": "${userHome}/.pico-sdk/sdk/2.3.1/src/${command:raspberry-pi-pico.getChip}/hardware_regs/${command:raspberry-pi-pico.getChipUppercase}.svd",
|
||||||
|
"runToEntryPoint": "main",
|
||||||
|
// Fix for no_flash binaries, where monitor reset halt doesn't do what is expected
|
||||||
|
// Also works fine for flash binaries
|
||||||
|
"overrideLaunchCommands": [
|
||||||
|
"monitor reset init",
|
||||||
|
"load \"${command:raspberry-pi-pico.launchTargetPath}\""
|
||||||
|
],
|
||||||
|
"openOCDLaunchCommands": [
|
||||||
|
"adapter speed 5000"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Pico Debug (Cortex-Debug with external OpenOCD)",
|
||||||
|
"cwd": "${workspaceRoot}",
|
||||||
|
"executable": "${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"request": "launch",
|
||||||
|
"type": "cortex-debug",
|
||||||
|
"servertype": "external",
|
||||||
|
"gdbTarget": "localhost:3333",
|
||||||
|
"gdbPath": "${command:raspberry-pi-pico.getGDBPath}",
|
||||||
|
"debuggerArgs": ["-ex", "set debug-file-directory /debug"],
|
||||||
|
"device": "${command:raspberry-pi-pico.getChipUppercase}",
|
||||||
|
"svdFile": "${userHome}/.pico-sdk/sdk/2.3.1/src/${command:raspberry-pi-pico.getChip}/hardware_regs/${command:raspberry-pi-pico.getChipUppercase}.svd",
|
||||||
|
"runToEntryPoint": "main",
|
||||||
|
// Fix for no_flash binaries, where monitor reset halt doesn't do what is expected
|
||||||
|
// Also works fine for flash binaries
|
||||||
|
"overrideLaunchCommands": [
|
||||||
|
"monitor reset init",
|
||||||
|
"load \"${command:raspberry-pi-pico.launchTargetPath}\""
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
Vendored
+46
@@ -0,0 +1,46 @@
|
|||||||
|
{
|
||||||
|
"cmake.showSystemKits": false,
|
||||||
|
"cmake.options.statusBarVisibility": "hidden",
|
||||||
|
"cmake.options.advanced": {
|
||||||
|
"build": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"launch": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"debug": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"variant": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"buildTarget": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"cmake.configureOnEdit": false,
|
||||||
|
"cmake.automaticReconfigure": false,
|
||||||
|
"cmake.configureOnOpen": false,
|
||||||
|
"cmake.generator": "Ninja",
|
||||||
|
"cmake.cmakePath": "${userHome}/.pico-sdk/cmake/v4.3.4/bin/cmake",
|
||||||
|
"C_Cpp.debugShortcut": false,
|
||||||
|
"terminal.integrated.env.windows": {
|
||||||
|
"PICO_SDK_PATH": "${env:USERPROFILE}/.pico-sdk/sdk/2.3.1",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:USERPROFILE}/.pico-sdk/toolchain/15_2_Rel1",
|
||||||
|
"Path": "${env:USERPROFILE}/.pico-sdk/toolchain/15_2_Rel1/bin;${env:USERPROFILE}/.pico-sdk/picotool/2.3.1/picotool;${env:USERPROFILE}/.pico-sdk/cmake/v4.3.4/bin;${env:USERPROFILE}/.pico-sdk/ninja/v1.13.2;${env:PATH}"
|
||||||
|
},
|
||||||
|
"terminal.integrated.env.osx": {
|
||||||
|
"PICO_SDK_PATH": "${env:HOME}/.pico-sdk/sdk/2.3.1",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:HOME}/.pico-sdk/toolchain/15_2_Rel1",
|
||||||
|
"PATH": "${env:HOME}/.pico-sdk/toolchain/15_2_Rel1/bin:${env:HOME}/.pico-sdk/picotool/2.3.1/picotool:${env:HOME}/.pico-sdk/cmake/v4.3.4/bin:${env:HOME}/.pico-sdk/ninja/v1.13.2:${env:PATH}"
|
||||||
|
},
|
||||||
|
"terminal.integrated.env.linux": {
|
||||||
|
"PICO_SDK_PATH": "${env:HOME}/.pico-sdk/sdk/2.3.1",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:HOME}/.pico-sdk/toolchain/15_2_Rel1",
|
||||||
|
"PATH": "${env:HOME}/.pico-sdk/toolchain/15_2_Rel1/bin:${env:HOME}/.pico-sdk/picotool/2.3.1/picotool:${env:HOME}/.pico-sdk/cmake/v4.3.4/bin:${env:HOME}/.pico-sdk/ninja/v1.13.2:${env:PATH}"
|
||||||
|
},
|
||||||
|
"raspberry-pi-pico.cmakeAutoConfigure": true,
|
||||||
|
"raspberry-pi-pico.useCmakeTools": false,
|
||||||
|
"raspberry-pi-pico.cmakePath": "${HOME}/.pico-sdk/cmake/v4.3.4/bin/cmake",
|
||||||
|
"raspberry-pi-pico.ninjaPath": "${HOME}/.pico-sdk/ninja/v1.13.2/ninja"
|
||||||
|
}
|
||||||
Vendored
+102
@@ -0,0 +1,102 @@
|
|||||||
|
{
|
||||||
|
"version": "2.0.0",
|
||||||
|
"tasks": [
|
||||||
|
{
|
||||||
|
"label": "Compile Project",
|
||||||
|
"type": "process",
|
||||||
|
"isBuildCommand": true,
|
||||||
|
"command": "${userHome}/.pico-sdk/ninja/v1.13.2/ninja",
|
||||||
|
"args": ["-C", "${workspaceFolder}/build"],
|
||||||
|
"group": "build",
|
||||||
|
"presentation": {
|
||||||
|
"reveal": "always",
|
||||||
|
"panel": "dedicated"
|
||||||
|
},
|
||||||
|
"problemMatcher": "$gcc",
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/ninja/v1.13.2/ninja.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Run Project",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${env:HOME}/.pico-sdk/picotool/2.3.1/picotool/picotool",
|
||||||
|
"args": [
|
||||||
|
"load",
|
||||||
|
"${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"-fx"
|
||||||
|
],
|
||||||
|
"presentation": {
|
||||||
|
"reveal": "always",
|
||||||
|
"panel": "dedicated"
|
||||||
|
},
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/picotool/2.3.1/picotool/picotool.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Flash",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/${command:raspberry-pi-pico.getTarget}.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; program \"${command:raspberry-pi-pico.launchTargetPath}\" verify reset exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Rescue Reset",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/${command:raspberry-pi-pico.getChip}-rescue.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; reset halt; exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "RISC-V Reset (RP2350)",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-c",
|
||||||
|
"set USE_CORE { rv0 rv1 cm0 cm1 }",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/rp2350.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; init;",
|
||||||
|
"-c",
|
||||||
|
"write_memory 0x40120158 8 { 0x3 }; echo [format \"Info : ARCHSEL 0x%02x\" [read_memory 0x40120158 8 1]];",
|
||||||
|
"-c",
|
||||||
|
"reset halt; targets rp2350.rv0; echo [format \"Info : ARCHSEL_STATUS 0x%02x\" [read_memory 0x4012015C 8 1]]; exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -0,0 +1,91 @@
|
|||||||
|
# MIT License
|
||||||
|
#
|
||||||
|
# Copyright (c) 2026 Kevin Thomas
|
||||||
|
#
|
||||||
|
# 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.
|
||||||
|
#
|
||||||
|
# Author: Kevin Thomas
|
||||||
|
# Email: kevin@mytechnotalent.com
|
||||||
|
# GitHub: https://github.com/mytechnotalent
|
||||||
|
# File: CMakeLists.txt
|
||||||
|
# Desc: Configures the RP2350 Pico SDK project for the Operation Black Start
|
||||||
|
# CTF relay firmware.
|
||||||
|
# Created: 2026
|
||||||
|
|
||||||
|
cmake_minimum_required(VERSION 3.13)
|
||||||
|
|
||||||
|
set(CMAKE_C_STANDARD 11)
|
||||||
|
set(CMAKE_CXX_STANDARD 17)
|
||||||
|
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
|
||||||
|
|
||||||
|
# Initialise pico_sdk from installed location
|
||||||
|
# (note this can come from environment, CMake cache etc)
|
||||||
|
|
||||||
|
# == DO NOT EDIT THE FOLLOWING LINES for the Raspberry Pi Pico VS Code Extension to work ==
|
||||||
|
if(WIN32)
|
||||||
|
set(USERHOME $ENV{USERPROFILE})
|
||||||
|
else()
|
||||||
|
set(USERHOME $ENV{HOME})
|
||||||
|
endif()
|
||||||
|
set(sdkVersion 2.3.1)
|
||||||
|
set(toolchainVersion 15_2_Rel1)
|
||||||
|
set(picotoolVersion 2.3.1)
|
||||||
|
set(picoVscode ${USERHOME}/.pico-sdk/cmake/pico-vscode.cmake)
|
||||||
|
if (EXISTS ${picoVscode})
|
||||||
|
include(${picoVscode})
|
||||||
|
endif()
|
||||||
|
# ====================================================================================
|
||||||
|
set(PICO_BOARD pico2 CACHE STRING "Board type")
|
||||||
|
|
||||||
|
# Pull in Raspberry Pi Pico SDK (must be before project)
|
||||||
|
include(pico_sdk_import.cmake)
|
||||||
|
|
||||||
|
project(0x0001b_ctf C CXX ASM)
|
||||||
|
|
||||||
|
# Initialise the Raspberry Pi Pico SDK
|
||||||
|
pico_sdk_init()
|
||||||
|
|
||||||
|
# Add executable with modular sources in src/
|
||||||
|
add_executable(0x0001b_ctf
|
||||||
|
src/main.c
|
||||||
|
src/grid.c
|
||||||
|
src/console.c
|
||||||
|
)
|
||||||
|
|
||||||
|
pico_set_program_name(0x0001b_ctf "0x0001b_ctf")
|
||||||
|
pico_set_program_version(0x0001b_ctf "0.1")
|
||||||
|
|
||||||
|
# Modify the below lines to enable/disable output over UART/USB
|
||||||
|
pico_enable_stdio_uart(0x0001b_ctf 1)
|
||||||
|
pico_enable_stdio_usb(0x0001b_ctf 0)
|
||||||
|
target_compile_definitions(0x0001b_ctf PRIVATE
|
||||||
|
PICO_DEFAULT_UART_BAUD_RATE=115200
|
||||||
|
)
|
||||||
|
|
||||||
|
# Add the standard library to the build
|
||||||
|
target_link_libraries(0x0001b_ctf
|
||||||
|
pico_stdlib
|
||||||
|
)
|
||||||
|
|
||||||
|
# Add the standard include files to the build
|
||||||
|
target_include_directories(0x0001b_ctf PRIVATE
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}/include
|
||||||
|
)
|
||||||
|
|
||||||
|
pico_add_extra_outputs(0x0001b_ctf)
|
||||||
@@ -0,0 +1,442 @@
|
|||||||
|
# Operation Black Start - Student Instructions
|
||||||
|
|
||||||
|
**⚠ WORLDGRID EMERGENCY INCIDENT ⚠**
|
||||||
|
|
||||||
|
```
|
||||||
|
+----------------------------------------------------------------------------------------+
|
||||||
|
| |
|
||||||
|
| ██████╗ ██╗ █████╗ ██████╗██╗ ██╗███████╗████████╗ █████╗ ██████╗ ████████╗ |
|
||||||
|
| ██╔══██╗██║ ██╔══██╗██╔════╝██║ ██╔╝██╔════╝╚══██╔══╝██╔══██╗██╔══██╗╚══██╔══╝ |
|
||||||
|
| ██████╔╝██║ ███████║██║ █████╔╝ ███████╗ ██║ ███████║██████╔╝ ██║ |
|
||||||
|
| ██╔══██╗██║ ██╔══██║██║ ██╔═██╗ ╚════██║ ██║ ██╔══██║██╔══██╗ ██║ |
|
||||||
|
| ██████╔╝███████╗██║ ██║╚██████╗██║ ██╗███████╗ ██║ ██║ ██║██║ ██║ ██║ |
|
||||||
|
| ╚═════╝ ╚══════╝╚═╝ ╚═╝ ╚═════╝██║ ██║╚══════╝ ╚═╝ ╚═╝ ╚═╝██║ ██║ ██║ |
|
||||||
|
| |
|
||||||
|
| |
|
||||||
|
| O P E R A T I O N B L A C K S T A R T |
|
||||||
|
| |
|
||||||
|
| *** PRIORITY RED *** |
|
||||||
|
| |
|
||||||
|
+----------------------------------------------------------------------------------------+
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Project Overview
|
||||||
|
|
||||||
|
WorldGrid Compact's emergency firmware build for its GRID-7 relay fleet
|
||||||
|
shipped a miscompiled safety threshold and a hardcoded false status string,
|
||||||
|
so deployed relays report a false-safe "STABLE" status while the frozen
|
||||||
|
frequency deviation reading of 0.87 Hz is nearly 50% beyond the 0.60 Hz
|
||||||
|
engineering limit. The source was overwritten by the next build and cannot
|
||||||
|
be recovered, so the only surviving evidence is the exact miscompiled
|
||||||
|
training image. Students reverse engineer `CTF-01.bin` with Ghidra, locate
|
||||||
|
and patch both defects directly in the binary, export a corrected image,
|
||||||
|
flash it to a Pico 2, and prove the corrected behavior with GDB and a UART
|
||||||
|
console.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Scenario Briefing
|
||||||
|
|
||||||
|
### Background
|
||||||
|
|
||||||
|
**WorldGrid Compact** is the emergency interconnection standard shared by
|
||||||
|
three allied national grid operators. When any member's primary SCADA
|
||||||
|
network goes dark, a fleet of small embedded relay nodes - call sign
|
||||||
|
**GRID-7** - is the only thing standing between an orderly recovery and an
|
||||||
|
uncontrolled cascade. Each relay node watches the last known grid frequency
|
||||||
|
deviation, decides whether conditions are safe, and either **holds** the
|
||||||
|
automatic black-start dispatch or **authorizes** it.
|
||||||
|
|
||||||
|
At 03:11 UTC, a coordinated cyberattack severed the primary SCADA uplink
|
||||||
|
across the GRID-7 corridor and the WATER-3 aqueduct pumping stations that
|
||||||
|
depend on it. With the network coordination center offline and three
|
||||||
|
continents' worth of hospitals, rail systems, and water treatment plants
|
||||||
|
running on backup power, WorldGrid's engineering team did the only thing
|
||||||
|
they could: they rushed an emergency firmware build for the relay fleet and
|
||||||
|
pushed it within **eleven minutes** of the attack being detected.
|
||||||
|
|
||||||
|
### The Disaster
|
||||||
|
|
||||||
|
The engineer who built that emergency image, **Dr. Elias Renner**, has not
|
||||||
|
slept in thirty-one hours. He compiled the fix, ran a five-second bench
|
||||||
|
test, and shipped it - because the alternative was leaving the relay fleet
|
||||||
|
completely blind. It appears to work. The relay boots. It prints a status
|
||||||
|
report. It reports **GRID STATUS: STABLE** and **DISPATCH PATH:
|
||||||
|
AUTHORIZED**.
|
||||||
|
|
||||||
|
There is a problem: the frozen frequency reading latched at the moment
|
||||||
|
communications were cut shows a deviation of **0.87 Hz** - nearly *50%
|
||||||
|
beyond* WorldGrid's hard engineering limit of **0.60 Hz**. A deviation this
|
||||||
|
large, if trusted, means the grid is nowhere near stable enough for an
|
||||||
|
automatic black-start dispatch. If the fleet authorizes dispatch on a false
|
||||||
|
"STABLE" reading, cascading generator trips will follow within minutes,
|
||||||
|
and GRID-7 and WATER-3 will go dark for the second time - this time with no
|
||||||
|
backup plan.
|
||||||
|
|
||||||
|
**Dr. Renner's rushed build has a bug. Multiple relay nodes are already
|
||||||
|
reporting the same false-safe status. Nobody has found where in the
|
||||||
|
compiled firmware the error lives, because the source code used for that
|
||||||
|
emergency compile was overwritten by the next build fifteen minutes later
|
||||||
|
and cannot be recovered.**
|
||||||
|
|
||||||
|
### The Only Surviving Evidence
|
||||||
|
|
||||||
|
One relay node - the training/verification unit - still holds the exact
|
||||||
|
miscompiled image that shipped to the fleet. This binary, and this binary
|
||||||
|
alone, is the only remaining copy of the emergency build. There is no
|
||||||
|
source code. There is no build log. There is only the compiled image, a
|
||||||
|
UART cable, and whatever a skilled embedded reverse engineer can prove by
|
||||||
|
reading machine code.
|
||||||
|
|
||||||
|
### The Human Stakes
|
||||||
|
|
||||||
|
| Consequence if the false "STABLE" reading is trusted | Scale |
|
||||||
|
|---|---|
|
||||||
|
| Hospitals on generator backup past their fuel reserve | 214 facilities |
|
||||||
|
| Water treatment and pumping stations losing pressure | 3 aqueduct systems |
|
||||||
|
| Rail corridors stranded mid-route | 6 national rail networks |
|
||||||
|
| Estimated population affected by cascading failure | 40+ million people |
|
||||||
|
|
||||||
|
**The options are:**
|
||||||
|
|
||||||
|
1. ❌ **Trust the fleet's reported status** - dispatch fires on a false
|
||||||
|
reading, cascading failure follows within the hour.
|
||||||
|
2. ❌ **Shut the entire relay fleet down** - buys time, but leaves 40
|
||||||
|
million people with no automated recovery path at all.
|
||||||
|
3. **REVERSE ENGINEER THE EMERGENCY BUILD** - find the exact
|
||||||
|
miscompiled bytes, patch them, verify the corrected image on real
|
||||||
|
hardware, and hand the fix to the field team so the *rest of the fleet*
|
||||||
|
can be safely repatched before the next attempt.
|
||||||
|
|
||||||
|
### THE SHORTAGE
|
||||||
|
|
||||||
|
For years, the world treated embedded systems as invisible infrastructure.
|
||||||
|
The engineers who could read a vector table, decode a Thumb branch, or
|
||||||
|
patch a miscompiled constant directly in a stripped binary were never
|
||||||
|
numerous enough. Tonight almost all of them are already in the field
|
||||||
|
chasing other failures. **You are the reserve team.**
|
||||||
|
|
||||||
|
You were called in because you can do something Dr. Renner's exhausted
|
||||||
|
team cannot do right now: read what the processor is actually doing, with
|
||||||
|
no source code, no time for a rewrite, and no room for a guess.
|
||||||
|
|
||||||
|
> **⏰ TIME PRESSURE:** The field team is standing by to push your verified
|
||||||
|
> patch to the rest of the GRID-7 fleet. Every relay node still reporting
|
||||||
|
> a false "STABLE" status is one dispatch cycle away from disaster.
|
||||||
|
|
||||||
|
> **AUTHORIZED LAB ONLY:** This challenge uses a supplied Pico 2 training
|
||||||
|
> relay and its exact miscompiled firmware image. Do not connect this
|
||||||
|
> exercise to a public network, an operational grid, a water utility, or
|
||||||
|
> any device you do not own or have explicit written authorization to test.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Learning Objectives
|
||||||
|
|
||||||
|
- Decode the RP2350 / ARM Cortex-M33 vector table and identify the reset
|
||||||
|
handler and initial stack pointer.
|
||||||
|
- Trace the bootrom-to-reset handoff and translate Thumb reset-vector
|
||||||
|
addresses into real function entry points.
|
||||||
|
- Locate a miscompiled boundary comparison and reason about the correct
|
||||||
|
immediate value the compiler should have encoded.
|
||||||
|
- Patch compare instructions and a status string directly in a raw binary
|
||||||
|
with Ghidra.
|
||||||
|
- Recover a hidden quarantined dispatch frame from the compiled image.
|
||||||
|
- Export and UF2-convert a corrected image, then verify the corrected
|
||||||
|
behavior on real hardware with GDB and a UART console.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## What This Project Tests
|
||||||
|
|
||||||
|
| Week | Concepts Tested |
|
||||||
|
|------|-----------------|
|
||||||
|
| 1 | RP2350 architecture, ARM Cortex-M33 registers, stack, flash/RAM, Thumb assembly, Ghidra static analysis |
|
||||||
|
| 2 | GDB connection, breakpoints, disassembly, register and memory inspection, UART observation |
|
||||||
|
| 3 | Bootrom handoff, vector table, reset handler, startup code, XIP, Thumb-bit addressing |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Part 1: Understanding the System
|
||||||
|
|
||||||
|
### GRID-7 Relay Hardware
|
||||||
|
|
||||||
|
| Component | Connection | Purpose |
|
||||||
|
|-----------|------------|---------|
|
||||||
|
| Raspberry Pi Pico 2 | RP2350 | Runs the miscompiled emergency firmware |
|
||||||
|
| UART TX | GPIO 0 | Relay telemetry output |
|
||||||
|
| UART RX | GPIO 1 | Reserved (no command parser is implemented) |
|
||||||
|
| SWD debug interface | Supplied probe | Authorized GDB inspection |
|
||||||
|
|
||||||
|
No LED, relay output, sensor, display, or other peripheral is part of this
|
||||||
|
CTF. Every graded finding lives in flash (`.rodata`/`.text`) or SRAM, and is
|
||||||
|
reachable with only the Weeks 1-3 toolset: Ghidra, GDB, and a UART monitor.
|
||||||
|
|
||||||
|
### UART Configuration
|
||||||
|
|
||||||
|
- Baud: `115200`
|
||||||
|
- Data: `8 bits`
|
||||||
|
- Parity: `none`
|
||||||
|
- Stop: `1`
|
||||||
|
- Logic: `3.3 V`
|
||||||
|
|
||||||
|
### Normal (Intended) Behavior
|
||||||
|
|
||||||
|
The relay should latch the frozen deviation reading, compare it against the
|
||||||
|
**real** WorldGrid safety limit of **60** (0.60 Hz, encoded as an integer
|
||||||
|
`x100`), and report honestly:
|
||||||
|
|
||||||
|
```
|
||||||
|
+-----------------------------------------------------------------+
|
||||||
|
| Intended Relay Behavior |
|
||||||
|
| |
|
||||||
|
| 1. Boot and initialize UART |
|
||||||
|
| 2. Print the boot identity and a signal-quality banner |
|
||||||
|
| 3. Compare the frozen 87 (0.87 Hz) reading against the 60 |
|
||||||
|
| (0.60 Hz) safety limit |
|
||||||
|
| 4. 87 exceeds 60, so the grid is NOT stable |
|
||||||
|
| 5. Report GRID STATUS: CRITICAL and DISPATCH PATH: HELD |
|
||||||
|
| 6. Repeat the report once per second until conditions change |
|
||||||
|
+-----------------------------------------------------------------+
|
||||||
|
```
|
||||||
|
|
||||||
|
### Observed (Buggy) Behavior - What You Will See When You First Flash `CTF-01.uf2`
|
||||||
|
|
||||||
|
```text
|
||||||
|
GLOBAL EMBEDDED RESPONSE NETWORK
|
||||||
|
BLACK START WINDOW: 27 MINUTES
|
||||||
|
UART0 115200 8N1 | AUTHORIZED LAB CONSOLE
|
||||||
|
SIGNAL: NORMAL
|
||||||
|
RESPONSE> GRID STATUS: STABLE
|
||||||
|
DISPATCH PATH: AUTHORIZED
|
||||||
|
LAST FRAME: QUARANTINED
|
||||||
|
RESPONSE>
|
||||||
|
```
|
||||||
|
|
||||||
|
> **Terminal Timing Note:** The first four lines (`GLOBAL EMBEDDED...` through
|
||||||
|
> `SIGNAL: NORMAL`) represent the **initial boot banner**, emitted once during
|
||||||
|
> startup. If your serial terminal (PuTTY) connects after the board has
|
||||||
|
> booted, you will observe the continuous 1-second status stream (`GRID
|
||||||
|
> STATUS...` and `DISPATCH PATH...`). To view the boot banner in your terminal,
|
||||||
|
> reset the Pico (pulse `RUN` to `GND`) while PuTTY is actively connected.
|
||||||
|
|
||||||
|
This is exactly what Dr. Renner's team is seeing on the deployed fleet. It
|
||||||
|
is wrong, and it is wrong in **two independent ways** inside the compiled
|
||||||
|
binary. Do not assume the first readable sentence is the full truth -
|
||||||
|
treat every printed line as evidence to be checked against the machine
|
||||||
|
code, not as a fact on its own.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Part 2: The Firmware
|
||||||
|
|
||||||
|
You do not have the source code. It was overwritten fifteen minutes after
|
||||||
|
the emergency build shipped. You have only the compiled image. Your job is
|
||||||
|
to reverse engineer it with Ghidra, locate the defects, and patch the
|
||||||
|
binary directly - exactly the way Dr. Renner's field team will need to
|
||||||
|
patch the rest of the deployed fleet.
|
||||||
|
|
||||||
|
### What The Firmware Does
|
||||||
|
|
||||||
|
1. Initializes UART0 and stdio.
|
||||||
|
2. Reads a frozen grid-frequency-deviation reading that was latched in
|
||||||
|
memory before communications were severed.
|
||||||
|
3. Compares that reading against a compiled-in safety threshold - **twice**,
|
||||||
|
once for each independent status line it reports.
|
||||||
|
4. Prints a boot banner containing an unconditional signal-quality line.
|
||||||
|
5. Enters an infinite loop printing the grid classification and dispatch
|
||||||
|
decision once per second.
|
||||||
|
|
||||||
|
### Bug Summary - What You Are Graded On
|
||||||
|
|
||||||
|
| Bug # | Category | Severity | Description | Hint |
|
||||||
|
|-------|----------|----------|--------------|------|
|
||||||
|
| **Bug #1** | Miscompiled safety constant | **CRITICAL** | The safety threshold used to classify the frozen reading was compiled far too permissive. It is used **twice** - once for the operator-facing status and once for the automated dispatch decision - and **both** copies must be corrected. | The real WorldGrid safety limit is 60 (0.60 Hz). Search for the wrong immediate value used in the comparison. |
|
||||||
|
| **Bug #2** | Hardcoded string literal | **HIGH** | The boot banner unconditionally prints a signal-quality word that does not reflect the actual reading, regardless of what the relay later reports. | The correct word describes the true state of a 0.87 Hz deviation against a 0.60 Hz limit - not "NORMAL". |
|
||||||
|
|
||||||
|
**Important:** The replacement text for Bug #2 **must be the same length**
|
||||||
|
as the original - patching a shorter or longer string will corrupt
|
||||||
|
adjacent flash data.
|
||||||
|
|
||||||
|
### A Third Finding - Not a Bug, a Recovery Task
|
||||||
|
|
||||||
|
Somewhere in this image is the **quarantined black-start authorization
|
||||||
|
frame** - the exact frame the relay is supposed to transmit to the
|
||||||
|
regional dispatcher once a human operator confirms it is safe to proceed.
|
||||||
|
It is never printed by the firmware. Recovering it (without patching
|
||||||
|
anything) is required evidence for your final report.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Part 3: Your Assignment
|
||||||
|
|
||||||
|
Whenever a task asks you to **Document** or **answer**, write your answers
|
||||||
|
in a single file named `CTF-01-Answers.md`.
|
||||||
|
|
||||||
|
### Task 1: Setup and Initial Analysis
|
||||||
|
|
||||||
|
1. Create a new Ghidra project named `Black_Start_Investigation`.
|
||||||
|
2. Import `CTF-01.bin`.
|
||||||
|
3. Configure the language as **ARM Cortex 32-bit, little endian**.
|
||||||
|
4. Set the base address to `0x10000000`.
|
||||||
|
5. Run auto-analysis.
|
||||||
|
|
||||||
|
**Document:**
|
||||||
|
- A screenshot of the Ghidra **Import Results** or **Program Information**
|
||||||
|
window showing the project name, processor settings, and base address.
|
||||||
|
- The address of `main()`.
|
||||||
|
- The address of the recurring status loop (the branch target that repeats
|
||||||
|
once per second).
|
||||||
|
- The vector-table base, the initial stack pointer, and the reset-handler
|
||||||
|
pointer as stored (note its Thumb bit) versus the actual instruction
|
||||||
|
address.
|
||||||
|
|
||||||
|
### Task 2: Find and Patch Bug #1 - The Miscalibrated Safety Threshold
|
||||||
|
|
||||||
|
1. Find **both** locations where the frozen reading is compared against
|
||||||
|
the miscompiled safety constant.
|
||||||
|
2. Document the exact address, the original instruction, and the original
|
||||||
|
immediate value at each location.
|
||||||
|
3. Determine the correct immediate value. **Caution:** the compiler may
|
||||||
|
not have encoded the raw threshold you expect - a strict "less than"
|
||||||
|
comparison against an unsigned value is often optimized into a
|
||||||
|
"less-or-equal" comparison against one less than the threshold. Show
|
||||||
|
your reasoning.
|
||||||
|
4. Patch **both** locations in Ghidra using the **Bytes Window** workflow:
|
||||||
|
> **Critical ARM Thumb-2 Patching Note:** In ARM Cortex-M, compare instructions that directly precede conditional execution blocks (`ite hi`) must **not** be patched using the right-click *Patch Instruction* dialog. Ghidra's automatic re-disassembler encounters an internal context conflict with the subsequent `ite hi` instruction, which collapses Thumb decoding and swallows Compare Site B (`0x1000020A`).
|
||||||
|
>
|
||||||
|
> To patch cleanly without breaking downstream disassembly, use the **Bytes Window**:
|
||||||
|
> 1. Ensure the Bytes window is open (**Window** -> **Bytes: CTF-01.bin**).
|
||||||
|
> 2. In the Bytes window toolbar, click the **pencil icon** (**Toggle Edit Mode**).
|
||||||
|
> 3. In the Listing window, click on address `0x100001FC` (Compare Site A) and press **`C`** (**Clear Code Bytes**). The instruction temporarily clears into raw bytes (`5E 2B`).
|
||||||
|
> 4. In the Bytes window, locate offset `100001fc`, click on `5E`, and change it to **`3B`**.
|
||||||
|
> 5. Click back in the Listing window on address `0x100001FC` and press **`D`** (**Disassemble**). The instruction immediately disassembles cleanly as `cmp r3, #0x3b`.
|
||||||
|
> 6. Notice that Compare Site B at `0x1000020A` remains completely intact and visible! Repeat the exact same steps at `0x1000020A`: click `0x1000020A` in the Listing, press **`C`**, change `5E` to **`3B`** in the Bytes window, click back in the Listing, and press **`D`**.
|
||||||
|
|
||||||
|
**Questions to answer:**
|
||||||
|
- Why must both locations be patched? What happens if you only patch one?
|
||||||
|
- Why is a false "STABLE" classification on an 0.87 Hz reading dangerous
|
||||||
|
for an automated black-start dispatch?
|
||||||
|
|
||||||
|
### Task 3: Find and Patch Bug #2 - The False Signal Banner
|
||||||
|
|
||||||
|
1. Find the boot-banner string that unconditionally reports the wrong
|
||||||
|
signal quality.
|
||||||
|
2. Document its address and the exact bytes that must change.
|
||||||
|
3. Patch the string, preserving its exact length.
|
||||||
|
|
||||||
|
**Questions to answer:**
|
||||||
|
- Document the original vs. patched bytes, character by character.
|
||||||
|
- Why is a hardcoded, unconditional status word more dangerous than one
|
||||||
|
that is at least computed from a (miscalibrated) reading?
|
||||||
|
|
||||||
|
### Task 4: Recover the Quarantined Dispatch Frame
|
||||||
|
|
||||||
|
1. Use Ghidra's Defined Strings (or a raw string search) to locate the
|
||||||
|
hidden black-start authorization frame.
|
||||||
|
2. Document its address and explain why it is never transmitted by the
|
||||||
|
current firmware.
|
||||||
|
3. Do **not** attempt to patch this value - it is evidence, not a bug.
|
||||||
|
|
||||||
|
### Task 5: Export and Verify
|
||||||
|
|
||||||
|
1. Export your patched binary as `CTF-01_fixed.bin`.
|
||||||
|
2. Convert it to UF2 format for the RP2350:
|
||||||
|
```bash
|
||||||
|
python uf2conv.py CTF-01_fixed.bin --base 0x10000000 --family 0xe48bff59 --output CTF-01_fixed.uf2
|
||||||
|
```
|
||||||
|
3. Flash `CTF-01_fixed.uf2` to your Pico 2 and capture the corrected UART
|
||||||
|
output.
|
||||||
|
4. Confirm that the corrected image now reports **GRID STATUS: CRITICAL**,
|
||||||
|
**DISPATCH PATH: HELD**, and the corrected signal-quality word - an
|
||||||
|
honest, safe report instead of a false "all clear."
|
||||||
|
5. Build a summary table of every patch: address, original bytes, patched
|
||||||
|
bytes, and a one-line description.
|
||||||
|
|
||||||
|
### Task 6: Written Reflection (short answers, 150 words or less each)
|
||||||
|
|
||||||
|
1. Why is "the build was rushed under emergency pressure" not an
|
||||||
|
acceptable excuse for shipping a firmware defect that could trigger a
|
||||||
|
cascading grid failure?
|
||||||
|
2. Name one concrete engineering practice (code review, static analysis,
|
||||||
|
hardware-in-the-loop test, etc.) that would have caught **each** of the
|
||||||
|
two graded bugs before this image ever reached the fleet.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## How To Breadboard
|
||||||
|
|
||||||
|
- Pico 2 **GPIO 0 / UART TX** -> USB-UART adapter **RX**
|
||||||
|
- Pico 2 **GPIO 1 / UART RX** -> USB-UART adapter **TX**
|
||||||
|
- Pico 2 **GND** -> USB-UART adapter **GND**
|
||||||
|
- Use **3.3 V logic only**. Never connect a 5 V line to a Pico GPIO.
|
||||||
|
- Connect the supplied SWD probe according to its documented pinout.
|
||||||
|
|
||||||
|
The supplied image is `CTF-01.bin` (for Ghidra analysis) and `CTF-01.uf2`
|
||||||
|
(for flashing). If your instructor supplies different filenames, record the
|
||||||
|
actual filenames in your report.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Memory Map Reference
|
||||||
|
|
||||||
|
| Region | Address | Purpose |
|
||||||
|
|--------|---------|---------|
|
||||||
|
| Bootrom | `0x00000000` | Immutable boot code |
|
||||||
|
| Flash/XIP | `0x10000000` | Vector table, code, constants, strings |
|
||||||
|
| SRAM | `0x20000000` | Stack and writable state |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Submission Format
|
||||||
|
|
||||||
|
Submit a folder containing:
|
||||||
|
|
||||||
|
- `CTF-01-Answers.md`;
|
||||||
|
- screenshots or terminal transcripts;
|
||||||
|
- `CTF-01_fixed.bin` and `CTF-01_fixed.uf2`;
|
||||||
|
- the original image hash.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Success Criteria
|
||||||
|
|
||||||
|
You complete the challenge when you can prove all of the following:
|
||||||
|
|
||||||
|
- You can explain how the RP2350 reaches the relay's code from reset.
|
||||||
|
- You can locate and patch both copies of the miscalibrated threshold.
|
||||||
|
- You can locate and patch the false signal-quality string without
|
||||||
|
corrupting adjacent data.
|
||||||
|
- You can export, convert, and flash a corrected image.
|
||||||
|
- You can prove on real hardware that the corrected image reports the
|
||||||
|
true, dangerous state instead of the false "all clear."
|
||||||
|
- You can recover the quarantined dispatch frame as evidence.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Academic Integrity
|
||||||
|
|
||||||
|
By submitting this CTF work, you certify that:
|
||||||
|
|
||||||
|
1. You used only the supplied training relay, image, and lab interface.
|
||||||
|
2. You did not connect the challenge to a public network, an operational
|
||||||
|
grid, a water utility, or any third-party device.
|
||||||
|
3. You understand that embedded reverse engineering and binary patching
|
||||||
|
require explicit authorization in any real-world context.
|
||||||
|
4. You will report any discovered weakness responsibly to the course
|
||||||
|
instructor.
|
||||||
|
|
||||||
|
The world is short on people who can do this work. Treat that
|
||||||
|
responsibility seriously: verify before you patch, patch before you trust,
|
||||||
|
and never confuse a clean-looking status line with a safe system.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Reference Material
|
||||||
|
|
||||||
|
- ARM Cortex-M33 Technical Reference Manual
|
||||||
|
- RP2350 datasheet
|
||||||
|
- GDB documentation
|
||||||
|
- Ghidra documentation: [https://ghidra-sre.org/](https://ghidra-sre.org/)
|
||||||
Binary file not shown.
@@ -0,0 +1,237 @@
|
|||||||
|
# Operation Black Start - Requirements & Grading Criteria
|
||||||
|
|
||||||
|
```
|
||||||
|
+----------------------------------------------------------------------------------------+
|
||||||
|
| |
|
||||||
|
| ██████╗ ██╗ █████╗ ██████╗██╗ ██╗███████╗████████╗ █████╗ ██████╗ ████████╗ |
|
||||||
|
| ██╔══██╗██║ ██╔══██╗██╔════╝██║ ██╔╝██╔════╝╚══██╔══╝██╔══██╗██╔══██╗╚══██╔══╝ |
|
||||||
|
| ██████╔╝██║ ███████║██║ █████╔╝ ███████╗ ██║ ███████║██████╔╝ ██║ |
|
||||||
|
| ██╔══██╗██║ ██╔══██║██║ ██╔═██╗ ╚════██║ ██║ ██╔══██║██╔══██╗ ██║ |
|
||||||
|
| ██████╔╝███████╗██║ ██║╚██████╗██║ ██╗███████╗ ██║ ██║ ██║██║ ██║ ██║ |
|
||||||
|
| ╚═════╝ ╚══════╝╚═╝ ╚═╝ ╚═════╝██║ ██║╚══════╝ ╚═╝ ╚═╝ ╚═╝██║ ██║ ██║ |
|
||||||
|
| |
|
||||||
|
| |
|
||||||
|
| O P E R A T I O N B L A C K S T A R T |
|
||||||
|
| |
|
||||||
|
| REQUIREMENTS & GRADING CRITERIA |
|
||||||
|
| |
|
||||||
|
+----------------------------------------------------------------------------------------+
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Project Overview
|
||||||
|
|
||||||
|
Students are the reverse-engineering reserve team called in after WorldGrid
|
||||||
|
Compact's emergency firmware build shipped a miscompiled safety threshold and
|
||||||
|
a false status string to its GRID-7 relay fleet. Students reverse engineer
|
||||||
|
`CTF-01.bin` with Ghidra, locate two real defects, patch them in the binary,
|
||||||
|
export a corrected image, flash it to real hardware, and prove the corrected
|
||||||
|
behavior with the debugger and the console.
|
||||||
|
|
||||||
|
The challenge is separate from all FINAL projects and contains no FINAL-project
|
||||||
|
answer, constant, address, bug, or patch.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Learning Objectives
|
||||||
|
|
||||||
|
- Decode an ARM Cortex-M33 vector table and identify the reset handler and
|
||||||
|
initial stack pointer.
|
||||||
|
- Translate Thumb reset-vector addresses into real function entry points.
|
||||||
|
- Locate a miscompiled boundary comparison and reason about its immediate
|
||||||
|
value.
|
||||||
|
- Patch compare instructions and a status string in a raw binary with Ghidra.
|
||||||
|
- Export and UF2-convert a corrected image, then verify it on real hardware.
|
||||||
|
- Capture derived state with GDB and read UART console output.
|
||||||
|
|
||||||
|
Students must use only Weeks 1-3 concepts: ARM registers and stack behavior,
|
||||||
|
UART output, GDB, Ghidra static analysis and binary patching, vector tables,
|
||||||
|
reset startup, XIP, and Thumb addressing.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Deliverables Checklist
|
||||||
|
|
||||||
|
| # | Deliverable | Format | Criterion |
|
||||||
|
|---|-------------|--------|-----------|
|
||||||
|
| 1 | Ghidra project screenshot (project name, processor, base address) | PNG/JPG | 1.1 |
|
||||||
|
| 2 | `main()` and status-loop addresses | Inside `CTF-01-Answers.md` | 1.2 |
|
||||||
|
| 3 | Vector table base, initial SP, reset pointer | Inside `CTF-01-Answers.md` | 1.3 |
|
||||||
|
| 4 | Thumb bit explanation | Inside `CTF-01-Answers.md` | 1.4 |
|
||||||
|
| 5 | Bug #1 evidence and patches (both compare sites) | Inside `CTF-01-Answers.md` | 2.1-2.6 |
|
||||||
|
| 6 | Bug #2 evidence and patch (six characters) | Inside `CTF-01-Answers.md` | 3.1-3.4 |
|
||||||
|
| 7 | Recovered dispatch frame and address | Inside `CTF-01-Answers.md` | 4.1-4.2 |
|
||||||
|
| 8 | `CTF-01_fixed.bin` | BIN file | 5.1 |
|
||||||
|
| 9 | `CTF-01_fixed.uf2` | UF2 file | 5.2 |
|
||||||
|
| 10 | Corrected console transcript | Inside `CTF-01-Answers.md` | 5.3 |
|
||||||
|
| 11 | Summary table of all patches | Inside `CTF-01-Answers.md` | 5.4 |
|
||||||
|
| 12 | Written reflection | Inside `CTF-01-Answers.md` | 6.1-6.2 |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Required Tools and Equipment
|
||||||
|
|
||||||
|
| Tool | Purpose |
|
||||||
|
|------|---------|
|
||||||
|
| Raspberry Pi Pico 2 | Isolated target |
|
||||||
|
| 3.3 V USB-UART adapter | UART capture on GPIO 0 (TX) / GPIO 1 (RX) |
|
||||||
|
| Serial monitor | Observe output |
|
||||||
|
| Ghidra | Static analysis and binary patching |
|
||||||
|
| Python (`uf2conv.py`) | UF2 conversion |
|
||||||
|
| `CTF-01.bin` and `CTF-01.uf2` | Supplied artifacts |
|
||||||
|
|
||||||
|
UART settings: **115200 baud, 8 data bits, no parity, 1 stop bit**.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Artifact Identity
|
||||||
|
|
||||||
|
The instructor-issued artifact hashes are:
|
||||||
|
|
||||||
|
```text
|
||||||
|
CTF-01.bin 425591AC17FF4C22206286EE6F40B06A89523483804850A41854A9B6F89D7B70
|
||||||
|
CTF-01.uf2 B1552EE3BB5763D96C65D8DF1C86984EE842EF1A823FDF5D94132B1E10FF9D16
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Grading Rubric - Detailed Breakdown
|
||||||
|
|
||||||
|
### Task 1: Setup and Initial Analysis (15 points)
|
||||||
|
|
||||||
|
| Criterion | Points | Full credit | Partial credit | No credit |
|
||||||
|
|-----------|--------|-------------|----------------|-----------|
|
||||||
|
| Criterion 1.1: Ghidra Project Setup | 3 | Correct project name, `ARM:LE:32:Cortex` (ARM Cortex 32-bit little endian), base `0x10000000` | One item off | Not set up |
|
||||||
|
| Criterion 1.2: main() and Status-Loop Addresses | 4 | Both addresses correct | One correct | Neither found |
|
||||||
|
| Criterion 1.3: Vector Table Decoding | 4 | Correct base, initial SP, reset pointer | One missing | Not found |
|
||||||
|
| Criterion 1.4: Thumb Addressing | 4 | Correctly clears bit 0 and identifies `main()` | General explanation | Incorrect |
|
||||||
|
|
||||||
|
### Task 2: Find and Patch Bug #1: The Miscalibrated Safety Threshold (30 points)
|
||||||
|
|
||||||
|
| Criterion | Points | Full credit | Partial credit | No credit |
|
||||||
|
|-----------|--------|-------------|----------------|-----------|
|
||||||
|
| Criterion 2.1: Locate Compare Site A | 5 | Correct address and original bytes | Address off | Not found |
|
||||||
|
| Criterion 2.2: Locate Compare Site B | 5 | Correct address and original bytes | Address off | Not found |
|
||||||
|
| Criterion 2.3: Correct Immediate-Value Reasoning | 8 | Explains the `<` to `<=` transform and gives `0x3B` | Correct value, no reasoning | Wrong value |
|
||||||
|
| Criterion 2.4: Patch Compare Site A | 4 | Byte change verified | Wrong byte | Not patched |
|
||||||
|
| Criterion 2.5: Patch Compare Site B | 4 | Byte change verified | Wrong byte | Not patched |
|
||||||
|
| Criterion 2.6: Explain Why Both Sites Must Be Patched | 4 | Clear explanation of the two independent comparisons | Vague | Missing |
|
||||||
|
|
||||||
|
### Task 3: Find and Patch Bug #2: The False Signal Banner (20 points)
|
||||||
|
|
||||||
|
| Criterion | Points | Full credit | Partial credit | No credit |
|
||||||
|
|-----------|--------|-------------|----------------|-----------|
|
||||||
|
| Criterion 3.1: Locate the Banner String | 5 | Correct address | Approximate | Not found |
|
||||||
|
| Criterion 3.2: Patch Six Characters | 8 | All six bytes changed, length preserved | Correct text, wrong bytes documented | Wrong length |
|
||||||
|
| Criterion 3.3: Character-by-Character Documentation | 4 | Original vs patched byte for all six characters | Partial | Missing |
|
||||||
|
| Criterion 3.4: Explain the Danger of a Hardcoded Status Word | 3 | Clear, specific reasoning | Generic | Missing |
|
||||||
|
|
||||||
|
### Task 4: Recover the Quarantined Dispatch Frame (10 points)
|
||||||
|
|
||||||
|
| Criterion | Points | Full credit | Partial credit | No credit |
|
||||||
|
|-----------|--------|-------------|----------------|-----------|
|
||||||
|
| Criterion 4.1: Recover the Dispatch Frame | 6 | Correct address and full text | Partial text | Not found |
|
||||||
|
| Criterion 4.2: Explain Why It Is Never Transmitted | 4 | Clear static-analysis explanation | Vague | Missing |
|
||||||
|
|
||||||
|
### Task 5: Export and Verify (20 points)
|
||||||
|
|
||||||
|
| Criterion | Points | Full credit | Partial credit | No credit |
|
||||||
|
|-----------|--------|-------------|----------------|-----------|
|
||||||
|
| Criterion 5.1: Export CTF-01_fixed.bin | 4 | Valid patched binary | Corrupted | Not submitted |
|
||||||
|
| Criterion 5.2: Convert to CTF-01_fixed.uf2 | 4 | Correct base and family flags | Wrong flags | Not submitted |
|
||||||
|
| Criterion 5.3: Hardware Verification | 8 | Corrected console output confirmed (CRITICAL/HELD in 1s stream; DANGER at boot/Ghidra) | Some lines corrected | No verification |
|
||||||
|
| Criterion 5.4: Summary Table of All Patches | 4 | Complete address and before/after table | Missing entries | No table |
|
||||||
|
|
||||||
|
### Task 6: Written Reflection (5 points)
|
||||||
|
|
||||||
|
| Criterion | Points | Full credit | Partial credit | No credit |
|
||||||
|
|-----------|--------|-------------|----------------|-----------|
|
||||||
|
| Criterion 6.1: "Rushed Build" Is Not an Excuse | 2 | Specific, grounded reasoning | Generic | Missing |
|
||||||
|
| Criterion 6.2: One Engineering Practice per Bug | 3 | Concrete practice for each bug | One bug only | Missing |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Common Pitfalls
|
||||||
|
|
||||||
|
| Pitfall | Consequence | Avoidance |
|
||||||
|
|---------|-------------|-----------|
|
||||||
|
| Patching only one threshold site | One status line still lies | Patch both `0x100001FC` and `0x1000020A` |
|
||||||
|
| Assuming the immediate equals the limit | Off-by-one, wrong boundary | Use `0x3B` (59), not `0x3C` (60) |
|
||||||
|
| Using Patch Instruction before IT block | Re-disassembler context conflict swallows Site B | In Listing press `C` -> edit byte in Bytes window (pencil) -> press `D` |
|
||||||
|
| Missing boot banner in serial terminal | PuTTY misses one-time 5ms boot banner | Pulse RUN to GND while connected to capture |
|
||||||
|
| Replacing a string with a different length | Corrupts adjacent flash | `NORMAL` and `DANGER` are both 6 bytes |
|
||||||
|
| Treating an odd vector address as invalid | Thumb analysis fails | Clear bit 0 |
|
||||||
|
| Modifying the quarantined dispatch frame | Destroys evidence | Recover it, do not patch it |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## How To Breadboard
|
||||||
|
|
||||||
|
- **Raspberry Pi Pico 2** powered over USB.
|
||||||
|
- **3.3 V USB-UART adapter**:
|
||||||
|
- Adapter RX to Pico GP0 (UART0 TX)
|
||||||
|
- Adapter TX to Pico GP1 (UART0 RX)
|
||||||
|
- Adapter GND to Pico GND
|
||||||
|
- Do not connect the adapter VCC while the Pico is USB powered.
|
||||||
|
- **Serial monitor:** 115200 baud, 8 data bits, no parity, 1 stop bit.
|
||||||
|
- No other peripherals are required; all evidence is obtained from the console.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Memory Map Reference
|
||||||
|
|
||||||
|
| Region | Address | Purpose |
|
||||||
|
|--------|---------|---------|
|
||||||
|
| Bootrom | `0x00000000` | Immutable boot code |
|
||||||
|
| Flash/XIP | `0x10000000` | Vector table, code, constants, strings |
|
||||||
|
| SRAM | `0x20000000` | Stack and writable state |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Deadline & Submission
|
||||||
|
|
||||||
|
- Create a folder containing the Ghidra screenshot, `CTF-01_fixed.bin`, and
|
||||||
|
`CTF-01_fixed.uf2`.
|
||||||
|
- Write all written answers in a single file named `CTF-01-Answers.md` inside that
|
||||||
|
folder.
|
||||||
|
- ZIP the folder as `lastname-firstname-CTF-01.zip`.
|
||||||
|
- Submit the ZIP before the posted deadline; late submissions lose 10 percent
|
||||||
|
per day.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Grade Scale
|
||||||
|
|
||||||
|
| Grade | Percentage | Points |
|
||||||
|
|-------|------------|--------|
|
||||||
|
| A+ | 97-100% | 97-100 |
|
||||||
|
| A | 93-96% | 93-96 |
|
||||||
|
| A- | 90-92% | 90-92 |
|
||||||
|
| B+ | 87-89% | 87-89 |
|
||||||
|
| B | 84-86% | 84-86 |
|
||||||
|
| B- | 80-83% | 80-83 |
|
||||||
|
| C | 70-79% | 70-79 |
|
||||||
|
| F | 0-69% | 0-69 |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Academic Integrity
|
||||||
|
|
||||||
|
Use only the supplied Pico 2 and firmware. Do not connect the exercise to an
|
||||||
|
operational grid, water plant, public network, military system, or third-party
|
||||||
|
device. This is a controlled, isolated educational exercise. All analysis and
|
||||||
|
patches must be your own work; sharing binaries, addresses, or answers is a
|
||||||
|
violation of the academic integrity policy.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Reference Material
|
||||||
|
|
||||||
|
| Topic | Reference |
|
||||||
|
|-------|-----------|
|
||||||
|
| ARM Cortex-M33 registers and stack | Week 1 |
|
||||||
|
| UART output and console capture | Week 2 |
|
||||||
|
| Vector tables, reset startup, and XIP | Week 2 |
|
||||||
|
| Ghidra static analysis and binary patching | Week 3 |
|
||||||
|
| Thumb addressing | Week 3 |
|
||||||
Binary file not shown.
@@ -0,0 +1,467 @@
|
|||||||
|
# Operation Black Start - Instructor Solution Key
|
||||||
|
|
||||||
|
```
|
||||||
|
+----------------------------------------------------------------------------------------+
|
||||||
|
| |
|
||||||
|
| ██████╗ ██╗ █████╗ ██████╗██╗ ██╗███████╗████████╗ █████╗ ██████╗ ████████╗ |
|
||||||
|
| ██╔══██╗██║ ██╔══██╗██╔════╝██║ ██╔╝██╔════╝╚══██╔══╝██╔══██╗██╔══██╗╚══██╔══╝ |
|
||||||
|
| ██████╔╝██║ ███████║██║ █████╔╝ ███████╗ ██║ ███████║██████╔╝ ██║ |
|
||||||
|
| ██╔══██╗██║ ██╔══██║██║ ██╔═██╗ ╚════██║ ██║ ██╔══██║██╔══██╗ ██║ |
|
||||||
|
| ██████╔╝███████╗██║ ██║╚██████╗██║ ██╗███████╗ ██║ ██║ ██║██║ ██║ ██║ |
|
||||||
|
| ╚═════╝ ╚══════╝╚═╝ ╚═╝ ╚═════╝██║ ██║╚══════╝ ╚═╝ ╚═╝ ╚═╝██║ ██║ ██║ |
|
||||||
|
| |
|
||||||
|
| |
|
||||||
|
| O P E R A T I O N B L A C K S T A R T |
|
||||||
|
| |
|
||||||
|
| *** INSTRUCTOR SOLUTION KEY - RESTRICTED *** |
|
||||||
|
| |
|
||||||
|
+----------------------------------------------------------------------------------------+
|
||||||
|
```
|
||||||
|
|
||||||
|
> The task and criterion headings in this key are word-for-word identical to
|
||||||
|
> `CTF-01-R.md`, so a student can match each criterion one-to-one.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Artifact Identity
|
||||||
|
|
||||||
|
| Artifact | Value |
|
||||||
|
|----------|-------|
|
||||||
|
| Student image | `CTF-01.bin` |
|
||||||
|
| Flash image | `CTF-01.uf2` |
|
||||||
|
| Target | Raspberry Pi Pico 2 / RP2350 ARM Cortex-M33 |
|
||||||
|
| Image base | `0x10000000` |
|
||||||
|
| Console | UART0, GPIO 0 TX / GPIO 1 RX, 115200 8N1 |
|
||||||
|
|
||||||
|
```text
|
||||||
|
CTF-01.bin 425591AC17FF4C22206286EE6F40B06A89523483804850A41854A9B6F89D7B70
|
||||||
|
CTF-01.uf2 B1552EE3BB5763D96C65D8DF1C86984EE842EF1A823FDF5D94132B1E10FF9D16
|
||||||
|
```
|
||||||
|
|
||||||
|
Proof tool: `python3 scripts/verify_ctf.py` returns `11/11 checks passed` against
|
||||||
|
`CTF-01.bin`.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Task 1: Setup and Initial Analysis (15 points)
|
||||||
|
|
||||||
|
### Solution
|
||||||
|
|
||||||
|
**Criterion 1.1: Ghidra Project Setup (3 points).** Import `CTF-01.bin` as
|
||||||
|
`Raw Binary`, language `ARM:LE:32:Cortex`, base address `0x10000000`, then run
|
||||||
|
auto-analysis.
|
||||||
|
|
||||||
|
**Criterion 1.2: main() and Status-Loop Addresses (4 points).**
|
||||||
|
|
||||||
|
| Element | Address |
|
||||||
|
|---------|---------|
|
||||||
|
| `main()` | `0x100001E0` |
|
||||||
|
| Recurring status loop start | `0x10000234` |
|
||||||
|
| Loop back-edge (`b.n 0x10000234`) | `0x10000266` |
|
||||||
|
|
||||||
|
The back-edge instruction at `0x10000266` is `b.n 0x10000234`, encoded as bytes
|
||||||
|
`E5 E7`.
|
||||||
|
|
||||||
|
**Criterion 1.3: Vector Table Decoding (4 points).**
|
||||||
|
First 32 bytes of `CTF-01.bin`:
|
||||||
|
|
||||||
|
```text
|
||||||
|
00 20 08 20 5B 01 00 10 1B 01 00 10 1D 01 00 10
|
||||||
|
11 01 00 10 11 01 00 10 11 01 00 10 11 01 00 10
|
||||||
|
```
|
||||||
|
|
||||||
|
| Evidence | Answer |
|
||||||
|
|----------|--------|
|
||||||
|
| Vector table base | `0x10000000` |
|
||||||
|
| Initial SP | `0x20082000` |
|
||||||
|
| Reset pointer (as stored) | `0x1000015B` |
|
||||||
|
| Reset instruction address | `0x1000015A` |
|
||||||
|
|
||||||
|
**Criterion 1.4: Thumb Addressing (4 points).**
|
||||||
|
The stored reset pointer `0x1000015B` has bit 0 set to 1, which selects Thumb
|
||||||
|
mode. Clearing bit 0 (`0x1000015B & ~1`) gives the real instruction address
|
||||||
|
`0x1000015A`. The equally odd interrupt vectors (`0x1000011B`, `0x1000011D`,
|
||||||
|
`0x10000111`) are handled the same way.
|
||||||
|
|
||||||
|
### Grading Rubric (1-to-1 Mapping)
|
||||||
|
|
||||||
|
| Criterion | Points | Full Credit (Answer Key) | Partial Credit | No Credit |
|
||||||
|
|-----------|--------|--------------------------|----------------|-----------|
|
||||||
|
| Criterion 1.1: Ghidra Project Setup | 3 | Correct project name, `ARM:LE:32:Cortex` (ARM Cortex 32-bit little endian), base `0x10000000` | One item off | Not set up |
|
||||||
|
| Criterion 1.2: main() and Status-Loop Addresses | 4 | Both addresses correct | One correct | Neither found |
|
||||||
|
| Criterion 1.3: Vector Table Decoding | 4 | Correct base, initial SP, reset pointer | One missing | Not found |
|
||||||
|
| Criterion 1.4: Thumb Addressing | 4 | Correctly clears bit 0 and identifies `main()` | General explanation | Incorrect |
|
||||||
|
|
||||||
|
### Instructor Notes & Assembly
|
||||||
|
|
||||||
|
- Confirm the Ghidra import used `Raw Binary`, `ARM:LE:32:Cortex`, base
|
||||||
|
`0x10000000`, and that auto-analysis completed before any address was read.
|
||||||
|
- Verify `main()` is `0x100001E0`, the loop head is `0x10000234`, and the
|
||||||
|
back-edge bytes `E5 E7` sit at `0x10000266`.
|
||||||
|
- The reset vector is stored as `0x1000015B`; the real Thumb entry is
|
||||||
|
`0x1000015A`. Do not accept the un-cleared `0x1000015B` as an instruction
|
||||||
|
address.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Task 2: Find and Patch Bug #1: The Miscalibrated Safety Threshold (30 points)
|
||||||
|
|
||||||
|
### Solution
|
||||||
|
|
||||||
|
`grid_deviation` is `volatile`, so the compiler emits two independent compares:
|
||||||
|
one for the operator status and one for the automated dispatch decision.
|
||||||
|
|
||||||
|
**Criterion 2.1: Locate Compare Site A (5 points).**
|
||||||
|
|
||||||
|
```text
|
||||||
|
100001fc: 2b5e cmp r3, #94 @ 0x5e
|
||||||
|
```
|
||||||
|
|
||||||
|
| Item | Value |
|
||||||
|
|------|-------|
|
||||||
|
| Address | `0x100001FC` |
|
||||||
|
| File offset | `0x1FC` |
|
||||||
|
| Original bytes | `5E 2B` |
|
||||||
|
| Original instruction | `cmp r3, #94` |
|
||||||
|
|
||||||
|
**Criterion 2.2: Locate Compare Site B (5 points).**
|
||||||
|
|
||||||
|
```text
|
||||||
|
1000020a: 2b5e cmp r3, #94 @ 0x5e
|
||||||
|
```
|
||||||
|
|
||||||
|
| Item | Value |
|
||||||
|
|------|-------|
|
||||||
|
| Address | `0x1000020A` |
|
||||||
|
| File offset | `0x20A` |
|
||||||
|
| Original bytes | `5E 2B` |
|
||||||
|
| Original instruction | `cmp r3, #94` |
|
||||||
|
|
||||||
|
**Criterion 2.3: Correct Immediate-Value Reasoning (8 points).**
|
||||||
|
The source constant is `SAFE_THRESHOLD = 95` and the test is `x < 95`. For an
|
||||||
|
unsigned value, `x < 95` is exactly `x <= 94`, which the compiler emits as
|
||||||
|
`cmp r3, #94` plus `ite hi`. The correct engineering limit is `60`, so the test
|
||||||
|
is `x < 60`, which is `x <= 59`. The correct patched immediate is therefore
|
||||||
|
**`0x3B` (59)**, not `0x3C` (60). Patching to `0x3C` would wrongly accept a
|
||||||
|
reading of exactly 60.
|
||||||
|
|
||||||
|
**Criterion 2.4: Patch Compare Site A (4 points).**
|
||||||
|
|
||||||
|
| Address | File Offset | Original | Patched | Before | After |
|
||||||
|
|---------|-------------|----------|---------|--------|-------|
|
||||||
|
| `0x100001FC` | `0x1FC` | `5E 2B` | `3B 2B` | `cmp r3, #94` | `cmp r3, #59` |
|
||||||
|
|
||||||
|
**Criterion 2.5: Patch Compare Site B (4 points).**
|
||||||
|
|
||||||
|
| Address | File Offset | Original | Patched | Before | After |
|
||||||
|
|---------|-------------|----------|---------|--------|-------|
|
||||||
|
| `0x1000020A` | `0x20A` | `5E 2B` | `3B 2B` | `cmp r3, #94` | `cmp r3, #59` |
|
||||||
|
|
||||||
|
**Criterion 2.6: Explain Why Both Sites Must Be Patched (4 points).**
|
||||||
|
`operator_state` (`0x20000844`) and `dispatch_state` (`0x20000834`) are each
|
||||||
|
computed from their own read of `grid_deviation`. Patching only site A fixes the
|
||||||
|
displayed text while the automated dispatch at site B still authorizes on the
|
||||||
|
dangerous reading. Frozen reading `87`: `87 <= 94` is true (STABLE/AUTHORIZED,
|
||||||
|
wrong); `87 <= 59` is false (CRITICAL/HELD, correct).
|
||||||
|
|
||||||
|
### Grading Rubric (1-to-1 Mapping)
|
||||||
|
|
||||||
|
| Criterion | Points | Full Credit (Answer Key) | Partial Credit | No Credit |
|
||||||
|
|-----------|--------|--------------------------|----------------|-----------|
|
||||||
|
| Criterion 2.1: Locate Compare Site A | 5 | Correct address and original bytes | Address off | Not found |
|
||||||
|
| Criterion 2.2: Locate Compare Site B | 5 | Correct address and original bytes | Address off | Not found |
|
||||||
|
| Criterion 2.3: Correct Immediate-Value Reasoning | 8 | Explains the `<` to `<=` transform and gives `0x3B` | Correct value, no reasoning | Wrong value |
|
||||||
|
| Criterion 2.4: Patch Compare Site A | 4 | Byte change verified | Wrong byte | Not patched |
|
||||||
|
| Criterion 2.5: Patch Compare Site B | 4 | Byte change verified | Wrong byte | Not patched |
|
||||||
|
| Criterion 2.6: Explain Why Both Sites Must Be Patched | 4 | Clear explanation of the two independent comparisons | Vague | Missing |
|
||||||
|
|
||||||
|
### Instructor Notes & Assembly
|
||||||
|
|
||||||
|
- Both sites must be patched: `0x100001FC` for operator status and
|
||||||
|
`0x1000020A` for the automated dispatch decision.
|
||||||
|
- The correct immediate is `0x3B` (59), not `0x3C` (60); the source test is a
|
||||||
|
strict `<`, compiled as `<= 94`.
|
||||||
|
- Verify the byte changes on hardware: after patching, `operator_state`
|
||||||
|
(`0x20000844`) and `dispatch_state` (`0x20000834`) read `0` and `0`.
|
||||||
|
- **Ghidra ARM/Thumb Context Note:** In raw `.bin` files, patching an instruction
|
||||||
|
that precedes an `IT` block (`ite hi`) using the GUI *Patch Instruction* action
|
||||||
|
triggers Ghidra's `ReDisassembleCommand`. The re-disassembler encounters an
|
||||||
|
internal context register conflict when trying to re-declare the `ITBlock`
|
||||||
|
context over existing instructions, collapsing Thumb decoding into 32-bit ARM
|
||||||
|
mode and swallowing Site B (`0x1000020A`). Students must patch using the Bytes
|
||||||
|
window workflow (Clear `C` -> edit byte `5E` -> `3B` in Bytes window with pencil
|
||||||
|
icon -> Disassemble `D`) to keep Site B visible and cleanly aligned.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Task 3: Find and Patch Bug #2: The False Signal Banner (20 points)
|
||||||
|
|
||||||
|
### Solution
|
||||||
|
|
||||||
|
**Criterion 3.1: Locate the Banner String (5 points).**
|
||||||
|
|
||||||
|
| String | Address |
|
||||||
|
|--------|---------|
|
||||||
|
| `"SIGNAL: NORMAL\r"` | `0x10003678` |
|
||||||
|
| `"NORMAL"` substring to patch | `0x10003680` |
|
||||||
|
|
||||||
|
The string is loaded at call site `0x10000224` (`ldr r0, [pc, #92]` ->
|
||||||
|
`0x10003678`) and printed by `bl __wrap_puts` at `0x10000226`. It is printed
|
||||||
|
once at boot and never recomputed.
|
||||||
|
|
||||||
|
**Criterion 3.2: Patch Six Characters (8 points).**
|
||||||
|
`NORMAL` and `DANGER` are both six ASCII characters, so the patch preserves the
|
||||||
|
string length.
|
||||||
|
|
||||||
|
| Address Range | Original Bytes | Patched Bytes |
|
||||||
|
|---------------|----------------|---------------|
|
||||||
|
| `0x10003680` - `0x10003685` | `4E 4F 52 4D 41 4C` | `44 41 4E 47 45 52` |
|
||||||
|
|
||||||
|
**Criterion 3.3: Character-by-Character Documentation (4 points).**
|
||||||
|
|
||||||
|
| Address | Original Char | Original Byte | Patched Char | Patched Byte |
|
||||||
|
|---------|---------------|---------------|--------------|--------------|
|
||||||
|
| `0x10003680` | N | `4E` | D | `44` |
|
||||||
|
| `0x10003681` | O | `4F` | A | `41` |
|
||||||
|
| `0x10003682` | R | `52` | N | `4E` |
|
||||||
|
| `0x10003683` | M | `4D` | G | `47` |
|
||||||
|
| `0x10003684` | A | `41` | E | `45` |
|
||||||
|
| `0x10003685` | L | `4C` | R | `52` |
|
||||||
|
|
||||||
|
**Criterion 3.4: Explain the Danger of a Hardcoded Status Word (3 points).**
|
||||||
|
The banner never consults the reading, so it reports a healthy line even while
|
||||||
|
the frozen reading is dangerous. Operators trust supervisory banners, so a
|
||||||
|
hardcoded `NORMAL` masks the hazard and prevents manual intervention.
|
||||||
|
|
||||||
|
### Grading Rubric (1-to-1 Mapping)
|
||||||
|
|
||||||
|
| Criterion | Points | Full Credit (Answer Key) | Partial Credit | No Credit |
|
||||||
|
|-----------|--------|--------------------------|----------------|-----------|
|
||||||
|
| Criterion 3.1: Locate the Banner String | 5 | Correct address | Approximate | Not found |
|
||||||
|
| Criterion 3.2: Patch Six Characters | 8 | All six bytes changed, length preserved | Correct text, wrong bytes documented | Wrong length |
|
||||||
|
| Criterion 3.3: Character-by-Character Documentation | 4 | Original vs patched byte for all six characters | Partial | Missing |
|
||||||
|
| Criterion 3.4: Explain the Danger of a Hardcoded Status Word | 3 | Clear, specific reasoning | Generic | Missing |
|
||||||
|
|
||||||
|
### Instructor Notes & Assembly
|
||||||
|
|
||||||
|
- `NORMAL` and `DANGER` are both six characters; the patch must not change the
|
||||||
|
string length or overwrite adjacent flash.
|
||||||
|
- The banner is printed once at boot and never recomputed, so it is a separate
|
||||||
|
defect from the threshold and must be graded independently.
|
||||||
|
- Confirm the patch covers `0x10003680` through `0x10003685` exactly.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Task 4: Recover the Quarantined Dispatch Frame (10 points)
|
||||||
|
|
||||||
|
### Solution
|
||||||
|
|
||||||
|
**Criterion 4.1: Recover the Dispatch Frame (6 points).**
|
||||||
|
Address `0x100037A0` in flash `.rodata`:
|
||||||
|
|
||||||
|
```text
|
||||||
|
WORLDGRID:BLACKSTART:GRID-7:WATER-3
|
||||||
|
```
|
||||||
|
|
||||||
|
**Criterion 4.2: Explain Why It Is Never Transmitted (4 points).**
|
||||||
|
`retain_dispatch_frame()` reads only the first character into a `volatile` local
|
||||||
|
so the linker keeps the string, but the pointer is never passed to any print or
|
||||||
|
UART routine. The frame is evidence only and must not be patched.
|
||||||
|
|
||||||
|
### Grading Rubric (1-to-1 Mapping)
|
||||||
|
|
||||||
|
| Criterion | Points | Full Credit (Answer Key) | Partial Credit | No Credit |
|
||||||
|
|-----------|--------|--------------------------|----------------|-----------|
|
||||||
|
| Criterion 4.1: Recover the Dispatch Frame | 6 | Correct address and full text | Partial text | Not found |
|
||||||
|
| Criterion 4.2: Explain Why It Is Never Transmitted | 4 | Clear static-analysis explanation | Vague | Missing |
|
||||||
|
|
||||||
|
### Instructor Notes & Assembly
|
||||||
|
|
||||||
|
- Accept the full string `WORLDGRID:BLACKSTART:GRID-7:WATER-3` at `0x100037A0`
|
||||||
|
in flash `.rodata`.
|
||||||
|
- The frame is evidence only. Penalize any submission that patches or rewrites
|
||||||
|
it instead of recovering it.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Task 5: Export and Verify (20 points)
|
||||||
|
|
||||||
|
### Solution
|
||||||
|
|
||||||
|
**Criterion 5.1: Export CTF-01_fixed.bin (4 points).**
|
||||||
|
Export the patched program from Ghidra (`File -> Export Program...`, `Binary
|
||||||
|
Format`) as `CTF-01_fixed.bin`.
|
||||||
|
|
||||||
|
**Criterion 5.2: Convert to CTF-01_fixed.uf2 (4 points).**
|
||||||
|
|
||||||
|
```bash
|
||||||
|
python uf2conv.py CTF-01_fixed.bin --base 0x10000000 --family 0xe48bff59 --output CTF-01_fixed.uf2
|
||||||
|
```
|
||||||
|
|
||||||
|
**Criterion 5.3: Hardware Verification (8 points).**
|
||||||
|
|
||||||
|
Before patching:
|
||||||
|
|
||||||
|
```text
|
||||||
|
GLOBAL EMBEDDED RESPONSE NETWORK
|
||||||
|
BLACK START WINDOW: 27 MINUTES
|
||||||
|
UART0 115200 8N1 | AUTHORIZED LAB CONSOLE
|
||||||
|
SIGNAL: NORMAL
|
||||||
|
RESPONSE> GRID STATUS: STABLE
|
||||||
|
DISPATCH PATH: AUTHORIZED
|
||||||
|
LAST FRAME: QUARANTINED
|
||||||
|
RESPONSE>
|
||||||
|
```
|
||||||
|
|
||||||
|
After all three patches:
|
||||||
|
|
||||||
|
```text
|
||||||
|
GLOBAL EMBEDDED RESPONSE NETWORK
|
||||||
|
BLACK START WINDOW: 27 MINUTES
|
||||||
|
UART0 115200 8N1 | AUTHORIZED LAB CONSOLE
|
||||||
|
SIGNAL: DANGER
|
||||||
|
RESPONSE> GRID STATUS: CRITICAL
|
||||||
|
DISPATCH PATH: HELD
|
||||||
|
LAST FRAME: QUARANTINED
|
||||||
|
RESPONSE>
|
||||||
|
```
|
||||||
|
|
||||||
|
If the console is not wired, the same proof is read over SWD: after reset,
|
||||||
|
`operator_state` (`0x20000844`) and `dispatch_state` (`0x20000834`) are `1` and
|
||||||
|
`1` for the shipped image, and `0` and `0` for the patched image. This has been
|
||||||
|
confirmed on real hardware.
|
||||||
|
|
||||||
|
**Criterion 5.4: Summary Table of All Patches (4 points).**
|
||||||
|
|
||||||
|
| # | What | Address(es) | Original | Patched |
|
||||||
|
|---|------|-------------|----------|---------|
|
||||||
|
| 1a | Operator threshold | `0x100001FC` | `5E 2B` | `3B 2B` |
|
||||||
|
| 1b | Dispatch threshold | `0x1000020A` | `5E 2B` | `3B 2B` |
|
||||||
|
| 2 | Signal banner | `0x10003680`-`0x10003685` | `4E 4F 52 4D 41 4C` | `44 41 4E 47 45 52` |
|
||||||
|
|
||||||
|
Total: **8 bytes actually change** (one immediate byte at each compare site and
|
||||||
|
six string bytes).
|
||||||
|
|
||||||
|
### Grading Rubric (1-to-1 Mapping)
|
||||||
|
|
||||||
|
| Criterion | Points | Full Credit (Answer Key) | Partial Credit | No Credit |
|
||||||
|
|-----------|--------|--------------------------|----------------|-----------|
|
||||||
|
| Criterion 5.1: Export CTF-01_fixed.bin | 4 | Valid patched binary | Corrupted | Not submitted |
|
||||||
|
| Criterion 5.2: Convert to CTF-01_fixed.uf2 | 4 | Correct base and family flags | Wrong flags | Not submitted |
|
||||||
|
| Criterion 5.3: Hardware Verification | 8 | Corrected console output confirmed on hardware | Some lines corrected | No verification |
|
||||||
|
| Criterion 5.4: Summary Table of All Patches | 4 | Complete address and before/after table | Missing entries | No table |
|
||||||
|
|
||||||
|
### Instructor Notes & Assembly
|
||||||
|
|
||||||
|
- Verify the exported image with `python3 scripts/verify_ctf.py`; the shipped
|
||||||
|
check expects `11/11 checks passed` against `CTF-01.bin`.
|
||||||
|
- Confirm the UF2 conversion used base `0x10000000` and family `0xe48bff59`.
|
||||||
|
- **Serial Terminal Timing:** Note that `print_boot_banner()` (`SIGNAL: DANGER`)
|
||||||
|
fires within the first 5 milliseconds of boot. In normal lab usage, PuTTY
|
||||||
|
attaches after boot and will display the continuous 1-second status loop
|
||||||
|
(`GRID STATUS: CRITICAL`, `DISPATCH PATH: HELD`). To see `SIGNAL: DANGER`,
|
||||||
|
the student must pulse `RUN` to `GND` while PuTTY is open, or demonstrate
|
||||||
|
the string change at `0x10003680` via Ghidra static analysis.
|
||||||
|
- If no console is available, accept the SWD capture showing `operator_state`
|
||||||
|
and `dispatch_state` at `0` and `0` on the patched image.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Task 6: Written Reflection (5 points)
|
||||||
|
|
||||||
|
### Solution
|
||||||
|
|
||||||
|
**Criterion 6.1: "Rushed Build" Is Not an Excuse (2 points).**
|
||||||
|
The missed review step is exactly what shipped the false-safe report; pressure
|
||||||
|
explains why the safeguard was skipped, not why it should be skipped.
|
||||||
|
|
||||||
|
**Criterion 6.2: One Engineering Practice per Bug (3 points).**
|
||||||
|
- Bug #1 (duplicated threshold): a unit test or static-analysis rule that
|
||||||
|
requires every comparison against `SAFE_THRESHOLD` to use one shared source of
|
||||||
|
truth.
|
||||||
|
- Bug #2 (hardcoded banner): a hardware-in-the-loop smoke test that checks the
|
||||||
|
boot banner against the latched reading.
|
||||||
|
|
||||||
|
### Grading Rubric (1-to-1 Mapping)
|
||||||
|
|
||||||
|
| Criterion | Points | Full Credit (Answer Key) | Partial Credit | No Credit |
|
||||||
|
|-----------|--------|--------------------------|----------------|-----------|
|
||||||
|
| Criterion 6.1: "Rushed Build" Is Not an Excuse | 2 | Specific, grounded reasoning | Generic | Missing |
|
||||||
|
| Criterion 6.2: One Engineering Practice per Bug | 3 | Concrete practice for each bug | One bug only | Missing |
|
||||||
|
|
||||||
|
### Instructor Notes & Assembly
|
||||||
|
|
||||||
|
- Grade the specificity of the reasoning, not the length of the prose.
|
||||||
|
- Require one concrete engineering practice for each of the two bugs.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## How To Breadboard
|
||||||
|
|
||||||
|
- **Raspberry Pi Pico 2** powered over USB.
|
||||||
|
- **3.3 V USB-UART adapter**:
|
||||||
|
- Adapter RX to Pico GP0 (UART0 TX)
|
||||||
|
- Adapter TX to Pico GP1 (UART0 RX)
|
||||||
|
- Adapter GND to Pico GND
|
||||||
|
- Do not connect the adapter VCC while the Pico is USB powered.
|
||||||
|
- **Serial monitor:** 115200 baud, 8 data bits, no parity, 1 stop bit.
|
||||||
|
- No other peripherals are required; all evidence is obtained from the console.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Complete Grading Summary
|
||||||
|
|
||||||
|
| Task | Title | Points |
|
||||||
|
|------|-------|--------|
|
||||||
|
| Task 1 | Setup and Initial Analysis | 15 |
|
||||||
|
| Task 2 | Find and Patch Bug #1: The Miscalibrated Safety Threshold | 30 |
|
||||||
|
| Task 3 | Find and Patch Bug #2: The False Signal Banner | 20 |
|
||||||
|
| Task 4 | Recover the Quarantined Dispatch Frame | 10 |
|
||||||
|
| Task 5 | Export and Verify | 20 |
|
||||||
|
| Task 6 | Written Reflection | 5 |
|
||||||
|
| **TOTAL** | | **100** |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Instructor Notes
|
||||||
|
|
||||||
|
Safety: Use only the supplied Pico 2, 3.3 V UART adapter, and firmware. Never
|
||||||
|
connect the exercise to an operational grid, water plant, public network,
|
||||||
|
military system, or third-party device.
|
||||||
|
|
||||||
|
### Common Student Mistakes
|
||||||
|
|
||||||
|
- Patching only one threshold site (`0x100001FC` or `0x1000020A`), which leaves
|
||||||
|
one status line lying.
|
||||||
|
- Assuming the immediate equals the limit, producing an off-by-one boundary;
|
||||||
|
the correct byte is `0x3B` (59), not `0x3C` (60).
|
||||||
|
- Replacing the banner string with a different length, corrupting adjacent
|
||||||
|
flash; `NORMAL` and `DANGER` are both 6 bytes.
|
||||||
|
- Treating the odd vector address `0x1000015B` as invalid instead of clearing
|
||||||
|
bit 0 to get `0x1000015A`.
|
||||||
|
- Modifying the quarantined dispatch frame at `0x100037A0`, which destroys
|
||||||
|
evidence.
|
||||||
|
|
||||||
|
### Partial Credit Guidelines
|
||||||
|
|
||||||
|
- Award partial credit for one correct threshold site out of two, or for a
|
||||||
|
correct immediate value without the `<` to `<=` reasoning.
|
||||||
|
- Award partial credit for a correct banner text with incorrectly documented
|
||||||
|
bytes, or for partial character-by-character documentation.
|
||||||
|
- Accept an SWD read of `operator_state` and `dispatch_state` as equivalent
|
||||||
|
proof when no UART console is available.
|
||||||
|
- Award no credit for patches that change string length or overwrite adjacent
|
||||||
|
flash.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Appendix: Expected Binary Diff
|
||||||
|
|
||||||
|
| # | What | File Offset(s) | Address(es) | Original Bytes | Patched Bytes |
|
||||||
|
|---|------|----------------|-------------|----------------|---------------|
|
||||||
|
| 1a | Operator threshold | `0x1FC` | `0x100001FC` | `5E 2B` | `3B 2B` |
|
||||||
|
| 1b | Dispatch threshold | `0x20A` | `0x1000020A` | `5E 2B` | `3B 2B` |
|
||||||
|
| 2 | Signal banner | `0x3680` - `0x3685` | `0x10003680` - `0x10003685` | `4E 4F 52 4D 41 4C` | `44 41 4E 47 45 52` |
|
||||||
|
|
||||||
|
Total: **8 bytes actually change** (one immediate byte at each compare site and
|
||||||
|
six string bytes).
|
||||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -0,0 +1,72 @@
|
|||||||
|
// MIT License
|
||||||
|
//
|
||||||
|
// Copyright (c) 2026 Kevin Thomas
|
||||||
|
//
|
||||||
|
// 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.
|
||||||
|
//
|
||||||
|
// Author: Kevin Thomas
|
||||||
|
// Email: kevin@mytechnotalent.com
|
||||||
|
// GitHub: https://github.com/mytechnotalent
|
||||||
|
// File: console.h
|
||||||
|
// Desc: Declares the UART console banner and status reporting interface
|
||||||
|
// for Operation Black Start.
|
||||||
|
// Created: 2026
|
||||||
|
|
||||||
|
#ifndef CONSOLE_H
|
||||||
|
#define CONSOLE_H
|
||||||
|
|
||||||
|
#include "grid.h"
|
||||||
|
#include <stdio.h>
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Print the response controller's boot identity and unconditional signal line.
|
||||||
|
*
|
||||||
|
* Emits the boot banner, operation window, serial configuration banner,
|
||||||
|
* unconditional signal quality line, and the interactive command prompt.
|
||||||
|
*
|
||||||
|
* @param None.
|
||||||
|
* @return None.
|
||||||
|
*/
|
||||||
|
static inline void print_boot_banner(void)
|
||||||
|
{
|
||||||
|
printf("GLOBAL EMBEDDED RESPONSE NETWORK\r\n");
|
||||||
|
printf("BLACK START WINDOW: 27 MINUTES\r\n");
|
||||||
|
printf("UART0 115200 8N1 | AUTHORIZED LAB CONSOLE\r\n");
|
||||||
|
printf("SIGNAL: NORMAL\r\n");
|
||||||
|
printf("RESPONSE> ");
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Print the recurring grid classification and dispatch authorization report.
|
||||||
|
*
|
||||||
|
* Evaluates the current operator state and dispatch state flags and transmits
|
||||||
|
* the formatted status report over UART0 with the quarantined frame notification.
|
||||||
|
*
|
||||||
|
* @param None.
|
||||||
|
* @return None.
|
||||||
|
*/
|
||||||
|
static inline void print_status(void)
|
||||||
|
{
|
||||||
|
printf("GRID STATUS: %s\r\n", operator_state ? "STABLE" : "CRITICAL");
|
||||||
|
printf("DISPATCH PATH: %s\r\n", dispatch_state ? "AUTHORIZED" : "HELD");
|
||||||
|
printf("LAST FRAME: QUARANTINED\r\n");
|
||||||
|
printf("RESPONSE> ");
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif // CONSOLE_H
|
||||||
@@ -0,0 +1,85 @@
|
|||||||
|
// MIT License
|
||||||
|
//
|
||||||
|
// Copyright (c) 2026 Kevin Thomas
|
||||||
|
//
|
||||||
|
// 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.
|
||||||
|
//
|
||||||
|
// Author: Kevin Thomas
|
||||||
|
// Email: kevin@mytechnotalent.com
|
||||||
|
// GitHub: https://github.com/mytechnotalent
|
||||||
|
// File: grid.h
|
||||||
|
// Desc: Declares the grid telemetry and safety evaluation interface for
|
||||||
|
// Operation Black Start.
|
||||||
|
// Created: 2026
|
||||||
|
|
||||||
|
#ifndef GRID_H
|
||||||
|
#define GRID_H
|
||||||
|
|
||||||
|
#include <stdint.h>
|
||||||
|
|
||||||
|
// Safety margin (Hz deviation x100) below which grid frequency is tolerable.
|
||||||
|
// BUG: emergency build miscompiled this far too permissive; correct value is 60.
|
||||||
|
#define SAFE_THRESHOLD 95
|
||||||
|
|
||||||
|
// Frozen grid frequency deviation reading latched when comms were severed.
|
||||||
|
extern volatile uint32_t grid_deviation;
|
||||||
|
|
||||||
|
// Operator-facing classification of the frozen reading (drives GRID STATUS).
|
||||||
|
extern volatile uint32_t operator_state;
|
||||||
|
|
||||||
|
// Automated dispatch authorization decision (drives DISPATCH PATH).
|
||||||
|
extern volatile uint32_t dispatch_state;
|
||||||
|
|
||||||
|
// Quarantined black-start authorization frame, retained in flash, never sent.
|
||||||
|
static volatile const char dispatch_frame[] =
|
||||||
|
"WORLDGRID:BLACKSTART:GRID-7:WATER-3";
|
||||||
|
|
||||||
|
static inline void retain_dispatch_frame(void)
|
||||||
|
{
|
||||||
|
volatile char frame_marker = dispatch_frame[0];
|
||||||
|
(void)frame_marker;
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline void evaluate_grid(void)
|
||||||
|
{
|
||||||
|
operator_state = (grid_deviation < SAFE_THRESHOLD) ? 1 : 0;
|
||||||
|
dispatch_state = (grid_deviation < SAFE_THRESHOLD) ? 1 : 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Anchor the hidden dispatch frame in flash without transmitting it.
|
||||||
|
*
|
||||||
|
* Reads the first character of the quarantined black-start authorization
|
||||||
|
* frame into a volatile local marker to prevent the compiler from optimizing
|
||||||
|
* out the string literal from .rodata flash storage.
|
||||||
|
*
|
||||||
|
* @param None.
|
||||||
|
* @return None.
|
||||||
|
*/
|
||||||
|
/**
|
||||||
|
* @brief Classify the frozen telemetry reading against the compiled threshold.
|
||||||
|
*
|
||||||
|
* Evaluates the frozen grid deviation reading against SAFE_THRESHOLD twice,
|
||||||
|
* once for the operator-facing status line and once for the automated
|
||||||
|
* dispatch decision, mirroring the duplicated immediate comparison site.
|
||||||
|
*
|
||||||
|
* @param None.
|
||||||
|
* @return None.
|
||||||
|
*/
|
||||||
|
#endif // GRID_H
|
||||||
@@ -0,0 +1,121 @@
|
|||||||
|
# This is a copy of <PICO_SDK_PATH>/external/pico_sdk_import.cmake
|
||||||
|
|
||||||
|
# This can be dropped into an external project to help locate this SDK
|
||||||
|
# It should be include()ed prior to project()
|
||||||
|
|
||||||
|
# Copyright 2020 (c) 2020 Raspberry Pi (Trading) Ltd.
|
||||||
|
#
|
||||||
|
# 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. Neither the name of the copyright holder nor the names of its contributors may be used to endorse or promote products
|
||||||
|
# derived from this software without specific prior written permission.
|
||||||
|
#
|
||||||
|
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "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 COPYRIGHT HOLDER OR CONTRIBUTORS 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.
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_PATH} AND (NOT PICO_SDK_PATH))
|
||||||
|
set(PICO_SDK_PATH $ENV{PICO_SDK_PATH})
|
||||||
|
message("Using PICO_SDK_PATH from environment ('${PICO_SDK_PATH}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT} AND (NOT PICO_SDK_FETCH_FROM_GIT))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT $ENV{PICO_SDK_FETCH_FROM_GIT})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT from environment ('${PICO_SDK_FETCH_FROM_GIT}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT_PATH} AND (NOT PICO_SDK_FETCH_FROM_GIT_PATH))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_PATH $ENV{PICO_SDK_FETCH_FROM_GIT_PATH})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT_PATH from environment ('${PICO_SDK_FETCH_FROM_GIT_PATH}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT_TAG} AND (NOT PICO_SDK_FETCH_FROM_GIT_TAG))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG $ENV{PICO_SDK_FETCH_FROM_GIT_TAG})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT_TAG from environment ('${PICO_SDK_FETCH_FROM_GIT_TAG}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT AND NOT PICO_SDK_FETCH_FROM_GIT_TAG)
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG "master")
|
||||||
|
message("Using master as default value for PICO_SDK_FETCH_FROM_GIT_TAG")
|
||||||
|
endif()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH "${PICO_SDK_PATH}" CACHE PATH "Path to the Raspberry Pi Pico SDK")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT "${PICO_SDK_FETCH_FROM_GIT}" CACHE BOOL "Set to ON to fetch copy of SDK from git if not otherwise locatable")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_PATH "${PICO_SDK_FETCH_FROM_GIT_PATH}" CACHE FILEPATH "location to download SDK")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG "${PICO_SDK_FETCH_FROM_GIT_TAG}" CACHE FILEPATH "release tag for SDK")
|
||||||
|
|
||||||
|
if (NOT PICO_SDK_PATH)
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT)
|
||||||
|
include(FetchContent)
|
||||||
|
set(FETCHCONTENT_BASE_DIR_SAVE ${FETCHCONTENT_BASE_DIR})
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT_PATH)
|
||||||
|
get_filename_component(FETCHCONTENT_BASE_DIR "${PICO_SDK_FETCH_FROM_GIT_PATH}" REALPATH BASE_DIR "${CMAKE_SOURCE_DIR}")
|
||||||
|
endif ()
|
||||||
|
FetchContent_Declare(
|
||||||
|
pico_sdk
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
)
|
||||||
|
|
||||||
|
if (NOT pico_sdk)
|
||||||
|
message("Downloading Raspberry Pi Pico SDK")
|
||||||
|
# GIT_SUBMODULES_RECURSE was added in 3.17
|
||||||
|
if (${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.17.0")
|
||||||
|
FetchContent_Populate(
|
||||||
|
pico_sdk
|
||||||
|
QUIET
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
GIT_SUBMODULES_RECURSE FALSE
|
||||||
|
|
||||||
|
SOURCE_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-src
|
||||||
|
BINARY_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-build
|
||||||
|
SUBBUILD_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-subbuild
|
||||||
|
)
|
||||||
|
else ()
|
||||||
|
FetchContent_Populate(
|
||||||
|
pico_sdk
|
||||||
|
QUIET
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
|
||||||
|
SOURCE_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-src
|
||||||
|
BINARY_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-build
|
||||||
|
SUBBUILD_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-subbuild
|
||||||
|
)
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH ${pico_sdk_SOURCE_DIR})
|
||||||
|
endif ()
|
||||||
|
set(FETCHCONTENT_BASE_DIR ${FETCHCONTENT_BASE_DIR_SAVE})
|
||||||
|
else ()
|
||||||
|
message(FATAL_ERROR
|
||||||
|
"SDK location was not specified. Please set PICO_SDK_PATH or set PICO_SDK_FETCH_FROM_GIT to on to fetch from git."
|
||||||
|
)
|
||||||
|
endif ()
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
get_filename_component(PICO_SDK_PATH "${PICO_SDK_PATH}" REALPATH BASE_DIR "${CMAKE_BINARY_DIR}")
|
||||||
|
if (NOT EXISTS ${PICO_SDK_PATH})
|
||||||
|
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' not found")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_INIT_CMAKE_FILE ${PICO_SDK_PATH}/pico_sdk_init.cmake)
|
||||||
|
if (NOT EXISTS ${PICO_SDK_INIT_CMAKE_FILE})
|
||||||
|
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' does not appear to contain the Raspberry Pi Pico SDK")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH ${PICO_SDK_PATH} CACHE PATH "Path to the Raspberry Pi Pico SDK" FORCE)
|
||||||
|
|
||||||
|
include(${PICO_SDK_INIT_CMAKE_FILE})
|
||||||
@@ -0,0 +1,82 @@
|
|||||||
|
#!/usr/bin/env python3
|
||||||
|
"""Verify every technical claim of Operation Black Start against CTF-01.bin.
|
||||||
|
|
||||||
|
Exits 0 only when every address, byte, and hash in CTF-R.md and CTF-S.md
|
||||||
|
matches the shipped image.
|
||||||
|
"""
|
||||||
|
import hashlib
|
||||||
|
import struct
|
||||||
|
import sys
|
||||||
|
from pathlib import Path
|
||||||
|
|
||||||
|
BASE = 0x10000000
|
||||||
|
ROOT = Path(__file__).resolve().parent.parent
|
||||||
|
BIN = ROOT / "CTF-01.bin"
|
||||||
|
UF2 = ROOT / "CTF-01.uf2"
|
||||||
|
|
||||||
|
EXPECTED_BIN_SHA = "425591ac17ff4c22206286ee6f40b06a89523483804850a41854a9b6f89d7b70"
|
||||||
|
EXPECTED_UF2_SHA = "b1552ee3bb5763d96c65d8df1c86984ee842ef1a823fdf5d94132b1e10ff9d16"
|
||||||
|
|
||||||
|
CMP_A = 0x100001FC
|
||||||
|
CMP_B = 0x1000020A
|
||||||
|
STRING_SIGNAL = 0x10003678
|
||||||
|
STRING_FRAME = 0x100037A0
|
||||||
|
LOOP_BACK = 0x10000266
|
||||||
|
|
||||||
|
RESULTS = []
|
||||||
|
|
||||||
|
|
||||||
|
def check(label, ok, detail=""):
|
||||||
|
"""Record one verification result.
|
||||||
|
|
||||||
|
Parameters
|
||||||
|
----------
|
||||||
|
label : str
|
||||||
|
Human-readable check name.
|
||||||
|
ok : bool
|
||||||
|
Whether the check passed.
|
||||||
|
detail : str
|
||||||
|
Extra context printed with the result.
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
None
|
||||||
|
"""
|
||||||
|
RESULTS.append(ok)
|
||||||
|
print(f"[{'PASS' if ok else 'FAIL'}] {label} {detail}")
|
||||||
|
|
||||||
|
|
||||||
|
def main():
|
||||||
|
"""Run all verification checks.
|
||||||
|
|
||||||
|
Returns
|
||||||
|
-------
|
||||||
|
int
|
||||||
|
Zero when every check passes, else one.
|
||||||
|
"""
|
||||||
|
data = BIN.read_bytes()
|
||||||
|
check("CTF-01.bin SHA-256", hashlib.sha256(data).hexdigest() == EXPECTED_BIN_SHA)
|
||||||
|
check("CTF-01.uf2 SHA-256",
|
||||||
|
hashlib.sha256(UF2.read_bytes()).hexdigest() == EXPECTED_UF2_SHA)
|
||||||
|
check("vector table", data[0:32].hex() ==
|
||||||
|
"002008205b0100101b0100101d01001011010010110100101101001011010010")
|
||||||
|
check("initial SP", struct.unpack("<I", data[0:4])[0] == 0x20082000)
|
||||||
|
check("reset vector", struct.unpack("<I", data[4:8])[0] == 0x1000015B)
|
||||||
|
check("compare site A", data[CMP_A - BASE:CMP_A - BASE + 2]
|
||||||
|
== bytes.fromhex("5E2B"), "(cmp r3,#94)")
|
||||||
|
check("compare site B", data[CMP_B - BASE:CMP_B - BASE + 2]
|
||||||
|
== bytes.fromhex("5E2B"), "(cmp r3,#94)")
|
||||||
|
check("loop back-edge", data[LOOP_BACK - BASE:LOOP_BACK - BASE + 2]
|
||||||
|
== bytes.fromhex("E5E7"), "(b.n 0x10000234)")
|
||||||
|
check("SIGNAL banner", data[STRING_SIGNAL - BASE:STRING_SIGNAL - BASE + 15]
|
||||||
|
== b"SIGNAL: NORMAL\r")
|
||||||
|
check("dispatch frame", data[STRING_FRAME - BASE:STRING_FRAME - BASE + 36]
|
||||||
|
== b"WORLDGRID:BLACKSTART:GRID-7:WATER-3\x00")
|
||||||
|
check("grid_deviation init", data[0x3D94:0x3D98] == struct.pack("<I", 87))
|
||||||
|
total = sum(RESULTS)
|
||||||
|
print(f"\n{total}/{len(RESULTS)} checks passed")
|
||||||
|
return 0 if total == len(RESULTS) else 1
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == "__main__":
|
||||||
|
sys.exit(main())
|
||||||
@@ -0,0 +1 @@
|
|||||||
|
#include "console.h"
|
||||||
@@ -0,0 +1,6 @@
|
|||||||
|
#include "grid.h"
|
||||||
|
#include <stdint.h>
|
||||||
|
|
||||||
|
volatile uint32_t grid_deviation = 87;
|
||||||
|
volatile uint32_t operator_state = 0;
|
||||||
|
volatile uint32_t dispatch_state = 0;
|
||||||
@@ -0,0 +1,56 @@
|
|||||||
|
// MIT License
|
||||||
|
//
|
||||||
|
// Copyright (c) 2026 Kevin Thomas
|
||||||
|
//
|
||||||
|
// 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.
|
||||||
|
//
|
||||||
|
// Author: Kevin Thomas
|
||||||
|
// Email: kevin@mytechnotalent.com
|
||||||
|
// GitHub: https://github.com/mytechnotalent
|
||||||
|
// File: main.c
|
||||||
|
// Desc: Main entry point for the Operation Black Start CTF relay firmware.
|
||||||
|
// Created: 2026
|
||||||
|
|
||||||
|
#include "console.h"
|
||||||
|
#include "grid.h"
|
||||||
|
#include "pico/stdlib.h"
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Run the recurring UART evidence stream for the isolated CTF image.
|
||||||
|
*
|
||||||
|
* Initializes the standard I/O subsystems, anchors the quarantined dispatch
|
||||||
|
* frame in flash memory, evaluates the frozen telemetry against the compiled
|
||||||
|
* safety threshold, prints the startup banner, and repeatedly emits the
|
||||||
|
* system status report every second.
|
||||||
|
*
|
||||||
|
* @param None.
|
||||||
|
* @return int Standard exit code (never reached in normal firmware execution).
|
||||||
|
*/
|
||||||
|
int main(void)
|
||||||
|
{
|
||||||
|
stdio_init_all();
|
||||||
|
retain_dispatch_frame();
|
||||||
|
evaluate_grid();
|
||||||
|
print_boot_banner();
|
||||||
|
while (true) {
|
||||||
|
print_status();
|
||||||
|
sleep_ms(1000);
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
@@ -0,0 +1,22 @@
|
|||||||
|
[
|
||||||
|
{
|
||||||
|
"short_name": "RP2040",
|
||||||
|
"id": "0xe48bff56",
|
||||||
|
"description": "Raspberry Pi RP2040"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"short_name": "RP2350-ARM-S",
|
||||||
|
"id": "0xe48bff59",
|
||||||
|
"description": "Raspberry Pi RP2350, ARM, Secure"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"short_name": "RP2350-ARM-NS",
|
||||||
|
"id": "0xe48bff5a",
|
||||||
|
"description": "Raspberry Pi RP2350, ARM, Non-Secure"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"short_name": "RP2350-RISCV",
|
||||||
|
"id": "0xe48bff5b",
|
||||||
|
"description": "Raspberry Pi RP2350, RISC-V"
|
||||||
|
}
|
||||||
|
]
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
build
|
||||||
|
!.vscode/*
|
||||||
@@ -0,0 +1,22 @@
|
|||||||
|
{
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Pico",
|
||||||
|
"includePath": [
|
||||||
|
"${workspaceFolder}/**",
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.2.0/**"
|
||||||
|
],
|
||||||
|
"forcedInclude": [
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.2.0/src/common/pico_base_headers/include/pico.h",
|
||||||
|
"${workspaceFolder}/build/generated/pico_base/pico/config_autogen.h"
|
||||||
|
],
|
||||||
|
"defines": [],
|
||||||
|
"compilerPath": "${userHome}/.pico-sdk/toolchain/14_2_Rel1/bin/arm-none-eabi-gcc.exe",
|
||||||
|
"compileCommands": "${workspaceFolder}/build/compile_commands.json",
|
||||||
|
"cStandard": "c17",
|
||||||
|
"cppStandard": "c++14",
|
||||||
|
"intelliSenseMode": "linux-gcc-arm"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"version": 4
|
||||||
|
}
|
||||||
@@ -0,0 +1,15 @@
|
|||||||
|
[
|
||||||
|
{
|
||||||
|
"name": "Pico",
|
||||||
|
"compilers": {
|
||||||
|
"C": "${command:raspberry-pi-pico.getCompilerPath}",
|
||||||
|
"CXX": "${command:raspberry-pi-pico.getCxxCompilerPath}"
|
||||||
|
},
|
||||||
|
"environmentVariables": {
|
||||||
|
"PATH": "${command:raspberry-pi-pico.getEnvPath};${env:PATH}"
|
||||||
|
},
|
||||||
|
"cmakeSettings": {
|
||||||
|
"Python3_EXECUTABLE": "${command:raspberry-pi-pico.getPythonPath}"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
@@ -0,0 +1,9 @@
|
|||||||
|
{
|
||||||
|
"recommendations": [
|
||||||
|
"marus25.cortex-debug",
|
||||||
|
"ms-vscode.cpptools",
|
||||||
|
"ms-vscode.cpptools-extension-pack",
|
||||||
|
"ms-vscode.vscode-serial-monitor",
|
||||||
|
"raspberry-pi.raspberry-pi-pico"
|
||||||
|
]
|
||||||
|
}
|
||||||
+50
@@ -0,0 +1,50 @@
|
|||||||
|
{
|
||||||
|
"version": "0.2.0",
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Pico Debug (Cortex-Debug)",
|
||||||
|
"cwd": "${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"executable": "${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"request": "launch",
|
||||||
|
"type": "cortex-debug",
|
||||||
|
"servertype": "openocd",
|
||||||
|
"serverpath": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"gdbPath": "${command:raspberry-pi-pico.getGDBPath}",
|
||||||
|
"device": "${command:raspberry-pi-pico.getChipUppercase}",
|
||||||
|
"configFiles": [
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"target/${command:raspberry-pi-pico.getTarget}.cfg"
|
||||||
|
],
|
||||||
|
"svdFile": "${userHome}/.pico-sdk/sdk/2.2.0/src/${command:raspberry-pi-pico.getChip}/hardware_regs/${command:raspberry-pi-pico.getChipUppercase}.svd",
|
||||||
|
"runToEntryPoint": "main",
|
||||||
|
// Fix for no_flash binaries, where monitor reset halt doesn't do what is expected
|
||||||
|
// Also works fine for flash binaries
|
||||||
|
"overrideLaunchCommands": [
|
||||||
|
"monitor reset init",
|
||||||
|
"load \"${command:raspberry-pi-pico.launchTargetPath}\""
|
||||||
|
],
|
||||||
|
"openOCDLaunchCommands": [
|
||||||
|
"adapter speed 5000"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Pico Debug (Cortex-Debug with external OpenOCD)",
|
||||||
|
"cwd": "${workspaceRoot}",
|
||||||
|
"executable": "${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"request": "launch",
|
||||||
|
"type": "cortex-debug",
|
||||||
|
"servertype": "external",
|
||||||
|
"gdbTarget": "localhost:3333",
|
||||||
|
"gdbPath": "${command:raspberry-pi-pico.getGDBPath}",
|
||||||
|
"device": "${command:raspberry-pi-pico.getChipUppercase}",
|
||||||
|
"svdFile": "${userHome}/.pico-sdk/sdk/2.2.0/src/${command:raspberry-pi-pico.getChip}/hardware_regs/${command:raspberry-pi-pico.getChipUppercase}.svd",
|
||||||
|
"runToEntryPoint": "main",
|
||||||
|
// Fix for no_flash binaries, where monitor reset halt doesn't do what is expected
|
||||||
|
// Also works fine for flash binaries
|
||||||
|
"overrideLaunchCommands": [
|
||||||
|
"monitor reset init",
|
||||||
|
"load \"${command:raspberry-pi-pico.launchTargetPath}\""
|
||||||
|
]
|
||||||
|
},
|
||||||
|
]
|
||||||
|
}
|
||||||
+40
@@ -0,0 +1,40 @@
|
|||||||
|
{
|
||||||
|
"cmake.showSystemKits": false,
|
||||||
|
"cmake.options.statusBarVisibility": "hidden",
|
||||||
|
"cmake.options.advanced": {
|
||||||
|
"build": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"launch": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"debug": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"cmake.configureOnEdit": false,
|
||||||
|
"cmake.automaticReconfigure": false,
|
||||||
|
"cmake.configureOnOpen": false,
|
||||||
|
"cmake.generator": "Ninja",
|
||||||
|
"cmake.cmakePath": "${userHome}/.pico-sdk/cmake/v3.31.5/bin/cmake",
|
||||||
|
"C_Cpp.debugShortcut": false,
|
||||||
|
"terminal.integrated.env.windows": {
|
||||||
|
"PICO_SDK_PATH": "${env:USERPROFILE}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:USERPROFILE}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"Path": "${env:USERPROFILE}/.pico-sdk/toolchain/14_2_Rel1/bin;${env:USERPROFILE}/.pico-sdk/picotool/2.2.0/picotool;${env:USERPROFILE}/.pico-sdk/cmake/v3.31.5/bin;${env:USERPROFILE}/.pico-sdk/ninja/v1.12.1;${env:PATH}"
|
||||||
|
},
|
||||||
|
"terminal.integrated.env.osx": {
|
||||||
|
"PICO_SDK_PATH": "${env:HOME}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1/bin:${env:HOME}/.pico-sdk/picotool/2.2.0/picotool:${env:HOME}/.pico-sdk/cmake/v3.31.5/bin:${env:HOME}/.pico-sdk/ninja/v1.12.1:${env:PATH}"
|
||||||
|
},
|
||||||
|
"terminal.integrated.env.linux": {
|
||||||
|
"PICO_SDK_PATH": "${env:HOME}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1/bin:${env:HOME}/.pico-sdk/picotool/2.2.0/picotool:${env:HOME}/.pico-sdk/cmake/v3.31.5/bin:${env:HOME}/.pico-sdk/ninja/v1.12.1:${env:PATH}"
|
||||||
|
},
|
||||||
|
"raspberry-pi-pico.cmakeAutoConfigure": true,
|
||||||
|
"raspberry-pi-pico.useCmakeTools": false,
|
||||||
|
"raspberry-pi-pico.cmakePath": "${HOME}/.pico-sdk/cmake/v3.31.5/bin/cmake",
|
||||||
|
"raspberry-pi-pico.ninjaPath": "${HOME}/.pico-sdk/ninja/v1.12.1/ninja"
|
||||||
|
}
|
||||||
+102
@@ -0,0 +1,102 @@
|
|||||||
|
{
|
||||||
|
"version": "2.0.0",
|
||||||
|
"tasks": [
|
||||||
|
{
|
||||||
|
"label": "Compile Project",
|
||||||
|
"type": "process",
|
||||||
|
"isBuildCommand": true,
|
||||||
|
"command": "${userHome}/.pico-sdk/ninja/v1.12.1/ninja",
|
||||||
|
"args": ["-C", "${workspaceFolder}/build"],
|
||||||
|
"group": "build",
|
||||||
|
"presentation": {
|
||||||
|
"reveal": "always",
|
||||||
|
"panel": "dedicated"
|
||||||
|
},
|
||||||
|
"problemMatcher": "$gcc",
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/ninja/v1.12.1/ninja.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Run Project",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${env:HOME}/.pico-sdk/picotool/2.2.0/picotool/picotool",
|
||||||
|
"args": [
|
||||||
|
"load",
|
||||||
|
"${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"-fx"
|
||||||
|
],
|
||||||
|
"presentation": {
|
||||||
|
"reveal": "always",
|
||||||
|
"panel": "dedicated"
|
||||||
|
},
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/picotool/2.2.0/picotool/picotool.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Flash",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/${command:raspberry-pi-pico.getTarget}.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; program \"${command:raspberry-pi-pico.launchTargetPath}\" verify reset exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Rescue Reset",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/${command:raspberry-pi-pico.getChip}-rescue.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; reset halt; exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Risc-V Reset (RP2350)",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-c",
|
||||||
|
"set USE_CORE { rv0 rv1 cm0 cm1 }",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/rp2350.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; init;",
|
||||||
|
"-c",
|
||||||
|
"write_memory 0x40120158 8 { 0x3 }; echo [format \"Info : ARCHSEL 0x%02x\" [read_memory 0x40120158 8 1]];",
|
||||||
|
"-c",
|
||||||
|
"reset halt; targets rp2350.rv0; echo [format \"Info : ARCHSEL_STATUS 0x%02x\" [read_memory 0x4012015C 8 1]]; exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -0,0 +1,48 @@
|
|||||||
|
/**
|
||||||
|
* @file 0x0005_intro-to-variables.c
|
||||||
|
* @brief Introduction to variables: declare, assign, and print a uint8_t
|
||||||
|
* @author Kevin Thomas
|
||||||
|
* @date 2025
|
||||||
|
*
|
||||||
|
* MIT License
|
||||||
|
*
|
||||||
|
* Copyright (c) 2025 Kevin Thomas
|
||||||
|
*
|
||||||
|
* 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.
|
||||||
|
*
|
||||||
|
* -----------------------------------------------------------------------------
|
||||||
|
*
|
||||||
|
* Demonstrates declaring, initializing, and reassigning a uint8_t variable.
|
||||||
|
* Prints the variable value over UART in an infinite loop.
|
||||||
|
*
|
||||||
|
* Wiring:
|
||||||
|
* No external wiring required (USB serial).
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
#include "pico/stdlib.h"
|
||||||
|
|
||||||
|
int main(void) {
|
||||||
|
uint8_t age = 42;
|
||||||
|
age = 43;
|
||||||
|
stdio_init_all();
|
||||||
|
while (true) {
|
||||||
|
printf("age: %d\r\n", age);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,57 @@
|
|||||||
|
# Generated Cmake Pico project file
|
||||||
|
|
||||||
|
cmake_minimum_required(VERSION 3.13)
|
||||||
|
|
||||||
|
set(CMAKE_C_STANDARD 11)
|
||||||
|
set(CMAKE_CXX_STANDARD 17)
|
||||||
|
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
|
||||||
|
|
||||||
|
# Initialise pico_sdk from installed location
|
||||||
|
# (note this can come from environment, CMake cache etc)
|
||||||
|
|
||||||
|
# == DO NOT EDIT THE FOLLOWING LINES for the Raspberry Pi Pico VS Code Extension to work ==
|
||||||
|
if(WIN32)
|
||||||
|
set(USERHOME $ENV{USERPROFILE})
|
||||||
|
else()
|
||||||
|
set(USERHOME $ENV{HOME})
|
||||||
|
endif()
|
||||||
|
set(sdkVersion 2.2.0)
|
||||||
|
set(toolchainVersion 14_2_Rel1)
|
||||||
|
set(picotoolVersion 2.2.0)
|
||||||
|
set(picoVscode ${USERHOME}/.pico-sdk/cmake/pico-vscode.cmake)
|
||||||
|
if (EXISTS ${picoVscode})
|
||||||
|
include(${picoVscode})
|
||||||
|
endif()
|
||||||
|
# ====================================================================================
|
||||||
|
set(PICO_BOARD pico2 CACHE STRING "Board type")
|
||||||
|
|
||||||
|
# Pull in Raspberry Pi Pico SDK (must be before project)
|
||||||
|
include(pico_sdk_import.cmake)
|
||||||
|
|
||||||
|
project(0x0005_intro-to-variables C CXX ASM)
|
||||||
|
|
||||||
|
# Initialise the Raspberry Pi Pico SDK
|
||||||
|
pico_sdk_init()
|
||||||
|
|
||||||
|
# Add executable. Default name is the project name, version 0.1
|
||||||
|
|
||||||
|
add_executable(0x0005_intro-to-variables 0x0005_intro-to-variables.c )
|
||||||
|
|
||||||
|
pico_set_program_name(0x0005_intro-to-variables "0x0005_intro-to-variables")
|
||||||
|
pico_set_program_version(0x0005_intro-to-variables "0.1")
|
||||||
|
|
||||||
|
# Modify the below lines to enable/disable output over UART/USB
|
||||||
|
pico_enable_stdio_uart(0x0005_intro-to-variables 1)
|
||||||
|
pico_enable_stdio_usb(0x0005_intro-to-variables 0)
|
||||||
|
|
||||||
|
# Add the standard library to the build
|
||||||
|
target_link_libraries(0x0005_intro-to-variables
|
||||||
|
pico_stdlib)
|
||||||
|
|
||||||
|
# Add the standard include files to the build
|
||||||
|
target_include_directories(0x0005_intro-to-variables PRIVATE
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}
|
||||||
|
)
|
||||||
|
|
||||||
|
pico_add_extra_outputs(0x0005_intro-to-variables)
|
||||||
|
|
||||||
@@ -0,0 +1,121 @@
|
|||||||
|
# This is a copy of <PICO_SDK_PATH>/external/pico_sdk_import.cmake
|
||||||
|
|
||||||
|
# This can be dropped into an external project to help locate this SDK
|
||||||
|
# It should be include()ed prior to project()
|
||||||
|
|
||||||
|
# Copyright 2020 (c) 2020 Raspberry Pi (Trading) Ltd.
|
||||||
|
#
|
||||||
|
# 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. Neither the name of the copyright holder nor the names of its contributors may be used to endorse or promote products
|
||||||
|
# derived from this software without specific prior written permission.
|
||||||
|
#
|
||||||
|
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "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 COPYRIGHT HOLDER OR CONTRIBUTORS 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.
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_PATH} AND (NOT PICO_SDK_PATH))
|
||||||
|
set(PICO_SDK_PATH $ENV{PICO_SDK_PATH})
|
||||||
|
message("Using PICO_SDK_PATH from environment ('${PICO_SDK_PATH}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT} AND (NOT PICO_SDK_FETCH_FROM_GIT))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT $ENV{PICO_SDK_FETCH_FROM_GIT})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT from environment ('${PICO_SDK_FETCH_FROM_GIT}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT_PATH} AND (NOT PICO_SDK_FETCH_FROM_GIT_PATH))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_PATH $ENV{PICO_SDK_FETCH_FROM_GIT_PATH})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT_PATH from environment ('${PICO_SDK_FETCH_FROM_GIT_PATH}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT_TAG} AND (NOT PICO_SDK_FETCH_FROM_GIT_TAG))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG $ENV{PICO_SDK_FETCH_FROM_GIT_TAG})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT_TAG from environment ('${PICO_SDK_FETCH_FROM_GIT_TAG}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT AND NOT PICO_SDK_FETCH_FROM_GIT_TAG)
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG "master")
|
||||||
|
message("Using master as default value for PICO_SDK_FETCH_FROM_GIT_TAG")
|
||||||
|
endif()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH "${PICO_SDK_PATH}" CACHE PATH "Path to the Raspberry Pi Pico SDK")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT "${PICO_SDK_FETCH_FROM_GIT}" CACHE BOOL "Set to ON to fetch copy of SDK from git if not otherwise locatable")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_PATH "${PICO_SDK_FETCH_FROM_GIT_PATH}" CACHE FILEPATH "location to download SDK")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG "${PICO_SDK_FETCH_FROM_GIT_TAG}" CACHE FILEPATH "release tag for SDK")
|
||||||
|
|
||||||
|
if (NOT PICO_SDK_PATH)
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT)
|
||||||
|
include(FetchContent)
|
||||||
|
set(FETCHCONTENT_BASE_DIR_SAVE ${FETCHCONTENT_BASE_DIR})
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT_PATH)
|
||||||
|
get_filename_component(FETCHCONTENT_BASE_DIR "${PICO_SDK_FETCH_FROM_GIT_PATH}" REALPATH BASE_DIR "${CMAKE_SOURCE_DIR}")
|
||||||
|
endif ()
|
||||||
|
FetchContent_Declare(
|
||||||
|
pico_sdk
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
)
|
||||||
|
|
||||||
|
if (NOT pico_sdk)
|
||||||
|
message("Downloading Raspberry Pi Pico SDK")
|
||||||
|
# GIT_SUBMODULES_RECURSE was added in 3.17
|
||||||
|
if (${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.17.0")
|
||||||
|
FetchContent_Populate(
|
||||||
|
pico_sdk
|
||||||
|
QUIET
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
GIT_SUBMODULES_RECURSE FALSE
|
||||||
|
|
||||||
|
SOURCE_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-src
|
||||||
|
BINARY_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-build
|
||||||
|
SUBBUILD_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-subbuild
|
||||||
|
)
|
||||||
|
else ()
|
||||||
|
FetchContent_Populate(
|
||||||
|
pico_sdk
|
||||||
|
QUIET
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
|
||||||
|
SOURCE_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-src
|
||||||
|
BINARY_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-build
|
||||||
|
SUBBUILD_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-subbuild
|
||||||
|
)
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH ${pico_sdk_SOURCE_DIR})
|
||||||
|
endif ()
|
||||||
|
set(FETCHCONTENT_BASE_DIR ${FETCHCONTENT_BASE_DIR_SAVE})
|
||||||
|
else ()
|
||||||
|
message(FATAL_ERROR
|
||||||
|
"SDK location was not specified. Please set PICO_SDK_PATH or set PICO_SDK_FETCH_FROM_GIT to on to fetch from git."
|
||||||
|
)
|
||||||
|
endif ()
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
get_filename_component(PICO_SDK_PATH "${PICO_SDK_PATH}" REALPATH BASE_DIR "${CMAKE_BINARY_DIR}")
|
||||||
|
if (NOT EXISTS ${PICO_SDK_PATH})
|
||||||
|
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' not found")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_INIT_CMAKE_FILE ${PICO_SDK_PATH}/pico_sdk_init.cmake)
|
||||||
|
if (NOT EXISTS ${PICO_SDK_INIT_CMAKE_FILE})
|
||||||
|
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' does not appear to contain the Raspberry Pi Pico SDK")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH ${PICO_SDK_PATH} CACHE PATH "Path to the Raspberry Pi Pico SDK" FORCE)
|
||||||
|
|
||||||
|
include(${PICO_SDK_INIT_CMAKE_FILE})
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
build
|
||||||
|
!.vscode/*
|
||||||
@@ -0,0 +1,21 @@
|
|||||||
|
{
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Pico",
|
||||||
|
"includePath": [
|
||||||
|
"${workspaceFolder}/**",
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.2.0/**"
|
||||||
|
],
|
||||||
|
"forcedInclude": [
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.2.0/src/common/pico_base_headers/include/pico.h"
|
||||||
|
],
|
||||||
|
"defines": [],
|
||||||
|
"compilerPath": "${userHome}/.pico-sdk/toolchain/14_2_Rel1/bin/arm-none-eabi-gcc.exe",
|
||||||
|
"compileCommands": "${workspaceFolder}/build/compile_commands.json",
|
||||||
|
"cStandard": "c17",
|
||||||
|
"cppStandard": "c++14",
|
||||||
|
"intelliSenseMode": "linux-gcc-arm"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"version": 4
|
||||||
|
}
|
||||||
@@ -0,0 +1,15 @@
|
|||||||
|
[
|
||||||
|
{
|
||||||
|
"name": "Pico",
|
||||||
|
"compilers": {
|
||||||
|
"C": "${command:raspberry-pi-pico.getCompilerPath}",
|
||||||
|
"CXX": "${command:raspberry-pi-pico.getCxxCompilerPath}"
|
||||||
|
},
|
||||||
|
"environmentVariables": {
|
||||||
|
"PATH": "${command:raspberry-pi-pico.getEnvPath};${env:PATH}"
|
||||||
|
},
|
||||||
|
"cmakeSettings": {
|
||||||
|
"Python3_EXECUTABLE": "${command:raspberry-pi-pico.getPythonPath}"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
@@ -0,0 +1,9 @@
|
|||||||
|
{
|
||||||
|
"recommendations": [
|
||||||
|
"marus25.cortex-debug",
|
||||||
|
"ms-vscode.cpptools",
|
||||||
|
"ms-vscode.cpptools-extension-pack",
|
||||||
|
"ms-vscode.vscode-serial-monitor",
|
||||||
|
"raspberry-pi.raspberry-pi-pico"
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -0,0 +1,50 @@
|
|||||||
|
{
|
||||||
|
"version": "0.2.0",
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Pico Debug (Cortex-Debug)",
|
||||||
|
"cwd": "${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"executable": "${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"request": "launch",
|
||||||
|
"type": "cortex-debug",
|
||||||
|
"servertype": "openocd",
|
||||||
|
"serverpath": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"gdbPath": "${command:raspberry-pi-pico.getGDBPath}",
|
||||||
|
"device": "${command:raspberry-pi-pico.getChipUppercase}",
|
||||||
|
"configFiles": [
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"target/${command:raspberry-pi-pico.getTarget}.cfg"
|
||||||
|
],
|
||||||
|
"svdFile": "${userHome}/.pico-sdk/sdk/2.2.0/src/${command:raspberry-pi-pico.getChip}/hardware_regs/${command:raspberry-pi-pico.getChipUppercase}.svd",
|
||||||
|
"runToEntryPoint": "main",
|
||||||
|
// Fix for no_flash binaries, where monitor reset halt doesn't do what is expected
|
||||||
|
// Also works fine for flash binaries
|
||||||
|
"overrideLaunchCommands": [
|
||||||
|
"monitor reset init",
|
||||||
|
"load \"${command:raspberry-pi-pico.launchTargetPath}\""
|
||||||
|
],
|
||||||
|
"openOCDLaunchCommands": [
|
||||||
|
"adapter speed 5000"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Pico Debug (Cortex-Debug with external OpenOCD)",
|
||||||
|
"cwd": "${workspaceRoot}",
|
||||||
|
"executable": "${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"request": "launch",
|
||||||
|
"type": "cortex-debug",
|
||||||
|
"servertype": "external",
|
||||||
|
"gdbTarget": "localhost:3333",
|
||||||
|
"gdbPath": "${command:raspberry-pi-pico.getGDBPath}",
|
||||||
|
"device": "${command:raspberry-pi-pico.getChipUppercase}",
|
||||||
|
"svdFile": "${userHome}/.pico-sdk/sdk/2.2.0/src/${command:raspberry-pi-pico.getChip}/hardware_regs/${command:raspberry-pi-pico.getChipUppercase}.svd",
|
||||||
|
"runToEntryPoint": "main",
|
||||||
|
// Fix for no_flash binaries, where monitor reset halt doesn't do what is expected
|
||||||
|
// Also works fine for flash binaries
|
||||||
|
"overrideLaunchCommands": [
|
||||||
|
"monitor reset init",
|
||||||
|
"load \"${command:raspberry-pi-pico.launchTargetPath}\""
|
||||||
|
]
|
||||||
|
},
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -0,0 +1,40 @@
|
|||||||
|
{
|
||||||
|
"cmake.showSystemKits": false,
|
||||||
|
"cmake.options.statusBarVisibility": "hidden",
|
||||||
|
"cmake.options.advanced": {
|
||||||
|
"build": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"launch": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"debug": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"cmake.configureOnEdit": false,
|
||||||
|
"cmake.automaticReconfigure": false,
|
||||||
|
"cmake.configureOnOpen": false,
|
||||||
|
"cmake.generator": "Ninja",
|
||||||
|
"cmake.cmakePath": "${userHome}/.pico-sdk/cmake/v3.31.5/bin/cmake",
|
||||||
|
"C_Cpp.debugShortcut": false,
|
||||||
|
"terminal.integrated.env.windows": {
|
||||||
|
"PICO_SDK_PATH": "${env:USERPROFILE}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:USERPROFILE}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"Path": "${env:USERPROFILE}/.pico-sdk/toolchain/14_2_Rel1/bin;${env:USERPROFILE}/.pico-sdk/picotool/2.2.0/picotool;${env:USERPROFILE}/.pico-sdk/cmake/v3.31.5/bin;${env:USERPROFILE}/.pico-sdk/ninja/v1.12.1;${env:PATH}"
|
||||||
|
},
|
||||||
|
"terminal.integrated.env.osx": {
|
||||||
|
"PICO_SDK_PATH": "${env:HOME}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1/bin:${env:HOME}/.pico-sdk/picotool/2.2.0/picotool:${env:HOME}/.pico-sdk/cmake/v3.31.5/bin:${env:HOME}/.pico-sdk/ninja/v1.12.1:${env:PATH}"
|
||||||
|
},
|
||||||
|
"terminal.integrated.env.linux": {
|
||||||
|
"PICO_SDK_PATH": "${env:HOME}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1/bin:${env:HOME}/.pico-sdk/picotool/2.2.0/picotool:${env:HOME}/.pico-sdk/cmake/v3.31.5/bin:${env:HOME}/.pico-sdk/ninja/v1.12.1:${env:PATH}"
|
||||||
|
},
|
||||||
|
"raspberry-pi-pico.cmakeAutoConfigure": true,
|
||||||
|
"raspberry-pi-pico.useCmakeTools": false,
|
||||||
|
"raspberry-pi-pico.cmakePath": "${HOME}/.pico-sdk/cmake/v3.31.5/bin/cmake",
|
||||||
|
"raspberry-pi-pico.ninjaPath": "${HOME}/.pico-sdk/ninja/v1.12.1/ninja"
|
||||||
|
}
|
||||||
+102
@@ -0,0 +1,102 @@
|
|||||||
|
{
|
||||||
|
"version": "2.0.0",
|
||||||
|
"tasks": [
|
||||||
|
{
|
||||||
|
"label": "Compile Project",
|
||||||
|
"type": "process",
|
||||||
|
"isBuildCommand": true,
|
||||||
|
"command": "${userHome}/.pico-sdk/ninja/v1.12.1/ninja",
|
||||||
|
"args": ["-C", "${workspaceFolder}/build"],
|
||||||
|
"group": "build",
|
||||||
|
"presentation": {
|
||||||
|
"reveal": "always",
|
||||||
|
"panel": "dedicated"
|
||||||
|
},
|
||||||
|
"problemMatcher": "$gcc",
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/ninja/v1.12.1/ninja.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Run Project",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${env:HOME}/.pico-sdk/picotool/2.2.0/picotool/picotool",
|
||||||
|
"args": [
|
||||||
|
"load",
|
||||||
|
"${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"-fx"
|
||||||
|
],
|
||||||
|
"presentation": {
|
||||||
|
"reveal": "always",
|
||||||
|
"panel": "dedicated"
|
||||||
|
},
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/picotool/2.2.0/picotool/picotool.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Flash",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/${command:raspberry-pi-pico.getTarget}.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; program \"${command:raspberry-pi-pico.launchTargetPath}\" verify reset exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Rescue Reset",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/${command:raspberry-pi-pico.getChip}-rescue.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; reset halt; exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Risc-V Reset (RP2350)",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-c",
|
||||||
|
"set USE_CORE { rv0 rv1 cm0 cm1 }",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/rp2350.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; init;",
|
||||||
|
"-c",
|
||||||
|
"write_memory 0x40120158 8 { 0x3 }; echo [format \"Info : ARCHSEL 0x%02x\" [read_memory 0x40120158 8 1]];",
|
||||||
|
"-c",
|
||||||
|
"reset halt; targets rp2350.rv0; echo [format \"Info : ARCHSEL_STATUS 0x%02x\" [read_memory 0x4012015C 8 1]]; exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -0,0 +1,53 @@
|
|||||||
|
/**
|
||||||
|
* @file 0x0008_uninitialized-variables-a.c
|
||||||
|
* @brief Blink LED using SDK gpio functions (no UART)
|
||||||
|
* @author Kevin Thomas
|
||||||
|
* @date 2025
|
||||||
|
*
|
||||||
|
* MIT License
|
||||||
|
*
|
||||||
|
* Copyright (c) 2025 Kevin Thomas
|
||||||
|
*
|
||||||
|
* 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.
|
||||||
|
*
|
||||||
|
* -----------------------------------------------------------------------------
|
||||||
|
*
|
||||||
|
* Blinks an LED on GPIO16 using the standard Pico SDK gpio_init / gpio_put
|
||||||
|
* functions. No UART output; pure GPIO blink demonstration.
|
||||||
|
*
|
||||||
|
* Wiring:
|
||||||
|
* GPIO16 -> LED anode (with current-limiting resistor to GND)
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
#include "pico/stdlib.h"
|
||||||
|
|
||||||
|
/** @brief GPIO pin number for the LED */
|
||||||
|
#define LED_PIN 16
|
||||||
|
|
||||||
|
int main(void) {
|
||||||
|
gpio_init(LED_PIN);
|
||||||
|
gpio_set_dir(LED_PIN, GPIO_OUT);
|
||||||
|
while (true) {
|
||||||
|
gpio_put(LED_PIN, 1);
|
||||||
|
sleep_ms(500);
|
||||||
|
gpio_put(LED_PIN, 0);
|
||||||
|
sleep_ms(500);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,57 @@
|
|||||||
|
# Generated Cmake Pico project file
|
||||||
|
|
||||||
|
cmake_minimum_required(VERSION 3.13)
|
||||||
|
|
||||||
|
set(CMAKE_C_STANDARD 11)
|
||||||
|
set(CMAKE_CXX_STANDARD 17)
|
||||||
|
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
|
||||||
|
|
||||||
|
# Initialise pico_sdk from installed location
|
||||||
|
# (note this can come from environment, CMake cache etc)
|
||||||
|
|
||||||
|
# == DO NOT EDIT THE FOLLOWING LINES for the Raspberry Pi Pico VS Code Extension to work ==
|
||||||
|
if(WIN32)
|
||||||
|
set(USERHOME $ENV{USERPROFILE})
|
||||||
|
else()
|
||||||
|
set(USERHOME $ENV{HOME})
|
||||||
|
endif()
|
||||||
|
set(sdkVersion 2.2.0)
|
||||||
|
set(toolchainVersion 14_2_Rel1)
|
||||||
|
set(picotoolVersion 2.2.0)
|
||||||
|
set(picoVscode ${USERHOME}/.pico-sdk/cmake/pico-vscode.cmake)
|
||||||
|
if (EXISTS ${picoVscode})
|
||||||
|
include(${picoVscode})
|
||||||
|
endif()
|
||||||
|
# ====================================================================================
|
||||||
|
set(PICO_BOARD pico2 CACHE STRING "Board type")
|
||||||
|
|
||||||
|
# Pull in Raspberry Pi Pico SDK (must be before project)
|
||||||
|
include(pico_sdk_import.cmake)
|
||||||
|
|
||||||
|
project(0x0008_uninitialized-variables-a C CXX ASM)
|
||||||
|
|
||||||
|
# Initialise the Raspberry Pi Pico SDK
|
||||||
|
pico_sdk_init()
|
||||||
|
|
||||||
|
# Add executable. Default name is the project name, version 0.1
|
||||||
|
|
||||||
|
add_executable(0x0008_uninitialized-variables-a 0x0008_uninitialized-variables-a.c )
|
||||||
|
|
||||||
|
pico_set_program_name(0x0008_uninitialized-variables-a "0x0008_uninitialized-variables-a")
|
||||||
|
pico_set_program_version(0x0008_uninitialized-variables-a "0.1")
|
||||||
|
|
||||||
|
# Modify the below lines to enable/disable output over UART/USB
|
||||||
|
pico_enable_stdio_uart(0x0008_uninitialized-variables-a 0)
|
||||||
|
pico_enable_stdio_usb(0x0008_uninitialized-variables-a 0)
|
||||||
|
|
||||||
|
# Add the standard library to the build
|
||||||
|
target_link_libraries(0x0008_uninitialized-variables-a
|
||||||
|
pico_stdlib)
|
||||||
|
|
||||||
|
# Add the standard include files to the build
|
||||||
|
target_include_directories(0x0008_uninitialized-variables-a PRIVATE
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}
|
||||||
|
)
|
||||||
|
|
||||||
|
pico_add_extra_outputs(0x0008_uninitialized-variables-a)
|
||||||
|
|
||||||
@@ -0,0 +1,121 @@
|
|||||||
|
# This is a copy of <PICO_SDK_PATH>/external/pico_sdk_import.cmake
|
||||||
|
|
||||||
|
# This can be dropped into an external project to help locate this SDK
|
||||||
|
# It should be include()ed prior to project()
|
||||||
|
|
||||||
|
# Copyright 2020 (c) 2020 Raspberry Pi (Trading) Ltd.
|
||||||
|
#
|
||||||
|
# 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. Neither the name of the copyright holder nor the names of its contributors may be used to endorse or promote products
|
||||||
|
# derived from this software without specific prior written permission.
|
||||||
|
#
|
||||||
|
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "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 COPYRIGHT HOLDER OR CONTRIBUTORS 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.
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_PATH} AND (NOT PICO_SDK_PATH))
|
||||||
|
set(PICO_SDK_PATH $ENV{PICO_SDK_PATH})
|
||||||
|
message("Using PICO_SDK_PATH from environment ('${PICO_SDK_PATH}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT} AND (NOT PICO_SDK_FETCH_FROM_GIT))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT $ENV{PICO_SDK_FETCH_FROM_GIT})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT from environment ('${PICO_SDK_FETCH_FROM_GIT}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT_PATH} AND (NOT PICO_SDK_FETCH_FROM_GIT_PATH))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_PATH $ENV{PICO_SDK_FETCH_FROM_GIT_PATH})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT_PATH from environment ('${PICO_SDK_FETCH_FROM_GIT_PATH}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT_TAG} AND (NOT PICO_SDK_FETCH_FROM_GIT_TAG))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG $ENV{PICO_SDK_FETCH_FROM_GIT_TAG})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT_TAG from environment ('${PICO_SDK_FETCH_FROM_GIT_TAG}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT AND NOT PICO_SDK_FETCH_FROM_GIT_TAG)
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG "master")
|
||||||
|
message("Using master as default value for PICO_SDK_FETCH_FROM_GIT_TAG")
|
||||||
|
endif()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH "${PICO_SDK_PATH}" CACHE PATH "Path to the Raspberry Pi Pico SDK")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT "${PICO_SDK_FETCH_FROM_GIT}" CACHE BOOL "Set to ON to fetch copy of SDK from git if not otherwise locatable")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_PATH "${PICO_SDK_FETCH_FROM_GIT_PATH}" CACHE FILEPATH "location to download SDK")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG "${PICO_SDK_FETCH_FROM_GIT_TAG}" CACHE FILEPATH "release tag for SDK")
|
||||||
|
|
||||||
|
if (NOT PICO_SDK_PATH)
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT)
|
||||||
|
include(FetchContent)
|
||||||
|
set(FETCHCONTENT_BASE_DIR_SAVE ${FETCHCONTENT_BASE_DIR})
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT_PATH)
|
||||||
|
get_filename_component(FETCHCONTENT_BASE_DIR "${PICO_SDK_FETCH_FROM_GIT_PATH}" REALPATH BASE_DIR "${CMAKE_SOURCE_DIR}")
|
||||||
|
endif ()
|
||||||
|
FetchContent_Declare(
|
||||||
|
pico_sdk
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
)
|
||||||
|
|
||||||
|
if (NOT pico_sdk)
|
||||||
|
message("Downloading Raspberry Pi Pico SDK")
|
||||||
|
# GIT_SUBMODULES_RECURSE was added in 3.17
|
||||||
|
if (${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.17.0")
|
||||||
|
FetchContent_Populate(
|
||||||
|
pico_sdk
|
||||||
|
QUIET
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
GIT_SUBMODULES_RECURSE FALSE
|
||||||
|
|
||||||
|
SOURCE_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-src
|
||||||
|
BINARY_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-build
|
||||||
|
SUBBUILD_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-subbuild
|
||||||
|
)
|
||||||
|
else ()
|
||||||
|
FetchContent_Populate(
|
||||||
|
pico_sdk
|
||||||
|
QUIET
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
|
||||||
|
SOURCE_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-src
|
||||||
|
BINARY_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-build
|
||||||
|
SUBBUILD_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-subbuild
|
||||||
|
)
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH ${pico_sdk_SOURCE_DIR})
|
||||||
|
endif ()
|
||||||
|
set(FETCHCONTENT_BASE_DIR ${FETCHCONTENT_BASE_DIR_SAVE})
|
||||||
|
else ()
|
||||||
|
message(FATAL_ERROR
|
||||||
|
"SDK location was not specified. Please set PICO_SDK_PATH or set PICO_SDK_FETCH_FROM_GIT to on to fetch from git."
|
||||||
|
)
|
||||||
|
endif ()
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
get_filename_component(PICO_SDK_PATH "${PICO_SDK_PATH}" REALPATH BASE_DIR "${CMAKE_BINARY_DIR}")
|
||||||
|
if (NOT EXISTS ${PICO_SDK_PATH})
|
||||||
|
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' not found")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_INIT_CMAKE_FILE ${PICO_SDK_PATH}/pico_sdk_init.cmake)
|
||||||
|
if (NOT EXISTS ${PICO_SDK_INIT_CMAKE_FILE})
|
||||||
|
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' does not appear to contain the Raspberry Pi Pico SDK")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH ${PICO_SDK_PATH} CACHE PATH "Path to the Raspberry Pi Pico SDK" FORCE)
|
||||||
|
|
||||||
|
include(${PICO_SDK_INIT_CMAKE_FILE})
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
build
|
||||||
|
!.vscode/*
|
||||||
@@ -0,0 +1,22 @@
|
|||||||
|
{
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Pico",
|
||||||
|
"includePath": [
|
||||||
|
"${workspaceFolder}/**",
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.2.0/**"
|
||||||
|
],
|
||||||
|
"forcedInclude": [
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.2.0/src/common/pico_base_headers/include/pico.h",
|
||||||
|
"${workspaceFolder}/build/generated/pico_base/pico/config_autogen.h"
|
||||||
|
],
|
||||||
|
"defines": [],
|
||||||
|
"compilerPath": "${userHome}/.pico-sdk/toolchain/14_2_Rel1/bin/arm-none-eabi-gcc.exe",
|
||||||
|
"compileCommands": "${workspaceFolder}/build/compile_commands.json",
|
||||||
|
"cStandard": "c17",
|
||||||
|
"cppStandard": "c++14",
|
||||||
|
"intelliSenseMode": "linux-gcc-arm"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"version": 4
|
||||||
|
}
|
||||||
@@ -0,0 +1,15 @@
|
|||||||
|
[
|
||||||
|
{
|
||||||
|
"name": "Pico",
|
||||||
|
"compilers": {
|
||||||
|
"C": "${command:raspberry-pi-pico.getCompilerPath}",
|
||||||
|
"CXX": "${command:raspberry-pi-pico.getCxxCompilerPath}"
|
||||||
|
},
|
||||||
|
"environmentVariables": {
|
||||||
|
"PATH": "${command:raspberry-pi-pico.getEnvPath};${env:PATH}"
|
||||||
|
},
|
||||||
|
"cmakeSettings": {
|
||||||
|
"Python3_EXECUTABLE": "${command:raspberry-pi-pico.getPythonPath}"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
@@ -0,0 +1,9 @@
|
|||||||
|
{
|
||||||
|
"recommendations": [
|
||||||
|
"marus25.cortex-debug",
|
||||||
|
"ms-vscode.cpptools",
|
||||||
|
"ms-vscode.cpptools-extension-pack",
|
||||||
|
"ms-vscode.vscode-serial-monitor",
|
||||||
|
"raspberry-pi.raspberry-pi-pico"
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -0,0 +1,50 @@
|
|||||||
|
{
|
||||||
|
"version": "0.2.0",
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Pico Debug (Cortex-Debug)",
|
||||||
|
"cwd": "${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"executable": "${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"request": "launch",
|
||||||
|
"type": "cortex-debug",
|
||||||
|
"servertype": "openocd",
|
||||||
|
"serverpath": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"gdbPath": "${command:raspberry-pi-pico.getGDBPath}",
|
||||||
|
"device": "${command:raspberry-pi-pico.getChipUppercase}",
|
||||||
|
"configFiles": [
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"target/${command:raspberry-pi-pico.getTarget}.cfg"
|
||||||
|
],
|
||||||
|
"svdFile": "${userHome}/.pico-sdk/sdk/2.2.0/src/${command:raspberry-pi-pico.getChip}/hardware_regs/${command:raspberry-pi-pico.getChipUppercase}.svd",
|
||||||
|
"runToEntryPoint": "main",
|
||||||
|
// Fix for no_flash binaries, where monitor reset halt doesn't do what is expected
|
||||||
|
// Also works fine for flash binaries
|
||||||
|
"overrideLaunchCommands": [
|
||||||
|
"monitor reset init",
|
||||||
|
"load \"${command:raspberry-pi-pico.launchTargetPath}\""
|
||||||
|
],
|
||||||
|
"openOCDLaunchCommands": [
|
||||||
|
"adapter speed 5000"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Pico Debug (Cortex-Debug with external OpenOCD)",
|
||||||
|
"cwd": "${workspaceRoot}",
|
||||||
|
"executable": "${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"request": "launch",
|
||||||
|
"type": "cortex-debug",
|
||||||
|
"servertype": "external",
|
||||||
|
"gdbTarget": "localhost:3333",
|
||||||
|
"gdbPath": "${command:raspberry-pi-pico.getGDBPath}",
|
||||||
|
"device": "${command:raspberry-pi-pico.getChipUppercase}",
|
||||||
|
"svdFile": "${userHome}/.pico-sdk/sdk/2.2.0/src/${command:raspberry-pi-pico.getChip}/hardware_regs/${command:raspberry-pi-pico.getChipUppercase}.svd",
|
||||||
|
"runToEntryPoint": "main",
|
||||||
|
// Fix for no_flash binaries, where monitor reset halt doesn't do what is expected
|
||||||
|
// Also works fine for flash binaries
|
||||||
|
"overrideLaunchCommands": [
|
||||||
|
"monitor reset init",
|
||||||
|
"load \"${command:raspberry-pi-pico.launchTargetPath}\""
|
||||||
|
]
|
||||||
|
},
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -0,0 +1,40 @@
|
|||||||
|
{
|
||||||
|
"cmake.showSystemKits": false,
|
||||||
|
"cmake.options.statusBarVisibility": "hidden",
|
||||||
|
"cmake.options.advanced": {
|
||||||
|
"build": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"launch": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"debug": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"cmake.configureOnEdit": false,
|
||||||
|
"cmake.automaticReconfigure": false,
|
||||||
|
"cmake.configureOnOpen": false,
|
||||||
|
"cmake.generator": "Ninja",
|
||||||
|
"cmake.cmakePath": "${userHome}/.pico-sdk/cmake/v3.31.5/bin/cmake",
|
||||||
|
"C_Cpp.debugShortcut": false,
|
||||||
|
"terminal.integrated.env.windows": {
|
||||||
|
"PICO_SDK_PATH": "${env:USERPROFILE}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:USERPROFILE}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"Path": "${env:USERPROFILE}/.pico-sdk/toolchain/14_2_Rel1/bin;${env:USERPROFILE}/.pico-sdk/picotool/2.2.0/picotool;${env:USERPROFILE}/.pico-sdk/cmake/v3.31.5/bin;${env:USERPROFILE}/.pico-sdk/ninja/v1.12.1;${env:PATH}"
|
||||||
|
},
|
||||||
|
"terminal.integrated.env.osx": {
|
||||||
|
"PICO_SDK_PATH": "${env:HOME}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1/bin:${env:HOME}/.pico-sdk/picotool/2.2.0/picotool:${env:HOME}/.pico-sdk/cmake/v3.31.5/bin:${env:HOME}/.pico-sdk/ninja/v1.12.1:${env:PATH}"
|
||||||
|
},
|
||||||
|
"terminal.integrated.env.linux": {
|
||||||
|
"PICO_SDK_PATH": "${env:HOME}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1/bin:${env:HOME}/.pico-sdk/picotool/2.2.0/picotool:${env:HOME}/.pico-sdk/cmake/v3.31.5/bin:${env:HOME}/.pico-sdk/ninja/v1.12.1:${env:PATH}"
|
||||||
|
},
|
||||||
|
"raspberry-pi-pico.cmakeAutoConfigure": true,
|
||||||
|
"raspberry-pi-pico.useCmakeTools": false,
|
||||||
|
"raspberry-pi-pico.cmakePath": "${HOME}/.pico-sdk/cmake/v3.31.5/bin/cmake",
|
||||||
|
"raspberry-pi-pico.ninjaPath": "${HOME}/.pico-sdk/ninja/v1.12.1/ninja"
|
||||||
|
}
|
||||||
+102
@@ -0,0 +1,102 @@
|
|||||||
|
{
|
||||||
|
"version": "2.0.0",
|
||||||
|
"tasks": [
|
||||||
|
{
|
||||||
|
"label": "Compile Project",
|
||||||
|
"type": "process",
|
||||||
|
"isBuildCommand": true,
|
||||||
|
"command": "${userHome}/.pico-sdk/ninja/v1.12.1/ninja",
|
||||||
|
"args": ["-C", "${workspaceFolder}/build"],
|
||||||
|
"group": "build",
|
||||||
|
"presentation": {
|
||||||
|
"reveal": "always",
|
||||||
|
"panel": "dedicated"
|
||||||
|
},
|
||||||
|
"problemMatcher": "$gcc",
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/ninja/v1.12.1/ninja.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Run Project",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${env:HOME}/.pico-sdk/picotool/2.2.0/picotool/picotool",
|
||||||
|
"args": [
|
||||||
|
"load",
|
||||||
|
"${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"-fx"
|
||||||
|
],
|
||||||
|
"presentation": {
|
||||||
|
"reveal": "always",
|
||||||
|
"panel": "dedicated"
|
||||||
|
},
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/picotool/2.2.0/picotool/picotool.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Flash",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/${command:raspberry-pi-pico.getTarget}.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; program \"${command:raspberry-pi-pico.launchTargetPath}\" verify reset exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Rescue Reset",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/${command:raspberry-pi-pico.getChip}-rescue.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; reset halt; exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Risc-V Reset (RP2350)",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-c",
|
||||||
|
"set USE_CORE { rv0 rv1 cm0 cm1 }",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/rp2350.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; init;",
|
||||||
|
"-c",
|
||||||
|
"write_memory 0x40120158 8 { 0x3 }; echo [format \"Info : ARCHSEL 0x%02x\" [read_memory 0x40120158 8 1]];",
|
||||||
|
"-c",
|
||||||
|
"reset halt; targets rp2350.rv0; echo [format \"Info : ARCHSEL_STATUS 0x%02x\" [read_memory 0x4012015C 8 1]]; exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -0,0 +1,80 @@
|
|||||||
|
/**
|
||||||
|
* @file 0x0008_uninitialized-variables-b.c
|
||||||
|
* @brief Blink LED using gpioc coprocessor bit-level functions
|
||||||
|
* @author Kevin Thomas
|
||||||
|
* @date 2025
|
||||||
|
*
|
||||||
|
* MIT License
|
||||||
|
*
|
||||||
|
* Copyright (c) 2025 Kevin Thomas
|
||||||
|
*
|
||||||
|
* 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.
|
||||||
|
*
|
||||||
|
* -----------------------------------------------------------------------------
|
||||||
|
*
|
||||||
|
* Blinks an LED on GPIO16 using the RP2350 gpioc coprocessor bit-level
|
||||||
|
* functions (gpioc_bit_oe_put / gpioc_bit_out_put) instead of the standard
|
||||||
|
* gpio_init / gpio_put SDK calls.
|
||||||
|
*
|
||||||
|
* Wiring:
|
||||||
|
* GPIO16 -> LED anode (with current-limiting resistor to GND)
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
#include "pico/stdlib.h"
|
||||||
|
|
||||||
|
/** @brief GPIO pin number for the LED */
|
||||||
|
#define LED_PIN 16
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Initialize GPIO16 for output using coprocessor bit functions
|
||||||
|
*
|
||||||
|
* @details Configures the pad for SIO, sets direction to input first,
|
||||||
|
* clears the output, selects SIO function, then enables output.
|
||||||
|
*
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
static void gpio_coprocessor_init(void) {
|
||||||
|
gpio_set_dir(LED_PIN, GPIO_IN);
|
||||||
|
gpio_put(LED_PIN, 0);
|
||||||
|
gpio_set_function(LED_PIN, GPIO_FUNC_SIO);
|
||||||
|
gpioc_bit_oe_put(LED_PIN, GPIO_OUT);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Blink LED using coprocessor bit output functions
|
||||||
|
*
|
||||||
|
* @details Toggles the LED on and off with 500ms delays using
|
||||||
|
* gpioc_bit_out_put and sleep_us.
|
||||||
|
*
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
static void blink_cycle(void) {
|
||||||
|
gpioc_bit_out_put(LED_PIN, 1);
|
||||||
|
sleep_us(500 * 1000ull);
|
||||||
|
gpioc_bit_out_put(LED_PIN, 0);
|
||||||
|
sleep_us(500 * 1000ull);
|
||||||
|
}
|
||||||
|
|
||||||
|
int main(void) {
|
||||||
|
gpio_coprocessor_init();
|
||||||
|
while (true) {
|
||||||
|
blink_cycle();
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,57 @@
|
|||||||
|
# Generated Cmake Pico project file
|
||||||
|
|
||||||
|
cmake_minimum_required(VERSION 3.13)
|
||||||
|
|
||||||
|
set(CMAKE_C_STANDARD 11)
|
||||||
|
set(CMAKE_CXX_STANDARD 17)
|
||||||
|
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
|
||||||
|
|
||||||
|
# Initialise pico_sdk from installed location
|
||||||
|
# (note this can come from environment, CMake cache etc)
|
||||||
|
|
||||||
|
# == DO NOT EDIT THE FOLLOWING LINES for the Raspberry Pi Pico VS Code Extension to work ==
|
||||||
|
if(WIN32)
|
||||||
|
set(USERHOME $ENV{USERPROFILE})
|
||||||
|
else()
|
||||||
|
set(USERHOME $ENV{HOME})
|
||||||
|
endif()
|
||||||
|
set(sdkVersion 2.2.0)
|
||||||
|
set(toolchainVersion 14_2_Rel1)
|
||||||
|
set(picotoolVersion 2.2.0)
|
||||||
|
set(picoVscode ${USERHOME}/.pico-sdk/cmake/pico-vscode.cmake)
|
||||||
|
if (EXISTS ${picoVscode})
|
||||||
|
include(${picoVscode})
|
||||||
|
endif()
|
||||||
|
# ====================================================================================
|
||||||
|
set(PICO_BOARD pico2 CACHE STRING "Board type")
|
||||||
|
|
||||||
|
# Pull in Raspberry Pi Pico SDK (must be before project)
|
||||||
|
include(pico_sdk_import.cmake)
|
||||||
|
|
||||||
|
project(0x0008_uninitialized-variables-b C CXX ASM)
|
||||||
|
|
||||||
|
# Initialise the Raspberry Pi Pico SDK
|
||||||
|
pico_sdk_init()
|
||||||
|
|
||||||
|
# Add executable. Default name is the project name, version 0.1
|
||||||
|
|
||||||
|
add_executable(0x0008_uninitialized-variables-b 0x0008_uninitialized-variables-b.c )
|
||||||
|
|
||||||
|
pico_set_program_name(0x0008_uninitialized-variables-b "0x0008_uninitialized-variables-b")
|
||||||
|
pico_set_program_version(0x0008_uninitialized-variables-b "0.1")
|
||||||
|
|
||||||
|
# Modify the below lines to enable/disable output over UART/USB
|
||||||
|
pico_enable_stdio_uart(0x0008_uninitialized-variables-b 0)
|
||||||
|
pico_enable_stdio_usb(0x0008_uninitialized-variables-b 0)
|
||||||
|
|
||||||
|
# Add the standard library to the build
|
||||||
|
target_link_libraries(0x0008_uninitialized-variables-b
|
||||||
|
pico_stdlib)
|
||||||
|
|
||||||
|
# Add the standard include files to the build
|
||||||
|
target_include_directories(0x0008_uninitialized-variables-b PRIVATE
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}
|
||||||
|
)
|
||||||
|
|
||||||
|
pico_add_extra_outputs(0x0008_uninitialized-variables-b)
|
||||||
|
|
||||||
@@ -0,0 +1,121 @@
|
|||||||
|
# This is a copy of <PICO_SDK_PATH>/external/pico_sdk_import.cmake
|
||||||
|
|
||||||
|
# This can be dropped into an external project to help locate this SDK
|
||||||
|
# It should be include()ed prior to project()
|
||||||
|
|
||||||
|
# Copyright 2020 (c) 2020 Raspberry Pi (Trading) Ltd.
|
||||||
|
#
|
||||||
|
# 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. Neither the name of the copyright holder nor the names of its contributors may be used to endorse or promote products
|
||||||
|
# derived from this software without specific prior written permission.
|
||||||
|
#
|
||||||
|
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "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 COPYRIGHT HOLDER OR CONTRIBUTORS 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.
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_PATH} AND (NOT PICO_SDK_PATH))
|
||||||
|
set(PICO_SDK_PATH $ENV{PICO_SDK_PATH})
|
||||||
|
message("Using PICO_SDK_PATH from environment ('${PICO_SDK_PATH}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT} AND (NOT PICO_SDK_FETCH_FROM_GIT))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT $ENV{PICO_SDK_FETCH_FROM_GIT})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT from environment ('${PICO_SDK_FETCH_FROM_GIT}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT_PATH} AND (NOT PICO_SDK_FETCH_FROM_GIT_PATH))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_PATH $ENV{PICO_SDK_FETCH_FROM_GIT_PATH})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT_PATH from environment ('${PICO_SDK_FETCH_FROM_GIT_PATH}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT_TAG} AND (NOT PICO_SDK_FETCH_FROM_GIT_TAG))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG $ENV{PICO_SDK_FETCH_FROM_GIT_TAG})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT_TAG from environment ('${PICO_SDK_FETCH_FROM_GIT_TAG}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT AND NOT PICO_SDK_FETCH_FROM_GIT_TAG)
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG "master")
|
||||||
|
message("Using master as default value for PICO_SDK_FETCH_FROM_GIT_TAG")
|
||||||
|
endif()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH "${PICO_SDK_PATH}" CACHE PATH "Path to the Raspberry Pi Pico SDK")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT "${PICO_SDK_FETCH_FROM_GIT}" CACHE BOOL "Set to ON to fetch copy of SDK from git if not otherwise locatable")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_PATH "${PICO_SDK_FETCH_FROM_GIT_PATH}" CACHE FILEPATH "location to download SDK")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG "${PICO_SDK_FETCH_FROM_GIT_TAG}" CACHE FILEPATH "release tag for SDK")
|
||||||
|
|
||||||
|
if (NOT PICO_SDK_PATH)
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT)
|
||||||
|
include(FetchContent)
|
||||||
|
set(FETCHCONTENT_BASE_DIR_SAVE ${FETCHCONTENT_BASE_DIR})
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT_PATH)
|
||||||
|
get_filename_component(FETCHCONTENT_BASE_DIR "${PICO_SDK_FETCH_FROM_GIT_PATH}" REALPATH BASE_DIR "${CMAKE_SOURCE_DIR}")
|
||||||
|
endif ()
|
||||||
|
FetchContent_Declare(
|
||||||
|
pico_sdk
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
)
|
||||||
|
|
||||||
|
if (NOT pico_sdk)
|
||||||
|
message("Downloading Raspberry Pi Pico SDK")
|
||||||
|
# GIT_SUBMODULES_RECURSE was added in 3.17
|
||||||
|
if (${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.17.0")
|
||||||
|
FetchContent_Populate(
|
||||||
|
pico_sdk
|
||||||
|
QUIET
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
GIT_SUBMODULES_RECURSE FALSE
|
||||||
|
|
||||||
|
SOURCE_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-src
|
||||||
|
BINARY_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-build
|
||||||
|
SUBBUILD_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-subbuild
|
||||||
|
)
|
||||||
|
else ()
|
||||||
|
FetchContent_Populate(
|
||||||
|
pico_sdk
|
||||||
|
QUIET
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
|
||||||
|
SOURCE_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-src
|
||||||
|
BINARY_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-build
|
||||||
|
SUBBUILD_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-subbuild
|
||||||
|
)
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH ${pico_sdk_SOURCE_DIR})
|
||||||
|
endif ()
|
||||||
|
set(FETCHCONTENT_BASE_DIR ${FETCHCONTENT_BASE_DIR_SAVE})
|
||||||
|
else ()
|
||||||
|
message(FATAL_ERROR
|
||||||
|
"SDK location was not specified. Please set PICO_SDK_PATH or set PICO_SDK_FETCH_FROM_GIT to on to fetch from git."
|
||||||
|
)
|
||||||
|
endif ()
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
get_filename_component(PICO_SDK_PATH "${PICO_SDK_PATH}" REALPATH BASE_DIR "${CMAKE_BINARY_DIR}")
|
||||||
|
if (NOT EXISTS ${PICO_SDK_PATH})
|
||||||
|
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' not found")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_INIT_CMAKE_FILE ${PICO_SDK_PATH}/pico_sdk_init.cmake)
|
||||||
|
if (NOT EXISTS ${PICO_SDK_INIT_CMAKE_FILE})
|
||||||
|
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' does not appear to contain the Raspberry Pi Pico SDK")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH ${PICO_SDK_PATH} CACHE PATH "Path to the Raspberry Pi Pico SDK" FORCE)
|
||||||
|
|
||||||
|
include(${PICO_SDK_INIT_CMAKE_FILE})
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
build
|
||||||
|
!.vscode/*
|
||||||
@@ -0,0 +1,22 @@
|
|||||||
|
{
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Pico",
|
||||||
|
"includePath": [
|
||||||
|
"${workspaceFolder}/**",
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.2.0/**"
|
||||||
|
],
|
||||||
|
"forcedInclude": [
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.2.0/src/common/pico_base_headers/include/pico.h",
|
||||||
|
"${workspaceFolder}/build/generated/pico_base/pico/config_autogen.h"
|
||||||
|
],
|
||||||
|
"defines": [],
|
||||||
|
"compilerPath": "${userHome}/.pico-sdk/toolchain/14_2_Rel1/bin/arm-none-eabi-gcc.exe",
|
||||||
|
"compileCommands": "${workspaceFolder}/build/compile_commands.json",
|
||||||
|
"cStandard": "c17",
|
||||||
|
"cppStandard": "c++14",
|
||||||
|
"intelliSenseMode": "linux-gcc-arm"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"version": 4
|
||||||
|
}
|
||||||
@@ -0,0 +1,15 @@
|
|||||||
|
[
|
||||||
|
{
|
||||||
|
"name": "Pico",
|
||||||
|
"compilers": {
|
||||||
|
"C": "${command:raspberry-pi-pico.getCompilerPath}",
|
||||||
|
"CXX": "${command:raspberry-pi-pico.getCxxCompilerPath}"
|
||||||
|
},
|
||||||
|
"environmentVariables": {
|
||||||
|
"PATH": "${command:raspberry-pi-pico.getEnvPath};${env:PATH}"
|
||||||
|
},
|
||||||
|
"cmakeSettings": {
|
||||||
|
"Python3_EXECUTABLE": "${command:raspberry-pi-pico.getPythonPath}"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
@@ -0,0 +1,9 @@
|
|||||||
|
{
|
||||||
|
"recommendations": [
|
||||||
|
"marus25.cortex-debug",
|
||||||
|
"ms-vscode.cpptools",
|
||||||
|
"ms-vscode.cpptools-extension-pack",
|
||||||
|
"ms-vscode.vscode-serial-monitor",
|
||||||
|
"raspberry-pi.raspberry-pi-pico"
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -0,0 +1,50 @@
|
|||||||
|
{
|
||||||
|
"version": "0.2.0",
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Pico Debug (Cortex-Debug)",
|
||||||
|
"cwd": "${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"executable": "${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"request": "launch",
|
||||||
|
"type": "cortex-debug",
|
||||||
|
"servertype": "openocd",
|
||||||
|
"serverpath": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"gdbPath": "${command:raspberry-pi-pico.getGDBPath}",
|
||||||
|
"device": "${command:raspberry-pi-pico.getChipUppercase}",
|
||||||
|
"configFiles": [
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"target/${command:raspberry-pi-pico.getTarget}.cfg"
|
||||||
|
],
|
||||||
|
"svdFile": "${userHome}/.pico-sdk/sdk/2.2.0/src/${command:raspberry-pi-pico.getChip}/hardware_regs/${command:raspberry-pi-pico.getChipUppercase}.svd",
|
||||||
|
"runToEntryPoint": "main",
|
||||||
|
// Fix for no_flash binaries, where monitor reset halt doesn't do what is expected
|
||||||
|
// Also works fine for flash binaries
|
||||||
|
"overrideLaunchCommands": [
|
||||||
|
"monitor reset init",
|
||||||
|
"load \"${command:raspberry-pi-pico.launchTargetPath}\""
|
||||||
|
],
|
||||||
|
"openOCDLaunchCommands": [
|
||||||
|
"adapter speed 5000"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Pico Debug (Cortex-Debug with external OpenOCD)",
|
||||||
|
"cwd": "${workspaceRoot}",
|
||||||
|
"executable": "${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"request": "launch",
|
||||||
|
"type": "cortex-debug",
|
||||||
|
"servertype": "external",
|
||||||
|
"gdbTarget": "localhost:3333",
|
||||||
|
"gdbPath": "${command:raspberry-pi-pico.getGDBPath}",
|
||||||
|
"device": "${command:raspberry-pi-pico.getChipUppercase}",
|
||||||
|
"svdFile": "${userHome}/.pico-sdk/sdk/2.2.0/src/${command:raspberry-pi-pico.getChip}/hardware_regs/${command:raspberry-pi-pico.getChipUppercase}.svd",
|
||||||
|
"runToEntryPoint": "main",
|
||||||
|
// Fix for no_flash binaries, where monitor reset halt doesn't do what is expected
|
||||||
|
// Also works fine for flash binaries
|
||||||
|
"overrideLaunchCommands": [
|
||||||
|
"monitor reset init",
|
||||||
|
"load \"${command:raspberry-pi-pico.launchTargetPath}\""
|
||||||
|
]
|
||||||
|
},
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -0,0 +1,40 @@
|
|||||||
|
{
|
||||||
|
"cmake.showSystemKits": false,
|
||||||
|
"cmake.options.statusBarVisibility": "hidden",
|
||||||
|
"cmake.options.advanced": {
|
||||||
|
"build": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"launch": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"debug": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"cmake.configureOnEdit": false,
|
||||||
|
"cmake.automaticReconfigure": false,
|
||||||
|
"cmake.configureOnOpen": false,
|
||||||
|
"cmake.generator": "Ninja",
|
||||||
|
"cmake.cmakePath": "${userHome}/.pico-sdk/cmake/v3.31.5/bin/cmake",
|
||||||
|
"C_Cpp.debugShortcut": false,
|
||||||
|
"terminal.integrated.env.windows": {
|
||||||
|
"PICO_SDK_PATH": "${env:USERPROFILE}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:USERPROFILE}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"Path": "${env:USERPROFILE}/.pico-sdk/toolchain/14_2_Rel1/bin;${env:USERPROFILE}/.pico-sdk/picotool/2.2.0/picotool;${env:USERPROFILE}/.pico-sdk/cmake/v3.31.5/bin;${env:USERPROFILE}/.pico-sdk/ninja/v1.12.1;${env:PATH}"
|
||||||
|
},
|
||||||
|
"terminal.integrated.env.osx": {
|
||||||
|
"PICO_SDK_PATH": "${env:HOME}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1/bin:${env:HOME}/.pico-sdk/picotool/2.2.0/picotool:${env:HOME}/.pico-sdk/cmake/v3.31.5/bin:${env:HOME}/.pico-sdk/ninja/v1.12.1:${env:PATH}"
|
||||||
|
},
|
||||||
|
"terminal.integrated.env.linux": {
|
||||||
|
"PICO_SDK_PATH": "${env:HOME}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1/bin:${env:HOME}/.pico-sdk/picotool/2.2.0/picotool:${env:HOME}/.pico-sdk/cmake/v3.31.5/bin:${env:HOME}/.pico-sdk/ninja/v1.12.1:${env:PATH}"
|
||||||
|
},
|
||||||
|
"raspberry-pi-pico.cmakeAutoConfigure": true,
|
||||||
|
"raspberry-pi-pico.useCmakeTools": false,
|
||||||
|
"raspberry-pi-pico.cmakePath": "${HOME}/.pico-sdk/cmake/v3.31.5/bin/cmake",
|
||||||
|
"raspberry-pi-pico.ninjaPath": "${HOME}/.pico-sdk/ninja/v1.12.1/ninja"
|
||||||
|
}
|
||||||
+102
@@ -0,0 +1,102 @@
|
|||||||
|
{
|
||||||
|
"version": "2.0.0",
|
||||||
|
"tasks": [
|
||||||
|
{
|
||||||
|
"label": "Compile Project",
|
||||||
|
"type": "process",
|
||||||
|
"isBuildCommand": true,
|
||||||
|
"command": "${userHome}/.pico-sdk/ninja/v1.12.1/ninja",
|
||||||
|
"args": ["-C", "${workspaceFolder}/build"],
|
||||||
|
"group": "build",
|
||||||
|
"presentation": {
|
||||||
|
"reveal": "always",
|
||||||
|
"panel": "dedicated"
|
||||||
|
},
|
||||||
|
"problemMatcher": "$gcc",
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/ninja/v1.12.1/ninja.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Run Project",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${env:HOME}/.pico-sdk/picotool/2.2.0/picotool/picotool",
|
||||||
|
"args": [
|
||||||
|
"load",
|
||||||
|
"${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"-fx"
|
||||||
|
],
|
||||||
|
"presentation": {
|
||||||
|
"reveal": "always",
|
||||||
|
"panel": "dedicated"
|
||||||
|
},
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/picotool/2.2.0/picotool/picotool.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Flash",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/${command:raspberry-pi-pico.getTarget}.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; program \"${command:raspberry-pi-pico.launchTargetPath}\" verify reset exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Rescue Reset",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/${command:raspberry-pi-pico.getChip}-rescue.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; reset halt; exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Risc-V Reset (RP2350)",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-c",
|
||||||
|
"set USE_CORE { rv0 rv1 cm0 cm1 }",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/rp2350.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; init;",
|
||||||
|
"-c",
|
||||||
|
"write_memory 0x40120158 8 { 0x3 }; echo [format \"Info : ARCHSEL 0x%02x\" [read_memory 0x40120158 8 1]];",
|
||||||
|
"-c",
|
||||||
|
"reset halt; targets rp2350.rv0; echo [format \"Info : ARCHSEL_STATUS 0x%02x\" [read_memory 0x4012015C 8 1]]; exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -0,0 +1,85 @@
|
|||||||
|
/**
|
||||||
|
* @file 0x0008_uninitialized-variables-c.c
|
||||||
|
* @brief Blink LED using direct register-level pad and IO bank configuration
|
||||||
|
* @author Kevin Thomas
|
||||||
|
* @date 2025
|
||||||
|
*
|
||||||
|
* MIT License
|
||||||
|
*
|
||||||
|
* Copyright (c) 2025 Kevin Thomas
|
||||||
|
*
|
||||||
|
* 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.
|
||||||
|
*
|
||||||
|
* -----------------------------------------------------------------------------
|
||||||
|
*
|
||||||
|
* Blinks an LED on GPIO16 using direct register writes to PADS_BANK0 and
|
||||||
|
* IO_BANK0 for pad configuration, plus gpioc coprocessor bit-level functions
|
||||||
|
* for output enable and data. Demonstrates the register-level equivalent of
|
||||||
|
* gpio_init / gpio_set_function.
|
||||||
|
*
|
||||||
|
* Wiring:
|
||||||
|
* GPIO16 -> LED anode (with current-limiting resistor to GND)
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
#include "pico/stdlib.h"
|
||||||
|
|
||||||
|
/** @brief GPIO pin number for the LED */
|
||||||
|
#define LED_PIN 16
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Configure pad and IO bank registers for GPIO16 as SIO output
|
||||||
|
*
|
||||||
|
* @details Sets PADS_BANK0 IE/OD bits, assigns FUNCSEL to SIO in IO_BANK0,
|
||||||
|
* clears the ISO bit, and enables output via the coprocessor.
|
||||||
|
*
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
static void configure_pad_and_iobank(void) {
|
||||||
|
gpioc_bit_oe_put(LED_PIN, GPIO_OUT);
|
||||||
|
gpioc_bit_out_put(LED_PIN, 0);
|
||||||
|
hw_write_masked(&pads_bank0_hw->io[LED_PIN],
|
||||||
|
PADS_BANK0_GPIO0_IE_BITS,
|
||||||
|
PADS_BANK0_GPIO0_IE_BITS | PADS_BANK0_GPIO0_OD_BITS);
|
||||||
|
io_bank0_hw->io[LED_PIN].ctrl = GPIO_FUNC_SIO << IO_BANK0_GPIO0_CTRL_FUNCSEL_LSB;
|
||||||
|
hw_clear_bits(&pads_bank0_hw->io[LED_PIN], PADS_BANK0_GPIO0_ISO_BITS);
|
||||||
|
gpioc_bit_oe_put(LED_PIN, GPIO_OUT);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Blink LED using coprocessor bit output functions
|
||||||
|
*
|
||||||
|
* @details Toggles the LED on and off with 500ms delays using
|
||||||
|
* gpioc_bit_out_put and sleep_us.
|
||||||
|
*
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
static void blink_cycle(void) {
|
||||||
|
gpioc_bit_out_put(LED_PIN, 1);
|
||||||
|
sleep_us(500 * 1000ull);
|
||||||
|
gpioc_bit_out_put(LED_PIN, 0);
|
||||||
|
sleep_us(500 * 1000ull);
|
||||||
|
}
|
||||||
|
|
||||||
|
int main(void) {
|
||||||
|
configure_pad_and_iobank();
|
||||||
|
while (true) {
|
||||||
|
blink_cycle();
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,57 @@
|
|||||||
|
# Generated Cmake Pico project file
|
||||||
|
|
||||||
|
cmake_minimum_required(VERSION 3.13)
|
||||||
|
|
||||||
|
set(CMAKE_C_STANDARD 11)
|
||||||
|
set(CMAKE_CXX_STANDARD 17)
|
||||||
|
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
|
||||||
|
|
||||||
|
# Initialise pico_sdk from installed location
|
||||||
|
# (note this can come from environment, CMake cache etc)
|
||||||
|
|
||||||
|
# == DO NOT EDIT THE FOLLOWING LINES for the Raspberry Pi Pico VS Code Extension to work ==
|
||||||
|
if(WIN32)
|
||||||
|
set(USERHOME $ENV{USERPROFILE})
|
||||||
|
else()
|
||||||
|
set(USERHOME $ENV{HOME})
|
||||||
|
endif()
|
||||||
|
set(sdkVersion 2.2.0)
|
||||||
|
set(toolchainVersion 14_2_Rel1)
|
||||||
|
set(picotoolVersion 2.2.0)
|
||||||
|
set(picoVscode ${USERHOME}/.pico-sdk/cmake/pico-vscode.cmake)
|
||||||
|
if (EXISTS ${picoVscode})
|
||||||
|
include(${picoVscode})
|
||||||
|
endif()
|
||||||
|
# ====================================================================================
|
||||||
|
set(PICO_BOARD pico2 CACHE STRING "Board type")
|
||||||
|
|
||||||
|
# Pull in Raspberry Pi Pico SDK (must be before project)
|
||||||
|
include(pico_sdk_import.cmake)
|
||||||
|
|
||||||
|
project(0x0008_uninitialized-variables-c C CXX ASM)
|
||||||
|
|
||||||
|
# Initialise the Raspberry Pi Pico SDK
|
||||||
|
pico_sdk_init()
|
||||||
|
|
||||||
|
# Add executable. Default name is the project name, version 0.1
|
||||||
|
|
||||||
|
add_executable(0x0008_uninitialized-variables-c 0x0008_uninitialized-variables-c.c )
|
||||||
|
|
||||||
|
pico_set_program_name(0x0008_uninitialized-variables-c "0x0008_uninitialized-variables-c")
|
||||||
|
pico_set_program_version(0x0008_uninitialized-variables-c "0.1")
|
||||||
|
|
||||||
|
# Modify the below lines to enable/disable output over UART/USB
|
||||||
|
pico_enable_stdio_uart(0x0008_uninitialized-variables-c 0)
|
||||||
|
pico_enable_stdio_usb(0x0008_uninitialized-variables-c 0)
|
||||||
|
|
||||||
|
# Add the standard library to the build
|
||||||
|
target_link_libraries(0x0008_uninitialized-variables-c
|
||||||
|
pico_stdlib)
|
||||||
|
|
||||||
|
# Add the standard include files to the build
|
||||||
|
target_include_directories(0x0008_uninitialized-variables-c PRIVATE
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}
|
||||||
|
)
|
||||||
|
|
||||||
|
pico_add_extra_outputs(0x0008_uninitialized-variables-c)
|
||||||
|
|
||||||
@@ -0,0 +1,121 @@
|
|||||||
|
# This is a copy of <PICO_SDK_PATH>/external/pico_sdk_import.cmake
|
||||||
|
|
||||||
|
# This can be dropped into an external project to help locate this SDK
|
||||||
|
# It should be include()ed prior to project()
|
||||||
|
|
||||||
|
# Copyright 2020 (c) 2020 Raspberry Pi (Trading) Ltd.
|
||||||
|
#
|
||||||
|
# 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. Neither the name of the copyright holder nor the names of its contributors may be used to endorse or promote products
|
||||||
|
# derived from this software without specific prior written permission.
|
||||||
|
#
|
||||||
|
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "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 COPYRIGHT HOLDER OR CONTRIBUTORS 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.
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_PATH} AND (NOT PICO_SDK_PATH))
|
||||||
|
set(PICO_SDK_PATH $ENV{PICO_SDK_PATH})
|
||||||
|
message("Using PICO_SDK_PATH from environment ('${PICO_SDK_PATH}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT} AND (NOT PICO_SDK_FETCH_FROM_GIT))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT $ENV{PICO_SDK_FETCH_FROM_GIT})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT from environment ('${PICO_SDK_FETCH_FROM_GIT}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT_PATH} AND (NOT PICO_SDK_FETCH_FROM_GIT_PATH))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_PATH $ENV{PICO_SDK_FETCH_FROM_GIT_PATH})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT_PATH from environment ('${PICO_SDK_FETCH_FROM_GIT_PATH}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT_TAG} AND (NOT PICO_SDK_FETCH_FROM_GIT_TAG))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG $ENV{PICO_SDK_FETCH_FROM_GIT_TAG})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT_TAG from environment ('${PICO_SDK_FETCH_FROM_GIT_TAG}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT AND NOT PICO_SDK_FETCH_FROM_GIT_TAG)
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG "master")
|
||||||
|
message("Using master as default value for PICO_SDK_FETCH_FROM_GIT_TAG")
|
||||||
|
endif()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH "${PICO_SDK_PATH}" CACHE PATH "Path to the Raspberry Pi Pico SDK")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT "${PICO_SDK_FETCH_FROM_GIT}" CACHE BOOL "Set to ON to fetch copy of SDK from git if not otherwise locatable")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_PATH "${PICO_SDK_FETCH_FROM_GIT_PATH}" CACHE FILEPATH "location to download SDK")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG "${PICO_SDK_FETCH_FROM_GIT_TAG}" CACHE FILEPATH "release tag for SDK")
|
||||||
|
|
||||||
|
if (NOT PICO_SDK_PATH)
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT)
|
||||||
|
include(FetchContent)
|
||||||
|
set(FETCHCONTENT_BASE_DIR_SAVE ${FETCHCONTENT_BASE_DIR})
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT_PATH)
|
||||||
|
get_filename_component(FETCHCONTENT_BASE_DIR "${PICO_SDK_FETCH_FROM_GIT_PATH}" REALPATH BASE_DIR "${CMAKE_SOURCE_DIR}")
|
||||||
|
endif ()
|
||||||
|
FetchContent_Declare(
|
||||||
|
pico_sdk
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
)
|
||||||
|
|
||||||
|
if (NOT pico_sdk)
|
||||||
|
message("Downloading Raspberry Pi Pico SDK")
|
||||||
|
# GIT_SUBMODULES_RECURSE was added in 3.17
|
||||||
|
if (${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.17.0")
|
||||||
|
FetchContent_Populate(
|
||||||
|
pico_sdk
|
||||||
|
QUIET
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
GIT_SUBMODULES_RECURSE FALSE
|
||||||
|
|
||||||
|
SOURCE_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-src
|
||||||
|
BINARY_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-build
|
||||||
|
SUBBUILD_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-subbuild
|
||||||
|
)
|
||||||
|
else ()
|
||||||
|
FetchContent_Populate(
|
||||||
|
pico_sdk
|
||||||
|
QUIET
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
|
||||||
|
SOURCE_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-src
|
||||||
|
BINARY_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-build
|
||||||
|
SUBBUILD_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-subbuild
|
||||||
|
)
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH ${pico_sdk_SOURCE_DIR})
|
||||||
|
endif ()
|
||||||
|
set(FETCHCONTENT_BASE_DIR ${FETCHCONTENT_BASE_DIR_SAVE})
|
||||||
|
else ()
|
||||||
|
message(FATAL_ERROR
|
||||||
|
"SDK location was not specified. Please set PICO_SDK_PATH or set PICO_SDK_FETCH_FROM_GIT to on to fetch from git."
|
||||||
|
)
|
||||||
|
endif ()
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
get_filename_component(PICO_SDK_PATH "${PICO_SDK_PATH}" REALPATH BASE_DIR "${CMAKE_BINARY_DIR}")
|
||||||
|
if (NOT EXISTS ${PICO_SDK_PATH})
|
||||||
|
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' not found")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_INIT_CMAKE_FILE ${PICO_SDK_PATH}/pico_sdk_init.cmake)
|
||||||
|
if (NOT EXISTS ${PICO_SDK_INIT_CMAKE_FILE})
|
||||||
|
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' does not appear to contain the Raspberry Pi Pico SDK")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH ${PICO_SDK_PATH} CACHE PATH "Path to the Raspberry Pi Pico SDK" FORCE)
|
||||||
|
|
||||||
|
include(${PICO_SDK_INIT_CMAKE_FILE})
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
build
|
||||||
|
!.vscode/*
|
||||||
@@ -0,0 +1,22 @@
|
|||||||
|
{
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Pico",
|
||||||
|
"includePath": [
|
||||||
|
"${workspaceFolder}/**",
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.2.0/**"
|
||||||
|
],
|
||||||
|
"forcedInclude": [
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.2.0/src/common/pico_base_headers/include/pico.h",
|
||||||
|
"${workspaceFolder}/build/generated/pico_base/pico/config_autogen.h"
|
||||||
|
],
|
||||||
|
"defines": [],
|
||||||
|
"compilerPath": "${userHome}/.pico-sdk/toolchain/14_2_Rel1/bin/arm-none-eabi-gcc.exe",
|
||||||
|
"compileCommands": "${workspaceFolder}/build/compile_commands.json",
|
||||||
|
"cStandard": "c17",
|
||||||
|
"cppStandard": "c++14",
|
||||||
|
"intelliSenseMode": "linux-gcc-arm"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"version": 4
|
||||||
|
}
|
||||||
@@ -0,0 +1,15 @@
|
|||||||
|
[
|
||||||
|
{
|
||||||
|
"name": "Pico",
|
||||||
|
"compilers": {
|
||||||
|
"C": "${command:raspberry-pi-pico.getCompilerPath}",
|
||||||
|
"CXX": "${command:raspberry-pi-pico.getCxxCompilerPath}"
|
||||||
|
},
|
||||||
|
"environmentVariables": {
|
||||||
|
"PATH": "${command:raspberry-pi-pico.getEnvPath};${env:PATH}"
|
||||||
|
},
|
||||||
|
"cmakeSettings": {
|
||||||
|
"Python3_EXECUTABLE": "${command:raspberry-pi-pico.getPythonPath}"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
@@ -0,0 +1,9 @@
|
|||||||
|
{
|
||||||
|
"recommendations": [
|
||||||
|
"marus25.cortex-debug",
|
||||||
|
"ms-vscode.cpptools",
|
||||||
|
"ms-vscode.cpptools-extension-pack",
|
||||||
|
"ms-vscode.vscode-serial-monitor",
|
||||||
|
"raspberry-pi.raspberry-pi-pico"
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -0,0 +1,50 @@
|
|||||||
|
{
|
||||||
|
"version": "0.2.0",
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Pico Debug (Cortex-Debug)",
|
||||||
|
"cwd": "${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"executable": "${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"request": "launch",
|
||||||
|
"type": "cortex-debug",
|
||||||
|
"servertype": "openocd",
|
||||||
|
"serverpath": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"gdbPath": "${command:raspberry-pi-pico.getGDBPath}",
|
||||||
|
"device": "${command:raspberry-pi-pico.getChipUppercase}",
|
||||||
|
"configFiles": [
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"target/${command:raspberry-pi-pico.getTarget}.cfg"
|
||||||
|
],
|
||||||
|
"svdFile": "${userHome}/.pico-sdk/sdk/2.2.0/src/${command:raspberry-pi-pico.getChip}/hardware_regs/${command:raspberry-pi-pico.getChipUppercase}.svd",
|
||||||
|
"runToEntryPoint": "main",
|
||||||
|
// Fix for no_flash binaries, where monitor reset halt doesn't do what is expected
|
||||||
|
// Also works fine for flash binaries
|
||||||
|
"overrideLaunchCommands": [
|
||||||
|
"monitor reset init",
|
||||||
|
"load \"${command:raspberry-pi-pico.launchTargetPath}\""
|
||||||
|
],
|
||||||
|
"openOCDLaunchCommands": [
|
||||||
|
"adapter speed 5000"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "Pico Debug (Cortex-Debug with external OpenOCD)",
|
||||||
|
"cwd": "${workspaceRoot}",
|
||||||
|
"executable": "${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"request": "launch",
|
||||||
|
"type": "cortex-debug",
|
||||||
|
"servertype": "external",
|
||||||
|
"gdbTarget": "localhost:3333",
|
||||||
|
"gdbPath": "${command:raspberry-pi-pico.getGDBPath}",
|
||||||
|
"device": "${command:raspberry-pi-pico.getChipUppercase}",
|
||||||
|
"svdFile": "${userHome}/.pico-sdk/sdk/2.2.0/src/${command:raspberry-pi-pico.getChip}/hardware_regs/${command:raspberry-pi-pico.getChipUppercase}.svd",
|
||||||
|
"runToEntryPoint": "main",
|
||||||
|
// Fix for no_flash binaries, where monitor reset halt doesn't do what is expected
|
||||||
|
// Also works fine for flash binaries
|
||||||
|
"overrideLaunchCommands": [
|
||||||
|
"monitor reset init",
|
||||||
|
"load \"${command:raspberry-pi-pico.launchTargetPath}\""
|
||||||
|
]
|
||||||
|
},
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -0,0 +1,40 @@
|
|||||||
|
{
|
||||||
|
"cmake.showSystemKits": false,
|
||||||
|
"cmake.options.statusBarVisibility": "hidden",
|
||||||
|
"cmake.options.advanced": {
|
||||||
|
"build": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"launch": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
},
|
||||||
|
"debug": {
|
||||||
|
"statusBarVisibility": "hidden"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"cmake.configureOnEdit": false,
|
||||||
|
"cmake.automaticReconfigure": false,
|
||||||
|
"cmake.configureOnOpen": false,
|
||||||
|
"cmake.generator": "Ninja",
|
||||||
|
"cmake.cmakePath": "${userHome}/.pico-sdk/cmake/v3.31.5/bin/cmake",
|
||||||
|
"C_Cpp.debugShortcut": false,
|
||||||
|
"terminal.integrated.env.windows": {
|
||||||
|
"PICO_SDK_PATH": "${env:USERPROFILE}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:USERPROFILE}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"Path": "${env:USERPROFILE}/.pico-sdk/toolchain/14_2_Rel1/bin;${env:USERPROFILE}/.pico-sdk/picotool/2.2.0/picotool;${env:USERPROFILE}/.pico-sdk/cmake/v3.31.5/bin;${env:USERPROFILE}/.pico-sdk/ninja/v1.12.1;${env:PATH}"
|
||||||
|
},
|
||||||
|
"terminal.integrated.env.osx": {
|
||||||
|
"PICO_SDK_PATH": "${env:HOME}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1/bin:${env:HOME}/.pico-sdk/picotool/2.2.0/picotool:${env:HOME}/.pico-sdk/cmake/v3.31.5/bin:${env:HOME}/.pico-sdk/ninja/v1.12.1:${env:PATH}"
|
||||||
|
},
|
||||||
|
"terminal.integrated.env.linux": {
|
||||||
|
"PICO_SDK_PATH": "${env:HOME}/.pico-sdk/sdk/2.2.0",
|
||||||
|
"PICO_TOOLCHAIN_PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1",
|
||||||
|
"PATH": "${env:HOME}/.pico-sdk/toolchain/14_2_Rel1/bin:${env:HOME}/.pico-sdk/picotool/2.2.0/picotool:${env:HOME}/.pico-sdk/cmake/v3.31.5/bin:${env:HOME}/.pico-sdk/ninja/v1.12.1:${env:PATH}"
|
||||||
|
},
|
||||||
|
"raspberry-pi-pico.cmakeAutoConfigure": true,
|
||||||
|
"raspberry-pi-pico.useCmakeTools": false,
|
||||||
|
"raspberry-pi-pico.cmakePath": "${HOME}/.pico-sdk/cmake/v3.31.5/bin/cmake",
|
||||||
|
"raspberry-pi-pico.ninjaPath": "${HOME}/.pico-sdk/ninja/v1.12.1/ninja"
|
||||||
|
}
|
||||||
+102
@@ -0,0 +1,102 @@
|
|||||||
|
{
|
||||||
|
"version": "2.0.0",
|
||||||
|
"tasks": [
|
||||||
|
{
|
||||||
|
"label": "Compile Project",
|
||||||
|
"type": "process",
|
||||||
|
"isBuildCommand": true,
|
||||||
|
"command": "${userHome}/.pico-sdk/ninja/v1.12.1/ninja",
|
||||||
|
"args": ["-C", "${workspaceFolder}/build"],
|
||||||
|
"group": "build",
|
||||||
|
"presentation": {
|
||||||
|
"reveal": "always",
|
||||||
|
"panel": "dedicated"
|
||||||
|
},
|
||||||
|
"problemMatcher": "$gcc",
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/ninja/v1.12.1/ninja.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Run Project",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${env:HOME}/.pico-sdk/picotool/2.2.0/picotool/picotool",
|
||||||
|
"args": [
|
||||||
|
"load",
|
||||||
|
"${command:raspberry-pi-pico.launchTargetPath}",
|
||||||
|
"-fx"
|
||||||
|
],
|
||||||
|
"presentation": {
|
||||||
|
"reveal": "always",
|
||||||
|
"panel": "dedicated"
|
||||||
|
},
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/picotool/2.2.0/picotool/picotool.exe"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Flash",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/${command:raspberry-pi-pico.getTarget}.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; program \"${command:raspberry-pi-pico.launchTargetPath}\" verify reset exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Rescue Reset",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/${command:raspberry-pi-pico.getChip}-rescue.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; reset halt; exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"label": "Risc-V Reset (RP2350)",
|
||||||
|
"type": "process",
|
||||||
|
"command": "${userHome}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
"args": [
|
||||||
|
"-s",
|
||||||
|
"${userHome}/.pico-sdk/openocd/0.12.0+dev/scripts",
|
||||||
|
"-c",
|
||||||
|
"set USE_CORE { rv0 rv1 cm0 cm1 }",
|
||||||
|
"-f",
|
||||||
|
"interface/cmsis-dap.cfg",
|
||||||
|
"-f",
|
||||||
|
"target/rp2350.cfg",
|
||||||
|
"-c",
|
||||||
|
"adapter speed 5000; init;",
|
||||||
|
"-c",
|
||||||
|
"write_memory 0x40120158 8 { 0x3 }; echo [format \"Info : ARCHSEL 0x%02x\" [read_memory 0x40120158 8 1]];",
|
||||||
|
"-c",
|
||||||
|
"reset halt; targets rp2350.rv0; echo [format \"Info : ARCHSEL_STATUS 0x%02x\" [read_memory 0x4012015C 8 1]]; exit"
|
||||||
|
],
|
||||||
|
"problemMatcher": [],
|
||||||
|
"windows": {
|
||||||
|
"command": "${env:USERPROFILE}/.pico-sdk/openocd/0.12.0+dev/openocd.exe",
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -0,0 +1,144 @@
|
|||||||
|
/**
|
||||||
|
* @file 0x0008_uninitialized-variables-d.c
|
||||||
|
* @brief Blink LED using pico_default_asm_volatile coprocessor instructions
|
||||||
|
* @author Kevin Thomas
|
||||||
|
* @date 2025
|
||||||
|
*
|
||||||
|
* MIT License
|
||||||
|
*
|
||||||
|
* Copyright (c) 2025 Kevin Thomas
|
||||||
|
*
|
||||||
|
* 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.
|
||||||
|
*
|
||||||
|
* -----------------------------------------------------------------------------
|
||||||
|
*
|
||||||
|
* Blinks an LED on GPIO16 using pico_default_asm_volatile to emit mcrr
|
||||||
|
* coprocessor instructions for GPIO output enable and data, plus inline
|
||||||
|
* assembly for pad configuration (hw_write_masked, IO_BANK0 FUNCSEL,
|
||||||
|
* hw_clear_bits equivalents).
|
||||||
|
*
|
||||||
|
* Wiring:
|
||||||
|
* GPIO16 -> LED anode (with current-limiting resistor to GND)
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
#include "pico/stdlib.h"
|
||||||
|
|
||||||
|
/** @brief GPIO pin number for the LED */
|
||||||
|
#define LED_PIN 16
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Enable output and set initial coprocessor OE/OUT via mcrr
|
||||||
|
*
|
||||||
|
* @details Issues two mcrr p0 instructions: one to enable output direction,
|
||||||
|
* one to set the initial output state.
|
||||||
|
*
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
static void asm_set_oe_and_out(void) {
|
||||||
|
pico_default_asm_volatile ("mcrr p0, #4, %0, %1, c4" : : "r" (LED_PIN), "r" (GPIO_OUT));
|
||||||
|
pico_default_asm_volatile ("mcrr p0, #4, %0, %1, c4" : : "r" (LED_PIN), "r" (GPIO_OUT));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Configure PADS_BANK0 IE/OD bits via inline assembly hw_xor_bits
|
||||||
|
*
|
||||||
|
* @details Performs a read-modify-write on the pad register to set IE
|
||||||
|
* and clear OD, replicating hw_write_masked behavior.
|
||||||
|
*
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
static void asm_configure_pad(void) {
|
||||||
|
pico_default_asm_volatile (
|
||||||
|
"ldr r2, [%0]\n" // load current pad register
|
||||||
|
"eor r2, r2, %1\n" // xor with IE bit
|
||||||
|
"and r2, r2, %2\n" // mask with (IE|OD)
|
||||||
|
"eor r2, r2, %1\n" // recombine (hw_xor_bits logic)
|
||||||
|
"str r2, [%0]\n" // write back
|
||||||
|
:
|
||||||
|
: "r" (&pads_bank0_hw->io[LED_PIN]),
|
||||||
|
"r" (PADS_BANK0_GPIO0_IE_BITS),
|
||||||
|
"r" (PADS_BANK0_GPIO0_IE_BITS | PADS_BANK0_GPIO0_OD_BITS)
|
||||||
|
: "r2", "memory"
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Set IO_BANK0 FUNCSEL to SIO via inline assembly store
|
||||||
|
*
|
||||||
|
* @details Writes the SIO function select value directly to the
|
||||||
|
* IO_BANK0 GPIO control register.
|
||||||
|
*
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
static void asm_set_funcsel(void) {
|
||||||
|
pico_default_asm_volatile (
|
||||||
|
"str %1, [%0]\n"
|
||||||
|
:
|
||||||
|
: "r" (&io_bank0_hw->io[LED_PIN].ctrl),
|
||||||
|
"r" (GPIO_FUNC_SIO << IO_BANK0_GPIO0_CTRL_FUNCSEL_LSB)
|
||||||
|
: "memory"
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Clear ISO bits in PADS_BANK0 via inline assembly
|
||||||
|
*
|
||||||
|
* @details Performs a read-modify-write to clear the pad isolation
|
||||||
|
* bit, un-isolating the pad for normal operation.
|
||||||
|
*
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
static void asm_clear_iso(void) {
|
||||||
|
pico_default_asm_volatile (
|
||||||
|
"ldr r2, [%0]\n" // load current register value
|
||||||
|
"bic r2, r2, %1\n" // clear the ISO bits (bit clear)
|
||||||
|
"str r2, [%0]\n" // write back
|
||||||
|
:
|
||||||
|
: "r" (&pads_bank0_hw->io[LED_PIN]),
|
||||||
|
"r" (PADS_BANK0_GPIO0_ISO_BITS)
|
||||||
|
: "r2", "memory"
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Blink LED using coprocessor mcrr output instructions
|
||||||
|
*
|
||||||
|
* @details Toggles the LED on and off with 500ms delays using
|
||||||
|
* pico_default_asm_volatile mcrr instructions.
|
||||||
|
*
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
static void asm_blink_cycle(void) {
|
||||||
|
pico_default_asm_volatile ("mcrr p0, #4, %0, %1, c0" : : "r" (LED_PIN), "r" (1));
|
||||||
|
sleep_us(500 * 1000ull);
|
||||||
|
pico_default_asm_volatile ("mcrr p0, #4, %0, %1, c0" : : "r" (LED_PIN), "r" (0));
|
||||||
|
sleep_us(500 * 1000ull);
|
||||||
|
}
|
||||||
|
|
||||||
|
int main(void) {
|
||||||
|
asm_set_oe_and_out();
|
||||||
|
asm_configure_pad();
|
||||||
|
asm_set_funcsel();
|
||||||
|
asm_clear_iso();
|
||||||
|
pico_default_asm_volatile ("mcrr p0, #4, %0, %1, c4" : : "r" (LED_PIN), "r" (GPIO_OUT));
|
||||||
|
while (true) {
|
||||||
|
asm_blink_cycle();
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,57 @@
|
|||||||
|
# Generated Cmake Pico project file
|
||||||
|
|
||||||
|
cmake_minimum_required(VERSION 3.13)
|
||||||
|
|
||||||
|
set(CMAKE_C_STANDARD 11)
|
||||||
|
set(CMAKE_CXX_STANDARD 17)
|
||||||
|
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
|
||||||
|
|
||||||
|
# Initialise pico_sdk from installed location
|
||||||
|
# (note this can come from environment, CMake cache etc)
|
||||||
|
|
||||||
|
# == DO NOT EDIT THE FOLLOWING LINES for the Raspberry Pi Pico VS Code Extension to work ==
|
||||||
|
if(WIN32)
|
||||||
|
set(USERHOME $ENV{USERPROFILE})
|
||||||
|
else()
|
||||||
|
set(USERHOME $ENV{HOME})
|
||||||
|
endif()
|
||||||
|
set(sdkVersion 2.2.0)
|
||||||
|
set(toolchainVersion 14_2_Rel1)
|
||||||
|
set(picotoolVersion 2.2.0)
|
||||||
|
set(picoVscode ${USERHOME}/.pico-sdk/cmake/pico-vscode.cmake)
|
||||||
|
if (EXISTS ${picoVscode})
|
||||||
|
include(${picoVscode})
|
||||||
|
endif()
|
||||||
|
# ====================================================================================
|
||||||
|
set(PICO_BOARD pico2 CACHE STRING "Board type")
|
||||||
|
|
||||||
|
# Pull in Raspberry Pi Pico SDK (must be before project)
|
||||||
|
include(pico_sdk_import.cmake)
|
||||||
|
|
||||||
|
project(0x0008_uninitialized-variables-d C CXX ASM)
|
||||||
|
|
||||||
|
# Initialise the Raspberry Pi Pico SDK
|
||||||
|
pico_sdk_init()
|
||||||
|
|
||||||
|
# Add executable. Default name is the project name, version 0.1
|
||||||
|
|
||||||
|
add_executable(0x0008_uninitialized-variables-d 0x0008_uninitialized-variables-d.c )
|
||||||
|
|
||||||
|
pico_set_program_name(0x0008_uninitialized-variables-d "0x0008_uninitialized-variables-d")
|
||||||
|
pico_set_program_version(0x0008_uninitialized-variables-d "0.1")
|
||||||
|
|
||||||
|
# Modify the below lines to enable/disable output over UART/USB
|
||||||
|
pico_enable_stdio_uart(0x0008_uninitialized-variables-d 0)
|
||||||
|
pico_enable_stdio_usb(0x0008_uninitialized-variables-d 0)
|
||||||
|
|
||||||
|
# Add the standard library to the build
|
||||||
|
target_link_libraries(0x0008_uninitialized-variables-d
|
||||||
|
pico_stdlib)
|
||||||
|
|
||||||
|
# Add the standard include files to the build
|
||||||
|
target_include_directories(0x0008_uninitialized-variables-d PRIVATE
|
||||||
|
${CMAKE_CURRENT_LIST_DIR}
|
||||||
|
)
|
||||||
|
|
||||||
|
pico_add_extra_outputs(0x0008_uninitialized-variables-d)
|
||||||
|
|
||||||
@@ -0,0 +1,121 @@
|
|||||||
|
# This is a copy of <PICO_SDK_PATH>/external/pico_sdk_import.cmake
|
||||||
|
|
||||||
|
# This can be dropped into an external project to help locate this SDK
|
||||||
|
# It should be include()ed prior to project()
|
||||||
|
|
||||||
|
# Copyright 2020 (c) 2020 Raspberry Pi (Trading) Ltd.
|
||||||
|
#
|
||||||
|
# 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. Neither the name of the copyright holder nor the names of its contributors may be used to endorse or promote products
|
||||||
|
# derived from this software without specific prior written permission.
|
||||||
|
#
|
||||||
|
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "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 COPYRIGHT HOLDER OR CONTRIBUTORS 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.
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_PATH} AND (NOT PICO_SDK_PATH))
|
||||||
|
set(PICO_SDK_PATH $ENV{PICO_SDK_PATH})
|
||||||
|
message("Using PICO_SDK_PATH from environment ('${PICO_SDK_PATH}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT} AND (NOT PICO_SDK_FETCH_FROM_GIT))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT $ENV{PICO_SDK_FETCH_FROM_GIT})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT from environment ('${PICO_SDK_FETCH_FROM_GIT}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT_PATH} AND (NOT PICO_SDK_FETCH_FROM_GIT_PATH))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_PATH $ENV{PICO_SDK_FETCH_FROM_GIT_PATH})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT_PATH from environment ('${PICO_SDK_FETCH_FROM_GIT_PATH}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (DEFINED ENV{PICO_SDK_FETCH_FROM_GIT_TAG} AND (NOT PICO_SDK_FETCH_FROM_GIT_TAG))
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG $ENV{PICO_SDK_FETCH_FROM_GIT_TAG})
|
||||||
|
message("Using PICO_SDK_FETCH_FROM_GIT_TAG from environment ('${PICO_SDK_FETCH_FROM_GIT_TAG}')")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT AND NOT PICO_SDK_FETCH_FROM_GIT_TAG)
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG "master")
|
||||||
|
message("Using master as default value for PICO_SDK_FETCH_FROM_GIT_TAG")
|
||||||
|
endif()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH "${PICO_SDK_PATH}" CACHE PATH "Path to the Raspberry Pi Pico SDK")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT "${PICO_SDK_FETCH_FROM_GIT}" CACHE BOOL "Set to ON to fetch copy of SDK from git if not otherwise locatable")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_PATH "${PICO_SDK_FETCH_FROM_GIT_PATH}" CACHE FILEPATH "location to download SDK")
|
||||||
|
set(PICO_SDK_FETCH_FROM_GIT_TAG "${PICO_SDK_FETCH_FROM_GIT_TAG}" CACHE FILEPATH "release tag for SDK")
|
||||||
|
|
||||||
|
if (NOT PICO_SDK_PATH)
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT)
|
||||||
|
include(FetchContent)
|
||||||
|
set(FETCHCONTENT_BASE_DIR_SAVE ${FETCHCONTENT_BASE_DIR})
|
||||||
|
if (PICO_SDK_FETCH_FROM_GIT_PATH)
|
||||||
|
get_filename_component(FETCHCONTENT_BASE_DIR "${PICO_SDK_FETCH_FROM_GIT_PATH}" REALPATH BASE_DIR "${CMAKE_SOURCE_DIR}")
|
||||||
|
endif ()
|
||||||
|
FetchContent_Declare(
|
||||||
|
pico_sdk
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
)
|
||||||
|
|
||||||
|
if (NOT pico_sdk)
|
||||||
|
message("Downloading Raspberry Pi Pico SDK")
|
||||||
|
# GIT_SUBMODULES_RECURSE was added in 3.17
|
||||||
|
if (${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.17.0")
|
||||||
|
FetchContent_Populate(
|
||||||
|
pico_sdk
|
||||||
|
QUIET
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
GIT_SUBMODULES_RECURSE FALSE
|
||||||
|
|
||||||
|
SOURCE_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-src
|
||||||
|
BINARY_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-build
|
||||||
|
SUBBUILD_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-subbuild
|
||||||
|
)
|
||||||
|
else ()
|
||||||
|
FetchContent_Populate(
|
||||||
|
pico_sdk
|
||||||
|
QUIET
|
||||||
|
GIT_REPOSITORY https://github.com/raspberrypi/pico-sdk
|
||||||
|
GIT_TAG ${PICO_SDK_FETCH_FROM_GIT_TAG}
|
||||||
|
|
||||||
|
SOURCE_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-src
|
||||||
|
BINARY_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-build
|
||||||
|
SUBBUILD_DIR ${FETCHCONTENT_BASE_DIR}/pico_sdk-subbuild
|
||||||
|
)
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH ${pico_sdk_SOURCE_DIR})
|
||||||
|
endif ()
|
||||||
|
set(FETCHCONTENT_BASE_DIR ${FETCHCONTENT_BASE_DIR_SAVE})
|
||||||
|
else ()
|
||||||
|
message(FATAL_ERROR
|
||||||
|
"SDK location was not specified. Please set PICO_SDK_PATH or set PICO_SDK_FETCH_FROM_GIT to on to fetch from git."
|
||||||
|
)
|
||||||
|
endif ()
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
get_filename_component(PICO_SDK_PATH "${PICO_SDK_PATH}" REALPATH BASE_DIR "${CMAKE_BINARY_DIR}")
|
||||||
|
if (NOT EXISTS ${PICO_SDK_PATH})
|
||||||
|
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' not found")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_INIT_CMAKE_FILE ${PICO_SDK_PATH}/pico_sdk_init.cmake)
|
||||||
|
if (NOT EXISTS ${PICO_SDK_INIT_CMAKE_FILE})
|
||||||
|
message(FATAL_ERROR "Directory '${PICO_SDK_PATH}' does not appear to contain the Raspberry Pi Pico SDK")
|
||||||
|
endif ()
|
||||||
|
|
||||||
|
set(PICO_SDK_PATH ${PICO_SDK_PATH} CACHE PATH "Path to the Raspberry Pi Pico SDK" FORCE)
|
||||||
|
|
||||||
|
include(${PICO_SDK_INIT_CMAKE_FILE})
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
build
|
||||||
|
!.vscode/*
|
||||||
@@ -0,0 +1,22 @@
|
|||||||
|
{
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Pico",
|
||||||
|
"includePath": [
|
||||||
|
"${workspaceFolder}/**",
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.2.0/**"
|
||||||
|
],
|
||||||
|
"forcedInclude": [
|
||||||
|
"${userHome}/.pico-sdk/sdk/2.2.0/src/common/pico_base_headers/include/pico.h",
|
||||||
|
"${workspaceFolder}/build/generated/pico_base/pico/config_autogen.h"
|
||||||
|
],
|
||||||
|
"defines": [],
|
||||||
|
"compilerPath": "${userHome}/.pico-sdk/toolchain/14_2_Rel1/bin/arm-none-eabi-gcc.exe",
|
||||||
|
"compileCommands": "${workspaceFolder}/build/compile_commands.json",
|
||||||
|
"cStandard": "c17",
|
||||||
|
"cppStandard": "c++14",
|
||||||
|
"intelliSenseMode": "linux-gcc-arm"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"version": 4
|
||||||
|
}
|
||||||
Loaded 100 of 499 files, more files were not shown because too many files have changed in this diff.
Show more
Reference in new issue
Block a user