Hello, I have isolated the bare minimum of math functions that need to be provided by rtai_math.ko for LinuxCNC.
Currently, in both my master branch and RTAI mainline, rtai_math.ko depends on a C library (such as musl) to provide the math functions. Two problems come with this: 1.) It is undeniably clumsy to have such a library integrated into a kernel module. 2.) Warnings, lots of them. rtai_math.ko gets built (with a lot of EXPORT_SYMBOLS that are undefined right away) then becomes linked with a C library after the fact, which defines all those symbols that just spammed your terminal. Everything works as-is but this is not good practice. To solve the issue, I have imported the old RTAI math code (from RTAI 3 and 4) down to only what is needed: https://github.com/NTULINUX/RTAI/tree/tiny-math However it is to the best of my knowledge that LinuxCNC should also go with this patch along with that RTAI branch: diff --git a/src/rtapi/rtapi_math.h b/src/rtapi/rtapi_math.h index 1f3788081..99e16fd79 100644 --- a/src/rtapi/rtapi_math.h +++ b/src/rtapi/rtapi_math.h @@ -32,18 +32,19 @@ #if defined(__KERNEL__) extern double sin(double); extern double cos(double); -extern double tan(double); -extern double sqrt(double); -extern double fabs(double); -extern double atan(double); -extern double atan2(double, double); -extern double asin(double); -extern double acos(double); -extern double exp(double); -extern double pow(double, double); +#define tan(x) __builtin_tan(x) +#define sqrt(x) __builtin_sqrt(x) +#define fabs(x) __builtin_fabs(x) +#define atan(x) __builtin_atan(x) +#define atan2(y, x) __builtin_atan2(y, x) +#define asin(x) __builtin_asin(x) +#define acos(x) __builtin_acos(x) +#define exp(x) __builtin_exp(x) +#define pow(x, y) __builtin_pow(x, y) +#define fmod(x, y) __builtin_fmod(x, y) + extern double fmin(double, double); -extern double fmax(double, double); -extern double fmod(double, double); +#define fmax(x,y) __builtin_fmax(x,y) extern double round(double); extern double ceil(double); @@ -57,21 +58,6 @@ extern double floor(double); #define isinf(x) __builtin_isinf((x)) #define isfinite(x) __builtin_isfinite((x)) -extern __inline double atan (double __y) { - return atan2(__y, 1.); -} - -extern __inline double asin (double __x) { - return atan2(__x, sqrt (1.0 - __x * __x)); -} - -extern __inline double acos (double __x) { - return atan2(sqrt(1.0 - __x * __x), __x); -} - -extern __inline double fmax(double __y, double __x) { - return __y > __x || __builtin_isnan(__x) ? __y : __x; -} extern __inline double fmin(double __y, double __x) { return __y < __x || __builtin_isnan(__x) ? __y : __x; } The use of built-ins are fine since most of them aren't even used with RT, as noted in src/tests/mathtests.c: extern double sin(double); used in posemath, siggen, & noncartesian kins extern double cos(double); used in posemath, siggen, & noncartesian kins extern double tan(double); not used in RT extern double asin(double); not used in RT extern double acos(double); used in posemath & noncartesian kins extern double atan2(double, double); used in posemath & noncartesian kins extern double sinh(double); not used in RT extern double cosh(double); not used in RT extern double tanh(double); not used in RT extern double exp(double); not used in RT extern double log(double); not used in RT extern double log10(double); not used in RT extern double pow(double, double); not used in RT extern double sqrt(double); used in tc, segmot, & noncartesean kins. extern double ceil(double); used in segmot & emcpid extern double floor(double); used by siggen & segmot extern double fabs(double); used a lot in RT extern double ldexp(double, int); not used in RT I haven't tested the `tiny-math` RTAI branch paired with the use of LinuxCNC using GCC built-ins in a real world scenario, but runtests completed successfully, including the tests for math. I spoke to the musl developers on IRC, and they informed me that aside from some IEEE elementary functions, GCC does not actually define math functions. This information however conflicts with the information from RTAI (math/README.KLIBM) as noted here: ***************************** A FINAL IMPORTANT REMARK ***************************** Nowadays, depending of the gcc version and enabled compiler standard options (e.g. ISOC99) most of the functions provided by the RTAI kernel math support (rtai_math.ko) are compiler builtins. Therefore, it is likely that your applications will end in not using any of the rtai_math.ko functions. Thus, even if it is insmoded, it will do nothing. To check if such is the case and what functions of rtai_math.ko are being used eventually, you have just to insmod your application module without insmoding rtai_math.ko. You will then be able to see, just by using dmesg, the missing functions, if any, that will be provided by rtai_math.ko. "Most of the functions" (RTAI) is vague, but so is "aside from some IEEE elementary functions" (musl developers.) According to this page: https://gcc.gnu.org/onlinedocs/gcc/Other-Builtins.html GCC takes care of the following math functions actually used in LinuxCNC's RT code: acos (ISO C90 built-in) atan2 (ISO C90 built-in) sqrt (ISO C90 built-in) ceil (ISO C90 built-in) floor (ISO C90 built-in) Here is the interesting part: In the GCC doc in the link above, it says both sin and cos are _also_ ISO C90 built-ins however sincos (sincos, all one word) becomes undefined symbol in several LinuxCNC drivers when sin and cos are both switched to built-ins (like the other ones in the patch above) in src/rtapi/rtapi_math.h The problem might be related to these: https://gcc.gnu.org/bugzilla/show_bug.cgi?id=40393 https://gcc.gnu.org/bugzilla/show_bug.cgi?id=46926 I'm not sure how to fix this, I haven't played with LinuxCNC's CFLAGS much, perhaps someone can chime in and hopefully provide some insight. In any case, just to make sure the functions that have been switched to built-ins in this example still work, how much effort would it be to test this change and make sure things like acos, atan2, sqrt, ceil and floor are in fact working the way they should? With proper implementation, we could move away from depending on rtai_math.ko at all (at least according to the GCC docs and the documentation written by the RTAI developers) making all of this a non-issue. Open to any thoughts, opinions, and advice. Anything at all to try, I'm all ears! Thank you so much! Alec _______________________________________________ Emc-developers mailing list [email protected] https://lists.sourceforge.net/lists/listinfo/emc-developers
