Gentoo Websites Logo
Go to: Gentoo Home Documentation Forums Lists Bugs Planet Store Wiki Get Gentoo!
Bug 822036 - sys-devel/gcc: enable CET for USE=hardened
Summary: sys-devel/gcc: enable CET for USE=hardened
Status: RESOLVED FIXED
Alias: None
Product: Gentoo Linux
Classification: Unclassified
Component: Hardened (show other bugs)
Hardware: All Linux
: Normal normal (vote)
Assignee: The Gentoo Linux Hardened Team
URL:
Whiteboard:
Keywords:
Depends on: 777117 827880 827905 828081 828400 828546 828549 830454 891655
Blocks: future-profile
  Show dependency tree
 
Reported: 2021-11-06 01:59 UTC by Sam James
Modified: 2023-01-23 00:46 UTC (History)
2 users (show)

See Also:
Package list:
Runtime testing required: ---


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Sam James archtester Gentoo Infrastructure gentoo-dev Security 2021-11-06 01:59:50 UTC
This bug is specifically for adding CET to be enabled by default with USE=hardened.

There's a PR with work by xaero here: https://github.com/gentoo/gentoo/pull/21588. Needs a tweak to the specs patch.

(The linked PR also adds USE=cet to GCC but that's orthogonal to having CET functionality by default when compiling.)

Plan is to let it soak in hardened for a bit and then try to upstream it with a nice configure option, like with -fstack-clash-protection, SSP, etc.

Note that Ubuntu have been doing this for quite some time without many issues: https://salsa.debian.org/toolchain-team/gcc/-/blob/master/debian/patches/gcc-distro-specs.diff.
Comment 1 Sam James archtester Gentoo Infrastructure gentoo-dev Security 2021-12-28 03:54:54 UTC
Enabled by default in https://gitweb.gentoo.org/proj/gcc-patches.git/commit/?id=51a7ace358097005038a0d31350b0c6d3da34e00 for USE=cet && USE=hardened.

See also:
- https://github.com/gentoo/gentoo/commit/98e481cd2d539c32a7a094d0e5ca6de36f9a0639 (toolchain.eclass: enable CET by default on hardened for >= gcc 11.2.1)
- https://github.com/gentoo/gentoo/commit/10bad611687710903699c02b6a0d12280337f96b (profiles/features/hardened/amd64: unmask CET)
- https://github.com/gentoo/gentoo/commit/b034debd0ee10095843845b6f1f6e7385188c208 (profiles/base: mask sys-devel/gcc[cet] in base)
Comment 2 Larry the Git Cow gentoo-dev 2021-12-28 05:57:46 UTC
The bug has been referenced in the following commit(s):

https://gitweb.gentoo.org/proj/gcc-patches.git/commit/?id=2b36f3ad2ba0114eae1d32bae5e395e098b3714b

commit 2b36f3ad2ba0114eae1d32bae5e395e098b3714b
Author:     Sam James <sam@gentoo.org>
AuthorDate: 2021-12-28 03:44:47 +0000
Commit:     Sam James <sam@gentoo.org>
CommitDate: 2021-12-28 03:55:44 +0000

    11.3.0: fix CET patch
    
    Our patch was causing unhandled state to leak into the LTO metadata writer,
    it shouldn't have got that far though. Instead of messing about with GCC's
    option handling, use the macro they provide for purposes like this, which
    makes things far simpler (and less fragile).
    
    Bug: https://bugs.gentoo.org/828400
    Bug: https://bugs.gentoo.org/822036
    Thanks-to: Sergei Trofimovich <slyich@gmail.com> (debugging help in #gentoo-toolchain)
    Thanks-to: Georgy Yakovlev <gyakovlev@gentoo.org> (debugging)
    Reported-by: matoro <matoro@airmail.cc>
    Signed-off-by: Sam James <sam@gentoo.org>

 11.3.0/gentoo/26_all_enable-cet.patch | 65 +++++------------------------------
 1 file changed, 9 insertions(+), 56 deletions(-)
Comment 3 Larry the Git Cow gentoo-dev 2022-01-18 13:19:57 UTC
The bug has been referenced in the following commit(s):

https://gitweb.gentoo.org/repo/gentoo.git/commit/?id=b96fd11e3e5626181c32c38381f814aba21fb9f0

commit b96fd11e3e5626181c32c38381f814aba21fb9f0
Author:     Sam James <sam@gentoo.org>
AuthorDate: 2022-01-18 13:16:42 +0000
Commit:     Sam James <sam@gentoo.org>
CommitDate: 2022-01-18 13:19:30 +0000

    sys-devel/gcc: add 11.2.1_p20220115
    
    Fairly minor changes upstream since the last snapshot of the 11
    stable branch. Includes more CET fixes and the upstream cross-compile
    patch.
    
    Also, the PCH ICE fix, although we've since masked PCH globally
    due to its instability.
    
    Bug: https://bugs.gentoo.org/822036
    Closes: https://bugs.gentoo.org/803371
    Closes: https://bugs.gentoo.org/828400
    Closes: https://bugs.gentoo.org/822690
    Signed-off-by: Sam James <sam@gentoo.org>

 profiles/base/package.use.mask            |  2 +-
 sys-devel/gcc/Manifest                    |  3 +++
 sys-devel/gcc/gcc-11.2.1_p20220115.ebuild | 26 ++++++++++++++++++++++++++
 3 files changed, 30 insertions(+), 1 deletion(-)
Comment 4 Niklāvs Koļesņikovs 2022-05-28 19:06:15 UTC
Multiple people myself included have been running CET enabled toolchain for a while (with a CET capable CPU, of course). Could this maybe be ready for going default?

One thing that kinda makes me doubt things is that from what I have read and understood -fcf-protection requires both the binary as well as all of its libraries to be built with -mshstk or the support for CET will be silently disabled by, I believe, the dynamic linker. Is or could there be some kind of sanity check tool to ensure that there's an actual CF enforcement rather than a dud?
Comment 5 Sam James archtester Gentoo Infrastructure gentoo-dev Security 2022-05-28 19:13:42 UTC
(In reply to Niklāvs Koļesņikovs from comment #4)
> Multiple people myself included have been running CET enabled toolchain for
> a while (with a CET capable CPU, of course). Could this maybe be ready for
> going default?

Yeah, I don't think we've had any reported problems at all. So, we probably can soon.

> 
> One thing that kinda makes me doubt things is that from what I have read and
> understood -fcf-protection requires both the binary as well as all of its
> libraries to be built with -mshstk or the support for CET will be silently
> disabled by, I believe, the dynamic linker. Is or could there be some kind
> of sanity check tool to ensure that there's an actual CF enforcement rather
> than a dud?

I don't think this is the case for modern GCCs. Please provide some sources if you believe it is and I'll look into it, but when I researched it before (and had to in order to do the patching), I had no such indications.
Comment 6 Niklāvs Koļesņikovs 2022-05-28 19:51:52 UTC
The best I could immediately find is this: https://developers.redhat.com/blog/2018/03/21/compiler-and-linker-flags-gcc which specifies that Fedora 28 onwards will use `-mcet -fcf-protection` (Fedora 28 hardening notes clear up that it's -fcf-protection=full).

As far as I could google, at some point GCC replaced the Intel specific -mcet with the vendor neutral -mshstk which is or will be available for at least AMD64 and some(?) ARM64 ISA. Therefore the current CFLAGS should be `fcf-protection=full -mshstk`.

Regarding the statement that not just the binary but all of its libraries must be built with support for CET (to be clear I merely omitted -fcf-protection for brevity, -mshstk may or may be enough for libraries), I tried but could not find the source of that but hopefully someone will have better luck than me.

Finally I was under impression that -fcf-protection on its own does nothing if -mshstk is also not specified, however its `man gcc` entry only says that:

"The -mshstk option enables shadow stack built-in functions from x86 Control-flow Enforcement Technology (CET)."

So I'm now left unsure if -mshstk is merely good and helpful or, because it replaces -mcet, mandatory for -fcf-protection to work.

One thing I have not checked but that may be happening is that perhaps -march=native or -fcf-protection either on their own or together enable -mshstk on CET capable or maybe even all CPUs that can support multi-byte NOPs (please don't ask me if multi-byte there means >8 bits or >16 bits or more).
Comment 7 Sam James archtester Gentoo Infrastructure gentoo-dev Security 2022-05-28 22:22:34 UTC
(In reply to Niklāvs Koļesņikovs from comment #6)
> The best I could immediately find is this:
> https://developers.redhat.com/blog/2018/03/21/compiler-and-linker-flags-gcc
> which specifies that Fedora 28 onwards will use `-mcet -fcf-protection`
> (Fedora 28 hardening notes clear up that it's -fcf-protection=full).

I think the 28 stuff predates the GCC changes to simplify the picture.

From building a test binary with -fcf-protection=full, if I use 'readelf -n /tmp/a.out', I see:
>      Properties: x86 feature: IBT, SHSTK

It's identical if I append -mshstk.

> 
> Finally I was under impression that -fcf-protection on its own does nothing
> if -mshstk is also not specified, however its `man gcc` entry only says that:
> 
> "The -mshstk option enables shadow stack built-in functions from x86
> Control-flow Enforcement Technology (CET)."
> 
> So I'm now left unsure if -mshstk is merely good and helpful or, because it
> replaces -mcet, mandatory for -fcf-protection to work.
> 

I don't think it's necessary at all, as far as I can tell.

> One thing I have not checked but that may be happening is that perhaps
> -march=native or -fcf-protection either on their own or together enable
> -mshstk on CET capable or maybe even all CPUs that can support multi-byte
> NOPs (please don't ask me if multi-byte there means >8 bits or >16 bits or
> more).

Yes, that's possible. I think one is to indicate that your CPU supports it, but -march= might imply it a lot of the time? But indeed I see SHSTK being mentioned via the notes section even without -march, or by picking something older like core2.

I'm not sure -mshstk actually matters given that in terms of code emitted, the CMOVs used by CET are completely safe on i686+ (and indeed we only bother enabling it for 64-bit && CMOV being available as a sanity check).

All this to say: I don't yet see any difference from adding -mshstk.

-fcf-protection=full implies the relevant options (it implies both shstk and ibt, because both are necessary for -fcf-protection=return and -fcf-protection=branch respectively)

In gcc-config/i386/gnu-property.cc, we have:
```
file_end_indicate_exec_stack_and_gnu_property(void) {
  [...]
  if (flag_cf_protection & CF_BRANCH)
    /* GNU_PROPERTY_X86_FEATURE_1_IBT.  */
    feature_1 |= 0x1;

  if (flag_cf_protection & CF_RETURN)
    /* GNU_PROPERTY_X86_FEATURE_1_SHSTK.  */
    feature_1 |= 0x2;
  [...]
}
```

In gcc/config/i386/i386.md, we have:
```
;; CET instructions
(define_insn "@rdssp<mode>"
  [(set (match_operand:SWI48 0 "register_operand" "=r")
        (unspec_volatile:SWI48 [(match_operand:SWI48 1 "register_operand" "0")]
                               UNSPECV_NOP_RDSSP))]
  "TARGET_SHSTK || (flag_cf_protection & CF_RETURN)"
  "rdssp<mskmodesuffix>\t%0"
  [(set_attr "length" "6")
   (set_attr "type" "other")])
[...]
```

What's confusing is, while instructions are emitted for -fcf-protection=full and such, there's a few parts gated by SHSTK only.

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=85417 has some interesting background here.

Ubuntu don't bother either (Debian may be using their patch too): https://salsa.debian.org/toolchain-team/gcc/-/blob/master/debian/patches/gcc-distro-specs.diff.
Comment 8 Sam James archtester Gentoo Infrastructure gentoo-dev Security 2022-05-28 22:27:42 UTC
Wanted to split this part into a new comment. I think I get it now.

>This patch changes -fcf-protection to implement indirect branch and
>return address tracking with multi-byte NOPs.  -mibt and -mshstk are
>changed to only enable CET built-in functions.

gcc/config/i386/cetintrin.h are the builtins that hj lu refers to in https://gcc.gnu.org/bugzilla/show_bug.cgi?id=85417.

I think you might need -mibt and -mshstk if you want the whole program to be using CET, *but* it comes at the cost that you cannot disable it for any component that gets linked.

GCC's view appears to be that it's unsuitable to set this by default or imply it by -fcf-protection=*:
>-fcf-protection -mcet can't be used with IFUNC features, like symbol
>multiversioning or target clone, since IBT/SHSTK are applied to the whole
>program and they may be disabled in some functions.

It's also harmful to compatibility then.

(-mcet got renamed, as you noted).

The question is how much these builtins really matter. Given that it does seem to actually work (I get e.g. __CET__ defined and Ubuntu had issues w/ say https://news.ycombinator.com/item?id=26060748, https://github.com/ipxe/ipxe/commit/e8393c372), I'm inclined to say we're fine.

It seems that -mshstk and -mibt are only appropriate per-program if it's known to work with it. It's unclear to me if it's safe to build your system with it.
Comment 9 Sam James archtester Gentoo Infrastructure gentoo-dev Security 2022-05-28 22:29:34 UTC
(In reply to Sam James from comment #8)
> 
> It seems that -mshstk and -mibt are only appropriate per-program if it's
> known to work with it. It's unclear to me if it's safe to build your system
> with it.

The fact that it breaks IFUNC seems to me to be a dealbreaker for doing that by default: https://sourceware.org/glibc/wiki/GNU_IFUNC.
Comment 10 Niklāvs Koļesņikovs 2022-05-28 23:19:47 UTC
Thank you for the good explanation. I had found and read https://gcc.gnu.org/bugzilla/show_bug.cgi?id=85417 once or twice but somehow it didn't occur to me that setting -mshstk was a bad idea.

The only issue I have observed that may or may not be related is that since the upgrade to Firefox 100 the widevince plugin has been crashing with www-client/firefox{,-bin} but not the Flatpak Firefox. And while I definitely did suspect -fcf-protection -mshstk as being the likely culprits, it has been a very low priority issue for me, so I have not gotten to rebuilding everything without one of them yet (but I'll try removing -mshstk at some point).
Comment 11 Larry the Git Cow gentoo-dev 2022-05-28 23:35:15 UTC
The bug has been referenced in the following commit(s):

https://gitweb.gentoo.org/repo/gentoo.git/commit/?id=2a542765c79efb7cb7767f1c4ace4abcb45c9420

commit 2a542765c79efb7cb7767f1c4ace4abcb45c9420
Author:     Sam James <sam@gentoo.org>
AuthorDate: 2022-05-28 23:30:26 +0000
Commit:     Sam James <sam@gentoo.org>
CommitDate: 2022-05-28 23:30:26 +0000

    sys-devel/gcc: add 12.1.1_p20220528; patch set 6
    
    New patch set just includes CET default dropped from 11->12 at some point.
    
    Not that it matters much given it's all unkw'd anyway, but still.
    
    Bug: https://bugs.gentoo.org/822036
    Signed-off-by: Sam James <sam@gentoo.org>

 sys-devel/gcc/Manifest                    |  3 +++
 sys-devel/gcc/gcc-12.1.1_p20220528.ebuild | 27 +++++++++++++++++++++++++++
 sys-devel/gcc/gcc-12.2.9999.ebuild        |  6 +++---
 3 files changed, 33 insertions(+), 3 deletions(-)
Comment 12 Larry the Git Cow gentoo-dev 2022-05-28 23:36:33 UTC
The bug has been referenced in the following commit(s):

https://gitweb.gentoo.org/proj/gcc-patches.git/commit/?id=ce1ac49c2c52611e507c4ec853f5eef3770aa723

commit ce1ac49c2c52611e507c4ec853f5eef3770aa723
Author:     Sam James <sam@gentoo.org>
AuthorDate: 2022-05-28 23:19:08 +0000
Commit:     Sam James <sam@gentoo.org>
CommitDate: 2022-05-28 23:36:28 +0000

    12.1.0: restore 26_all_enable-cet.patch
    
    Got lost apparently in 11->12 migration.
    
    Bug: https://bugs.gentoo.org/822036
    Signed-off-by: Sam James <sam@gentoo.org>

 12.1.0/gentoo/26_all_enable-cet.patch | 57 +++++++++++++++++++++++++++++++++++
 12.1.0/gentoo/README.history          |  4 +++
 2 files changed, 61 insertions(+)
Comment 13 Larry the Git Cow gentoo-dev 2022-06-02 07:15:32 UTC
The bug has been referenced in the following commit(s):

https://gitweb.gentoo.org/proj/gcc-patches.git/commit/?id=d67ec824d290c0e678b1d7d71ba47e24e2d892ca

commit d67ec824d290c0e678b1d7d71ba47e24e2d892ca
Author:     Sam James <sam@gentoo.org>
AuthorDate: 2022-05-30 06:41:16 +0000
Commit:     Sam James <sam@gentoo.org>
CommitDate: 2022-06-02 07:15:27 +0000

    12.1.0: update CET patch
    
    Bug: https://bugs.gentoo.org/822036
    Signed-off-by: Sam James <sam@gentoo.org>

 12.1.0/gentoo/26_all_enable-cet.patch | 225 ++++++++++++++++++++++++++++------
 12.1.0/gentoo/README.history          |   4 +
 2 files changed, 191 insertions(+), 38 deletions(-)
Comment 14 Larry the Git Cow gentoo-dev 2022-06-02 07:15:47 UTC
The bug has been referenced in the following commit(s):

https://gitweb.gentoo.org/repo/gentoo.git/commit/?id=9eab5244a2b42dba2fac3ecb7be347b841c2ab15

commit 9eab5244a2b42dba2fac3ecb7be347b841c2ab15
Author:     Sam James <sam@gentoo.org>
AuthorDate: 2022-06-02 06:27:01 +0000
Commit:     Sam James <sam@gentoo.org>
CommitDate: 2022-06-02 07:15:41 +0000

    sys-devel/gcc: update CET patch for 12
    
    Let's switch to the Ubuntu-style spec changing given that
    the old approach was fragile and could fall over w/
    bootstrap (at least w/ USE="pgo lto jit"). Didn't
    seem to happen with different combinations though.
    
    Bug: https://bugs.gentoo.org/822036
    Signed-off-by: Sam James <sam@gentoo.org>

 sys-devel/gcc/Manifest                       |  1 +
 sys-devel/gcc/gcc-12.1.1_p20220528-r1.ebuild | 27 +++++++++++++++++++++++++++
 sys-devel/gcc/gcc-12.2.9999.ebuild           |  2 +-
 3 files changed, 29 insertions(+), 1 deletion(-)
Comment 15 Larry the Git Cow gentoo-dev 2023-01-20 21:18:33 UTC
The bug has been closed via the following commit(s):

https://gitweb.gentoo.org/repo/gentoo.git/commit/?id=f69a93f7c1aac2540ea2ecd80a264b7b8ba1094a

commit f69a93f7c1aac2540ea2ecd80a264b7b8ba1094a
Author:     Sam James <sam@gentoo.org>
AuthorDate: 2023-01-20 21:18:02 +0000
Commit:     Sam James <sam@gentoo.org>
CommitDate: 2023-01-20 21:18:02 +0000

    profiles/features/hardened/amd64: enable USE=cet
    
    Closes: https://bugs.gentoo.org/822036
    Signed-off-by: Sam James <sam@gentoo.org>

 profiles/features/hardened/amd64/make.defaults | 5 ++---
 1 file changed, 2 insertions(+), 3 deletions(-)
Comment 16 Larry the Git Cow gentoo-dev 2023-01-23 00:35:26 UTC
The bug has been referenced in the following commit(s):

https://gitweb.gentoo.org/proj/gcc-patches.git/commit/?id=15daf0510a5fab17cd556261d688a6618391a0c1

commit 15daf0510a5fab17cd556261d688a6618391a0c1
Author:     Sam James <sam@gentoo.org>
AuthorDate: 2023-01-22 08:35:13 +0000
Commit:     Sam James <sam@gentoo.org>
CommitDate: 2023-01-23 00:35:20 +0000

    11.4.0: drop 26_all_enable-cet.patch (bootstrapping issues with PGO/LTO?)
    
    See https://bugs.gentoo.org/891655#c2 in particular:
    """
    In https://bugs.gentoo.org/822036#c14, I got fed up and changed to the Ubuntu-style
    specs patching for the time being, because it was too fragile otherwise.
    
    We should probably just drop the CET patch for 11.x. We can keep the USE in
    make.defaults for CET on hardened profiles though, as support for it is still useful, but it'll only be on by default with 12.
    
    I do want to revisit the specs patch later on as it's not very maintainable though.
    """
    
    11.x is really not the place we want to experiment further at this point,
    so go for the safe option and either develop the approach further for 12
    or maybe even 13.
    
    Arsen notes that we might be able to try --enable-cet=yes (rather than
    default auto) but let's leave that for now given ^ wrt 11.
    
    Bug: https://bugs.gentoo.org/822036
    Closes: https://bugs.gentoo.org/891655
    Signed-off-by: Sam James <sam@gentoo.org>

 11.4.0/gentoo/26_all_enable-cet.patch | 48 -----------------------------------
 11.4.0/gentoo/README.history          |  3 +++
 2 files changed, 3 insertions(+), 48 deletions(-)
Comment 17 Larry the Git Cow gentoo-dev 2023-01-23 00:43:39 UTC
The bug has been referenced in the following commit(s):

https://gitweb.gentoo.org/repo/gentoo.git/commit/?id=016184c289f2cc6c6ade496a700a12f135fbae07

commit 016184c289f2cc6c6ade496a700a12f135fbae07
Author:     Sam James <sam@gentoo.org>
AuthorDate: 2023-01-23 00:25:35 +0000
Commit:     Sam James <sam@gentoo.org>
CommitDate: 2023-01-23 00:42:40 +0000

    sys-devel/gcc: backport CET fix for 11; further make jobserver related fixes for all
    
    - jobserver:
     Led to crashes during build in some cases. Note that this is a bug in the driver
     so could easily happen when using GCC to build other things too.
    
    - CET:
      See https://gitweb.gentoo.org/proj/gcc-patches.git/commit/?id=15daf0510a5fab17cd556261d688a6618391a0c1
      for details, but went for a more conservative approach for GCC 11.
    
    Bug: https://bugs.gentoo.org/822036
    Closes: https://bugs.gentoo.org/885501
    Closes: https://bugs.gentoo.org/891655
    Signed-off-by: Sam James <sam@gentoo.org>

 sys-devel/gcc/Manifest                             |  4 +-
 ...30119.ebuild => gcc-10.4.1_p20230119-r1.ebuild} |  8 ++--
 ...30120.ebuild => gcc-11.3.1_p20230120-r1.ebuild} |  8 ++--
 sys-devel/gcc/gcc-12.2.1_p20230121-r1.ebuild       | 52 ++++++++++++++++++++++
 4 files changed, 63 insertions(+), 9 deletions(-)