On 8/27/23 01:06, Jacob Bachmeyer wrote:
As I understand the history, Linux was the first clearly Free kernel
available. At the time, BSD still had a dark cloud hanging over it
due to its (distant) origins at AT&T; the BSD and AT&T UNIX codebases
would not be legally recognized as separate until February 1994,
although BSD had honestly (almost?) completely diverged from the AT&T
codebase in June 1991 with Net/2. Mach was still proprietary; RMS was
(or would later be) campaigning for its liberation, which would not
occur until some years later. It is worth noting that Linux was
originally a toy kernel, and it only attracted the effort it did and
grew like it did because it was basically the last missing piece for
fully Free systems at the time.
Yes that is how I understand it too
Ah sorry, I shouldn't have made reference to JSON at all --- what I
really was getting at is the /abstract syntax/. In particular, rather
than having an abstract syntax of "list of strings" (parsing today's
concrete syntax by breaking on dash), where the meaning of each
string is ambiguous / context-sensative, we have of "keys mapped to
enumerations", i.e. one always knows the meaning of each component
explicitly / without inspecting it or its context.
JSON or your flat list in canonical ordering (where I assume we are
careful to never skip a type of component) are both valid concrete
syntaxes that can be parsed / printed from this abstract syntax.
JSON is far too complicated to use here, except possibly as a
"pre-parsed" form that config.sub could output on request for programs
that want a structured form instead of parsing the tuple themselves.
But for that case, why use JSON instead of a trivial multi-line
key=value format?
Hypothetical Example:
$ config.sub --parse x86_64-linux-gnu
cpu=x86_64
vendor=pc
kernel=linux
os=gnu
$
Note that this example both canonicalizes and parses.
Yes that looks great to me. This shares the abstract syntax with what I
had in mind, and anything that understands JSON can easily convert back
and forth between the two.
I argue for "duck-typing" here from the user's perspective: if and
only if the system in all meaningful ways appears to be the GNU
system, there should be a *-gnu* somewhere in the configuration tuple.
I am OK with duck-typing, but what is "all meaningful ways"? Sure, POSIX
is meaningful, the exact output of uname is not, etc. but where do we
draw the line?
This is also the framework in which *-*-linux-gnu-musl makes sense for
a system that uses Musl libc but is otherwise a GNU/Linux system.
Right but again where do we draw the line? For example, can one use
systemd and its large entourage of intertwined software, or must one use
GNU Shepherd or System V init?
Effectively, a different libc is a different ABI.
Agreed, especially when the syscall interface isn't stable, like with
many non-Windows kernels.
My larger goal here is to smooth the way for multi-arch systems, with
/usr/CPU-VENDOR-KERNEL-OS-ABI or so as the --prefix for binaries built
for each architecture. This means that configuration tuples should be
detailed enough to allow the needed distinctions, but not so detailed
as to themselves become an artificial incompatibility. In larger
networked environments, even KERNEL and OS could vary.
It's a great goal, and mine too! :)
Yeah whatever windows-something we settle on for MinGW, I promise my
offer still stands to try to get get LLVM to (a) accept it, and (b)
steer people away from windows-gnu towards it.
Thanks.
No problem! :)
This is the major expectation that using *-*-windows-gnu for MinGW
violates: GNU implements POSIX and MinGW does not. Using *-mingnu
still leaves considerable room for confusion in my view, which using
*-mingw avoids.
That is fine with me. Agreed "mingnu" takes the proper noun and turns it
back into a common noun phrase --- i.e. "minimal GNU" has many valid
interpretations while "MinGW" avoids that be being a known quantity.
After that, I think we are close enough to convene a working group
for a JSON/whatever explicit standard. And that would be amazing.
I still oppose JSON because it is way too verbose for this:
configuration tuples need to be both expressive and simple enough to
type at a shell prompt as arguments to configure. Using JSON by
default would also be a very nasty "flag day" that would break all
existing programs that use config.sub. Perhaps config.sub could
accept an --as=json parameter for JSON output?
Yes exactly, JSON is a no-go for prefixed binaries, but probably
better for things like Autoconf which needs to parse the output of
config.sub either way.
No, because Autoconf uses the shell and JSON is a [*profanity elided*]
to parse using shell constructs. A flat list of hyphen-delimited tags
is almost ideal for the parsing that configure needs to do. In fact,
with a few restrictions (met by using canonical ordering) this is what
configure /already/ parses.
Oops, yes I was being sloppy confusing concrete and abstract syntax
again. Sorry!
I think while that for something like Meson or CMake JSON could be
better, for Autoconf your ${key}=${value}\n format is perfect. Easy to
parse and fully disambiguated.
And of course, GNU config should care more about Autoconf than Meson or
CMake.
Note that config.sub is itself a shell script, and handling JSON in
shell is a giant pain. The most we could reasonably do is what
config.sub already does: determine each component as a separate
variable and then output that by substituting text into a template.
Yes I agree config.sub in its current form (must be highly portable
across different Bourne-shell derivatives) has no hope of parsing JSON.
It could output it or it could also output your ${key}=${value}\n
format, and it could also consume your format. Your format is ideal for it!
The hyphen-separated form is unambiguous as it stands, or close enough
to be resolvable with minimal effort. With a dictionary of allowed
element values, it is unambiguous, even if some elements are omitted;
resolving ambiguous forms to unambiguous forms using such a dictionary
is what config.sub /does/.
Yes config.sub should continue to take ambiguous format(s), because
normalizing them is its purpose. But see
08ede0dcc1bcfd8b77a80605d4de89c768cab2c7 where I also made sure
config.sub was idempotent, correcting some longstanding bugs in the process!
I think ensuring it is idempotent both on the ambiguous dash-separated
format, /and/ on the unambiguous key-value format, would make for a more
exacting additional impotency test suite.
Thank you; as I mentioned above, the goal is to best support
heterogeneous multi-arch systems, but recognizing a tension here. For
configure, the configuration tuple should not contain information that
can be determined by testing, but for storing multiple binary sets,
ABIs do need to be part of the name, even if they can be determined by
configure tests.
Agreed configure tests are better for the "long tail" of other
attributes. (IMO if we were to define "operating system", it would be
something like the "limit" of all configure checks.)
But a big part of my "kernel-libc" thinking (and I think also Connor's)
is that kernel + libc mostly determines on OS for toolchain purposes.
E.g. even if there exists both GNU-like and non-GNU linux-musl systems,
they can share the same prefixed binaries, so there is no need to
distinguish them at the config level.
Do you have a counter-example where a sameKernel-OS_0-sameLibc and a
sameKernel-OS_1-sameLibc would need different prefixed binaries, and
thus the inclusion of OS in addition to kernel and libc is necessary to
avoid binary name collisions?
(FWIW, since I use NixOS, I can always distinguish toolchains by
absolute path. Guix has the same property. This might have lead me to
miss cases over the years where the prefix was not enough! :))
I called the fifth field "LIBCABI" because it can be a libc name or an
ABI name; in practice the two are usually closely related. Some
existing tuples place a libc name in that slot, while others use a
more generic ABI or file format name, such as "elf" in your example.
For it to be a source of confusion, there would need to be a libc that
supports multiple ABIs, and you would simply use the ABI names in that
case.
Perhaps you know of examples of existing ones out in the wild that I am
not aware of that need to include kernel, OS, and libc? Do share if you do!
John