Skip to content
Merged
Show file tree
Hide file tree
Changes from 19 commits
Commits
Show all changes
25 commits
Select commit Hold shift + click to select a range
b2bf5db
Enable hard-float ABI support for pico_float and pico_double on m33
andylinpersonal Jan 5, 2026
97267d6
Add (non google) LLVM support, and replace calling convention check w…
kilograham Feb 8, 2026
5b344af
switch float.h to use static inline method for int2float() etc in VFP…
kilograham Feb 8, 2026
42dd301
float/double test cleanup - particularly:
kilograham Feb 8, 2026
c1deef2
fix some issues with newer llvm_libc/compiler as used by bazel build
kilograham Feb 8, 2026
3a670ca
keep check_configs happy
kilograham Feb 8, 2026
0881f7f
another bazel issue
kilograham Feb 8, 2026
11325e7
introduce pico_double_pico_dcp for consistency
kilograham Feb 8, 2026
0ff893f
fixup debug output based on previous commit
kilograham Feb 8, 2026
fd8f966
remove unnecessary build guard from double_conv_m33.S
kilograham Feb 8, 2026
533b172
allow -1 for neg_denormal->int rounding towards minus infinity
kilograham Feb 8, 2026
ab0aa00
Update test/pico_float_test/CMakeLists.txt
kilograham Mar 2, 2026
3e8cfae
Update test/pico_float_test/CMakeLists.txt
kilograham Mar 2, 2026
e631f30
- add fma/_fast functions to pico_float_test/pico_double_test
kilograham Mar 3, 2026
fc579bc
- double functions were only wrapped in pico_double_pico not pico_dou…
kilograham Mar 3, 2026
acb2bd7
avoid extra stack alignment push (per review comment)
kilograham Mar 3, 2026
8a2b852
fix fma return code in VFP mode (register transfer was the wrong way …
kilograham Mar 3, 2026
5466d9d
separate PCS=VFP and non-PCS-VFP versions of fma_fast
kilograham Mar 3, 2026
6f08aa2
remove saving_func_return (which is just bx lr) and fold the separate…
kilograham Mar 3, 2026
164091a
better fix for wrapping right libraries
kilograham Mar 3, 2026
afee868
rename some labels from _entry (which is an internal entry point) to …
kilograham Mar 3, 2026
e815d94
Make bazel pico_float build not wrap SCI functions on RISC-V to match…
kilograham Mar 4, 2026
17bbade
Split out FMAF as a selectable wrapped item since we don't want to wr…
kilograham Mar 4, 2026
7fda44c
fix typos
kilograham Mar 4, 2026
b9da105
fix test
kilograham Mar 4, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 12 additions & 3 deletions cmake/preload/toolchains/pico_arm_cortex_m33_clang.cmake
Original file line number Diff line number Diff line change
@@ -1,8 +1,17 @@
set(CMAKE_SYSTEM_PROCESSOR cortex-m33)

# these are all the directories under LLVM embedded toolchain for ARM (newlib or pibolibc) and under llvm_libc
set(PICO_CLANG_RUNTIMES armv8m.main_soft_nofp armv8m.main_soft_nofp_unaligned armv8m.main-unknown-none-eabi)
set(PICO_COMMON_LANG_FLAGS "-mcpu=cortex-m33 --target=armv8m.main-none-eabi -march=armv8m.main+fp+dsp")

if (PICO_HARD_FLOAT_ABI)
set(PICO_COMMON_LANG_FLAGS "${PICO_COMMON_LANG_FLAGS} -mfloat-abi=hard")
# todo - doesn't seem to be a hard_fp variant for google atm?
# these are all the directories under LLVM embedded toolchain for ARM (newlib or pibolibc)
set(PICO_CLANG_RUNTIMES armv8m.main_hard_fp armv8m.main_hard_fp_unaligned)
else()
set(PICO_COMMON_LANG_FLAGS "${PICO_COMMON_LANG_FLAGS} -mfloat-abi=softfp")
# these are all the directories under LLVM embedded toolchain for ARM (newlib or pibolibc) and under llvm_libc
set(PICO_CLANG_RUNTIMES armv8m.main_soft_nofp armv8m.main_soft_nofp_unaligned armv8m.main-unknown-none-eabi)
endif()

set(PICO_COMMON_LANG_FLAGS "-mcpu=cortex-m33 --target=armv8m.main-none-eabi -mfloat-abi=softfp -march=armv8m.main+fp+dsp")
set(PICO_DISASM_OBJDUMP_ARGS --mcpu=cortex-m33 --arch=armv8m.main+fp+dsp)
include(${CMAKE_CURRENT_LIST_DIR}/util/pico_arm_clang_common.cmake)
8 changes: 7 additions & 1 deletion cmake/preload/toolchains/pico_arm_cortex_m33_gcc.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,13 @@ set(CMAKE_SYSTEM_PROCESSOR cortex-m33)
set(PICO_DEFAULT_GCC_TRIPLE arm-none-eabi)

set(PICO_COMMON_LANG_FLAGS " -mcpu=cortex-m33 -mthumb -march=armv8-m.main+fp+dsp")
set(PICO_COMMON_LANG_FLAGS "${PICO_COMMON_LANG_FLAGS} -mfloat-abi=softfp")
# PICO_CMAKE_CONFIG: PICO_HARD_FLOAT_ABI, use hard floating point ABI, type=bool, default=0, group=build, docref=cmake-toolchain-config
if (PICO_HARD_FLOAT_ABI)
set(PICO_COMMON_LANG_FLAGS "${PICO_COMMON_LANG_FLAGS} -mfloat-abi=hard")
else()
set(PICO_COMMON_LANG_FLAGS "${PICO_COMMON_LANG_FLAGS} -mfloat-abi=softfp")
endif()

# PICO_CMAKE_CONFIG: PICO_NO_CMSE, Disable CMSE compiler extensions, type=bool, default=0, group=build, docref=cmake-toolchain-config
if (NOT PICO_NO_CMSE)
set(PICO_COMMON_LANG_FLAGS "${PICO_COMMON_LANG_FLAGS} -mcmse")
Expand Down
4 changes: 3 additions & 1 deletion cmake/preload/toolchains/util/pico_arm_clang_common.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,9 @@ if (PICO_CLIB STREQUAL "llvm_libc")
# TODO: Remove -nostdlib++ once we include libc++ in the toolchain.
# TODO: Move -nostartfiles to the appropriate library.
foreach(TYPE IN ITEMS EXE SHARED MODULE)
set(CMAKE_${TYPE}_LINKER_FLAGS_INIT "-nostdlib++ -nostartfiles")
# note --unwindlib=none is only needed on recent compiler/lib versions, however just produces a
# warning on earlier versions, so not attempting a version check for now
set(CMAKE_${TYPE}_LINKER_FLAGS_INIT "-nostdlib++ -nostartfiles --unwindlib=none")
endforeach()
else()
if (NOT PICO_COMPILER_SYSROOT)
Expand Down
10 changes: 6 additions & 4 deletions src/rp2_common/pico_double/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,6 @@ if (NOT TARGET pico_double)
target_link_libraries(pico_double INTERFACE
$<IF:$<BOOL:$<TARGET_PROPERTY:PICO_TARGET_DOUBLE_IMPL>>,$<TARGET_PROPERTY:PICO_TARGET_DOUBLE_IMPL>,${PICO_DEFAULT_DOUBLE_IMPL}>)

# todo maybe this should be pico_double_dcp (note FreeRTOS has a dependency on the LIB_PICO_DOUBLE_FOO)
pico_add_library(pico_double_pico)
if (PICO_RP2040)
target_sources(pico_double_pico INTERFACE
Expand All @@ -31,17 +30,20 @@ if (NOT TARGET pico_double)
${CMAKE_CURRENT_LIST_DIR}/double_math.c
${CMAKE_CURRENT_LIST_DIR}/double_v1_rom_shim_rp2040.S
)
target_link_libraries(pico_double_pico INTERFACE pico_bootrom pico_double_headers hardware_divider)
elseif(NOT PICO_RISCV)
target_sources(pico_double_pico INTERFACE
pico_add_library(pico_double_pico_dcp)
target_sources(pico_double_pico_dcp INTERFACE
${CMAKE_CURRENT_LIST_DIR}/double_math.c
${CMAKE_CURRENT_LIST_DIR}/double_aeabi_dcp.S
${CMAKE_CURRENT_LIST_DIR}/double_fma_dcp.S
${CMAKE_CURRENT_LIST_DIR}/double_sci_m33.S
${CMAKE_CURRENT_LIST_DIR}/double_conv_m33.S
)
target_link_libraries(pico_double_pico_dcp INTERFACE pico_double_headers)
target_link_libraries(pico_double_pico INTERFACE pico_double_pico_dcp)
endif()

target_link_libraries(pico_double_pico INTERFACE pico_bootrom pico_double_headers hardware_divider)

pico_add_library(pico_double_none)
target_sources(pico_double_none INTERFACE
Expand Down Expand Up @@ -119,7 +121,7 @@ if (NOT TARGET pico_double)
pico_wrap_function(${TARGET} fma)
endfunction()

wrap_double_functions(pico_double_pico)
wrap_double_functions(pico_double_pico_dcp)
wrap_double_functions(pico_double_none)

macro(pico_set_double_implementation TARGET IMPL)
Expand Down
110 changes: 110 additions & 0 deletions src/rp2_common/pico_double/double_aeabi_dcp.S
Original file line number Diff line number Diff line change
Expand Up @@ -114,7 +114,14 @@ saving_func wrapper __aeabi_dmul

double_section ddiv_fast
saving_func regular ddiv_fast
#if defined(__ARM_PCS_VFP)
vmov r0,r1,d0
vmov r2,r3,d1
#endif
dcp_ddiv_fast_m r0,r1,r0,r1,r2,r3,r0,r1,r2,r3,r12
#if defined(__ARM_PCS_VFP)
vmov d0,r0,r1
#endif
saving_func_return

double_wrapper_section __aeabi_ddiv
Expand All @@ -125,40 +132,99 @@ saving_func wrapper __aeabi_ddiv

double_section sqrt_fast
saving_func regular sqrt_fast
#if defined(__ARM_PCS_VFP)
vmov r0,r1,d0
#endif
dcp_dsqrt_fast_m r0,r1,r0,r1,r0,r1,r2,r3,r12
#if defined(__ARM_PCS_VFP)
vmov d0,r0,r1
#endif
saving_func_return

double_wrapper_section sqrt
saving_func wrapper sqrt
#if defined(__ARM_PCS_VFP)
vmov r0,r1,d0
#endif
@ with correct rounding
dcp_dsqrt_m r0,r1,r0,r1,r0,r1,r2,r3,r12
#if defined(__ARM_PCS_VFP)
vmov d0,r0,r1
#endif
saving_func_return

double_section dclassify
saving_func regular dclassify
#if defined(__ARM_PCS_VFP)
vmov r0,r1,d0
#endif
dcp_dclassify_m apsr_nzcv,r0,r1
saving_func_return

// ============== CONVERSION FUNCTIONS ===============

double_wrapper_section __aeabi_d2f
#if defined(__ARM_PCS_VFP)
saving_func wrapper __aeabi_d2f
#else
saving_func wrapper __aeabi_d2f double2float
#endif
@ with rounding
dcp_double2float_m r0,r0,r1
saving_func_return

#if defined(__ARM_PCS_VFP)
double_section double2float
regular_func double2float
push {lr}
vmov r0,r1,d0
bl WRAPPER_FUNC_NAME(__aeabi_d2f)
vmov s0,r0
pop {pc}
#endif

double_wrapper_section __aeabi_i2d
#if defined(__ARM_PCS_VFP)
saving_func wrapper __aeabi_i2d
#else
saving_func wrapper __aeabi_i2d int2double
#endif
dcp_int2double_m r0,r1,r0
saving_func_return

#if defined(__ARM_PCS_VFP)
double_section int2double
regular_func int2double
push {lr}
bl WRAPPER_FUNC_NAME(__aeabi_i2d)
vmov d0,r0,r1
pop {pc}
#endif

double_wrapper_section __aeabi_ui2d
#if defined(__ARM_PCS_VFP)
saving_func wrapper __aeabi_ui2d
#else
saving_func wrapper __aeabi_ui2d uint2double
#endif
dcp_uint2double_m r0,r1,r0
saving_func_return

#if defined(__ARM_PCS_VFP)
double_section uint2double
regular_func uint2double
push {lr}
bl WRAPPER_FUNC_NAME(__aeabi_ui2d)
vmov d0,r0,r1
pop {pc}
#endif

double_section double2fix_z
saving_func regular double2fix_z
#if defined(__ARM_PCS_VFP)
mov r2, r0
vmov r0, r1, d0
#endif
ubfx r3, r1, #20, #11
adds r3, r2
beq 1f // very small; we don't care that we might make a denormal
Expand All @@ -173,6 +239,10 @@ saving_func regular double2fix_z

double_section double2ufix
saving_func regular double2ufix_z double2ufix
#if defined(__ARM_PCS_VFP)
mov r2, r0
vmov r0, r1, d0
#endif
double2ufix_z_entry:
ubfx r3, r1, #20, #11
adds r3, r2
Expand All @@ -188,6 +258,10 @@ double2ufix_z_entry:

double_section double2fix
saving_func regular double2fix
#if defined(__ARM_PCS_VFP)
mov r2, r0
vmov r0, r1, d0
#endif
ubfx r3, r1, #20, #11
cbz r3, 2f // 0 or denormal
adds r3, r2
Expand All @@ -207,6 +281,9 @@ saving_func_return

double_section double2int
saving_func regular double2int
#if defined(__ARM_PCS_VFP)
vmov r0, r1, d0
#endif
double2int_entry:
lsls r2, r1, #1
bcc double2int_z_entry // positive is ok for int64_z
Expand All @@ -230,29 +307,62 @@ double2int_entry:
saving_func_return

double_wrapper_section __aeabi_d2iz
#if defined(__ARM_PCS_VFP)
saving_func wrapper __aeabi_d2iz
#else
saving_func wrapper __aeabi_d2iz double2int_z
#endif
double2int_z_entry:
@ with truncation towards 0
dcp_double2int_m r0,r0,r1
// note: this works with either saved or not saved call as it is just a `bx lr`
saving_func_return

#if defined(__ARM_PCS_VFP)
double_section double2int_z
regular_func double2int_z
vmov r0,r1,d0
push {r4,lr}
bl WRAPPER_FUNC_NAME(__aeabi_d2iz)
pop {r4,pc}
#endif

double_wrapper_section __aeabi_d2uiz
#if defined(__ARM_PCS_VFP)
saving_func wrapper __aeabi_d2uiz
#else
saving_func wrapper __aeabi_d2uiz double2uint double2uint_z
#endif
double2uint_z_entry:
@ with truncation towards 0
dcp_double2uint_m r0,r0,r1
saving_func_return

#if defined(__ARM_PCS_VFP)
double_section double2uint
regular_func double2uint
regular_func double2uint_z
vmov r0,r1,d0
push {r4,lr}
bl WRAPPER_FUNC_NAME(__aeabi_d2uiz)
pop {r4,pc}
#endif

double_section double2int_r
saving_func regular double2int_r
@ with rounding
#if defined(__ARM_PCS_VFP)
vmov r0,r1,d0
#endif
dcp_double2int_r_m r0,r0,r1
saving_func_return

double_section double2uint_r
saving_func regular double2uint_r
@ with rounding
#if defined(__ARM_PCS_VFP)
vmov r0,r1,d0
#endif
dcp_double2uint_r_m r0,r0,r1
saving_func_return

Expand Down
Loading
Loading