Re: devel/arm-none-eabi-newlib headers inconsistencies (not functional) or am I misusing something?

From: Mark Millard <marklmi_at_yahoo.com>
Date: Sat, 27 May 2023 10:18:03 UTC
On May 27, 2023, at 02:13, José Pérez <fbl@aoek.com> wrote:

> El 2023-05-26 18:53, José Pérez escribió:
>> Hi,
>> a source as simple as this does not compile with
>> devel/arm-none-eabi-newlib installed
>> #include <stdio.h>
>> int main(int argc, char *argv[]) {
>>  return 0;
>> }
> 
> I elaborate a little more with the hope to understand how to wire things
> up the proper way.
> 
> devel/arm-none-eabi-newlib is not a dependency of devel/arm-none-eabi-gcc
> (but it should?).

devel/arm-none-eabi-gcc is used by other ports without
having devel/arm-none-eabi-newlib installed. Examples
include:

sysutils/atf-rk3399
sysutils/u-boot-a13-olinuxino
. . .
sysutils/u-boot-master
. . .
sysutils/u-boot-orangepi-plus-2e
. . .
sysutils/u-boot-rpi2
. . .

devel/arm-none-eabi-gcc can be built and used
for various purposes without ever having built
or installed devel/arm-none-eabi-newlib .


But devel/arm-none-eabi-newlib has a build
dependency on devel/arm-none-eabi-gcc .
(Which means that devel/arm-none-eabi-gcc
can not depend on devel/arm-none-eabi-newlib .)


> When only devel/arm-none-eabi-gcc is installed
> (which btw correctly installs arm-none-eabi-binutils as a dependency)
> the compiler is unusable:

The compiler is usable and I use it,
just not for what you are trying to do.

> % arm-none-eabi-gcc break_arm.c

You need command line options to tell
arm-none-eabi-gcc to use the
devel/arm-none-eabi-newlib materials.
It is not the default/automatic. 

> /usr/local/bin/arm-none-eabi-ld: cannot find crt0.o: No such file or directory
> /lib/libc.so.7: file not recognized: file format not recognized
> collect2: error: ld returned 1 exit status
> 
> Do you think this missing port dependency

No dependency is missing. Command line options
are missing that would be required for what you
are trying to do.

> should be fixed or is it ok
> to leave it as it is now?

Leave it as it is.

> Looking at the missing types more closely, arm-none-eabi-gcc header
> search path defaults as follows:
> /usr/local/lib/gcc/arm-none-eabi/11.3.0/include
> /usr/local/lib/gcc/arm-none-eabi/11.3.0/include-fixed
> /usr/local/arm-none-eabi/include
> /usr/include

You need to tell the compiler to use non-default paths.
devel/arm-none-eabi-newlib has its files in:

/usr/local/arm-none-eabi/

Not in:

/usr/local/lib/gcc/arm-none-eabi

You reported that it found 

/usr/local/lib/gcc/arm-none-eabi/11.3.0/include-fixed/stdio.h

instead of:

/usr/local/arm-none-eabi/11.3.0/include-fixed/stdio.h

That is because tegh default search paths are
wrong for your purpose. You need
/usr/local/lib/gcc/arm-none-eabi to be first (or
the only entry).

> devel/arm-none-eabi-gcc populates the former two and
> devel/arm-none-eabi-newlib populates the third.

True. But the files under:

/usr/local/lib/gcc/arm-none-eabi/11.3.0/include
and
/usr/local/lib/gcc/arm-none-eabi/11.3.0/include-fixed

are found and used instead of what is under:

/usr/local/lib/gcc/arm-none-eabi

when there is a file name match. You reported
the it found and used the wrong stdio.h in your
original message:

/usr/local/lib/gcc/arm-none-eabi/11.3.0/include-fixed/stdio.h

You need /usr/local/lib/gcc/arm-none-eabi to be
first in the search path used. That requires
command line options to be supplied.

> Both ports relay on a number of types defined in /usr/include

If /usr/local/lib/gcc/arm-none-eabi is first in the search
path, then it will find all the files it needs from there,
no matter what the later search path entries may be.

None of the FreeBSD headers should be used for your
purpose, only headers from under
/usr/local/lib/gcc/arm-none-eabi . A similar point goes
for the types of files used in linking.

> and those files are opaqued out by files by the same name, but
> significantly different content,

and are the wrong files for it to use for your
purpose. You need it to find and use the files
under /usr/local/lib/gcc/arm-none-eabi instead.

> located in directories appearing
> earlier in the search path.
> 
> __off_t, __ssize_t, __off64_t, __mbstate_t and __va_list are
> defined in the system default header:
> /usr/include/sys/_types.h:94:typedef       __int64_t       __ssize_t;      /* byte count or error */
> /usr/include/sys/_types.h:97:typedef       __int32_t       __ssize_t;      /* byte count or error */
> /usr/include/sys/_types.h:133:typedef      __int64_t       __off_t;        /* file offset */
> /usr/include/sys/_types.h:134:typedef      __int64_t       __off64_t;      /* file offset (alias) */
> /usr/include/sys/_types.h:203:} __mbstate_t;
> /usr/include/sys/_types.h:211:typedef      __builtin_va_list       __va_list;      /* internally known to gcc */
> 
> Which is never included because /usr/local/arm-none-eabi/include/sys/_types.h
> exists and appears earlier in the search path.
> 
> Note that newlib's /usr/local/arm-none-eabi/include/sys/_types.h seems
> to be partially aware of the problem and does something, but it's not a
> full fix:
> 15:#ifndef __off_t_defined
> 16:typedef long _off_t;
> 17:#endif
> 
> Note how it checks for __off_defined (two underscores at the beginning of
> the type name) and defines _off_t (one underscore only).
> 
> The file also does similar fixes for a bunch of other types including
> __ssize_t, __off64_t and __mbstate_t that pop up while trying to
> compile my test .c file: i.e.
> it checks for __foo_t and, if not found, defines _foo_t but not __foo_t
> 
> Shall I patch newlib's sys/type.h to define also __foo_t, not only _foo_t
> or is there a bettere way to handle this?
> 
> 
> There is an exception: __va_list is not mentioned in newlib's headers
> but only system default sys/_types.h, so I suspect this is not an isolated
> case, and maybe a different approach shall be used? I.e. manually bring in
> all that is typedef'd in system defaults sys/_types.h and make sure there is
> a corresponding entry in newlib's version of the same file? Furthermore,
> how shall the missing types be defined? The types are defined differently
> by the system default and newlib.
> 
> E.g. __off_t (two underscores) in system default is:
> /usr/include/sys/_types.h:133:typedef      __int64_t       __off_t;        /* file offset */
> and _off_t (one underscore) in newlibs lingo is:
> /usr/local/arm-none-eabi/include/sys/_types.h:16-typedef long _off_t;
> 
> which might or might not be the same thing.
> 
> In any case, this solution smells bad to me, that's why I ask before I do anything.
> 

Your proposed change will break all the other uses
of devel/arm-none-eabi-gcc . You need to leave it
as is.

===
Mark Millard
marklmi at yahoo.com