Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

treewide: isArm -> isAarch32 #37401

Merged
merged 1 commit into from Apr 25, 2018
Merged

Conversation

Ericson2314
Copy link
Member

@Ericson2314 Ericson2314 commented Mar 20, 2018

Following legacy packing conventions, isArm was defined just for
32-bit ARM instruction set. This is confusing to non packagers though,
because Aarch64 is an ARM instruction set.

The official ARM overview for ARMv81 is surprisingly not confusing,
given the overall state of affairs for ARM naming conventions, and
offers us a solution. It divides the nomenclature into three levels:

ISA:             ARMv8   {-A, -R, -M}
                 /    \
Mode:     Aarch64     Aarch32
             |         /   \
Encoding:   A64      A32   T32

At the top is the overall v8 instruction set archicture. Second are the
two modes, defined by bitwidth but differing in other semantics too, and
buttom are the encodings, (hopefully?) isomorphic if they encode the
same mode.

The 32 bit encodings are mostly backwards compatible with previous
non-Thumb and Thumb encodings, and if so we can pun the mode names to
instead mean "sets of compatable or isomorphic encodings", and then
voilà we have nice names for 32-bit and 64-bit arm instruction sets
which do not use the word ARM so as to not confused either laymen or
experienced ARM packages.

Motivation for this change
Things done
  • Tested using sandboxing (nix.useSandbox on NixOS, or option build-use-sandbox in nix.conf on non-NixOS)
  • Built on platform(s)
    • NixOS
    • macOS
    • other Linux distributions
  • Tested via one or more NixOS test(s) if existing and applicable for the change (look inside nixos/tests)
  • Tested compilation of all pkgs that depend on this change using nix-shell -p nox --run "nox-review wip"
  • Tested execution of all binary files (usually in ./result/bin/)
  • Fits CONTRIBUTING.md.

@Ericson2314
Copy link
Member Author

Credit to @Mistuke for showing me these docs in https://github.com/haskell/cabal/pull/5221/files#r175566986

@Ericson2314
Copy link
Member Author

As to comparability, my preference would be to bite the bullet on master, and add a isAarch32 forward-compat synonym on 18.03 to help people migrating from there post release.

@@ -7,7 +7,7 @@ in rec {
inherit (lib.systems.doubles) all mesaPlatforms;
none = [];

arm = [ patterns.isArm ];
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'll get this next if this goes through.

Copy link
Member

@abbradar abbradar left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Much better naming than current. FYU there's also Linux kernel's option of arm and arm64 but I like this more for clarity.

Didn't notice anything wrong.in the code.

@dezgeg
Copy link
Contributor

dezgeg commented Mar 20, 2018

Absolutely no. Just because the ARM Ltd. marketing department decides to come up with a new name for an instruction set that had been called 'ARM' for over 25 years does not mean it's a good idea to follow. Just as well Intel's marketing calls the 32-bit x86 architecture IA-32 and nobody calls it that either.

Next to everything in the open-source ecosystem calls this architecture ARM. uname -m on Linux will return something like armv7l. The GNU target triplets will start with arm. builtins.currentSystem on Nix will return something like "armv7l-linux". A GCC built to generate ARM code calls itself arm-linux-gnueabihf-gcc or something of that sort.

Thumb is not relevant to the discussion since ARM and Thumb instruction encodings can transparently call into each other within the same program. It's an implementation detail that ordinary programmers don't need to care about most of the time. E.g. even if you're compiling code for those ARM microcontrollers which only support Thumb instructions, you don't use a thumb-none-eabi-gcc, you use a arm-none-eabi-gcc.

Now for AArch64, indeed some people made the annoying decision to be different and call it arm64. But nevertheless, that won't change the fact that there uname -m on Linux will return aarch64. The GNU target triplets will start with aarch64. builtins.currentSystem on Nix will return"aarch64-linux". A GCC built to generate AArch64 code calls itself aarch64-linux-gnu-gcc or something of that sort.

The current names used in Nixpkgs are widely-used standard names. The proposed name is inventing a yet another naming convention used by nobody else.

@shlevy
Copy link
Member

shlevy commented Mar 20, 2018

@dezgeg Should isArm be true or false on aarch64? If it's true, then people will accidentally write conditionals that match both when they really just want 32-bit Arm. If it's false, then (empirically!) people will be confused, because everyone (reasonably) thinks of aarch64 as "being Arm" in some meaningful sense.

Would you object to is32BitArm?

@Ericson2314
Copy link
Member Author

Ericson2314 commented Mar 20, 2018

@dezgeg What I don't understand about your argument is I didn't rename any concrete architecture. arm armv5tel armv6l armv7a form our current (arbitrary) whitelist, just as as before. And so target triples will be parsed or not parsed just as before. Target triple wise, these are only called "arm" insofar that they start with arm. Target triple land doesn't have equivalence classes.

CPP is a better of your argument. Yes __arm__ is defined just for 32-bit, and __aarch64__ just for 64-bit. But, __ARM_ARCH_8 and similar is defined in both cases (when the chip in question is new enough), so clearly the open source community also think Aarch64 is ARM. The treatment of __arm__ looks more like a necessity for backwards compatibility than something anyone would desire in a vacuum.

We, with our monorepo, are not so constrained by backwards compatibility, and again, by not defining an isArm at all, we avoid directly contradicting any past precedent.

@FRidh FRidh removed their request for review March 20, 2018 15:26
@Ericson2314
Copy link
Member Author

Ping it would be nice to wrap this up.

@dezgeg
Copy link
Contributor

dezgeg commented Apr 4, 2018

AArch64 is definitely not ARM and should not match isArm. It might be tempting to think it is, but lots of things will simply break down if one does.

For one, ARM code is 99% backward compatible between architecture revisions (modulo some deprecated instructions which will trap on new chips and can typically be emulated in kernel with just a loss of performance) as in ARMv5 binaries still run fine on ARMv7 chips. While most chips that run AArch64 can also run ARM code, some chips like the Cavium ThunderX on our Hydra support only AArch64 mode. Also to bring more confusion to the mix, there are also some CPU cores labeled "ARMv8-A" that only do 32-bit mode.

Second, an ARM GCC can compile code for all ARM architecture revisions just by passing and -march=armvX. (This is required by for example when compiling U-Boot for my board where the first-stage bootloader runs on a tiny auxilary ARMv4 core which then boots the proper bootloader on the big ARMv7 CPU.). In contrast, an AArch64 GCC can't build 32-bit code at all (and neither can an AArch64 binutils assemble it).

ARM and AArch64 assembly language are not at all compatible. They even the changed the comment character in the AArch64 assembler syntax. (In contrast, some x86 assembler code in the kernel works for both the i686 and x86_64, with an admittedly obnoxious amount of macros).

As far as I can tell, other distros don't treat AArch64 as ARM either. In Fedora's RPM spec files, %ifarch %{arm} does not match AArch64. In Buildroot, having BR2_aarch64 set does not imply BR2_arm being set, they are mutually exclusive. In Gentoo, KEYWORDS=arm does not imply anything about AArch64 support.

So in short, the current names+behaviour match what other distros are using. I see no reason to be diverging from them.

@Ericson2314
Copy link
Member Author

Ericson2314 commented Apr 4, 2018

@dezgeg this PR get's rid of isArm altogether; there is no conflict with other distros and tools. I agree isArm is confusing if it means Aarch64 too, the problem is it is also confusing if it doesn't. Removing it removes the confusion, does it not?

@wmertens
Copy link
Contributor

wmertens commented Apr 5, 2018

Good arguments on both sides, but I must say that getting rid of isArm gets rid of a potential source of confusion. 👍

@Ericson2314
Copy link
Member Author

Let's take this to a vote.

@dezgeg
Copy link
Contributor

dezgeg commented Apr 17, 2018

The names aarch64 and arm are the standard names used in e.g. GNU triplets as mentioned. This is what most other distros call them. Why is that simply not good enough? Should we now start renaming isi686 and others to something else as well? And better yet, do we do all these renames again in a couple of years when the marketing department of ARM comes up with yet another naming convention for their products or when someone else comes up with the same idea of 'all these old names and interfaces suck, let's rename them to what I think is better'?

Nix and the related projects are tools. Our users are expected to write their own packages for their internal company projects or whatever. And each time when the code they wrote that used to work just fine no longer works after upgrading Nixpkgs reflects badly on those tools. So renaming things around, removing or changing behaviour of existing interfaces has a cost. Therefore it follows that such changes simply should not be done if the actual benefits of the changes are miniscule compared to the pains of the code churn.

@shlevy
Copy link
Member

shlevy commented Apr 17, 2018

@dezgeg I think your opinion is clear. Do you see a path toward consensus? If not, it seems like a vote is the best option.

@Ericson2314
Copy link
Member Author

Hello people. Please vote. Thumb up and down this post.

@ElvishJerricco
Copy link
Contributor

The ambiguity has bit me before; I think it's a problem. Seeing as this does not change any actual triples or rename any actual architectures, and only changes a superficial nix-level binding, I see no tangible drawbacks beyond an occasional user wondering why isArm doesn't exist (who will be quickly satisfied to find is32BitArm).

@Ericson2314
Copy link
Member Author

Ericson2314 commented Apr 24, 2018

N.B. when I rebase I will add back an isArm deprecated back compat, as @dezgeg at least does use this outside of nixpkgs.

Following legacy packing conventions, `isArm` was defined just for
32-bit ARM instruction set. This is confusing to non packagers though,
because Aarch64 is an ARM instruction set.

The official ARM overview for ARMv8[1] is surprisingly not confusing,
given the overall state of affairs for ARM naming conventions, and
offers us a solution. It divides the nomenclature into three levels:

```
ISA:             ARMv8   {-A, -R, -M}
                 /    \
Mode:     Aarch32     Aarch64
             |         /   \
Encoding:   A64      A32   T32
```

At the top is the overall v8 instruction set archicture. Second are the
two modes, defined by bitwidth but differing in other semantics too, and
buttom are the encodings, (hopefully?) isomorphic if they encode the
same mode.

The 32 bit encodings are mostly backwards compatible with previous
non-Thumb and Thumb encodings, and if so we can pun the mode names to
instead mean "sets of compatable or isomorphic encodings", and then
voilà we have nice names for 32-bit and 64-bit arm instruction sets
which do not use the word ARM so as to not confused either laymen or
experienced ARM packages.

[1]: https://developer.arm.com/products/architecture/a-profile
@@ -41,6 +41,9 @@ rec {

isEfi = map (family: { cpu.family = family; })
[ "x86" "arm" "aarch64" ];

# Deprecated
isArm = isAarch32;
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For @dezgeg

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

And also for the principle of back-compat

@GrahamcOfBorg GrahamcOfBorg added 6.topic: stdenv Standard environment and removed 6.topic: python labels Apr 25, 2018
@Ericson2314
Copy link
Member Author

Ericson2314 commented Apr 25, 2018

There seems to be a consensus by voting, in line with that previously expressed in other mediums. I've rebased and added the deprecation.

@Ericson2314 Ericson2314 merged commit 948c8dc into NixOS:master Apr 25, 2018
@Ericson2314 Ericson2314 deleted the aarch32 branch April 25, 2018 19:42
@dezgeg
Copy link
Contributor

dezgeg commented Apr 25, 2018

@edolstra any opinions on this sorts of tree-wide mass renames?

@Ericson2314 Ericson2314 mentioned this pull request May 1, 2018
8 tasks
@Ericson2314 Ericson2314 added 6.topic: portability General portability concerns, not specific to cross-compilation or a specific platform 9.needs: port to stable A PR needs a backport to the stable release. 8.has: port to stable A PR already has a backport to the stable release. labels May 1, 2018
@dezgeg
Copy link
Contributor

dezgeg commented May 7, 2018

I don't see the backward compat:

error: while evaluating the attribute 'activationScript' of the derivation 'nixos-system-jetson-18.09pre-git' at /home/tmtynkky/nixos-configs/nixpkgs/pkgs/stdenv/generic/make-derivation.nix:148:11:
while evaluating the attribute 'system.activationScripts.script' at /home/tmtynkky/nixos-configs/nixpkgs/nixos/modules/system/activation/activation-script.nix:62:9:
while evaluating 'textClosureMap' at /home/tmtynkky/nixos-configs/nixpkgs/lib/strings-with-deps.nix:70:35, called from /home/tmtynkky/nixos-configs/nixpkgs/nixos/modules/system/activation/activation-script.nix:83:18:
while evaluating 'textClosureList' at /home/tmtynkky/nixos-configs/nixpkgs/lib/strings-with-deps.nix:54:33, called from /home/tmtynkky/nixos-configs/nixpkgs/lib/strings-with-deps.nix:71:35:
while evaluating 'f' at /home/tmtynkky/nixos-configs/nixpkgs/lib/strings-with-deps.nix:56:17, called from /home/tmtynkky/nixos-configs/nixpkgs/lib/strings-with-deps.nix:68:9:
while evaluating 'mapAttrs' at /home/tmtynkky/nixos-configs/nixpkgs/lib/attrsets.nix:198:17, called from /home/tmtynkky/nixos-configs/nixpkgs/nixos/modules/system/activation/activation-script.nix:82:33:
while evaluating 'mapAttrs' at /home/tmtynkky/nixos-configs/nixpkgs/lib/attrsets.nix:198:17, called from /home/tmtynkky/nixos-configs/nixpkgs/nixos/modules/system/activation/activation-script.nix:81:24:
while evaluating the attribute 'mergedValue' at /home/tmtynkky/nixos-configs/nixpkgs/lib/modules.nix:339:5:
while evaluating anonymous function at /home/tmtynkky/nixos-configs/nixpkgs/lib/modules.nix:339:32, called from /home/tmtynkky/nixos-configs/nixpkgs/lib/modules.nix:339:19:
while evaluating 'merge' at /home/tmtynkky/nixos-configs/nixpkgs/lib/types.nix:267:20, called from /home/tmtynkky/nixos-configs/nixpkgs/lib/modules.nix:342:8:
while evaluating 'mapAttrs' at /home/tmtynkky/nixos-configs/nixpkgs/lib/attrsets.nix:198:17, called from /home/tmtynkky/nixos-configs/nixpkgs/lib/types.nix:268:9:
while evaluating 'filterAttrs' at /home/tmtynkky/nixos-configs/nixpkgs/lib/attrsets.nix:115:23, called from /home/tmtynkky/nixos-configs/nixpkgs/lib/types.nix:268:35:
while evaluating 'concatMap' at /home/tmtynkky/nixos-configs/nixpkgs/lib/lists.nix:104:18, called from /home/tmtynkky/nixos-configs/nixpkgs/lib/attrsets.nix:116:18:
while evaluating anonymous function at /home/tmtynkky/nixos-configs/nixpkgs/lib/attrsets.nix:116:29, called from undefined position:
while evaluating anonymous function at /home/tmtynkky/nixos-configs/nixpkgs/lib/types.nix:268:51, called from /home/tmtynkky/nixos-configs/nixpkgs/lib/attrsets.nix:116:62:
while evaluating the attribute 'udevd' at /home/tmtynkky/nixos-configs/nixpkgs/lib/attrsets.nix:334:7:
while evaluating anonymous function at /home/tmtynkky/nixos-configs/nixpkgs/lib/types.nix:268:86, called from /home/tmtynkky/nixos-configs/nixpkgs/lib/attrsets.nix:334:15:
while evaluating the attribute 'optionalValue' at /home/tmtynkky/nixos-configs/nixpkgs/lib/modules.nix:346:5:
while evaluating 'filterOverrides' at /home/tmtynkky/nixos-configs/nixpkgs/lib/modules.nix:419:21, called from /home/tmtynkky/nixos-configs/nixpkgs/lib/modules.nix:328:18:
while evaluating 'concatMap' at /home/tmtynkky/nixos-configs/nixpkgs/lib/lists.nix:104:18, called from /home/tmtynkky/nixos-configs/nixpkgs/lib/modules.nix:425:8:
while evaluating 'concatMap' at /home/tmtynkky/nixos-configs/nixpkgs/lib/lists.nix:104:18, called from /home/tmtynkky/nixos-configs/nixpkgs/lib/modules.nix:323:17:
while evaluating anonymous function at /home/tmtynkky/nixos-configs/nixpkgs/lib/modules.nix:323:28, called from undefined position:
while evaluating 'dischargeProperties' at /home/tmtynkky/nixos-configs/nixpkgs/lib/modules.nix:386:25, called from /home/tmtynkky/nixos-configs/nixpkgs/lib/modules.nix:324:62:
while evaluating the attribute 'value' at /home/tmtynkky/nixos-configs/nixpkgs/lib/types.nix:273:55:
while evaluating the attribute 'udevd' at /home/tmtynkky/nixos-configs/nixpkgs/nixos/modules/services/hardware/udev.nix:304:5:
while evaluating the attribute 'passAsFile' of the derivation 'firmware' at /home/tmtynkky/nixos-configs/nixpkgs/pkgs/stdenv/generic/make-derivation.nix:148:11:
while evaluating the attribute 'out.outPath' at /home/tmtynkky/nixos-configs/nixpkgs/lib/customisation.nix:147:13:
while evaluating the attribute 'configurePhase' of the derivation 'linux-4.16.7' at /home/tmtynkky/nixos-configs/nixpkgs/pkgs/stdenv/generic/make-derivation.nix:148:11:
while evaluating the attribute 'patches' of the derivation 'linux-config-4.16.7' at /home/tmtynkky/nixos-configs/nixpkgs/pkgs/stdenv/generic/make-derivation.nix:148:11:
while evaluating the attribute 'patches' at /home/tmtynkky/nixos-configs/nixpkgs/pkgs/os-specific/linux/kernel/manual-config.nix:97:7:
while evaluating 'optional' at /home/tmtynkky/nixos-configs/nixpkgs/lib/lists.nix:200:20, called from /home/tmtynkky/nixos-configs/nixpkgs/pkgs/os-specific/linux/kernel/manual-config.nix:97:53:
attribute 'isArm' missing, at /home/tmtynkky/nixos-configs/nixpkgs/pkgs/os-specific/linux/kernel/manual-config.nix:97:74

Grumble.

@Ericson2314
Copy link
Member Author

Ah is that stdenv.isArm? The needs a new alias for back-compat as the old one got sedded with everything else.

@Ericson2314
Copy link
Member Author

Ericson2314 commented May 8, 2018

#40154 should fix it. Sorry I forgot to include this as part of the original PR.

@samueldr samueldr removed the 9.needs: port to stable A PR needs a backport to the stable release. label Apr 17, 2019
chkno added a commit to chkno/nixpkgs that referenced this pull request Feb 5, 2020
This is the last package reference to isArm.  isArm is deprecated after 18.03.
This substitution was performed tree-wide in NixOS#37401.
chkno added a commit to chkno/nixpkgs that referenced this pull request Feb 5, 2020
This is the last reference to isArm.  isArm is deprecated after 18.03.
This substitution was performed tree-wide in NixOS#37401.
chkno added a commit to chkno/nixpkgs that referenced this pull request Feb 5, 2020
isArm has been deprecated for three releases.  All references have been
removed.  Tree-wide substitution was performed in NixOS#37401 21 months ago.
@chkno chkno mentioned this pull request Feb 5, 2020
10 tasks
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
6.topic: golang 6.topic: haskell 6.topic: nixos 6.topic: portability General portability concerns, not specific to cross-compilation or a specific platform 6.topic: stdenv Standard environment 8.has: module (update) 8.has: port to stable A PR already has a backport to the stable release. 10.rebuild-darwin: 0 10.rebuild-linux: 0
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

10 participants