• I usually pass floats in flat arrays in and out of compiled C via pointers in my code, so I am not sure where the passing in registers comes in here...

    Yes, in that case it won't be an issue. I think it's when trying to call a function like void foo(float) - but Espruino doesn't support automatically converting floats anyway, so I think you'd have to do:

    foo((new Uint32Array((new Float32Array([1234])).buffer)[0])
    

    So it's a bit contrived.

    However @fanoush you're totally right - we don't pass any floats into the library, so I guess as long as it's not using anything external it doesn't really matter. It's just a matter of convincing the Linker it's ok, as that was what was throwing the error before.

    So I guess it may be enough to edit the .o files headers so that GCC thinks they are softfp?

    As you say, since Espruino uses doubles for most stuff the hardfp doesn't feel like it'd be needed. And in fact double passing may in fact be an issue (or maybe it's just for floats?). In the current build Espruino assumes the doubles are passed in registers/stack just like ints - so switching to hardfp may actually break stuff (although in initial tests it doesn't seem to have).

    Does the proprietary firmware also provide a SpO2 value?

    @user140377 The one included at the moment doesn't. There are separate binaries for SpO2 sensing that could be included, but you have to put the sensor into a special mode first where it samples a lot faster and also samples the Infrared at the same rate.

    It's definitely possible and I can provide the binaries to anyone who is interested in looking into it, but it's quite a lot of work.

  • we don't pass any floats into the library, so I guess as long as it's not using anything external it doesn't really matter. It's just a matter of convincing the Linker it's ok, as that was what was throwing the error before.

    Yes, and when dumping the object files I don't even see any floating point code inside at all. it is all integer math.

    ~/Espruino/libs/misc/vc31_binary$ for i in  *.o  ; do arm-none-eabi-objdump -d $i ; done | grep vmov
    

    gives nothing.

    I tried to make a library from it

     arm-none-eabi-gcc-ar -cr libvc31.a *.o
    arm-none-eabi-gcc-ranlib libvc31.a
    

    and trying to pass LDFLAGS += -Llibs/misc/vc31_binary -lvc31
    but it didn't work- it cannot find that Algo_ methods in such library. I guess it is becasue of LTO and the library may not be well made for LTO.

    I see the
    ld: error: libs/misc/vc31_binary/algo.o uses VFP register arguments, bin/espruino_2v17.47_banglejs2.elf does not error. Also tried to strip

    arm-none-eabi-strip -N 'BuildAttributes$$THM_ISAv4$E$P$D$K$B$S$7EM$VFPi3$EXTD16$VFPS$VFMA$PE$A:L22UL41UL21$X:L11$S22US41US21$IEEE1$IW$USESV6$~STKCKD$USESV7$~SHL$OSPACE$EBA8$REQ8$PRES8$EABIv2' *.o 
    

    and looks like it is gone from .o files but this was not enough so the flag is somewhere else.

    But still if you see hardfp being faster then it is also good. But I find it strange since it must shuffle between those registers more than before, if you check https://gist.github.com/fanoush/0da3e47aee9e20fb11b010cc3aa4e16e then it can be seen that for math operation * it calls __aeabi_dmul which has softfloat convention even if file was compiled with -mfloat-abi=hard so the __hard_f2d and __hard_powd there needs to unpack arguments from vfp to integer register before calling the multiplication eabi builtin (unlike the first f2d method or __softfp_powd that just calls it directly). So I wonder what else offsets this extra code to still make it faster.

  • So I guess it may be enough to edit the .o files headers so that GCC thinks they are softfp?

    I tried the objcopy trick from https://stackoverflow.com/a/51439150 and it links fine. Not sure whether it still works :-)

About

Avatar for Gordon @Gordon started