Cortex M0+ math lib - Page 1
Forum section: electronics / general

author: analityk
author_rank: Regular Contributor
timestamp: November 19, 2023, 03:17:12 pm
content: How it is work: calculations of sine function on avr cost few kB of code added once for near all math functions but when I was trying to calculate sine function on Cortex M0+ it cost more than 16kB code and much SRAM so it was useles on 32 kB devices.It was on PSoC4 cy4245axi uC.Calculate FFT and IFFT on avr is slow but cost 5kB flash but on fancy 48MHz uC is unobtainable. Is this GCC configurations or default libraries? How to use sin or exp on Cortex M0+?

author: ataradov
author_rank: Super Contributor
timestamp: November 19, 2023, 05:03:52 pm
content: Generic GCC libraries are not extremely optimized specifically for Cortex-M0. One thing you can do to reduce the code size is to make sure you are only using single precision values and function.This code is 12.6 KB:Code:volatile float a = 123.456;volatile float b = sin(a);And this code is 8.3 KB:Code:volatile float a = 123.456f;volatile float b = sinf(a);Also note that the function itself is small, but it calls a lot of common support code, so incremental size increase is less significant after you take the first hit.There are likely hand-optimized versions of the FTT, but I have not looked for them.

author: DavidAlfa
author_rank: Super Contributor
timestamp: November 19, 2023, 05:39:53 pm
content: Also code for arm will be larger due the different architecture, load-and-store needs more instructions as every variable address must be loaded into a register before accessing it, avr and pic can do this with one instruction most of the time, except when requiring bank switching.Also avr code likely used simple floats instead doubles.

author: analityk
author_rank: Regular Contributor
timestamp: November 19, 2023, 05:40:59 pm
content: There is not problem with FFT itself but definitely with sin, cos and exp function.

author: ArdWar
author_rank: Frequent Contributor
timestamp: November 19, 2023, 05:41:42 pm
content: Try using size optimized library like picolibc or newlib-nano instead and see if there's improvement. Heck, that should be de facto "standard" library for most MCU projects.The standard glibc are optimized for portability and isn't exactly known for its compactness or speed. However it still shouldn't be 16KB, hmm...

author: DavidAlfa
author_rank: Super Contributor
timestamp: November 19, 2023, 05:43:54 pm
content: But, as you've been told, usesinf, cosf, expf, otherwise you'll be using doubles, with much larger and slower libs than single precision floats.Probably he's using newlibnano already, most if not all arm-gcc toolchains use it?

author: gf
author_rank: Super Contributor
timestamp: November 19, 2023, 05:44:43 pm
content: Quote from: analityk on November 19, 2023, 03:17:12 pmTo compute the FFT, you typically don't evaluate sin/cos on the fly, but use a pre-calculated sin/cos lookup table.

author: iMo
author_rank: Super Contributor
timestamp: November 19, 2023, 05:45:30 pm
content: .. and do not include printf()..

author: langwadt
author_rank: Super Contributor
timestamp: November 19, 2023, 05:54:16 pm
content: Quote from: ataradov on November 19, 2023, 05:03:52 pmthere's also arm_math.h and lib, though I don't know if it is optimized for size or performance

author: gf
author_rank: Super Contributor
timestamp: November 19, 2023, 06:09:44 pm
content: Quote from: gf on November 19, 2023, 05:44:43 pmAnd on a CPU without an FPU, you might consider doing your computations in fixed-point if speed is important.Quote from: langwadt on November 19, 2023, 05:54:16 pmFor Cortex-M, there is also the CMSIS-DSP library, which also includes fast sin/cos functions (for float, q15, q31), and a set of FFT functions.

author: langwadt
author_rank: Super Contributor
timestamp: November 19, 2023, 06:20:21 pm
content: Quote from: gf on November 19, 2023, 06:09:44 pmthat's the lib for with arm_math.h

author: AVI-crak
author_rank: Regular Contributor
timestamp: November 19, 2023, 06:58:49 pm
content: Stop raping the Cortex M0, it's in a lot of pain.

author: nctnico
author_rank: Super Contributor
timestamp: November 19, 2023, 07:07:53 pm
content: Quote from: analityk on November 19, 2023, 03:17:12 pmProbably the libraries. This is the right time to take a look under the hood and see what gets linked into the executable. The best way is to let the linker create a map file; this file shows the size of each function and variable in memory (and where it comes from) which is super useful information. Likely there are options in the IDE to choose which libraries to use.

author: Siwastaja
author_rank: Super Contributor
timestamp: November 19, 2023, 07:21:09 pm
content: Often a simple lookup table and fixed point numbers get the job done. Also if you can convert angles into 2*pi rad == 2^n (e.g., 360 degrees = 256 units), then you can directly lookup a table like sine_table[(uint8_t)angle] for 256 elements with automagic zero-cost wrap-around, or sine_table[angle&mask] for other values of 2^n. You can even bake in any constant multipliers into the table itself for further savings.What are your accuracy requirements, i.e. what are you doing?

author: langwadt
author_rank: Super Contributor
timestamp: November 19, 2023, 08:48:49 pm
content: Quote from: Siwastaja on November 19, 2023, 07:21:09 pmthat is basically what is in the CMSIS DSP lib,https://github.com/ARM-software/CMSIS_4/tree/master/CMSIS/DSP_Lib/Source/FastMathFunctions

author: SiliconWizard
author_rank: Super Contributor
timestamp: November 19, 2023, 10:08:07 pm
content: If you absolutely need floating point (not sure), you can have a look at that:https://www.quinapalus.com/qfplib.htmlGreat stuff.

author: brucehoult
author_rank: Super Contributor
timestamp: November 19, 2023, 10:08:39 pm
content: Quote from: DavidAlfa on November 19, 2023, 05:39:53 pmWhy do people confidently post information that is false, especially when it can be easily checked? We just had someone in another thread claim that AVR passes function arguments on the stack.https://en.wikipedia.org/wiki/Atmel_AVR_instruction_setAVR also has a "load-and-store" architecture. The load and store instructions do only that. The arithmetic instructions take all their operands from registers and put the result in registers.Cortex-M0 instructions and AVR instructions are the same size, 2 bytes, but as the Arm is dealing with data 4 bytes at a time while the AVR is operating on 1 byte at a time (except MOVW, ADDIW, SUBIW, which operate on two 1-byte registers) you will find that if you are dealing with values larger than 1 byte then for the same algorithm Arm code will always be smaller than AVR code because the AVR needs 4 instructions to deal with 4-byte values -- and a lot more instructions than that for multiply.I guess it's good in a way that people can successfully use these devices just using C without really knowing what is going on underneath.

author: langwadt
author_rank: Super Contributor
timestamp: November 19, 2023, 10:42:33 pm
content: Quote from: DavidAlfa on November 19, 2023, 05:39:53 pmafaik avr-gcc implements all floating-point arithmetic both 'float' and 'double' as 32-bit

author: analityk
author_rank: Regular Contributor
timestamp: November 19, 2023, 11:01:27 pm
content: So many replies, i was not expect that.First of all - I used the DSP in CM-SIS from ARM on a much larger uC (SAME70Q21 - 300MHz cortex m7 with so many kB of flash.... those few kB were not a problem at the time, so I didn't worry about it then). Everything worked as expected.My goal is to use as little flash per code (and SRAM, there is only 4kB) as practically possible. This time I collected (saved) the data and the speed of calculations does not matter, although I expect faster calculations than on the AVR. I know that there is no FPU, even the basic instruction set is smaller, but I still think that the calculation of the sine function should not cost 20kB of flash.Comparasion with AVR is good in terms of code size. Why we can not use avr library on Cortex M0+? Single floating-point arithmetic is good enough for me.I'll check dsp from cmsis package and if it doesn't bring a solution, I'll come back here.deepl is good bro

author: brucehoult
author_rank: Super Contributor
timestamp: November 19, 2023, 11:20:59 pm
content: Quote from: langwadt on November 19, 2023, 10:42:33 pmThat is correct. Also the FP functions are optimised for speed and small code, not strict IEEE-754 compliance and 0.5 ULP accuracy on basic functions like the Arm ones will be.

author: nctnico
author_rank: Super Contributor
timestamp: November 19, 2023, 11:56:08 pm
content: Quote from: analityk on November 19, 2023, 11:01:27 pmIf you have the source code for the AVR library AND it is all written in C, you should be able to compile it for ARM without much trouble. I have been using the C library that comes with very old versions of MSP430-GCC for my ARM projects for ages because it is so small.

author: brucehoult
author_rank: Super Contributor
timestamp: November 20, 2023, 12:55:12 am
content: Quote from: nctnico on November 19, 2023, 11:56:08 pmEveryone does.https://github.com/avrdudes/avr-libc/tree/main/libm/fplibQuoteAhahahahahaha.

author: tridac
author_rank: Regular Contributor
timestamp: November 20, 2023, 01:00:38 am
content: Math libs are often not that efficient, because they are expected to handle generalised conditions. Try to avoid math lib for embedded work, and prefer to use, depending on resolution, for example, a single quadrant sine lookup table, then perhaps interpolate for finer resolution. Say, use a 1 k lookup table, single quadrant, then use reflection and inversion for the remaining quadrants. Much faster than brute force calculation and more memory efficient as well. Optimise for the project requirements etc...

author: DavidAlfa
author_rank: Super Contributor
timestamp: November 20, 2023, 04:59:19 am
content: Quote from: brucehoult on November 19, 2023, 10:08:39 pmYep, sorry, I never used AVR, for some reason I mistakenly thought they were Harvard architecture like PICs.Check this CM0 math lib, states to use only 1KB:https://github.com/mysterywolf/Qfplib-M0-tinyYou have to set include_scientific=1 :Quote

author: brucehoult
author_rank: Super Contributor
timestamp: November 20, 2023, 06:55:54 am
content: Quote from: DavidAlfa on November 20, 2023, 04:59:19 amThey are.Harvard and load/store (the main part of RISC) are unrelated properties.Harvard architecture means instructions and data come on different buses -- traditionally different address spaces -- so that loads and stores do not interfere with fetching the next instruction.High performance CPUs such as in PCs have been pseudo-Harvard since the 80386 and 68020 (and even, optionally, Cortex M7) in that they fetch instructions from a small instruction cache, which is in the same address space as data but keeps copies of recently used instructions. From time to time the instruction cache has to be synchronised with any changes made to those memory locations by the data bus side of the CPU.Arm's load/store (or push/pop) multiple registers instructions were included primarily to decrease instruction fetch conflicts. They are not so useful (at least for speed) if you have an icache and Arm dropped them in Arm64.

author: gf
author_rank: Super Contributor
timestamp: November 20, 2023, 08:14:24 am
content: There is also this fixed-point FFT implementation:https://gist.github.com/Tomwi/3842231Certainly not as optimized as some other FFT libs, but completely self-contained and no externals libs required.Compiles to less than 600 bytes of code for the cortex-m0 with gcc -Os, plus the space required for the sine table (1.5 kiB for 1024 points).

author: westfw
author_rank: Super Contributor
timestamp: November 23, 2023, 10:33:47 pm
content: Quote from: ataradov on November 19, 2023, 10:03:52 amYeah, that. "popular" architectures will get a carefully hand-written set of software floating point function, usually written in assembly language, and designed for speed and/or space efficiency. If no one has written such a library for an architectures, gcc "falls back" to some very generic floating point libraries written in C. I'm sure it's all correct and complete, but it is neither fast nor small :-(avr-gcc has an assembly-language math library for 32bit floats.arm-v7m (CM3, CM4, etc) has an assembly language math library for both 32 and 65 bit floats.arm-v6m (CM0, CM0+) doesn't, and uses the generic gcc C functions. (last time I looked. anyway.)QuoteYes; highly recommended. They fit a relatively complete 32bit float library for CM0 in 1k, a more complete and faster 32/64 bit float library for CM0 in 6k, and have an improved CM3 library as well.The RPi Pico has adopted qfplib as their standard float library in their SDK, and put the qfplib functions in ROM. (alas, not all development environments include all the magic linker statements needed to make this work.)

author: nctnico
author_rank: Super Contributor
timestamp: November 23, 2023, 10:36:19 pm
content: Unfortunatly qfplib is under the GPL license so no go for commercial projects.

author: DavidAlfa
author_rank: Super Contributor
timestamp: November 23, 2023, 11:16:09 pm
content: No problem with gpl license and commercial projects.Basically, you simply have to indicate it somewhere (I.E. in the manual), listing the GPL software used and linking to their sources.The code will be still under GPL license if you modify it for your needs.Companies might ship the GPL code in the CD/DVD having the PC software, or in their website (Very common to see User manual, PC software, firmware update... And GPL code), or making a GitHub account and uploading it there.Usually you find thw bunch of libraries used in the fw, and that's it, nothing about the propietary firmware itself.Private code is still private, no sharing required, it's completely your's.

author: brucehoult
author_rank: Super Contributor
timestamp: November 23, 2023, 11:16:40 pm
content: Quote from: westfw on November 23, 2023, 10:33:47 pmCorrectly rounded to even 0.5 ULP +-*/ in 1 KB is quite impressive. The overview page doesn't say whether that includes denorms, but as they claim IEEE compliance and don't say it doesn't, I assume that it does.Most MCU software doesn't require that level of accuracy -- when your ADC is 10 or 12 bits it doesn't matter whether your maths is accurate to 23 bits or only 20 -- so an even smaller library is possible.

author: brucehoult
author_rank: Super Contributor
timestamp: November 23, 2023, 11:20:21 pm
content: Quote from: DavidAlfa on November 23, 2023, 11:16:09 pmUnder GPL2 (which this uses) for PC software where you ship the GPL code as a DLL, yes, because the user can replace the library with a different library, or newer version, or whatever.If you statically link then you must make all of your commercial code open source also.Embedded code, in a ROM, is by definition statically linked.

author: nctnico
author_rank: Super Contributor
timestamp: November 23, 2023, 11:21:22 pm
content: Quote from: DavidAlfa on November 23, 2023, 11:16:09 pmYes it is. Or do you want to have a runtime linker on your MCU to link the library dynamically at startup? Last time I checked GPL prohibits linking code statically into closed source projects without disclosing the source of the entire project.https://www.revenera.com/blog/software-composition-analysis/field-notes-understanding-gpl-linking-exceptions/

author: SiliconWizard
author_rank: Super Contributor
timestamp: November 23, 2023, 11:50:22 pm
content: Quote from: brucehoult on November 23, 2023, 11:16:40 pmI will check that out.Quote from: brucehoult on November 23, 2023, 11:16:40 pmYes, and often FP is not required at all either. But people like it because it's usually much easier to deal with than fixed point.(Note that the FP library provided in ROM for the RP2040 is based on qfplib AFAIR.)

author: nimish
author_rank: Regular Contributor
timestamp: November 23, 2023, 11:57:42 pm
content: Quote from: brucehoult on November 23, 2023, 11:20:21 pmStrictly, no. There is no settled definition of what a derivative work w.r.t. the GPL means that matters to a court (yet). If this matters to you, consult an IP lawyer.Do not rely on the internet to determine what is and isn't distribution, linkage and other critical terms or you might regret it. There are always ways to isolate code and argue it's communicated over a "network" or in a separate executable process, or other such workarounds -- hence the AGPL.Every RTOS worth its salt has a dynamic linker built in, so this is not an academic exercise.

author: Nominal Animal
author_rank: Super Contributor
timestamp: November 24, 2023, 01:55:22 am
content: Free Software Foundation, the authors of the GPL license, are of the opinion thatLinking a GPL covered work statically or dynamically with other modules is making a combined work based on the GPL covered work. Thus, the terms and conditions of the GNU General Public License cover the whole combination.While one can argue whether this is the correct understanding of derivative work in any particular legal jurisdiction, I personally would take heed, especially because of the associatedSoftware Freedom Conservancy's Copyleft Compliance programs.In particular, you might wish to read about theThe Strategic GPL Enforcement Initiative, and theFirmware Liberation Project(which albeit focusing on Linux-based systems, is exactly about combining GPL-licensed works with proprietary code).So no, please do not assume that you can dynamically link GPL-licensed libraries to proprietary binaries.The LGPL license is the one that explicitly allows linking with proprietary code, without pulling that proprietary code under the LGPL license. From theGPL FAQ:Does the LGPL have different requirements for statically vs dynamically linked modules with a covered work?Quote from:This is how for example one can useLGPL-licensed Qt modulesto create a commercial application with proprietary components, without purchasing a commercial Qt license. For example, one can use Python for the UI, dynamically linking to the standard Qt dynamic libraries, but also to your own proprietary dynamic libraries. (Python itself provides the relinking mechanism, as the user only needs to replace the dynamic library file with a different one.)As toavr-libc, it is licensed under amodified BSD license, which explicitly allows its use in proprietary applications. Similarly,newlib(or newlibc) is licensed underBSD- and MIT-style licenses, allowing its use in proprietary applications. TheGNU C libraryitself is licensed under LGPL 2.1, allowing its use with proprietary applications, noting the points from the LGPL FAQ above.As toQfplib(and its variants), it is licensed under GPL v2, and I do not know of any way to use it in a proprietary firmware whose source will not be available to the customers. Regardless of whether one links statically or dynamically, the combined work falls under the GPL license, as far as I am concerned.You will get better results by contacting the authors, explaining your use case and business model and asking for a separate license (perhaps LGPL), than concocting a novel legal theory that allows you to use GPL-licensed libraries as if they were LGPL-licensed originally.

author: DavidAlfa
author_rank: Super Contributor
timestamp: November 24, 2023, 04:35:56 am
content: Quote from: brucehoult on November 23, 2023, 11:20:21 pmAh! I'm used to see gpl in devices running an OS, so they do as you say, ”gpl used: libjpeg, busybox..., here you have their tar files".Didn't know the static thing. Thanks for the lesson!

author: cfbsoftware
author_rank: Regular Contributor
timestamp: November 24, 2023, 04:49:56 am
content: Quote from: analityk on November 19, 2023, 11:01:27 pmThat certainly sounds excessive. Is that just the calculation of the sine function or are you including the code required to show results, trap runtime errors etc.?For comparison, the 32-bit FPU and Math (ArcTan, Cos, Exp, Ln, Sin and Sqrt) libraries written in the Oberon language that we use in the Astrobe compiler for Cortex-M0 on STM32 hardware are only 1312bytesand 2632bytesof code respectively.

author: SiliconWizard
author_rank: Super Contributor
timestamp: November 24, 2023, 07:35:23 am
content: RISC-V has its own, but it's only arithmetic operations:https://github.com/pulp-platform/RVfplibThe license is GPL3.

author: westfw
author_rank: Super Contributor
timestamp: November 24, 2023, 10:09:18 pm
content: Quote from: DavidAlfa onYesterdayat 04:16:09 pmThat could be true if it were licensed LGPL (maybe: AFAIK, FSF (still!) doesn't have clear guidance for how LGPL applies to deeply embedded microcontroller code (ROM/Flash/etc), but QFPLIB is very explicitly NOT LGPL.OTOH, the qfplib author says that they have alternate licensing schemes available for commercial use. Unless you've investigated them, you shouldn't eliminate it as a possibility.(huh. I wonder if the RPi ROMed qfplib counts as "dynamically linked"? On the one hand, a user's application will contain none of the GPL code, just "OS calls." OTOH, being in ROM and thus not user-replaceable seems to go against the intended spirit. ("It's a trap: the ROM code is OK to use commerically, but if you need to upgrade the FP code (via static linking with a new version of the library), WHAM!")

author: SiliconWizard
author_rank: Super Contributor
timestamp: November 24, 2023, 11:01:38 pm
content: Quote from: westfw on November 24, 2023, 10:09:18 pmqfplib's team mentions it:QuoteGiven that the team openly talks about it, and it's been modified for the RP2040, so a derivative work AFAICT, I'm pretty sure they have arranged an appropriate licensing for the RPi foundation. That wasn't just "let's use that in our chip and see if we get away with it."I'm all the more convinced about the fact they've likely contracted a commercial license, for the reason that they have modified the library and the RPi haven't released the modified source code (at least AFAIK, if you can find the source code for the ROM FP library officially released, then I'm wrong.) Imagine that under a GPL license.

author: westfw
author_rank: Super Contributor
timestamp: November 25, 2023, 03:06:24 am
content: Quotehttps://github.com/raspberrypi/pico-bootrom/tree/master/bootrommufplib.S, mufplib-double.SBut you're notwrong, either...Code:/*** Copyright (c) 2020 Mark Owen https://www.quinapalus.com .** Raspberry Pi (Trading) Ltd (Licensor) hereby grants to you a non-exclusive license to use the software solely on a* Raspberry Pi RP2040 device. No other use is permitted under the terms of this license.

author: SiliconWizard
author_rank: Super Contributor
timestamp: November 25, 2023, 03:27:54 am
content: Ah thanks, didn't know they had released the source code for the boot rom entirely. Cool stuff.Yes, it would still look like this is a commercial license. Since the RPi released the source code, I'm not entirely sure why they have not been able to use the GPL. Other than they didn't want to have to license the bootrom source code under the GPL itself. Which may have its own reasons.Given that there seems to be an exclusive copyright of Mark Owen (the owner of quinaplus) in the modified files, I'm assuming *he* did optimize the library for the RP2040, and not someone from the RPi's team, probably as contract work. Just a guess.