คุณต้องตั้งค่า PICO_SDK_PATH ในสภาพแวดล้อมหรือส่งต่อไปยัง cmake ด้วย -DPICO_SDK_PATH=/path/to/pico-sdk
หากต้องการใช้คุณสมบัติต่างๆ เช่น การลงนามหรือการแฮช คุณจะต้องตรวจสอบให้แน่ใจว่าได้เช็คเอาท์โมดูลย่อย mbedtls ใน SDK แล้ว ซึ่งสามารถทำได้โดยการเรียกใช้สิ่งนี้จากไดเร็กทอรี SDK ของคุณ
git submodule update --init lib/mbedtls
คุณต้องติดตั้ง libusb-1.0
ด้วย
ใช้เครื่องมือแพ็คเกจที่คุณชื่นชอบเพื่อติดตั้งการอ้างอิง ตัวอย่างเช่น บน Ubuntu:
sudo apt install build-essential pkg-config libusb-1.0-0-dev cmake
จากนั้นเพียงสร้างเหมือนโปรเจ็กต์ CMake ปกติ:
mkdir build
cd build
cmake ..
make
บน Linux คุณสามารถเพิ่มกฎ udev เพื่อรัน picotool โดยไม่ต้องใช้ sudo:
sudo cp udev/99-picotool.rules /etc/udev/rules.d/
ดาวน์โหลด libUSB จากที่นี่ https://libusb.info/
ตั้งค่าตัวแปรสภาพแวดล้อม LIBUSB_ROOT ให้กับไดเร็กทอรีการติดตั้ง
mkdir build
cd build
cmake -G "NMake Makefiles" ..
nmake
ดาวน์โหลด libUSB จากที่นี่ https://libusb.info/
ตั้งค่าตัวแปรสภาพแวดล้อม LIBUSB_ROOT ให้กับไดเร็กทอรีการติดตั้ง
mkdir build
cd build
cmake ..
make
ไม่จำเป็นต้องดาวน์โหลด libusb แยกต่างหากหรือตั้งค่า LIBUSB_ROOT
pacman -S $MINGW_PACKAGE_PREFIX-{toolchain,cmake,libusb}
mkdir build
cd build
cmake .. -DCMAKE_INSTALL_PREFIX=$MINGW_PREFIX
cmake --build .
Raspberry Pi Pico SDK (pico-sdk) เวอร์ชัน 2.0.0 ขึ้นไปใช้ picotool
เพื่อทำการแปลง ELF เป็น UF2 ที่ก่อนหน้านี้จัดการโดยเครื่องมือ elf2uf2
ใน SDK SDK ยังใช้ picotool
เพื่อแฮชและลงนามไบนารี
แม้ว่า SDK จะสามารถดาวน์โหลด picotool ได้ด้วยตัวเองต่อโปรเจ็กต์ หากคุณมีหลายโปรเจ็กต์หรือสร้างการกำหนดค่า ก็ควรติดตั้ง picotool
ชุดเดียวในเครื่อง ซึ่งสามารถทำได้ง่ายที่สุดด้วย make install
หรือ cmake --install .
- SDK จะใช้เวอร์ชันที่ติดตั้งนี้เป็นค่าเริ่มต้น
หรือคุณสามารถติดตั้งในเส้นทางที่กำหนดเองผ่าน:
cmake -DCMAKE_INSTALL_PREFIX=$MY_INSTALL_DIR -DPICOTOOL_FLAT_INSTALL=1 ..
เพื่อให้ SDK ค้นหา picotool
ในเส้นทางที่กำหนดเองนี้ คุณจะต้องตั้งค่าตัวแปร picotool_DIR
ในโปรเจ็กต์ของคุณ โดยการตั้งค่าตัวแปรสภาพแวดล้อม picotool_DIR
โดยการส่ง -Dpicotool_DIR=$MY_INSTALL_DIR/picotool
ไปยังคำสั่ง cmake
ของคุณ หรือโดยการเพิ่ม set(picotool_DIR $MY_INSTALL_DIR/picotool)
ให้กับไฟล์ CMakeLists.txt ของคุณ
picotool
เป็นเครื่องมือสำหรับการทำงานกับไบนารี RP2040/RP2350 และโต้ตอบกับอุปกรณ์ RP2040/RP2350 เมื่ออยู่ในโหมด BOOTSEL (ในเวอร์ชัน 1.1 ของ picotool
เป็นไปได้ที่จะโต้ตอบกับอุปกรณ์ที่ไม่ได้อยู่ในโหมด BOOTSEL แต่ใช้การสนับสนุน USB stdio จาก Raspberry Pi Pico SDK โดยใช้อาร์กิวเมนต์ -f
ของ picotool
)
หมายเหตุสำหรับเอกสารเพิ่มเติมโปรดดูhttps://rptl.io/pico-get-started
$ picotool help
PICOTOOL:
Tool for interacting with RP2040/RP2350 device(s) in BOOTSEL mode, or with an RP2040/RP2350 binary
SYNOPSIS:
picotool info [-b] [-p] [-d] [--debug] [-l] [-a] [device-selection]
picotool info [-b] [-p] [-d] [--debug] [-l] [-a] [-t ]
picotool config [-s ] [-g ] [device-selection]
picotool config [-s ] [-g ] [-t ]
picotool load [-p] [-n] [-N] [-u] [-v] [-x] [-t ] [-o ] [device-selection]
picotool encrypt [--quiet] [--verbose] [--hash] [--sign] [-t ] [-o ] [-t ] [-t ] [] [-t ]
picotool seal [--quiet] [--verbose] [--hash] [--sign] [--clear] [-t ] [-o ] [-t ] [] [-t ] [] [-t ] [--major ] [--minor ] [--rollback [..]]
picotool link [--quiet] [--verbose] [-t ] [-t ] [-t ] [] [-t ] [-p]
picotool save [-p] [device-selection]
picotool save -a [device-selection]
picotool save -r [device-selection]
picotool verify [device-selection]
picotool reboot [-a] [-u] [-g ] [-c ] [device-selection]
picotool otp list|get|set|load|dump|permissions|white-label
picotool partition info|create
picotool uf2 info|convert
picotool version [-s] []
picotool coprodis [--quiet] [--verbose] [-t ] [-t ]
picotool help []
COMMANDS:
info Display information from the target device(s) or file.
Without any arguments, this will display basic information for all connected RP2040 devices in BOOTSEL mode
config Display or change program configuration settings from the target device(s) or file.
load Load the program / memory range stored in a file onto the device.
encrypt Encrypt the program.
seal Add final metadata to a binary, optionally including a hash and/or signature.
link Link multiple binaries into one block loop.
save Save the program / memory stored in flash on the device to a file.
verify Check that the device contents match those in the file.
reboot Reboot the device
otp Commands related to the RP2350 OTP (One-Time-Programmable) Memory
partition Commands related to RP2350 Partition Tables
uf2 Commands related to UF2 creation and status
version Display picotool version
coprodis Post-process coprocessor instructions in dissassembly files.
help Show general help or help for a specific command
Use "picotool help " for more info
หมายเหตุคำสั่งที่ไม่ทำงานกับไฟล์ต้องใช้อุปกรณ์ในโหมด BOOTSEL เพื่อเชื่อมต่อ
รองรับ ข้อมูลไบนารี ใน SDK ซึ่งช่วยให้จัดเก็บข้อมูลขนาดกะทัดรัดที่ picotool
สามารถค้นหาได้อย่างง่ายดาย (ดูส่วนข้อมูลไบนารีด้านล่าง) คำสั่ง info ใช้สำหรับอ่านข้อมูลนี้
ข้อมูลสามารถอ่านได้จากอุปกรณ์ที่เชื่อมต่อตั้งแต่หนึ่งเครื่องขึ้นไปในโหมด BOOTSEL หรือจากไฟล์ ไฟล์นี้อาจเป็นไฟล์ ELF, UF2 หรือ BIN
$ picotool help info
INFO:
Display information from the target device(s) or file.
Without any arguments, this will display basic information for all connected RP2040 devices in BOOTSEL mode
SYNOPSIS:
picotool info [-b] [-p] [-d] [--debug] [-l] [-a] [device-selection]
picotool info [-b] [-p] [-d] [--debug] [-l] [-a] [-t ]
OPTIONS:
Information to display
-b, --basic
Include basic information. This is the default
-p, --pins
Include pin information
-d, --device
Include device information
--debug
Include device debug information
-l, --build
Include build attributes
-a, --all
Include all information
TARGET SELECTION:
To target one or more connected RP2040 device(s) in BOOTSEL mode (the default)
--bus
Filter devices by USB bus number
--address
Filter devices by USB device address
--vid
Filter by vendor id
--pid
Filter by product id
--ser
Filter by serial number
-f, --force
Force a device not in BOOTSEL mode but running compatible code to reset so the command can be executed. After executing the
command (unless the command itself is a 'reboot') the device will be rebooted back to application mode
-F, --force-no-reboot
Force a device not in BOOTSEL mode but running compatible code to reset so the command can be executed. After executing the
command (unless the command itself is a 'reboot') the device will be left connected and accessible to picotool, but without the
RPI-RP2 drive mounted
To target a file
The file name
-t
Specify file type (uf2 | elf | bin) explicitly, ignoring file extension
โปรดทราบว่าอาร์กิวเมนต์ -f จะแตกต่างกันเล็กน้อยสำหรับแพลตฟอร์ม Windows และ macOS / Unix
เช่น
$ picotool info ชื่อข้อมูลโปรแกรม: คุณสมบัติ hello_world: stdout ถึง UART
$ picotool info -a
Program Information
name: hello_world
features: stdout to UART
binary start: 0x10000000
binary end: 0x1000606c
Fixed Pin Information
20: UART1 TX
21: UART1 RX
Build Information
build date: Dec 31 2020
build attributes: Debug build
Device Information
flash size: 2048K
ROM version: 2
$ picotool info -bp ชื่อข้อมูลโปรแกรม: คุณสมบัติ hello_world: stdout ถึง UART
ข้อมูลพินคงที่ 20: UART1 TX 21: UART1 RX
$ picotool info -a lcd_1602_i2c.uf2
File lcd_1602_i2c.uf2:
Program Information
name: lcd_1602_i2c
web site: https://github.com/raspberrypi/pico-examples/tree/HEAD/i2c/lcd_1602_i2c
binary start: 0x10000000
binary end: 0x10003c1c
Fixed Pin Information
4: I2C0 SDA
5: I2C0 SCL
Build Information
build date: Dec 31 2020
Config ช่วยให้คุณสามารถกำหนดค่าข้อมูลไบนารีบนอุปกรณ์ได้ หากกำหนดค่าได้ โดยเฉพาะ คุณสามารถกำหนดค่า bi_ptr_int32
และ bi_ptr_string
$ picotool help config
CONFIG:
Display or change program configuration settings from the target device(s) or file.
SYNOPSIS:
picotool config [-s ] [-g ] [device-selection]
picotool config [-s ] [-g ] [-t ]
OPTIONS:
Variable name
New value
-g
Filter by feature group
TARGET SELECTION:
To target one or more connected RP2040 device(s) in BOOTSEL mode (the default)
--bus
Filter devices by USB bus number
--address
Filter devices by USB device address
--vid
Filter by vendor id
--pid
Filter by product id
--ser
Filter by serial number
-f, --force
Force a device not in BOOTSEL mode but running compatible code to reset so the command can be executed. After executing the
command (unless the command itself is a 'reboot') the device will be rebooted back to application mode
-F, --force-no-reboot
Force a device not in BOOTSEL mode but running compatible code to reset so the command can be executed. After executing the
command (unless the command itself is a 'reboot') the device will be left connected and accessible to picotool, but without the
RPI-RP2 drive mounted
To target a file
The file name
-t
Specify file type (uf2 | elf | bin) explicitly, ignoring file extension
$ picotool config
n = 5
name = "Billy"
nonconst_pins:
default_pin = 3
default_name = "My First Pin"
$ picotool config -g nonconst_pins
nonconst_pins:
default_pin = 3
default_name = "My First Pin"
$ picotool config -s name Jane
name = "Billy"
setting name -> "Jane"
$ picotool config
n = 5
name = "Jane"
nonconst_pins:
default_pin = 3
default_name = "My First Pin"
load
ช่วยให้คุณสามารถเขียนข้อมูลจากไฟล์ลงในอุปกรณ์ได้ (ไม่ว่าจะเขียนลงแฟลชหรือลง RAM)
$ picotool help load
LOAD:
Load the program / memory range stored in a file onto the device.
SYNOPSIS:
picotool load [--ignore-partitions] [--family ] [-p ] [-n] [-N] [-u] [-v] [-x] [-t ] [-o
] [device-selection]
OPTIONS:
Post load actions
--ignore-partitions
When writing flash data, ignore the partition table and write to absolute space
--family
Specify the family ID of the file to load
family id to use for load
-p, --partition
Specify the partition to load into
partition to load into
-n, --no-overwrite
When writing flash data, do not overwrite an existing program in flash. If picotool cannot determine the size/presence of the
program in flash, the command fails
-N, --no-overwrite-unsafe
When writing flash data, do not overwrite an existing program in flash. If picotool cannot determine the size/presence of the
program in flash, the load continues anyway
-u, --update
Skip writing flash sectors that already contain identical data
-v, --verify
Verify the data was written correctly
-x, --execute
Attempt to execute the downloaded file as a program after the load
File to load from
The file name
-t
Specify file type (uf2 | elf | bin) explicitly, ignoring file extension
BIN file options
-o, --offset
Specify the load address for a BIN file
Load offset (memory address; default 0x10000000)
Target device selection
--bus
Filter devices by USB bus number
--address
Filter devices by USB device address
--vid
Filter by vendor id
--pid
Filter by product id
--ser
Filter by serial number
-f, --force
Force a device not in BOOTSEL mode but running compatible code to reset so the command can be executed. After executing the
command (unless the command itself is a 'reboot') the device will be rebooted back to application mode
-F, --force-no-reboot
Force a device not in BOOTSEL mode but running compatible code to reset so the command can be executed. After executing the
command (unless the command itself is a 'reboot') the device will be left connected and accessible to picotool, but without the
RPI-RP2 drive mounted
เช่น
$ picotool load blink.uf2
Loading into Flash: [==============================] 100%
save
ช่วยให้คุณสามารถบันทึกช่วง RAM โปรแกรมในแฟลช หรือช่วงแฟลชที่ชัดเจนจากอุปกรณ์ไปยังไฟล์ BIN หรือไฟล์ UF2
$ picotool help save
SAVE:
Save the program / memory stored in flash on the device to a file.
SYNOPSIS:
picotool save [-p] [device-selection]
picotool save -a [device-selection]
picotool save -r [device-selection]
OPTIONS:
Selection of data to save
-p, --program
Save the installed program only. This is the default
-a, --all
Save all of flash memory
-r, --range
Save a range of memory. Note that UF2s always store complete 256 byte-aligned blocks of 256 bytes, and the range is expanded
accordingly
The lower address bound in hex
The upper address bound in hex
Source device selection
--bus
Filter devices by USB bus number
--address
Filter devices by USB device address
--vid
Filter by vendor id
--pid
Filter by product id
--ser
Filter by serial number
-f, --force
Force a device not in BOOTSEL mode but running compatible code to reset so the command can be executed. After executing the
command (unless the command itself is a 'reboot') the device will be rebooted back to application mode
-F, --force-no-reboot
Force a device not in BOOTSEL mode but running compatible code to reset so the command can be executed. After executing the
command (unless the command itself is a 'reboot') the device will be left connected and accessible to picotool, but without the
RPI-RP2 drive mounted
File to save to
The file name
-t
Specify file type (uf2 | elf | bin) explicitly, ignoring file extension
เช่น ดูก่อนว่ามีอะไรอยู่ในเครื่อง...
$ picotool info
Program Information
name: lcd_1602_i2c
web site: https://github.com/raspberrypi/pico-examples/tree/HEAD/i2c/lcd_1602_i2c
... บันทึกเป็นไฟล์ ...
$ picotool save spoon.uf2
Saving file: [==============================] 100%
Wrote 51200 bytes to spoon.uf2
... และดูไฟล์:
$ picotool info spoon.uf2
File spoon.uf2:
Program Information
name: lcd_1602_i2c
web site: https://github.com/raspberrypi/pico-examples/tree/HEAD/i2c/lcd_1602_i2c
seal
ช่วยให้คุณสามารถลงชื่อและ/หรือแฮชไบนารี่เพื่อรันบน RP2350
ตามค่าเริ่มต้น ระบบจะลงนามในไบนารี่ แต่สามารถกำหนดค่าได้ด้วยอาร์กิวเมนต์ --hash
และ --no-sign
รหัสลงนามของคุณต้องเป็นของเส้นโค้ง secp256k1 ในรูปแบบ PEM คุณสามารถสร้างไฟล์ .PEM ด้วย:
openssl ecparam -name secp256k1 -genkey -out private.pem
$ picotool help seal
SEAL:
Add final metadata to a binary, optionally including a hash and/or signature.
SYNOPSIS:
picotool seal [--quiet] [--verbose] [--hash] [--sign] [--clear] [-t ] [-o ] [-t ] [] [-t
] [] [-t ] [--major ] [--minor ] [--rollback [..]]
OPTIONS:
--quiet
Don't print any output
--verbose
Print verbose output
--major
Add Major Version
--minor
Add Minor Version
--rollback [..]
Add Rollback Version
Configuration
--hash
Hash the file
--sign
Sign the file
--clear
Clear all of SRAM on load
File to load from
The file name
-t
Specify file type (uf2 | elf | bin) explicitly, ignoring file extension
BIN file options
-o, --offset
Specify the load address for a BIN file
Load offset (memory address; default 0x10000000)
File to save to
The file name
-t
Specify file type (uf2 | elf | bin) explicitly, ignoring file extension
Key file
The file name
-t
Specify file type (pem) explicitly, ignoring file extension
File to save OTP to (will edit existing file if it exists)
The file name
-t
Specify file type (json) explicitly, ignoring file extension
encrypt
ช่วยให้คุณสามารถเข้ารหัสและลงนามไบนารี่เพื่อใช้กับ RP2350 ตามค่าเริ่มต้น มันจะเซ็นชื่อไบนารีที่เข้ารหัส แต่สามารถกำหนดค่าได้คล้ายกับ picotool sign
ไบนารีที่เข้ารหัสจะมีโครงสร้างดังต่อไปนี้:
ต้องระบุคีย์ AES เป็นไฟล์ .bin ของคีย์ AES 256 บิตเพื่อใช้สำหรับการเข้ารหัส
$ picotool help encrypt
ENCRYPT:
Encrypt the program.
SYNOPSIS:
picotool encrypt [--quiet] [--verbose] [--hash] [--sign] [-t ] [-o ] [-t ] [-t ]
[] [-t ]
OPTIONS:
--quiet
Don't print any output
--verbose
Print verbose output
Signing Configuration
--hash
Hash the encrypted file
--sign
Sign the encrypted file
File to load from
The file name
-t
Specify file type (uf2 | elf | bin) explicitly, ignoring file extension
BIN file options
-o, --offset
Specify the load address for a BIN file
Load offset (memory address; default 0x10000000)
File to save to
The file name
-t
Specify file type (uf2 | elf | bin) explicitly, ignoring file extension
AES Key
The file name
-t
Specify file type (bin) explicitly, ignoring file extension
Signing Key file
The file name
-t
Specify file type (pem) explicitly, ignoring file extension
คำสั่ง partition
ช่วยให้คุณสามารถโต้ตอบกับตารางพาร์ติชันบนอุปกรณ์ RP2350 และยังสร้างคำสั่งเหล่านั้นด้วย
$ picotool help partition info
PARTITION INFO:
Print the device's partition table.
SYNOPSIS:
picotool partition info -m [device-selection]
OPTIONS:
-m [device-selection]
$ picotool partition info
un-partitioned_space : S(rw) NSBOOT(rw) NS(rw), uf2 { absolute }
partitions:
0(A) 00002000->00201000 S(rw) NSBOOT(rw) NS(rw), id=0000000000000000, "A", uf2 { rp2350-arm-s, rp2350-riscv }, arm_boot 1, riscv_boot 1
1(B w/ 0) 00201000->00400000 S(rw) NSBOOT(rw) NS(rw), id=0000000000000001, "B", uf2 { rp2350-arm-s, rp2350-riscv }, arm_boot 1, riscv_boot 1
$ picotool partition info -m rp2350-arm-s
un-partitioned_space : S(rw) NSBOOT(rw) NS(rw), uf2 { absolute }
partitions:
0(A) 00002000->00201000 S(rw) NSBOOT(rw) NS(rw), id=0000000000000000, "A", uf2 { rp2350-arm-s, rp2350-riscv }, arm_boot 1, riscv_boot 1
1(B w/ 0) 00201000->00400000 S(rw) NSBOOT(rw) NS(rw), id=0000000000000001, "B", uf2 { rp2350-arm-s, rp2350-riscv }, arm_boot 1, riscv_boot 1
Family id 'rp2350-arm-s' can be downloaded in partition 0:
00002000->00201000
คำสั่งนี้ช่วยให้คุณสร้างตารางพาร์ติชันและฝังเพิ่มเติมลงในบล็อกลูปหากไฟล์ ELF (เช่นสำหรับ bootloaders) ตามค่าเริ่มต้น ตารางพาร์ติชันทั้งหมดจะถูกแฮช และคุณยังสามารถเซ็นชื่อได้
$ picotool help partition create
PARTITION CREATE:
Create a partition table from json
SYNOPSIS:
picotool partition create [--quiet] [--verbose] [-t ] [-t ] [[-o ] [--family ]]
[] [-t ] [[--sign ] [-t ] [--no-hash] [--singleton]] [[--abs-block] []]
OPTIONS:
--quiet
Don't print any output
--verbose
Print verbose output
partition table JSON
The file name
-t
Specify file type (json) explicitly, ignoring file extension
output file
The file name
-t
Specify file type (uf2 | elf | bin) explicitly, ignoring file extension
UF2 output options
-o, --offset
Specify the load address for UF2 file output
Load offset (memory address; default 0x10000000)
--family
Specify the family if for UF2 file output
family id for UF2 (default absolute)
embed partition table into bootloader ELF
The file name
-t
Specify file type (elf) explicitly, ignoring file extension
Partition Table Options
--sign
The file name
-t
Specify file type (pem) explicitly, ignoring file extension
--no-hash
Don't hash the partition table
--singleton
Singleton partition table
Errata RP2350-E9 Fix
--abs-block
Enforce support for an absolute block
absolute block location (default to 0x10ffff00)
คำสั่ง uf2
อนุญาตให้สร้าง UF2 และ cam จะให้ข้อมูลเมื่อการดาวน์โหลด UF2 ล้มเหลว
คำสั่งนี้จะแทนที่ฟังก์ชันการทำงานของ elf2uf2 ที่เคยอยู่ใน Raspberry Pi Pico SDK มันจะพยายามตรวจจับ family ID โดยอัตโนมัติ แต่หากล้มเหลวคุณสามารถระบุได้ด้วยตนเองด้วยอาร์กิวเมนต์ --family
picotool help uf2 convert
UF2 CONVERT:
Convert ELF/BIN to UF2.
SYNOPSIS:
picotool uf2 convert [--quiet] [--verbose] [-t ] [-t ] [-o ] [--family ]
[[--abs-block] []]
OPTIONS:
--quiet
Don't print any output
--verbose
Print verbose output
File to load from
The file name
-t
Specify file type (uf2 | elf | bin) explicitly, ignoring file extension
File to save UF2 to
The file name
-t
Specify file type (uf2) explicitly, ignoring file extension
Packaging Options
-o, --offset
Specify the load address
Load offset (memory address; default 0x10000000 for BIN file)
UF2 Family options
family id for UF2
Errata RP2350-E9 Fix
--abs-block
Add an absolute block
absolute block location (default to 0x10ffff00)
คำสั่งนี้อ่านข้อมูลบนอุปกรณ์เกี่ยวกับสาเหตุที่การดาวน์โหลด UF2 ล้มเหลว มันจะให้ข้อมูลก็ต่อเมื่อการดาวน์โหลดครั้งล่าสุดล้มเหลว
$ picotool help uf2 info
UF2 INFO:
Print info about UF2 download.
SYNOPSIS:
picotool uf2 info [device-selection]
OPTIONS:
Target device selection
--bus
Filter devices by USB bus number
--address
Filter devices by USB device address
--vid
Filter by vendor id
--pid
Filter by product id
--ser
Filter by serial number
-f, --force
Force a device not in BOOTSEL mode but running compatible code to reset so the command can be executed. After executing the
command (unless the command itself is a 'reboot') the device will be rebooted back to application mode
-F, --force-no-reboot
Force a device not in BOOTSEL mode but running compatible code to reset so the command can be executed. After executing the
command (unless the command itself is a 'reboot') the device will be left connected and accessible to picotool, but without the
RPI-RP2 drive mounted
คำสั่ง otp
ใช้สำหรับโต้ตอบกับหน่วยความจำ RP2350 OTP ไม่มีให้บริการในอุปกรณ์ RP2040 เนื่องจาก RP2040 ไม่มี OTP
โปรดทราบว่าหน่วยความจำ OTP สามารถตั้งโปรแกรมได้ครั้งเดียว ซึ่งหมายความว่าเมื่อเปลี่ยนบิตจาก 0 เป็น 1 แล้ว จะไม่สามารถเปลี่ยนกลับได้ ดังนั้น ควรใช้ความระมัดระวังเมื่อใช้คำสั่งเหล่านี้ เนื่องจากอาจเสี่ยงต่อการปิดอุปกรณ์ RP2350 ของคุณ ตัวอย่างเช่น หากคุณตั้งค่า SECURE_BOOT_ENABLE แต่ไม่ได้ตั้งค่าคีย์การบูต และปิดใช้งานอินเทอร์เฟซ PICOBOOT อุปกรณ์ของคุณก็จะใช้งานไม่ได้
สำหรับคำสั่ง list
, set
, get
และ load
คุณสามารถกำหนดเค้าโครง OTP ของคุณเองในไฟล์ JSON และส่งผ่านสิ่งนั้นด้วยอาร์กิวเมนต์ -i
แถวเหล่านี้จะถูกเพิ่มลงในแถวเริ่มต้นเมื่อแยกวิเคราะห์
$ picotool help otp
OTP:
Commands related to the RP2350 OTP (One-Time-Programmable) Memory
SYNOPSIS:
picotool otp list [-p] [-n] [-i ] [..]
picotool otp get [-c ] [-r] [-e] [-n] [-i ] [device-selection] [-z] [..]
picotool otp set [-c ] [-r] [-e] [-i ] [-z] [device-selection]
picotool otp load [-r] [-e] [-s ] [-i ] [-t ] [device-selection]
picotool otp dump [-r] [-e] [device-selection]
picotool otp permissions [-t ] [--led ] [--hash] [--sign] [] [-t ] [device-selection]
picotool otp white-label -s [-t ] [device-selection]
SUB COMMANDS:
list List matching known registers/fields
get Get the value of one or more OTP registers/fields (RP2350 only)
set Set the value of an OTP row/field (RP2350 only)
load Load the row range stored in a file into OTP and verify. Data is 2 bytes/row for ECC, 4 bytes/row for raw. (RP2350 only)
dump Dump entire OTP (RP2350 only)
permissions Set the OTP access permissions (RP2350 only)
white-label Set the white labelling values in OTP (RP2350 only)
คำสั่งเหล่านี้จะตั้งค่า/รับแถวเฉพาะของ OTP ตามค่าเริ่มต้น พวกเขาจะเขียน/อ่านแถวที่ซ้ำซ้อนทั้งหมด แต่สามารถแทนที่ได้ด้วยอาร์กิวเมนต์ -c
คำสั่งนี้อนุญาตให้โหลดช่วง OTP แถวลงในอุปกรณ์ แหล่งที่มาอาจเป็นไฟล์ไบนารี่หรือไฟล์ JSON เช่นเอาต์พุตเดียวโดย picotool sign
ตัวอย่างเช่น หากคุณต้องการลงนามไบนารี่แล้วทดสอบการบูตอย่างปลอดภัย คุณสามารถรันชุดคำสั่งต่อไปนี้:
$ picotool sign hello_world.elf hello_world.signed.elf private.pem otp.json
$ picotool load hello_world.signed.elf
$ picotool otp load otp.json
$ picotool reboot
คำสั่งนี้อนุญาตให้ใช้ OTP white-labeling ซึ่งตั้งค่าการกำหนดค่า USB ที่อุปกรณ์ใช้ในโหมด BOOTSEL ซึ่งสามารถกำหนดค่าได้จากไฟล์ JSON ตัวอย่างที่อยู่ใน Sample-wl.json
$ picotool help otp white-label
OTP WHITE-LABEL:
Set the white labelling values in OTP
SYNOPSIS:
picotool otp white-label -s [-t ] [device-selection]
OPTIONS:
File with white labelling values
The file name
-t
Specify file type (json) explicitly, ignoring file extension
Target device selection
--bus
Filter devices by USB bus number
--address
Filter devices by USB device address
--vid
Filter by vendor id
--pid
Filter by product id
--ser
Filter by serial number
-f, --force
Force a device not in BOOTSEL mode but running compatible code to reset so the command can be executed. After executing the
command (unless the command itself is a 'reboot') the device will be rebooted back to application mode
-F, --force-no-reboot
Force a device not in BOOTSEL mode but running compatible code to reset so the command can be executed. After executing the
command (unless the command itself is a 'reboot') the device will be left connected and accessible to picotool, but without the
RPI-RP2 drive mounted
$ picotool otp white-label -s 0x100 ../sample-wl.json
Setting attributes 20e0
0x2e8b, 0x000e, 0x0215, 0x0c09, 0x1090, 0x200c, 0x2615, 0x20e0, 0x310b, 0x3706, 0x3a04, 0x3c04, 0x3e21, 0x4f15, 0x5a0a, 0x5f0a, 0x007a, 0x00df, 0x6c34, 0xd83c, 0xdf4c, 0x0020, 0x0054, 0x0065, 0x0073, 0x0074, 0x0027, 0x0073,
0x0020, 0x0050, 0x0069, 0x0073, 0x6554, 0x7473, 0x5220, 0x3250, 0x3533, 0x3f30, 0x6f6e, 0x6e74, 0x6365, 0x7365, 0x6173, 0x6972, 0x796c, 0x6e61, 0x6d75, 0x6562, 0x0072, 0x6554, 0x7473, 0x6950, 0x4220, 0x6f6f, 0x0074, 0x6554,
0x7473, 0x6950, 0x794d, 0x6950, 0x3876, 0x3739, 0x7468, 0x7074, 0x3a73, 0x2f2f, 0x7777, 0x2e77, 0x6172, 0x7073, 0x6562, 0x7272, 0x7079, 0x2e69, 0x6f63, 0x2f6d, 0x656e, 0x7377, 0x002f, 0x6f53, 0x656d, 0x4e20, 0x7765, 0x2073,
0x6241, 0x756f, 0x2074, 0x7453, 0x6675, 0x0066, 0x794d, 0x5420, 0x7365, 0x2074, 0x6950, 0x5054, 0x2d49, 0x5052, 0x3332, 0x3035,
$ picotool reboot -u
$ lsusb -v -s 1:102
Bus 001 Device 102: ID 2e8b:000e zß水? Test's Pis Test RP2350?
Device Descriptor:
bLength 18
bDescriptorType 1
bcdUSB 2.10
bDeviceClass 0
bDeviceSubClass 0
bDeviceProtocol 0
bMaxPacketSize0 64
idVendor 0x2e8b
idProduct 0x000e
bcdDevice 2.15
iManufacturer 1 zß水? Test's Pis
iProduct 2 Test RP2350?
iSerial 3 notnecessarilyanumber
bNumConfigurations 1
Configuration Descriptor:
bLength 9
bDescriptorType 2
wTotalLength 0x0037
bNumInterfaces 2
bConfigurationValue 1
iConfiguration 0
bmAttributes 0xc0
Self Powered
MaxPower 64mA
...
คำสั่งนี้จะเรียกใช้ไบนารีบนอุปกรณ์ของคุณเพื่อตั้งค่าสิทธิ์ OTP เนื่องจากไม่สามารถเข้าถึงได้โดยตรงจาก picotool
เนื่องจากการตั้งค่าสิทธิ์เริ่มต้นที่จำเป็นในการแก้ไข errata XXX บน RP2350 เนื่องจากไบนารี่ทำงาน จึงต้องเซ็นชื่อไบนารีหากเปิดใช้งานการบูตแบบปลอดภัย ไบนารี่จะพิมพ์สิ่งที่กำลังทำบน uart ซึ่งสามารถกำหนดค่าได้โดยใช้อาร์กิวเมนต์การกำหนดค่า UART คุณสามารถกำหนดสิทธิ์ OTP ของคุณในไฟล์ json ได้ ตัวอย่างอยู่ในไฟล์ example-permissions.json
$ picotool help otp permissions
OTP PERMISSIONS:
Set the OTP access permissions
SYNOPSIS:
picotool otp permissions [-t ] [--led ] [--hash] [--sign] [] [-t ] [device-selection]
OPTIONS:
File to load permissions from
The file name
-t
Specify file type (json) explicitly, ignoring file extension
--led
LED Pin to flash; default 25
Signing Configuration
--hash
Hash the executable
--sign
Sign the executable
Key file
The file name
-t
Specify file type (pem) explicitly, ignoring file extension
Target device selection
--bus
Filter devices by USB bus number
--address
Filter devices by USB device address
--vid
Filter by vendor id
--pid
Filter by product id
--ser
Filter by serial number
-f, --force
Force a device not in BOOTSEL mode but running compatible code to reset so the command can be executed. After executing the
command (unless the command itself is a 'reboot') the device will be rebooted back to application mode
-F, --force-no-reboot
Force a device not in BOOTSEL mode but running compatible code to reset so the command can be executed. After executing the
command (unless the command itself is a 'reboot') the device will be left connected and accessible to picotool, but without the
RPI-RP2 drive mounted
$ picotool otp permissions --sign private.pem --tx 46 ../sample-permissions.json
Picking file ./xip_ram_perms.elf
page10
page10 = 0
setting page10 -> 4063233
page11
page11 = 0
setting page11 -> 4128781
page12
page12 = 0
setting page12 -> 4128781
tx_pin = 0
setting tx_pin -> 46
Loading into XIP RAM: [==============================] 100%
>>> using flash update boot of 13ffc000
The device was rebooted to start the application.
ข้อมูลไบนารี่สามารถระบุตำแหน่งเครื่องได้ และโดยทั่วไปเป็นวัสดุสิ้นเปลืองในเครื่อง ฉันพูดโดยทั่วไปเพราะใครๆ ก็สามารถใส่ข้อมูลใดๆ ลงไปได้ และเราสามารถบอกได้จากเรา แต่ก็ขึ้นอยู่กับพวกเขาว่าพวกเขาจะทำให้ข้อมูลของตนอธิบายได้เองหรือไม่
โปรดทราบว่าเราจะเพิ่มข้อมูลไบนารี่มากขึ้นเรื่อยๆ เมื่อเวลาผ่านไป แต่ฉันอยากได้ชุดคอร์ขั้นต่ำที่รวมอยู่ในไบนารีส่วนใหญ่ตั้งแต่เปิดตัว!!
ข้อมูลนี้มีประโยชน์มากเมื่อคุณหยิบ Pico ขึ้นมาและไม่รู้ว่ามีอะไรอยู่บนนั้น!
ข้อมูลเบื้องต้นประกอบด้วย
ข้อมูลไบนารี่อธิบายได้ในตัว/ขยายได้ ดังนั้นโปรแกรมจึงสามารถรวมข้อมูลที่ picotool ไม่ทราบได้ (เช่น MicroPython มีรายการไลบรารีในตัว)
สิ่งนี้มีประโยชน์อย่างแน่นอนเมื่อคุณมีไฟล์เรียกทำงานที่เรียกว่า 'hello_world.elf' แต่คุณลืมว่าบอร์ดนี้สร้างมาเพื่ออะไร...
การกำหนดพินแบบคงที่ (คงที่) สามารถบันทึกลงในไบนารี่ในรูปแบบที่กะทัดรัดมาก:
$ picotool info --pins sprite_demo.elf
File sprite_demo.elf:
Fixed Pin Information
0-4: Red 0-4
6-10: Green 0-4
11-15: Blue 0-4
16: HSync
17: VSync
18: Display Enable
19: Pixel Clock
20: UART1 TX
21: UART1 RX
สิ่งนี้มีประโยชน์มากหากคุณต้องการแก้ไขพารามิเตอร์ในไบนารี่ โดยไม่ต้องคอมไพล์ใหม่
$ picotool config -s name Jane
name = "Billy"
setting name -> "Jane"
ข้อมูลไบนารีถูกประกาศในโปรแกรมโดยมาโคร (มาโครบิดเบี้ยวที่ชั่วร้าย); สำหรับตัวอย่างพิน:
$ picotool info --pins sprite_demo.elf
File sprite_demo.elf:
Fixed Pin Information
0-4: Red 0-4
6-10: Green 0-4
11-15: Blue 0-4
16: HSync
17: VSync
18: Display Enable
19: Pixel Clock
20: UART1 TX
21: UART1 RX
... มีหนึ่งบรรทัดในฟังก์ชัน setup_default_uart
:
bi_decl_if_func_used ( bi_2pins_with_func ( PICO_DEFAULT_UART_RX_PIN , PICO_DEFAULT_UART_TX_PIN , GPIO_FUNC_UART ));
หมายเลขพินสองตัวและฟังก์ชัน UART จะถูกจัดเก็บ จากนั้นถอดรหัสเป็นชื่อฟังก์ชันจริง (UART1 TX ฯลฯ) โดย picotool bi_decl_if_func_used
ทำให้แน่ใจว่าข้อมูลไบนารี่ถูกรวมไว้เมื่อมีการเรียกใช้ฟังก์ชันที่มีอยู่เท่านั้น
ในทำนองเดียวกัน โค้ดวิดีโอประกอบด้วยบรรทัดสองสามบรรทัดดังนี้:
bi_decl_if_func_used ( bi_pin_mask_with_name ( 0x1f << ( PICO_SCANVIDEO_COLOR_PIN_BASE + PICO_SCANVIDEO_DPI_PIXEL_RSHIFT ), "Red 0-4" ));
สำหรับตัวอย่างการกำหนดค่า คุณใส่บรรทัด
bi_decl ( bi_ptr_string ( 0x1111 , 0x3333 , name , "Billy" , 128 ));
ลงในโค้ดของคุณ ซึ่งจะสร้างตัวแปรชื่อให้คุณพิมพ์ในภายหลัง พารามิเตอร์ ได้แก่ แท็ก ID ชื่อตัวแปร ค่าเริ่มต้น และความยาวสตริงสูงสุด
printf ( "Name is %sn" , name );
สิ่งต่าง ๆ ได้รับการออกแบบมาเพื่อสิ้นเปลืองพื้นที่ให้น้อยที่สุด แต่คุณสามารถปิดทุกอย่างได้ด้วยตัวแปรพรีโปรเซสเซอร์ PICO_NO_BINARY_INFO=1
นอกจากนี้ โค้ด SDK ใดๆ ที่แทรกข้อมูลไบนารีสามารถแยกออกแยกต่างหากโดยตัวแปรตัวประมวลผลล่วงหน้าของตัวเอง
คุณต้องการ
#include "pico/binary_info.h"
โดยพื้นฐานแล้วคุณอาจใช้ bi_decl(bi_blah(...))
สำหรับการรวมข้อมูลไบนารี่แบบไม่มีเงื่อนไข blah หรือ bi_decl_if_func_used(bi_blah(...))
สำหรับข้อมูลไบนารีที่อาจถูกถอดออกหากฟังก์ชันการปิดล้อมไม่รวมอยู่ในไบนารีโดย ตัวเชื่อมโยง (คิดว่า --gc-sections
)
มีมาโคร bi_ จำนวนมากอยู่ในส่วนหัว
#define bi_binary_end ( end ) ...
#define bi_program_name ( name ) ...
#define bi_program_description ( description ) ...
#define bi_program_version_string ( version_string ) ...
#define bi_program_build_date_string ( date_string ) ...
#define bi_program_url ( url ) ...
#define bi_program_feature ( feature ) ...
#define bi_program_build_attribute ( attr ) ...
#define bi_1pin_with_func ( p0 , func ) ...
#define bi_2pins_with_func ( p0 , p1 , func ) ...
#define bi_3pins_with_func ( p0 , p1 , p2 , func ) ...
#define bi_4pins_with_func ( p0 , p1 , p2 , p3 , func ) ...
#define bi_5pins_with_func ( p0 , p1 , p2 , p3 , p4 , func ) ...
#define bi_pin_range_with_func ( plo , phi , func ) ...
#define bi_pin_mask_with_name ( pmask , label ) ...
#define bi_pin_mask_with_names ( pmask , label ) ...
#define bi_1pin_with_name ( p0 , name ) ...
#define bi_2pins_with_names ( p0 , name0 , p1 , name1 ) ...
#define bi_3pins_with_names ( p0 , name0 , p1 , name1 , p2 , name2 ) ...
#define bi_4pins_with_names ( p0 , name0 , p1 , name1 , p2 , name2 , p3 , name3 ) ...
ซึ่งใช้มาโครพื้นฐานเช่น
#define bi_program_url ( url ) bi_string(BINARY_INFO_TAG_RASPBERRY_PI, BINARY_INFO_ID_RP_PROGRAM_URL, url)
หมายเหตุ: เป็นเรื่องง่ายที่จะลืมใส่สิ่งเหล่านี้ใน bi_decl
ฯลฯ ดังนั้นจึงมีความพยายาม (โดยต้องเสียลูกแมวจำนวนมาก) เพื่อทำให้การสร้างล้มเหลวพร้อมข้อความแสดงข้อผิดพลาด ที่ เป็นประโยชน์หากคุณทำเช่นนั้น
เช่น พยายามคอมไพล์
bi_1pin_with_name ( 0 , "Toaster activator" );
ให้
/home/graham/dev/mu/pico_sdk/src/common/pico_binary_info/include/pico/binary_info/code.h:17:55: error: '_error_bi_is_missing_enclosing_decl_261' undeclared here (not in a function)
17 | #define __bi_enclosure_check_lineno_var_name __CONCAT(_error_bi_is_missing_enclosing_decl_,__LINE__)
| ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
... more macro call stack of doom
คุณสามารถใช้
pico_set_program_name(foo "not foo" ) # as "foo" would be the default
pico_set_program_description(foo "this is a foo" )
pico_set_program_version(foo "0.00001a" )
pico_set_program_url(foo "www.plinth.com/foo" )
โปรดทราบว่าสิ่งเหล่านี้ทั้งหมดจะถูกส่งผ่านเป็นอาร์กิวเมนต์บรรทัดคำสั่งในการคอมไพล์ ดังนั้นหากคุณวางแผนที่จะใช้เครื่องหมายคำพูด การขึ้นบรรทัดใหม่ ฯลฯ คุณอาจโชคดีกว่าในการกำหนดผ่าน bi_decl ในโค้ด
MicroPython และ CircuitPython ในที่สุด SDK และอื่น ๆ อาจรองรับอุปกรณ์จัดเก็บข้อมูลตั้งแต่หนึ่งตัวขึ้นไปในแฟลช เรามีมาโครที่จะกำหนดสิ่งเหล่านี้อยู่แล้ว แม้ว่า picotool จะยังไม่ได้ทำอะไรกับมันเลย... แต่การสำรอง/กู้คืน/คัดลอกไฟล์และแม้แต่การเมานต์ฟิวส์ในอนาคตอาจเป็นสิ่งที่น่าสนใจ
ฉันขอแนะนำให้เราแท็กสิ่งเหล่านี้ทันที...
นี่คือสิ่งที่ฉันมีตอนนี้จากด้านบนของหัว (ในขณะนั้น)
#define bi_block_device ( _tag , _name , _offset , _size , _extra , _flags )
โดยมีข้อมูลเข้าไป
typedef struct __packed _binary_info_block_device {
struct _binary_info_core core ;
bi_ptr_of ( const char ) name ; // optional static name (independent of what is formatted)
uint32_t offset ;
uint32_t size ;
bi_ptr_of ( binary_info_t ) extra ; // additional info
uint16_t flags ;
} binary_info_block_device_t ;
และ
enum {
BINARY_INFO_BLOCK_DEV_FLAG_READ = 1 << 0 , // if not readable, then it is basically hidden, but tools may choose to avoid overwriting it
BINARY_INFO_BLOCK_DEV_FLAG_WRITE = 1 << 1 ,
BINARY_INFO_BLOCK_DEV_FLAG_REFORMAT = 1 << 2 , // may be reformatted..
BINARY_INFO_BLOCK_DEV_FLAG_PT_UNKNOWN = 0 << 4 , // unknown free to look
BINARY_INFO_BLOCK_DEV_FLAG_PT_MBR = 1 << 4 , // expect MBR
BINARY_INFO_BLOCK_DEV_FLAG_PT_GPT = 2 << 4 , // expect GPT
BINARY_INFO_BLOCK_DEV_FLAG_PT_NONE = 3 << 4 , // no partition table
};
การรันคำสั่งด้วย -f/F
ต้องใช้โค้ดที่เข้ากันได้จึงจะรันบนอุปกรณ์ได้ คำจำกัดความของรหัสที่เข้ากันได้สำหรับวัตถุประสงค์ของไบนารีที่คอมไพล์โดยใช้ pico-sdk คือรหัสนั้น
-f/F
จะไม่ทำงาน - คุณสามารถตั้งค่าคำจำกัดความการคอมไพล์ PICO_ENTER_USB_BOOT_ON_EXIT
แทนเพื่อรีบูตและสามารถเข้าถึงได้โดย picotool เมื่อโค้ดของคุณดำเนินการเสร็จแล้ว เช่น ด้วย target_compile_definitions( PRIVATE PICO_ENTER_USB_BOOT_ON_EXIT=1)
stdio_init_all()
และคุณมี pico_enable_stdio_usb( 1)
ในไฟล์ CMakeLists.txt ของคุณ แสดงว่าคุณมีคุณสมบัติตรงตามข้อกำหนดนี้ (ดูตัวอย่าง hello_usb) หากคุณกด ctrl+c ในระหว่างการดำเนินการที่ยาวนาน ดูเหมือนว่า libusb จะสับสนเล็กน้อย ซึ่งหมายความว่าเราไม่สามารถปลดล็อคการเขียน USB MSD ของเราได้ (เราได้ปิดการทำงานเหล่านั้นเพื่อให้ผู้ใช้ไม่ได้ เหยียบเท้าตัวเอง) เพียงเรียกใช้ picotool info
อีกครั้งจะเป็นการปลดล็อคอย่างถูกต้องในครั้งต่อไป (หรือคุณสามารถรีบูตอุปกรณ์ได้)