unofficial mirror of libc-alpha@sourceware.org
 help / color / mirror / Atom feed
* [PATCH 1/2] string: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size
  2020-12-10 18:13 [PATCH " Siddhesh Poyarekar via Libc-alpha
@ 2020-12-10 18:13 ` Siddhesh Poyarekar via Libc-alpha
  2020-12-10 19:10   ` Paul Eggert
  0 siblings, 1 reply; 14+ messages in thread
From: Siddhesh Poyarekar via Libc-alpha @ 2020-12-10 18:13 UTC (permalink / raw
  To: libc-alpha; +Cc: jakub, fweimer

Introduce a new _FORTIFY_SOURCE level of 3 to enable additional
fortifications that may have a potential performance impact.  At the
moment this level of fortification involves the use of the
__builtin_dynamic_object_size builtin whenever the compiler supports
it.

This change enhances fortified string functions to use
__builtin_dynamic_object_size under _FORTIFY_SOURCE=3 whenever the
compiler supports it.

__builtin_dynamic_object_size
-----------------------------

__builtin_dynamic_object_size is an LLVM builtin that is similar to
__builtin_object_size.  In addition to what __builtin_object_size
does, i.e. replace the builtin call with a constant object size,
__builtin_dynamic_object_size will replace the call site with an
expression that evaluates to the object size, thus expanding its
applicability.  In practice, __builtin_dynamic_object_size evaluates
these expressions through malloc/calloc calls that it can associate
with the object being evaluated.

A simple motivating example is below; -D_FORTIFY_SOURCE=2 would miss
this and emit memcpy, but -D_FORTIFY_SOURCE=3 with the help of
__builtin_dynamic_object_size is able to emit __memcpy_chk with the
allocation size expression passed into the function:

void *copy_obj (const void *src, size_t alloc, size_t copysize)
{
  void *obj = malloc (alloc);
  memcpy (obj, src, copysize);

  return obj;
}

Limitations
-----------

If the object was allocated elsewhere that the compiler cannot see, or
if it was allocated in the function with a function that the compiler
does not recognize as an allocator then __builtin_dynamic_object_size
also returns -1.

Further, the expression used to compute object size may be non-trivial
and may potentially incur a noticeable performance impact.  These
fortifications are hence enabled at a new _FORTIFY_SOURCE level to
allow developers to make a choice on the tradeoff according to their
environment.
---
 NEWS                            |  4 ++++
 include/features.h              |  6 +++---
 include/string.h                |  5 +++--
 manual/creature.texi            |  3 ++-
 misc/sys/cdefs.h                |  9 +++++++++
 string/bits/string_fortified.h  | 22 +++++++++++-----------
 string/bits/strings_fortified.h |  4 ++--
 7 files changed, 34 insertions(+), 19 deletions(-)

diff --git a/NEWS b/NEWS
index 0820984547..449ba0074f 100644
--- a/NEWS
+++ b/NEWS
@@ -28,6 +28,10 @@ Major new features:
   The 32-bit RISC-V port requires at least Linux 5.4, GCC 7.1 and binutils
   2.28.
 
+* A new fortification level _FORTIFY_SOURCE=3 is available.  At this level,
+  glibc attempts to use compiler-specific checks to implement more
+  computationally expensive checks in addition to checks provided at level 2.
+
 Deprecated and removed features, and other changes affecting compatibility:
 
 * The mallinfo function is marked deprecated.  Callers should call
diff --git a/include/features.h b/include/features.h
index f3e62d3362..86409dd457 100644
--- a/include/features.h
+++ b/include/features.h
@@ -397,10 +397,10 @@
 #  warning _FORTIFY_SOURCE requires compiling with optimization (-O)
 # elif !__GNUC_PREREQ (4, 1)
 #  warning _FORTIFY_SOURCE requires GCC 4.1 or later
-# elif _FORTIFY_SOURCE > 1
-#  define __USE_FORTIFY_LEVEL 2
+# elif _FORTIFY_SOURCE > 2
+#  define __USE_FORTIFY_LEVEL 3
 # else
-#  define __USE_FORTIFY_LEVEL 1
+#  define __USE_FORTIFY_LEVEL _FORTIFY_SOURCE
 # endif
 #endif
 #ifndef __USE_FORTIFY_LEVEL
diff --git a/include/string.h b/include/string.h
index 7d344d77d4..841ee05a1d 100644
--- a/include/string.h
+++ b/include/string.h
@@ -123,10 +123,11 @@ libc_hidden_proto (__strerror_l)
 void __explicit_bzero_chk_internal (void *, size_t, size_t)
   __THROW __nonnull ((1)) attribute_hidden;
 # define explicit_bzero(buf, len) \
-  __explicit_bzero_chk_internal (buf, len, __bos0 (buf))
+  __explicit_bzero_chk_internal (buf, len, __objsize0 (buf))
 #elif !IS_IN (nonlib)
 void __explicit_bzero_chk (void *, size_t, size_t) __THROW __nonnull ((1));
-# define explicit_bzero(buf, len) __explicit_bzero_chk (buf, len, __bos0 (buf))
+# define explicit_bzero(buf, len) __explicit_bzero_chk (buf, len,	      \
+							__objsize0 (buf))
 #endif
 
 libc_hidden_builtin_proto (memchr)
diff --git a/manual/creature.texi b/manual/creature.texi
index be5050468b..e0ea799b6d 100644
--- a/manual/creature.texi
+++ b/manual/creature.texi
@@ -254,7 +254,8 @@ included.
 @standards{GNU, (none)}
 If this macro is defined to @math{1}, security hardening is added to
 various library functions.  If defined to @math{2}, even stricter
-checks are applied.
+checks are applied. If defined to @math{3}, @theglibc{} attempts to use
+compiler-specific checks that may be more computationally expensive.
 @end defvr
 
 @defvr Macro _REENTRANT
diff --git a/misc/sys/cdefs.h b/misc/sys/cdefs.h
index e94d09d7dd..563b238ed5 100644
--- a/misc/sys/cdefs.h
+++ b/misc/sys/cdefs.h
@@ -127,6 +127,15 @@
 #define __bos(ptr) __builtin_object_size (ptr, __USE_FORTIFY_LEVEL > 1)
 #define __bos0(ptr) __builtin_object_size (ptr, 0)
 
+/* Use __builtin_dynamic_object_size if available.  */
+#if __USE_FORTIFY_LEVEL == 3 && __glibc_clang_prereq (9, 0)
+# define __objsize0(__o) __builtin_dynamic_object_size (__o, 0)
+# define __objsize(__o) __builtin_dynamic_object_size (__o, 1)
+#else
+# define __objsize0(__o) __bos0 (__o)
+# define __objsize(__o) __bos (__o)
+#endif
+
 #if __GNUC_PREREQ (4,3)
 # define __warnattr(msg) __attribute__((__warning__ (msg)))
 # define __errordecl(name, msg) \
diff --git a/string/bits/string_fortified.h b/string/bits/string_fortified.h
index 4c1aeb45f1..c9f9197aef 100644
--- a/string/bits/string_fortified.h
+++ b/string/bits/string_fortified.h
@@ -26,13 +26,13 @@ __fortify_function void *
 __NTH (memcpy (void *__restrict __dest, const void *__restrict __src,
 	       size_t __len))
 {
-  return __builtin___memcpy_chk (__dest, __src, __len, __bos0 (__dest));
+  return __builtin___memcpy_chk (__dest, __src, __len, __objsize0 (__dest));
 }
 
 __fortify_function void *
 __NTH (memmove (void *__dest, const void *__src, size_t __len))
 {
-  return __builtin___memmove_chk (__dest, __src, __len, __bos0 (__dest));
+  return __builtin___memmove_chk (__dest, __src, __len, __objsize0 (__dest));
 }
 
 #ifdef __USE_GNU
@@ -40,7 +40,7 @@ __fortify_function void *
 __NTH (mempcpy (void *__restrict __dest, const void *__restrict __src,
 		size_t __len))
 {
-  return __builtin___mempcpy_chk (__dest, __src, __len, __bos0 (__dest));
+  return __builtin___mempcpy_chk (__dest, __src, __len, __objsize0 (__dest));
 }
 #endif
 
@@ -53,7 +53,7 @@ __NTH (mempcpy (void *__restrict __dest, const void *__restrict __src,
 __fortify_function void *
 __NTH (memset (void *__dest, int __ch, size_t __len))
 {
-  return __builtin___memset_chk (__dest, __ch, __len, __bos0 (__dest));
+  return __builtin___memset_chk (__dest, __ch, __len, __objsize0 (__dest));
 }
 
 #ifdef __USE_MISC
@@ -65,21 +65,21 @@ void __explicit_bzero_chk (void *__dest, size_t __len, size_t __destlen)
 __fortify_function void
 __NTH (explicit_bzero (void *__dest, size_t __len))
 {
-  __explicit_bzero_chk (__dest, __len, __bos0 (__dest));
+  __explicit_bzero_chk (__dest, __len, __objsize0 (__dest));
 }
 #endif
 
 __fortify_function char *
 __NTH (strcpy (char *__restrict __dest, const char *__restrict __src))
 {
-  return __builtin___strcpy_chk (__dest, __src, __bos (__dest));
+  return __builtin___strcpy_chk (__dest, __src, __objsize (__dest));
 }
 
 #ifdef __USE_GNU
 __fortify_function char *
 __NTH (stpcpy (char *__restrict __dest, const char *__restrict __src))
 {
-  return __builtin___stpcpy_chk (__dest, __src, __bos (__dest));
+  return __builtin___stpcpy_chk (__dest, __src, __objsize (__dest));
 }
 #endif
 
@@ -88,14 +88,14 @@ __fortify_function char *
 __NTH (strncpy (char *__restrict __dest, const char *__restrict __src,
 		size_t __len))
 {
-  return __builtin___strncpy_chk (__dest, __src, __len, __bos (__dest));
+  return __builtin___strncpy_chk (__dest, __src, __len, __objsize (__dest));
 }
 
 #if __GNUC_PREREQ (4, 7) || __glibc_clang_prereq (2, 6)
 __fortify_function char *
 __NTH (stpncpy (char *__dest, const char *__src, size_t __n))
 {
-  return __builtin___stpncpy_chk (__dest, __src, __n, __bos (__dest));
+  return __builtin___stpncpy_chk (__dest, __src, __n, __objsize (__dest));
 }
 #else
 extern char *__stpncpy_chk (char *__dest, const char *__src, size_t __n,
@@ -118,7 +118,7 @@ __NTH (stpncpy (char *__dest, const char *__src, size_t __n))
 __fortify_function char *
 __NTH (strcat (char *__restrict __dest, const char *__restrict __src))
 {
-  return __builtin___strcat_chk (__dest, __src, __bos (__dest));
+  return __builtin___strcat_chk (__dest, __src, __objsize (__dest));
 }
 
 
@@ -126,7 +126,7 @@ __fortify_function char *
 __NTH (strncat (char *__restrict __dest, const char *__restrict __src,
 		size_t __len))
 {
-  return __builtin___strncat_chk (__dest, __src, __len, __bos (__dest));
+  return __builtin___strncat_chk (__dest, __src, __len, __objsize (__dest));
 }
 
 #endif /* bits/string_fortified.h */
diff --git a/string/bits/strings_fortified.h b/string/bits/strings_fortified.h
index d4091f4f69..122199e036 100644
--- a/string/bits/strings_fortified.h
+++ b/string/bits/strings_fortified.h
@@ -22,13 +22,13 @@
 __fortify_function void
 __NTH (bcopy (const void *__src, void *__dest, size_t __len))
 {
-  (void) __builtin___memmove_chk (__dest, __src, __len, __bos0 (__dest));
+  (void) __builtin___memmove_chk (__dest, __src, __len, __objsize0 (__dest));
 }
 
 __fortify_function void
 __NTH (bzero (void *__dest, size_t __len))
 {
-  (void) __builtin___memset_chk (__dest, '\0', __len, __bos0 (__dest));
+  (void) __builtin___memset_chk (__dest, '\0', __len, __objsize0 (__dest));
 }
 
 #endif
-- 
2.28.0


^ permalink raw reply related	[flat|nested] 14+ messages in thread

* Re: [PATCH 1/2] string: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size
  2020-12-10 18:13 ` [PATCH 1/2] string: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size Siddhesh Poyarekar via Libc-alpha
@ 2020-12-10 19:10   ` Paul Eggert
  2020-12-11  1:36     ` Siddhesh Poyarekar via Libc-alpha
  0 siblings, 1 reply; 14+ messages in thread
From: Paul Eggert @ 2020-12-10 19:10 UTC (permalink / raw
  To: Siddhesh Poyarekar, libc-alpha; +Cc: jakub, fweimer

On 12/10/20 10:13 AM, Siddhesh Poyarekar via Libc-alpha wrote:

> +checks are applied. If defined to @math{3}, @theglibc{} attempts to use
> +compiler-specific checks that may be more computationally expensive.

Please change "attempts to use compiler-specific checks" to "may also use 
checks". The documentation need not mention compilers here, and the "also" 
documents that 3 subsumes 2.

>  # elif !__GNUC_PREREQ (4, 1)
>  #  warning _FORTIFY_SOURCE requires GCC 4.1 or later
> -# elif _FORTIFY_SOURCE > 1
> -#  define __USE_FORTIFY_LEVEL 2
> +# elif _FORTIFY_SOURCE > 2
> +#  define __USE_FORTIFY_LEVEL 3
>  # else
> -#  define __USE_FORTIFY_LEVEL 1
> +#  define __USE_FORTIFY_LEVEL _FORTIFY_SOURCE
>  # endif

The existing code warns if you define _FORTIFY_SOURCE on a platform that 
doesn't support _FORTIFY_SOURCE. Shouldn't the revised code warn if you 
define _FORTIFY_SOURCE to 3 on a platform that doesn't support that? 
Otherwise people may be lulled into the belief that -D_FORTIFY_SOURCE=3 
means something even on platforms where it doesn't.

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH 1/2] string: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size
  2020-12-10 19:10   ` Paul Eggert
@ 2020-12-11  1:36     ` Siddhesh Poyarekar via Libc-alpha
  2020-12-11  2:42       ` Paul Eggert
  0 siblings, 1 reply; 14+ messages in thread
From: Siddhesh Poyarekar via Libc-alpha @ 2020-12-11  1:36 UTC (permalink / raw
  To: Paul Eggert, libc-alpha; +Cc: jakub, fweimer

On 12/11/20 12:40 AM, Paul Eggert wrote:
> On 12/10/20 10:13 AM, Siddhesh Poyarekar via Libc-alpha wrote:
> 
>> +checks are applied. If defined to @math{3}, @theglibc{} attempts to use
>> +compiler-specific checks that may be more computationally expensive.
> 
> Please change "attempts to use compiler-specific checks" to "may also 
> use checks". The documentation need not mention compilers here, and the 
> "also" documents that 3 subsumes 2.

Thanks, I'll fix this.

>>  # elif !__GNUC_PREREQ (4, 1)
>>  #  warning _FORTIFY_SOURCE requires GCC 4.1 or later
>> -# elif _FORTIFY_SOURCE > 1
>> -#  define __USE_FORTIFY_LEVEL 2
>> +# elif _FORTIFY_SOURCE > 2
>> +#  define __USE_FORTIFY_LEVEL 3
>>  # else
>> -#  define __USE_FORTIFY_LEVEL 1
>> +#  define __USE_FORTIFY_LEVEL _FORTIFY_SOURCE
>>  # endif
> 
> The existing code warns if you define _FORTIFY_SOURCE on a platform that 
> doesn't support _FORTIFY_SOURCE. Shouldn't the revised code warn if you 
> define _FORTIFY_SOURCE to 3 on a platform that doesn't support that? 
> Otherwise people may be lulled into the belief that -D_FORTIFY_SOURCE=3 
> means something even on platforms where it doesn't.

Thanks, that's a good idea, I'll add a check.  I suppose I ought to 
document in the NEWS too that _FORTIFY_SOURCE=3 at present only adds 
additional checks with llvm 9 and later and that gcc-10.2 does not have 
the needed support?

Thanks,
Siddhesh

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH 1/2] string: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size
  2020-12-11  1:36     ` Siddhesh Poyarekar via Libc-alpha
@ 2020-12-11  2:42       ` Paul Eggert
  0 siblings, 0 replies; 14+ messages in thread
From: Paul Eggert @ 2020-12-11  2:42 UTC (permalink / raw
  To: Siddhesh Poyarekar, libc-alpha; +Cc: jakub, fweimer

On 12/10/20 5:36 PM, Siddhesh Poyarekar wrote:
> I suppose I ought to document in the NEWS too that _FORTIFY_SOURCE=3 at 
> present only adds additional checks with llvm 9 and later and that gcc-10.2 
> does not have the needed support?

Yes.

^ permalink raw reply	[flat|nested] 14+ messages in thread

* [PATCH v6 0/2] _FORTIFY_SOURCE=3
@ 2020-12-19  6:33 Siddhesh Poyarekar via Libc-alpha
  2020-12-19  6:33 ` [PATCH 1/2] string: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size Siddhesh Poyarekar via Libc-alpha
                   ` (2 more replies)
  0 siblings, 3 replies; 14+ messages in thread
From: Siddhesh Poyarekar via Libc-alpha @ 2020-12-19  6:33 UTC (permalink / raw
  To: libc-alpha; +Cc: fweimer, jakub

This patchset implements a new fortification level, _FORTIFY_SOURCE=3.
This level allows size information to be dynamic, which may potentially
have a noticeable performance impact.  It uses the
__builtin_dynamic_object_size builtin available in clang to expand
coverage of fortifications at the expense of some performance.

Patch 1/2 implements the base support and support for functions that
have builtins of string functions.  Additionally, the patch also
describes the use case and tradeoffs.

Patch 2/2 adds support for non-string functions that are
fortification-ready for levels 1 and 2.

Testing:

The glibc testsuite doesn't directly support clang at the moment, so
having tests in the glibc source tree is pointless as long as gcc does
not have support for __builtin_dynamic_object_size.  There is a separate
project on GitHub called fortify-test-suite[1] that houses fortification
tests and is capable of testing multiple levels of fortification with
multiple compilers.  I have proposed a PR[2] to add support for
_FORTIFY_SOURCE=3 and have verified my changes with those tests.

Those tests run clean for clang when run with these changes and PR[2]
and they fail at level 3 for gcc, as expected.

[1] https://github.com/serge-sans-paille/fortify-test-suite
[2] https://github.com/serge-sans-paille/fortify-test-suite/pull/9

Changes from previous series:

- Adopted Paul Eggert's macro soup because it has better texture while
  retaining the flavour.

Siddhesh Poyarekar (2):
  string: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size
  nonstring: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size

 NEWS                            |   6 ++
 include/features.h              |   8 ++
 include/string.h                |   5 +-
 io/bits/poll2.h                 |  16 ++--
 libio/bits/stdio.h              |   2 +-
 libio/bits/stdio2.h             |  53 ++++++-------
 manual/creature.texi            |   3 +-
 misc/sys/cdefs.h                |   9 +++
 posix/bits/unistd.h             | 112 ++++++++++++++-------------
 socket/bits/socket2.h           |  18 ++---
 stdlib/bits/stdlib.h            |  37 ++++-----
 string/bits/string_fortified.h  |  22 +++---
 string/bits/strings_fortified.h |   4 +-
 wcsmbs/bits/wchar2.h            | 131 ++++++++++++++++----------------
 14 files changed, 230 insertions(+), 196 deletions(-)

-- 
2.29.2


^ permalink raw reply	[flat|nested] 14+ messages in thread

* [PATCH 1/2] string: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size
  2020-12-19  6:33 [PATCH v6 0/2] _FORTIFY_SOURCE=3 Siddhesh Poyarekar via Libc-alpha
@ 2020-12-19  6:33 ` Siddhesh Poyarekar via Libc-alpha
  2020-12-28 16:44   ` Adhemerval Zanella via Libc-alpha
  2020-12-19  6:33 ` [PATCH 2/2] nonstring: " Siddhesh Poyarekar via Libc-alpha
  2020-12-22 13:00 ` [PATCH v6 0/2] _FORTIFY_SOURCE=3 Siddhesh Poyarekar
  2 siblings, 1 reply; 14+ messages in thread
From: Siddhesh Poyarekar via Libc-alpha @ 2020-12-19  6:33 UTC (permalink / raw
  To: libc-alpha; +Cc: fweimer, jakub

Introduce a new _FORTIFY_SOURCE level of 3 to enable additional
fortifications that may have a potential performance impact.  At the
moment this level of fortification involves the use of the
__builtin_dynamic_object_size builtin whenever the compiler supports
it.

This change enhances fortified string functions to use
__builtin_dynamic_object_size under _FORTIFY_SOURCE=3 whenever the
compiler supports it.

__builtin_dynamic_object_size
-----------------------------

__builtin_dynamic_object_size is an LLVM builtin that is similar to
__builtin_object_size.  In addition to what __builtin_object_size
does, i.e. replace the builtin call with a constant object size,
__builtin_dynamic_object_size will replace the call site with an
expression that evaluates to the object size, thus expanding its
applicability.  In practice, __builtin_dynamic_object_size evaluates
these expressions through malloc/calloc calls that it can associate
with the object being evaluated.

A simple motivating example is below; -D_FORTIFY_SOURCE=2 would miss
this and emit memcpy, but -D_FORTIFY_SOURCE=3 with the help of
__builtin_dynamic_object_size is able to emit __memcpy_chk with the
allocation size expression passed into the function:

void *copy_obj (const void *src, size_t alloc, size_t copysize)
{
  void *obj = malloc (alloc);
  memcpy (obj, src, copysize);

  return obj;
}

Limitations
-----------

If the object was allocated elsewhere that the compiler cannot see, or
if it was allocated in the function with a function that the compiler
does not recognize as an allocator then __builtin_dynamic_object_size
also returns -1.

Further, the expression used to compute object size may be non-trivial
and may potentially incur a noticeable performance impact.  These
fortifications are hence enabled at a new _FORTIFY_SOURCE level to
allow developers to make a choice on the tradeoff according to their
environment.

Other Changes
-------------

The _FORTIFY_SOURCE macro soup in features.h now warns about
unsupported fortification levels.  For example, it will warn about
_FORTIFY_SOURCE=3 and over for llvm older than 9.0 and for gcc and
_FORTIFY_SOURCE=4 will result in a warning on all compilers with an
indication of which level has been selected.

Co-authored-by: Paul Eggert <eggert@cs.ucla.edu>
---
 NEWS                            |  6 ++++++
 include/features.h              |  8 ++++++++
 include/string.h                |  5 +++--
 manual/creature.texi            |  3 ++-
 misc/sys/cdefs.h                |  9 +++++++++
 string/bits/string_fortified.h  | 22 +++++++++++-----------
 string/bits/strings_fortified.h |  4 ++--
 7 files changed, 41 insertions(+), 16 deletions(-)

diff --git a/NEWS b/NEWS
index 86e05fb023..8e02dbd0f7 100644
--- a/NEWS
+++ b/NEWS
@@ -28,6 +28,12 @@ Major new features:
   The 32-bit RISC-V port requires at least Linux 5.4, GCC 7.1 and binutils
   2.28.
 
+* A new fortification level _FORTIFY_SOURCE=3 is available.  At this level,
+  glibc may use additional checks that may have an additional performance
+  overhead.  At present these checks are available only on LLVM 9 and later.
+  The latest GCC available at this time (10.2) does not support this level of
+  fortification.
+
 Deprecated and removed features, and other changes affecting compatibility:
 
 * The mallinfo function is marked deprecated.  Callers should call
diff --git a/include/features.h b/include/features.h
index f3e62d3362..066eb0eecd 100644
--- a/include/features.h
+++ b/include/features.h
@@ -397,7 +397,15 @@
 #  warning _FORTIFY_SOURCE requires compiling with optimization (-O)
 # elif !__GNUC_PREREQ (4, 1)
 #  warning _FORTIFY_SOURCE requires GCC 4.1 or later
+# elif _FORTIFY_SOURCE > 2 && __glibc_clang_prereq (9, 0)
+#  if _FORTIFY_SOURCE > 3
+#   warning _FORTIFY_SOURCE > 3 is treated like 3 on this platform
+#  endif
+#  define __USE_FORTIFY_LEVEL 3
 # elif _FORTIFY_SOURCE > 1
+#  if _FORTIFY_SOURCE > 2
+#   warning _FORTIFY_SOURCE > 2 is treated like 2 on this platform
+#  endif
 #  define __USE_FORTIFY_LEVEL 2
 # else
 #  define __USE_FORTIFY_LEVEL 1
diff --git a/include/string.h b/include/string.h
index 7d344d77d4..841ee05a1d 100644
--- a/include/string.h
+++ b/include/string.h
@@ -123,10 +123,11 @@ libc_hidden_proto (__strerror_l)
 void __explicit_bzero_chk_internal (void *, size_t, size_t)
   __THROW __nonnull ((1)) attribute_hidden;
 # define explicit_bzero(buf, len) \
-  __explicit_bzero_chk_internal (buf, len, __bos0 (buf))
+  __explicit_bzero_chk_internal (buf, len, __objsize0 (buf))
 #elif !IS_IN (nonlib)
 void __explicit_bzero_chk (void *, size_t, size_t) __THROW __nonnull ((1));
-# define explicit_bzero(buf, len) __explicit_bzero_chk (buf, len, __bos0 (buf))
+# define explicit_bzero(buf, len) __explicit_bzero_chk (buf, len,	      \
+							__objsize0 (buf))
 #endif
 
 libc_hidden_builtin_proto (memchr)
diff --git a/manual/creature.texi b/manual/creature.texi
index be5050468b..31208ccb2b 100644
--- a/manual/creature.texi
+++ b/manual/creature.texi
@@ -254,7 +254,8 @@ included.
 @standards{GNU, (none)}
 If this macro is defined to @math{1}, security hardening is added to
 various library functions.  If defined to @math{2}, even stricter
-checks are applied.
+checks are applied. If defined to @math{3}, @theglibc{} may also use
+checks that may have an additional performance overhead.
 @end defvr
 
 @defvr Macro _REENTRANT
diff --git a/misc/sys/cdefs.h b/misc/sys/cdefs.h
index a06f1cfd91..ca51a5c3ad 100644
--- a/misc/sys/cdefs.h
+++ b/misc/sys/cdefs.h
@@ -127,6 +127,15 @@
 #define __bos(ptr) __builtin_object_size (ptr, __USE_FORTIFY_LEVEL > 1)
 #define __bos0(ptr) __builtin_object_size (ptr, 0)
 
+/* Use __builtin_dynamic_object_size at _FORTIFY_SOURCE=3 when available.  */
+#if __USE_FORTIFY_LEVEL == 3 && __glibc_clang_prereq (9, 0)
+# define __objsize0(__o) __builtin_dynamic_object_size (__o, 0)
+# define __objsize(__o) __builtin_dynamic_object_size (__o, 1)
+#else
+# define __objsize0(__o) __bos0 (__o)
+# define __objsize(__o) __bos (__o)
+#endif
+
 #if __GNUC_PREREQ (4,3)
 # define __warnattr(msg) __attribute__((__warning__ (msg)))
 # define __errordecl(name, msg) \
diff --git a/string/bits/string_fortified.h b/string/bits/string_fortified.h
index 4c1aeb45f1..c9f9197aef 100644
--- a/string/bits/string_fortified.h
+++ b/string/bits/string_fortified.h
@@ -26,13 +26,13 @@ __fortify_function void *
 __NTH (memcpy (void *__restrict __dest, const void *__restrict __src,
 	       size_t __len))
 {
-  return __builtin___memcpy_chk (__dest, __src, __len, __bos0 (__dest));
+  return __builtin___memcpy_chk (__dest, __src, __len, __objsize0 (__dest));
 }
 
 __fortify_function void *
 __NTH (memmove (void *__dest, const void *__src, size_t __len))
 {
-  return __builtin___memmove_chk (__dest, __src, __len, __bos0 (__dest));
+  return __builtin___memmove_chk (__dest, __src, __len, __objsize0 (__dest));
 }
 
 #ifdef __USE_GNU
@@ -40,7 +40,7 @@ __fortify_function void *
 __NTH (mempcpy (void *__restrict __dest, const void *__restrict __src,
 		size_t __len))
 {
-  return __builtin___mempcpy_chk (__dest, __src, __len, __bos0 (__dest));
+  return __builtin___mempcpy_chk (__dest, __src, __len, __objsize0 (__dest));
 }
 #endif
 
@@ -53,7 +53,7 @@ __NTH (mempcpy (void *__restrict __dest, const void *__restrict __src,
 __fortify_function void *
 __NTH (memset (void *__dest, int __ch, size_t __len))
 {
-  return __builtin___memset_chk (__dest, __ch, __len, __bos0 (__dest));
+  return __builtin___memset_chk (__dest, __ch, __len, __objsize0 (__dest));
 }
 
 #ifdef __USE_MISC
@@ -65,21 +65,21 @@ void __explicit_bzero_chk (void *__dest, size_t __len, size_t __destlen)
 __fortify_function void
 __NTH (explicit_bzero (void *__dest, size_t __len))
 {
-  __explicit_bzero_chk (__dest, __len, __bos0 (__dest));
+  __explicit_bzero_chk (__dest, __len, __objsize0 (__dest));
 }
 #endif
 
 __fortify_function char *
 __NTH (strcpy (char *__restrict __dest, const char *__restrict __src))
 {
-  return __builtin___strcpy_chk (__dest, __src, __bos (__dest));
+  return __builtin___strcpy_chk (__dest, __src, __objsize (__dest));
 }
 
 #ifdef __USE_GNU
 __fortify_function char *
 __NTH (stpcpy (char *__restrict __dest, const char *__restrict __src))
 {
-  return __builtin___stpcpy_chk (__dest, __src, __bos (__dest));
+  return __builtin___stpcpy_chk (__dest, __src, __objsize (__dest));
 }
 #endif
 
@@ -88,14 +88,14 @@ __fortify_function char *
 __NTH (strncpy (char *__restrict __dest, const char *__restrict __src,
 		size_t __len))
 {
-  return __builtin___strncpy_chk (__dest, __src, __len, __bos (__dest));
+  return __builtin___strncpy_chk (__dest, __src, __len, __objsize (__dest));
 }
 
 #if __GNUC_PREREQ (4, 7) || __glibc_clang_prereq (2, 6)
 __fortify_function char *
 __NTH (stpncpy (char *__dest, const char *__src, size_t __n))
 {
-  return __builtin___stpncpy_chk (__dest, __src, __n, __bos (__dest));
+  return __builtin___stpncpy_chk (__dest, __src, __n, __objsize (__dest));
 }
 #else
 extern char *__stpncpy_chk (char *__dest, const char *__src, size_t __n,
@@ -118,7 +118,7 @@ __NTH (stpncpy (char *__dest, const char *__src, size_t __n))
 __fortify_function char *
 __NTH (strcat (char *__restrict __dest, const char *__restrict __src))
 {
-  return __builtin___strcat_chk (__dest, __src, __bos (__dest));
+  return __builtin___strcat_chk (__dest, __src, __objsize (__dest));
 }
 
 
@@ -126,7 +126,7 @@ __fortify_function char *
 __NTH (strncat (char *__restrict __dest, const char *__restrict __src,
 		size_t __len))
 {
-  return __builtin___strncat_chk (__dest, __src, __len, __bos (__dest));
+  return __builtin___strncat_chk (__dest, __src, __len, __objsize (__dest));
 }
 
 #endif /* bits/string_fortified.h */
diff --git a/string/bits/strings_fortified.h b/string/bits/strings_fortified.h
index d4091f4f69..122199e036 100644
--- a/string/bits/strings_fortified.h
+++ b/string/bits/strings_fortified.h
@@ -22,13 +22,13 @@
 __fortify_function void
 __NTH (bcopy (const void *__src, void *__dest, size_t __len))
 {
-  (void) __builtin___memmove_chk (__dest, __src, __len, __bos0 (__dest));
+  (void) __builtin___memmove_chk (__dest, __src, __len, __objsize0 (__dest));
 }
 
 __fortify_function void
 __NTH (bzero (void *__dest, size_t __len))
 {
-  (void) __builtin___memset_chk (__dest, '\0', __len, __bos0 (__dest));
+  (void) __builtin___memset_chk (__dest, '\0', __len, __objsize0 (__dest));
 }
 
 #endif
-- 
2.29.2


^ permalink raw reply related	[flat|nested] 14+ messages in thread

* [PATCH 2/2] nonstring: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size
  2020-12-19  6:33 [PATCH v6 0/2] _FORTIFY_SOURCE=3 Siddhesh Poyarekar via Libc-alpha
  2020-12-19  6:33 ` [PATCH 1/2] string: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size Siddhesh Poyarekar via Libc-alpha
@ 2020-12-19  6:33 ` Siddhesh Poyarekar via Libc-alpha
  2020-12-28 17:36   ` Adhemerval Zanella via Libc-alpha
  2020-12-22 13:00 ` [PATCH v6 0/2] _FORTIFY_SOURCE=3 Siddhesh Poyarekar
  2 siblings, 1 reply; 14+ messages in thread
From: Siddhesh Poyarekar via Libc-alpha @ 2020-12-19  6:33 UTC (permalink / raw
  To: libc-alpha; +Cc: fweimer, jakub

These fortified functions use, roughly, the following idiom to
implement fortifications:

  if (__builtin_dynamic_object_size (obj) != -1)
    {
      __fortified_chk ();
      return;
    }
  __unfortified ();

LLVM is currently unable to fold the conditional; a patch has been
proposed[1] to fix this.

Due to this limitation in llvm, these fortifications have a higher
performance cost than those in the first patch.

[1] https://reviews.llvm.org/D93015
---
 io/bits/poll2.h       |  16 +++---
 libio/bits/stdio.h    |   2 +-
 libio/bits/stdio2.h   |  53 ++++++++---------
 posix/bits/unistd.h   | 112 +++++++++++++++++++-----------------
 socket/bits/socket2.h |  18 +++---
 stdlib/bits/stdlib.h  |  37 ++++++------
 wcsmbs/bits/wchar2.h  | 131 +++++++++++++++++++++---------------------
 7 files changed, 189 insertions(+), 180 deletions(-)

diff --git a/io/bits/poll2.h b/io/bits/poll2.h
index dca49717db..ce107b8e50 100644
--- a/io/bits/poll2.h
+++ b/io/bits/poll2.h
@@ -35,12 +35,12 @@ extern int __REDIRECT (__poll_chk_warn, (struct pollfd *__fds, nfds_t __nfds,
 __fortify_function int
 poll (struct pollfd *__fds, nfds_t __nfds, int __timeout)
 {
-  if (__bos (__fds) != (__SIZE_TYPE__) -1)
+  if (__objsize (__fds) != (__SIZE_TYPE__) -1)
     {
       if (! __builtin_constant_p (__nfds))
-	return __poll_chk (__fds, __nfds, __timeout, __bos (__fds));
-      else if (__bos (__fds) / sizeof (*__fds) < __nfds)
-	return __poll_chk_warn (__fds, __nfds, __timeout, __bos (__fds));
+	return __poll_chk (__fds, __nfds, __timeout, __objsize (__fds));
+      else if (__objsize (__fds) / sizeof (*__fds) < __nfds)
+	return __poll_chk_warn (__fds, __nfds, __timeout, __objsize (__fds));
     }
 
   return __poll_alias (__fds, __nfds, __timeout);
@@ -65,13 +65,13 @@ __fortify_function int
 ppoll (struct pollfd *__fds, nfds_t __nfds, const struct timespec *__timeout,
        const __sigset_t *__ss)
 {
-  if (__bos (__fds) != (__SIZE_TYPE__) -1)
+  if (__objsize (__fds) != (__SIZE_TYPE__) -1)
     {
       if (! __builtin_constant_p (__nfds))
-	return __ppoll_chk (__fds, __nfds, __timeout, __ss, __bos (__fds));
-      else if (__bos (__fds) / sizeof (*__fds) < __nfds)
+	return __ppoll_chk (__fds, __nfds, __timeout, __ss, __objsize (__fds));
+      else if (__objsize (__fds) / sizeof (*__fds) < __nfds)
 	return __ppoll_chk_warn (__fds, __nfds, __timeout, __ss,
-				 __bos (__fds));
+				 __objsize (__fds));
     }
 
   return __ppoll_alias (__fds, __nfds, __timeout, __ss);
diff --git a/libio/bits/stdio.h b/libio/bits/stdio.h
index 6745571ed5..6d1f0f9fc9 100644
--- a/libio/bits/stdio.h
+++ b/libio/bits/stdio.h
@@ -31,7 +31,7 @@
 
 
 #ifdef __USE_EXTERN_INLINES
-/* For -D_FORTIFY_SOURCE{,=2} bits/stdio2.h will define a different
+/* For -D_FORTIFY_SOURCE{,=2,=3} bits/stdio2.h will define a different
    inline.  */
 # if !(__USE_FORTIFY_LEVEL > 0 && defined __fortify_function)
 /* Write formatted output to stdout from argument list ARG.  */
diff --git a/libio/bits/stdio2.h b/libio/bits/stdio2.h
index ff9202c2cb..b5e804ca13 100644
--- a/libio/bits/stdio2.h
+++ b/libio/bits/stdio2.h
@@ -36,11 +36,11 @@ __fortify_function int
 __NTH (sprintf (char *__restrict __s, const char *__restrict __fmt, ...))
 {
   return __builtin___sprintf_chk (__s, __USE_FORTIFY_LEVEL - 1,
-				  __bos (__s), __fmt, __va_arg_pack ());
+				  __objsize (__s), __fmt, __va_arg_pack ());
 }
 #elif !defined __cplusplus
 # define sprintf(str, ...) \
-  __builtin___sprintf_chk (str, __USE_FORTIFY_LEVEL - 1, __bos (str), \
+  __builtin___sprintf_chk (str, __USE_FORTIFY_LEVEL - 1, __objsize (str), \
 			   __VA_ARGS__)
 #endif
 
@@ -49,7 +49,7 @@ __NTH (vsprintf (char *__restrict __s, const char *__restrict __fmt,
 		 __gnuc_va_list __ap))
 {
   return __builtin___vsprintf_chk (__s, __USE_FORTIFY_LEVEL - 1,
-				   __bos (__s), __fmt, __ap);
+				   __objsize (__s), __fmt, __ap);
 }
 
 #if defined __USE_ISOC99 || defined __USE_UNIX98
@@ -68,12 +68,12 @@ __NTH (snprintf (char *__restrict __s, size_t __n,
 		 const char *__restrict __fmt, ...))
 {
   return __builtin___snprintf_chk (__s, __n, __USE_FORTIFY_LEVEL - 1,
-				   __bos (__s), __fmt, __va_arg_pack ());
+				   __objsize (__s), __fmt, __va_arg_pack ());
 }
 # elif !defined __cplusplus
 #  define snprintf(str, len, ...) \
-  __builtin___snprintf_chk (str, len, __USE_FORTIFY_LEVEL - 1, __bos (str), \
-			    __VA_ARGS__)
+  __builtin___snprintf_chk (str, len, __USE_FORTIFY_LEVEL - 1,		      \
+			    __objsize (str), __VA_ARGS__)
 # endif
 
 __fortify_function int
@@ -81,7 +81,7 @@ __NTH (vsnprintf (char *__restrict __s, size_t __n,
 		  const char *__restrict __fmt, __gnuc_va_list __ap))
 {
   return __builtin___vsnprintf_chk (__s, __n, __USE_FORTIFY_LEVEL - 1,
-				    __bos (__s), __fmt, __ap);
+				    __objsize (__s), __fmt, __ap);
 }
 
 #endif
@@ -237,8 +237,8 @@ extern char *__REDIRECT (__gets_warn, (char *__str), gets)
 __fortify_function __wur char *
 gets (char *__str)
 {
-  if (__bos (__str) != (size_t) -1)
-    return __gets_chk (__str, __bos (__str));
+  if (__objsize (__str) != (size_t) -1)
+    return __gets_chk (__str, __objsize (__str));
   return __gets_warn (__str);
 }
 #endif
@@ -259,13 +259,13 @@ extern char *__REDIRECT (__fgets_chk_warn,
 __fortify_function __wur __attr_access ((__write_only__, 1, 2)) char *
 fgets (char *__restrict __s, int __n, FILE *__restrict __stream)
 {
-  if (__bos (__s) != (size_t) -1)
+  if (__objsize (__s) != (size_t) -1)
     {
       if (!__builtin_constant_p (__n) || __n <= 0)
-	return __fgets_chk (__s, __bos (__s), __n, __stream);
+	return __fgets_chk (__s, __objsize (__s), __n, __stream);
 
-      if ((size_t) __n > __bos (__s))
-	return __fgets_chk_warn (__s, __bos (__s), __n, __stream);
+      if ((size_t) __n > __objsize (__s))
+	return __fgets_chk_warn (__s, __objsize (__s), __n, __stream);
     }
   return __fgets_alias (__s, __n, __stream);
 }
@@ -289,15 +289,16 @@ __fortify_function __wur size_t
 fread (void *__restrict __ptr, size_t __size, size_t __n,
        FILE *__restrict __stream)
 {
-  if (__bos0 (__ptr) != (size_t) -1)
+  if (__objsize0 (__ptr) != (size_t) -1)
     {
       if (!__builtin_constant_p (__size)
 	  || !__builtin_constant_p (__n)
 	  || (__size | __n) >= (((size_t) 1) << (8 * sizeof (size_t) / 2)))
-	return __fread_chk (__ptr, __bos0 (__ptr), __size, __n, __stream);
+	return __fread_chk (__ptr, __objsize0 (__ptr), __size, __n, __stream);
 
-      if (__size * __n > __bos0 (__ptr))
-	return __fread_chk_warn (__ptr, __bos0 (__ptr), __size, __n, __stream);
+      if (__size * __n > __objsize0 (__ptr))
+	return __fread_chk_warn (__ptr, __objsize0 (__ptr), __size, __n,
+				 __stream);
     }
   return __fread_alias (__ptr, __size, __n, __stream);
 }
@@ -319,13 +320,13 @@ extern char *__REDIRECT (__fgets_unlocked_chk_warn,
 __fortify_function __wur __attr_access ((__write_only__, 1, 2)) char *
 fgets_unlocked (char *__restrict __s, int __n, FILE *__restrict __stream)
 {
-  if (__bos (__s) != (size_t) -1)
+  if (__objsize (__s) != (size_t) -1)
     {
       if (!__builtin_constant_p (__n) || __n <= 0)
-	return __fgets_unlocked_chk (__s, __bos (__s), __n, __stream);
+	return __fgets_unlocked_chk (__s, __objsize (__s), __n, __stream);
 
-      if ((size_t) __n > __bos (__s))
-	return __fgets_unlocked_chk_warn (__s, __bos (__s), __n, __stream);
+      if ((size_t) __n > __objsize (__s))
+	return __fgets_unlocked_chk_warn (__s, __objsize (__s), __n, __stream);
     }
   return __fgets_unlocked_alias (__s, __n, __stream);
 }
@@ -352,17 +353,17 @@ __fortify_function __wur size_t
 fread_unlocked (void *__restrict __ptr, size_t __size, size_t __n,
 		FILE *__restrict __stream)
 {
-  if (__bos0 (__ptr) != (size_t) -1)
+  if (__objsize0 (__ptr) != (size_t) -1)
     {
       if (!__builtin_constant_p (__size)
 	  || !__builtin_constant_p (__n)
 	  || (__size | __n) >= (((size_t) 1) << (8 * sizeof (size_t) / 2)))
-	return __fread_unlocked_chk (__ptr, __bos0 (__ptr), __size, __n,
+	return __fread_unlocked_chk (__ptr, __objsize0 (__ptr), __size, __n,
 				     __stream);
 
-      if (__size * __n > __bos0 (__ptr))
-	return __fread_unlocked_chk_warn (__ptr, __bos0 (__ptr), __size, __n,
-					  __stream);
+      if (__size * __n > __objsize0 (__ptr))
+	return __fread_unlocked_chk_warn (__ptr, __objsize0 (__ptr), __size,
+					  __n, __stream);
     }
 
 # ifdef __USE_EXTERN_INLINES
diff --git a/posix/bits/unistd.h b/posix/bits/unistd.h
index 725a83eb0d..e1c44da01c 100644
--- a/posix/bits/unistd.h
+++ b/posix/bits/unistd.h
@@ -35,13 +35,13 @@ extern ssize_t __REDIRECT (__read_chk_warn,
 __fortify_function __wur ssize_t
 read (int __fd, void *__buf, size_t __nbytes)
 {
-  if (__bos0 (__buf) != (size_t) -1)
+  if (__objsize0 (__buf) != (size_t) -1)
     {
       if (!__builtin_constant_p (__nbytes))
-	return __read_chk (__fd, __buf, __nbytes, __bos0 (__buf));
+	return __read_chk (__fd, __buf, __nbytes, __objsize0 (__buf));
 
-      if (__nbytes > __bos0 (__buf))
-	return __read_chk_warn (__fd, __buf, __nbytes, __bos0 (__buf));
+      if (__nbytes > __objsize0 (__buf))
+	return __read_chk_warn (__fd, __buf, __nbytes, __objsize0 (__buf));
     }
   return __read_alias (__fd, __buf, __nbytes);
 }
@@ -77,14 +77,15 @@ extern ssize_t __REDIRECT (__pread64_chk_warn,
 __fortify_function __wur ssize_t
 pread (int __fd, void *__buf, size_t __nbytes, __off_t __offset)
 {
-  if (__bos0 (__buf) != (size_t) -1)
+  if (__objsize0 (__buf) != (size_t) -1)
     {
       if (!__builtin_constant_p (__nbytes))
-	return __pread_chk (__fd, __buf, __nbytes, __offset, __bos0 (__buf));
+	return __pread_chk (__fd, __buf, __nbytes, __offset,
+			    __objsize0 (__buf));
 
-      if ( __nbytes > __bos0 (__buf))
+      if ( __nbytes > __objsize0 (__buf))
 	return __pread_chk_warn (__fd, __buf, __nbytes, __offset,
-				 __bos0 (__buf));
+				 __objsize0 (__buf));
     }
   return __pread_alias (__fd, __buf, __nbytes, __offset);
 }
@@ -92,14 +93,15 @@ pread (int __fd, void *__buf, size_t __nbytes, __off_t __offset)
 __fortify_function __wur ssize_t
 pread (int __fd, void *__buf, size_t __nbytes, __off64_t __offset)
 {
-  if (__bos0 (__buf) != (size_t) -1)
+  if (__objsize0 (__buf) != (size_t) -1)
     {
       if (!__builtin_constant_p (__nbytes))
-	return __pread64_chk (__fd, __buf, __nbytes, __offset, __bos0 (__buf));
+	return __pread64_chk (__fd, __buf, __nbytes, __offset,
+			      __objsize0 (__buf));
 
-      if ( __nbytes > __bos0 (__buf))
+      if ( __nbytes > __objsize0 (__buf))
 	return __pread64_chk_warn (__fd, __buf, __nbytes, __offset,
-				   __bos0 (__buf));
+				   __objsize0 (__buf));
     }
 
   return __pread64_alias (__fd, __buf, __nbytes, __offset);
@@ -110,14 +112,15 @@ pread (int __fd, void *__buf, size_t __nbytes, __off64_t __offset)
 __fortify_function __wur ssize_t
 pread64 (int __fd, void *__buf, size_t __nbytes, __off64_t __offset)
 {
-  if (__bos0 (__buf) != (size_t) -1)
+  if (__objsize0 (__buf) != (size_t) -1)
     {
       if (!__builtin_constant_p (__nbytes))
-	return __pread64_chk (__fd, __buf, __nbytes, __offset, __bos0 (__buf));
+	return __pread64_chk (__fd, __buf, __nbytes, __offset,
+			      __objsize0 (__buf));
 
-      if ( __nbytes > __bos0 (__buf))
+      if ( __nbytes > __objsize0 (__buf))
 	return __pread64_chk_warn (__fd, __buf, __nbytes, __offset,
-				   __bos0 (__buf));
+				   __objsize0 (__buf));
     }
 
   return __pread64_alias (__fd, __buf, __nbytes, __offset);
@@ -145,13 +148,13 @@ __fortify_function __nonnull ((1, 2)) __wur ssize_t
 __NTH (readlink (const char *__restrict __path, char *__restrict __buf,
 		 size_t __len))
 {
-  if (__bos (__buf) != (size_t) -1)
+  if (__objsize (__buf) != (size_t) -1)
     {
       if (!__builtin_constant_p (__len))
-	return __readlink_chk (__path, __buf, __len, __bos (__buf));
+	return __readlink_chk (__path, __buf, __len, __objsize (__buf));
 
-      if ( __len > __bos (__buf))
-	return __readlink_chk_warn (__path, __buf, __len, __bos (__buf));
+      if ( __len > __objsize (__buf))
+	return __readlink_chk_warn (__path, __buf, __len, __objsize (__buf));
     }
   return __readlink_alias (__path, __buf, __len);
 }
@@ -179,14 +182,15 @@ __fortify_function __nonnull ((2, 3)) __wur ssize_t
 __NTH (readlinkat (int __fd, const char *__restrict __path,
 		   char *__restrict __buf, size_t __len))
 {
-  if (__bos (__buf) != (size_t) -1)
+  if (__objsize (__buf) != (size_t) -1)
     {
       if (!__builtin_constant_p (__len))
-	return __readlinkat_chk (__fd, __path, __buf, __len, __bos (__buf));
+	return __readlinkat_chk (__fd, __path, __buf, __len,
+				 __objsize (__buf));
 
-      if (__len > __bos (__buf))
+      if (__len > __objsize (__buf))
 	return __readlinkat_chk_warn (__fd, __path, __buf, __len,
-				      __bos (__buf));
+				      __objsize (__buf));
     }
   return __readlinkat_alias (__fd, __path, __buf, __len);
 }
@@ -206,13 +210,13 @@ extern char *__REDIRECT_NTH (__getcwd_chk_warn,
 __fortify_function __wur char *
 __NTH (getcwd (char *__buf, size_t __size))
 {
-  if (__bos (__buf) != (size_t) -1)
+  if (__objsize (__buf) != (size_t) -1)
     {
       if (!__builtin_constant_p (__size))
-	return __getcwd_chk (__buf, __size, __bos (__buf));
+	return __getcwd_chk (__buf, __size, __objsize (__buf));
 
-      if (__size > __bos (__buf))
-	return __getcwd_chk_warn (__buf, __size, __bos (__buf));
+      if (__size > __objsize (__buf))
+	return __getcwd_chk_warn (__buf, __size, __objsize (__buf));
     }
   return __getcwd_alias (__buf, __size);
 }
@@ -227,8 +231,8 @@ extern char *__REDIRECT_NTH (__getwd_warn, (char *__buf), getwd)
 __fortify_function __nonnull ((1)) __attribute_deprecated__ __wur char *
 __NTH (getwd (char *__buf))
 {
-  if (__bos (__buf) != (size_t) -1)
-    return __getwd_chk (__buf, __bos (__buf));
+  if (__objsize (__buf) != (size_t) -1)
+    return __getwd_chk (__buf, __objsize (__buf));
   return __getwd_warn (__buf);
 }
 #endif
@@ -248,13 +252,13 @@ extern size_t __REDIRECT_NTH (__confstr_chk_warn,
 __fortify_function size_t
 __NTH (confstr (int __name, char *__buf, size_t __len))
 {
-  if (__bos (__buf) != (size_t) -1)
+  if (__objsize (__buf) != (size_t) -1)
     {
       if (!__builtin_constant_p (__len))
-	return __confstr_chk (__name, __buf, __len, __bos (__buf));
+	return __confstr_chk (__name, __buf, __len, __objsize (__buf));
 
-      if (__bos (__buf) < __len)
-	return __confstr_chk_warn (__name, __buf, __len, __bos (__buf));
+      if (__objsize (__buf) < __len)
+	return __confstr_chk_warn (__name, __buf, __len, __objsize (__buf));
     }
   return __confstr_alias (__name, __buf, __len);
 }
@@ -273,13 +277,13 @@ extern int __REDIRECT_NTH (__getgroups_chk_warn,
 __fortify_function int
 __NTH (getgroups (int __size, __gid_t __list[]))
 {
-  if (__bos (__list) != (size_t) -1)
+  if (__objsize (__list) != (size_t) -1)
     {
       if (!__builtin_constant_p (__size) || __size < 0)
-	return __getgroups_chk (__size, __list, __bos (__list));
+	return __getgroups_chk (__size, __list, __objsize (__list));
 
-      if (__size * sizeof (__gid_t) > __bos (__list))
-	return __getgroups_chk_warn (__size, __list, __bos (__list));
+      if (__size * sizeof (__gid_t) > __objsize (__list))
+	return __getgroups_chk_warn (__size, __list, __objsize (__list));
     }
   return __getgroups_alias (__size, __list);
 }
@@ -300,13 +304,13 @@ extern int __REDIRECT_NTH (__ttyname_r_chk_warn,
 __fortify_function int
 __NTH (ttyname_r (int __fd, char *__buf, size_t __buflen))
 {
-  if (__bos (__buf) != (size_t) -1)
+  if (__objsize (__buf) != (size_t) -1)
     {
       if (!__builtin_constant_p (__buflen))
-	return __ttyname_r_chk (__fd, __buf, __buflen, __bos (__buf));
+	return __ttyname_r_chk (__fd, __buf, __buflen, __objsize (__buf));
 
-      if (__buflen > __bos (__buf))
-	return __ttyname_r_chk_warn (__fd, __buf, __buflen, __bos (__buf));
+      if (__buflen > __objsize (__buf))
+	return __ttyname_r_chk_warn (__fd, __buf, __buflen, __objsize (__buf));
     }
   return __ttyname_r_alias (__fd, __buf, __buflen);
 }
@@ -326,13 +330,13 @@ extern int __REDIRECT (__getlogin_r_chk_warn,
 __fortify_function int
 getlogin_r (char *__buf, size_t __buflen)
 {
-  if (__bos (__buf) != (size_t) -1)
+  if (__objsize (__buf) != (size_t) -1)
     {
       if (!__builtin_constant_p (__buflen))
-	return __getlogin_r_chk (__buf, __buflen, __bos (__buf));
+	return __getlogin_r_chk (__buf, __buflen, __objsize (__buf));
 
-      if (__buflen > __bos (__buf))
-	return __getlogin_r_chk_warn (__buf, __buflen, __bos (__buf));
+      if (__buflen > __objsize (__buf))
+	return __getlogin_r_chk_warn (__buf, __buflen, __objsize (__buf));
     }
   return __getlogin_r_alias (__buf, __buflen);
 }
@@ -354,13 +358,13 @@ extern int __REDIRECT_NTH (__gethostname_chk_warn,
 __fortify_function int
 __NTH (gethostname (char *__buf, size_t __buflen))
 {
-  if (__bos (__buf) != (size_t) -1)
+  if (__objsize (__buf) != (size_t) -1)
     {
       if (!__builtin_constant_p (__buflen))
-	return __gethostname_chk (__buf, __buflen, __bos (__buf));
+	return __gethostname_chk (__buf, __buflen, __objsize (__buf));
 
-      if (__buflen > __bos (__buf))
-	return __gethostname_chk_warn (__buf, __buflen, __bos (__buf));
+      if (__buflen > __objsize (__buf))
+	return __gethostname_chk_warn (__buf, __buflen, __objsize (__buf));
     }
   return __gethostname_alias (__buf, __buflen);
 }
@@ -384,13 +388,13 @@ extern int __REDIRECT_NTH (__getdomainname_chk_warn,
 __fortify_function int
 __NTH (getdomainname (char *__buf, size_t __buflen))
 {
-  if (__bos (__buf) != (size_t) -1)
+  if (__objsize (__buf) != (size_t) -1)
     {
       if (!__builtin_constant_p (__buflen))
-	return __getdomainname_chk (__buf, __buflen, __bos (__buf));
+	return __getdomainname_chk (__buf, __buflen, __objsize (__buf));
 
-      if (__buflen > __bos (__buf))
-	return __getdomainname_chk_warn (__buf, __buflen, __bos (__buf));
+      if (__buflen > __objsize (__buf))
+	return __getdomainname_chk_warn (__buf, __buflen, __objsize (__buf));
     }
   return __getdomainname_alias (__buf, __buflen);
 }
diff --git a/socket/bits/socket2.h b/socket/bits/socket2.h
index c0421ce244..7f11cbeba9 100644
--- a/socket/bits/socket2.h
+++ b/socket/bits/socket2.h
@@ -33,13 +33,13 @@ extern ssize_t __REDIRECT (__recv_chk_warn,
 __fortify_function ssize_t
 recv (int __fd, void *__buf, size_t __n, int __flags)
 {
-  if (__bos0 (__buf) != (size_t) -1)
+  if (__objsize0 (__buf) != (size_t) -1)
     {
       if (!__builtin_constant_p (__n))
-	return __recv_chk (__fd, __buf, __n, __bos0 (__buf), __flags);
+	return __recv_chk (__fd, __buf, __n, __objsize0 (__buf), __flags);
 
-      if (__n > __bos0 (__buf))
-	return __recv_chk_warn (__fd, __buf, __n, __bos0 (__buf), __flags);
+      if (__n > __objsize0 (__buf))
+	return __recv_chk_warn (__fd, __buf, __n, __objsize0 (__buf), __flags);
     }
   return __recv_alias (__fd, __buf, __n, __flags);
 }
@@ -64,14 +64,14 @@ __fortify_function ssize_t
 recvfrom (int __fd, void *__restrict __buf, size_t __n, int __flags,
 	  __SOCKADDR_ARG __addr, socklen_t *__restrict __addr_len)
 {
-  if (__bos0 (__buf) != (size_t) -1)
+  if (__objsize0 (__buf) != (size_t) -1)
     {
       if (!__builtin_constant_p (__n))
-	return __recvfrom_chk (__fd, __buf, __n, __bos0 (__buf), __flags,
+	return __recvfrom_chk (__fd, __buf, __n, __objsize0 (__buf), __flags,
 			       __addr, __addr_len);
-      if (__n > __bos0 (__buf))
-	return __recvfrom_chk_warn (__fd, __buf, __n, __bos0 (__buf), __flags,
-				    __addr, __addr_len);
+      if (__n > __objsize0 (__buf))
+	return __recvfrom_chk_warn (__fd, __buf, __n, __objsize0 (__buf),
+				    __flags, __addr, __addr_len);
     }
   return __recvfrom_alias (__fd, __buf, __n, __flags, __addr, __addr_len);
 }
diff --git a/stdlib/bits/stdlib.h b/stdlib/bits/stdlib.h
index 9134d3f36b..3cb1bd9721 100644
--- a/stdlib/bits/stdlib.h
+++ b/stdlib/bits/stdlib.h
@@ -36,13 +36,14 @@ extern char *__REDIRECT_NTH (__realpath_chk_warn,
 __fortify_function __wur char *
 __NTH (realpath (const char *__restrict __name, char *__restrict __resolved))
 {
-  if (__bos (__resolved) != (size_t) -1)
+  if (__objsize (__resolved) != (size_t) -1)
     {
 #if defined _LIBC_LIMITS_H_ && defined PATH_MAX
-      if (__bos (__resolved) < PATH_MAX)
-	return __realpath_chk_warn (__name, __resolved, __bos (__resolved));
+      if (__objsize (__resolved) < PATH_MAX)
+	return __realpath_chk_warn (__name, __resolved,
+				    __objsize (__resolved));
 #endif
-      return __realpath_chk (__name, __resolved, __bos (__resolved));
+      return __realpath_chk (__name, __resolved, __objsize (__resolved));
     }
 
   return __realpath_alias (__name, __resolved);
@@ -64,12 +65,12 @@ extern int __REDIRECT_NTH (__ptsname_r_chk_warn,
 __fortify_function int
 __NTH (ptsname_r (int __fd, char *__buf, size_t __buflen))
 {
-  if (__bos (__buf) != (size_t) -1)
+  if (__objsize (__buf) != (size_t) -1)
     {
       if (!__builtin_constant_p (__buflen))
-	return __ptsname_r_chk (__fd, __buf, __buflen, __bos (__buf));
-      if (__buflen > __bos (__buf))
-	return __ptsname_r_chk_warn (__fd, __buf, __buflen, __bos (__buf));
+	return __ptsname_r_chk (__fd, __buf, __buflen, __objsize (__buf));
+      if (__buflen > __objsize (__buf))
+	return __ptsname_r_chk_warn (__fd, __buf, __buflen, __objsize (__buf));
     }
   return __ptsname_r_alias (__fd, __buf, __buflen);
 }
@@ -90,8 +91,8 @@ __NTH (wctomb (char *__s, wchar_t __wchar))
 #if defined MB_LEN_MAX && MB_LEN_MAX != __STDLIB_MB_LEN_MAX
 # error "Assumed value of MB_LEN_MAX wrong"
 #endif
-  if (__bos (__s) != (size_t) -1 && __STDLIB_MB_LEN_MAX > __bos (__s))
-    return __wctomb_chk (__s, __wchar, __bos (__s));
+  if (__objsize (__s) != (size_t) -1 && __STDLIB_MB_LEN_MAX > __objsize (__s))
+    return __wctomb_chk (__s, __wchar, __objsize (__s));
   return __wctomb_alias (__s, __wchar);
 }
 
@@ -116,15 +117,15 @@ __fortify_function size_t
 __NTH (mbstowcs (wchar_t *__restrict __dst, const char *__restrict __src,
 		 size_t __len))
 {
-  if (__bos (__dst) != (size_t) -1)
+  if (__objsize (__dst) != (size_t) -1)
     {
       if (!__builtin_constant_p (__len))
 	return __mbstowcs_chk (__dst, __src, __len,
-			       __bos (__dst) / sizeof (wchar_t));
+			       __objsize (__dst) / sizeof (wchar_t));
 
-      if (__len > __bos (__dst) / sizeof (wchar_t))
+      if (__len > __objsize (__dst) / sizeof (wchar_t))
 	return __mbstowcs_chk_warn (__dst, __src, __len,
-				     __bos (__dst) / sizeof (wchar_t));
+				     __objsize (__dst) / sizeof (wchar_t));
     }
   return __mbstowcs_alias (__dst, __src, __len);
 }
@@ -149,12 +150,12 @@ __fortify_function size_t
 __NTH (wcstombs (char *__restrict __dst, const wchar_t *__restrict __src,
 		 size_t __len))
 {
-  if (__bos (__dst) != (size_t) -1)
+  if (__objsize (__dst) != (size_t) -1)
     {
       if (!__builtin_constant_p (__len))
-	return __wcstombs_chk (__dst, __src, __len, __bos (__dst));
-      if (__len > __bos (__dst))
-	return __wcstombs_chk_warn (__dst, __src, __len, __bos (__dst));
+	return __wcstombs_chk (__dst, __src, __len, __objsize (__dst));
+      if (__len > __objsize (__dst))
+	return __wcstombs_chk_warn (__dst, __src, __len, __objsize (__dst));
     }
   return __wcstombs_alias (__dst, __src, __len);
 }
diff --git a/wcsmbs/bits/wchar2.h b/wcsmbs/bits/wchar2.h
index 86e8e23e76..6a67b4bc1c 100644
--- a/wcsmbs/bits/wchar2.h
+++ b/wcsmbs/bits/wchar2.h
@@ -39,15 +39,15 @@ __fortify_function wchar_t *
 __NTH (wmemcpy (wchar_t *__restrict __s1, const wchar_t *__restrict __s2,
 		size_t __n))
 {
-  if (__bos0 (__s1) != (size_t) -1)
+  if (__objsize0 (__s1) != (size_t) -1)
     {
       if (!__builtin_constant_p (__n))
 	return __wmemcpy_chk (__s1, __s2, __n,
-			      __bos0 (__s1) / sizeof (wchar_t));
+			      __objsize0 (__s1) / sizeof (wchar_t));
 
-      if (__n > __bos0 (__s1) / sizeof (wchar_t))
+      if (__n > __objsize0 (__s1) / sizeof (wchar_t))
 	return __wmemcpy_chk_warn (__s1, __s2, __n,
-				   __bos0 (__s1) / sizeof (wchar_t));
+				   __objsize0 (__s1) / sizeof (wchar_t));
     }
   return __wmemcpy_alias (__s1, __s2, __n);
 }
@@ -67,15 +67,15 @@ extern wchar_t *__REDIRECT_NTH (__wmemmove_chk_warn,
 __fortify_function wchar_t *
 __NTH (wmemmove (wchar_t *__s1, const wchar_t *__s2, size_t __n))
 {
-  if (__bos0 (__s1) != (size_t) -1)
+  if (__objsize0 (__s1) != (size_t) -1)
     {
       if (!__builtin_constant_p (__n))
 	return __wmemmove_chk (__s1, __s2, __n,
-			       __bos0 (__s1) / sizeof (wchar_t));
+			       __objsize0 (__s1) / sizeof (wchar_t));
 
-      if (__n > __bos0 (__s1) / sizeof (wchar_t))
+      if (__n > __objsize0 (__s1) / sizeof (wchar_t))
 	return __wmemmove_chk_warn (__s1, __s2, __n,
-				    __bos0 (__s1) / sizeof (wchar_t));
+				    __objsize0 (__s1) / sizeof (wchar_t));
     }
   return __wmemmove_alias (__s1, __s2, __n);
 }
@@ -100,15 +100,15 @@ __fortify_function wchar_t *
 __NTH (wmempcpy (wchar_t *__restrict __s1, const wchar_t *__restrict __s2,
 		 size_t __n))
 {
-  if (__bos0 (__s1) != (size_t) -1)
+  if (__objsize0 (__s1) != (size_t) -1)
     {
       if (!__builtin_constant_p (__n))
 	return __wmempcpy_chk (__s1, __s2, __n,
-			       __bos0 (__s1) / sizeof (wchar_t));
+			       __objsize0 (__s1) / sizeof (wchar_t));
 
-      if (__n > __bos0 (__s1) / sizeof (wchar_t))
+      if (__n > __objsize0 (__s1) / sizeof (wchar_t))
 	return __wmempcpy_chk_warn (__s1, __s2, __n,
-				    __bos0 (__s1) / sizeof (wchar_t));
+				    __objsize0 (__s1) / sizeof (wchar_t));
     }
   return __wmempcpy_alias (__s1, __s2, __n);
 }
@@ -128,14 +128,15 @@ extern wchar_t *__REDIRECT_NTH (__wmemset_chk_warn,
 __fortify_function wchar_t *
 __NTH (wmemset (wchar_t *__s, wchar_t __c, size_t __n))
 {
-  if (__bos0 (__s) != (size_t) -1)
+  if (__objsize0 (__s) != (size_t) -1)
     {
       if (!__builtin_constant_p (__n))
-	return __wmemset_chk (__s, __c, __n, __bos0 (__s) / sizeof (wchar_t));
+	return __wmemset_chk (__s, __c, __n,
+			      __objsize0 (__s) / sizeof (wchar_t));
 
-      if (__n > __bos0 (__s) / sizeof (wchar_t))
+      if (__n > __objsize0 (__s) / sizeof (wchar_t))
 	return __wmemset_chk_warn (__s, __c, __n,
-				   __bos0 (__s) / sizeof (wchar_t));
+				   __objsize0 (__s) / sizeof (wchar_t));
     }
   return __wmemset_alias (__s, __c, __n);
 }
@@ -151,8 +152,8 @@ extern wchar_t *__REDIRECT_NTH (__wcscpy_alias,
 __fortify_function wchar_t *
 __NTH (wcscpy (wchar_t *__restrict __dest, const wchar_t *__restrict __src))
 {
-  if (__bos (__dest) != (size_t) -1)
-    return __wcscpy_chk (__dest, __src, __bos (__dest) / sizeof (wchar_t));
+  if (__objsize (__dest) != (size_t) -1)
+    return __wcscpy_chk (__dest, __src, __objsize (__dest) / sizeof (wchar_t));
   return __wcscpy_alias (__dest, __src);
 }
 
@@ -167,8 +168,8 @@ extern wchar_t *__REDIRECT_NTH (__wcpcpy_alias,
 __fortify_function wchar_t *
 __NTH (wcpcpy (wchar_t *__restrict __dest, const wchar_t *__restrict __src))
 {
-  if (__bos (__dest) != (size_t) -1)
-    return __wcpcpy_chk (__dest, __src, __bos (__dest) / sizeof (wchar_t));
+  if (__objsize (__dest) != (size_t) -1)
+    return __wcpcpy_chk (__dest, __src, __objsize (__dest) / sizeof (wchar_t));
   return __wcpcpy_alias (__dest, __src);
 }
 
@@ -191,14 +192,14 @@ __fortify_function wchar_t *
 __NTH (wcsncpy (wchar_t *__restrict __dest, const wchar_t *__restrict __src,
 		size_t __n))
 {
-  if (__bos (__dest) != (size_t) -1)
+  if (__objsize (__dest) != (size_t) -1)
     {
       if (!__builtin_constant_p (__n))
 	return __wcsncpy_chk (__dest, __src, __n,
-			      __bos (__dest) / sizeof (wchar_t));
-      if (__n > __bos (__dest) / sizeof (wchar_t))
+			      __objsize (__dest) / sizeof (wchar_t));
+      if (__n > __objsize (__dest) / sizeof (wchar_t))
 	return __wcsncpy_chk_warn (__dest, __src, __n,
-				   __bos (__dest) / sizeof (wchar_t));
+				   __objsize (__dest) / sizeof (wchar_t));
     }
   return __wcsncpy_alias (__dest, __src, __n);
 }
@@ -222,14 +223,14 @@ __fortify_function wchar_t *
 __NTH (wcpncpy (wchar_t *__restrict __dest, const wchar_t *__restrict __src,
 		size_t __n))
 {
-  if (__bos (__dest) != (size_t) -1)
+  if (__objsize (__dest) != (size_t) -1)
     {
       if (!__builtin_constant_p (__n))
 	return __wcpncpy_chk (__dest, __src, __n,
-			      __bos (__dest) / sizeof (wchar_t));
-      if (__n > __bos (__dest) / sizeof (wchar_t))
+			      __objsize (__dest) / sizeof (wchar_t));
+      if (__n > __objsize (__dest) / sizeof (wchar_t))
 	return __wcpncpy_chk_warn (__dest, __src, __n,
-				   __bos (__dest) / sizeof (wchar_t));
+				   __objsize (__dest) / sizeof (wchar_t));
     }
   return __wcpncpy_alias (__dest, __src, __n);
 }
@@ -245,8 +246,8 @@ extern wchar_t *__REDIRECT_NTH (__wcscat_alias,
 __fortify_function wchar_t *
 __NTH (wcscat (wchar_t *__restrict __dest, const wchar_t *__restrict __src))
 {
-  if (__bos (__dest) != (size_t) -1)
-    return __wcscat_chk (__dest, __src, __bos (__dest) / sizeof (wchar_t));
+  if (__objsize (__dest) != (size_t) -1)
+    return __wcscat_chk (__dest, __src, __objsize (__dest) / sizeof (wchar_t));
   return __wcscat_alias (__dest, __src);
 }
 
@@ -263,9 +264,9 @@ __fortify_function wchar_t *
 __NTH (wcsncat (wchar_t *__restrict __dest, const wchar_t *__restrict __src,
 		size_t __n))
 {
-  if (__bos (__dest) != (size_t) -1)
+  if (__objsize (__dest) != (size_t) -1)
     return __wcsncat_chk (__dest, __src, __n,
-			  __bos (__dest) / sizeof (wchar_t));
+			  __objsize (__dest) / sizeof (wchar_t));
   return __wcsncat_alias (__dest, __src, __n);
 }
 
@@ -285,18 +286,18 @@ __fortify_function int
 __NTH (swprintf (wchar_t *__restrict __s, size_t __n,
 		 const wchar_t *__restrict __fmt, ...))
 {
-  if (__bos (__s) != (size_t) -1 || __USE_FORTIFY_LEVEL > 1)
+  if (__objsize (__s) != (size_t) -1 || __USE_FORTIFY_LEVEL > 1)
     return __swprintf_chk (__s, __n, __USE_FORTIFY_LEVEL - 1,
-			   __bos (__s) / sizeof (wchar_t),
+			   __objsize (__s) / sizeof (wchar_t),
 			   __fmt, __va_arg_pack ());
   return __swprintf_alias (__s, __n, __fmt, __va_arg_pack ());
 }
 #elif !defined __cplusplus
 /* XXX We might want to have support in gcc for swprintf.  */
 # define swprintf(s, n, ...) \
-  (__bos (s) != (size_t) -1 || __USE_FORTIFY_LEVEL > 1			      \
+  (__objsize (s) != (size_t) -1 || __USE_FORTIFY_LEVEL > 1		      \
    ? __swprintf_chk (s, n, __USE_FORTIFY_LEVEL - 1,			      \
-		     __bos (s) / sizeof (wchar_t), __VA_ARGS__)		      \
+		     __objsize (s) / sizeof (wchar_t), __VA_ARGS__)	      \
    : swprintf (s, n, __VA_ARGS__))
 #endif
 
@@ -315,9 +316,9 @@ __fortify_function int
 __NTH (vswprintf (wchar_t *__restrict __s, size_t __n,
 		  const wchar_t *__restrict __fmt, __gnuc_va_list __ap))
 {
-  if (__bos (__s) != (size_t) -1 || __USE_FORTIFY_LEVEL > 1)
+  if (__objsize (__s) != (size_t) -1 || __USE_FORTIFY_LEVEL > 1)
     return __vswprintf_chk (__s, __n,  __USE_FORTIFY_LEVEL - 1,
-			    __bos (__s) / sizeof (wchar_t), __fmt, __ap);
+			    __objsize (__s) / sizeof (wchar_t), __fmt, __ap);
   return __vswprintf_alias (__s, __n, __fmt, __ap);
 }
 
@@ -383,14 +384,14 @@ extern wchar_t *__REDIRECT (__fgetws_chk_warn,
 __fortify_function __wur wchar_t *
 fgetws (wchar_t *__restrict __s, int __n, __FILE *__restrict __stream)
 {
-  if (__bos (__s) != (size_t) -1)
+  if (__objsize (__s) != (size_t) -1)
     {
       if (!__builtin_constant_p (__n) || __n <= 0)
-	return __fgetws_chk (__s, __bos (__s) / sizeof (wchar_t),
+	return __fgetws_chk (__s, __objsize (__s) / sizeof (wchar_t),
 			     __n, __stream);
 
-      if ((size_t) __n > __bos (__s) / sizeof (wchar_t))
-	return __fgetws_chk_warn (__s, __bos (__s) / sizeof (wchar_t),
+      if ((size_t) __n > __objsize (__s) / sizeof (wchar_t))
+	return __fgetws_chk_warn (__s, __objsize (__s) / sizeof (wchar_t),
 				  __n, __stream);
     }
   return __fgetws_alias (__s, __n, __stream);
@@ -414,14 +415,15 @@ extern wchar_t *__REDIRECT (__fgetws_unlocked_chk_warn,
 __fortify_function __wur wchar_t *
 fgetws_unlocked (wchar_t *__restrict __s, int __n, __FILE *__restrict __stream)
 {
-  if (__bos (__s) != (size_t) -1)
+  if (__objsize (__s) != (size_t) -1)
     {
       if (!__builtin_constant_p (__n) || __n <= 0)
-	return __fgetws_unlocked_chk (__s, __bos (__s) / sizeof (wchar_t),
+	return __fgetws_unlocked_chk (__s, __objsize (__s) / sizeof (wchar_t),
 				      __n, __stream);
 
-      if ((size_t) __n > __bos (__s) / sizeof (wchar_t))
-	return __fgetws_unlocked_chk_warn (__s, __bos (__s) / sizeof (wchar_t),
+      if ((size_t) __n > __objsize (__s) / sizeof (wchar_t))
+	return __fgetws_unlocked_chk_warn (__s,
+					   __objsize (__s) / sizeof (wchar_t),
 					   __n, __stream);
     }
   return __fgetws_unlocked_alias (__s, __n, __stream);
@@ -447,8 +449,8 @@ __NTH (wcrtomb (char *__restrict __s, wchar_t __wchar,
 #if defined MB_LEN_MAX && MB_LEN_MAX != __WCHAR_MB_LEN_MAX
 # error "Assumed value of MB_LEN_MAX wrong"
 #endif
-  if (__bos (__s) != (size_t) -1 && __WCHAR_MB_LEN_MAX > __bos (__s))
-    return __wcrtomb_chk (__s, __wchar, __ps, __bos (__s));
+  if (__objsize (__s) != (size_t) -1 && __WCHAR_MB_LEN_MAX > __objsize (__s))
+    return __wcrtomb_chk (__s, __wchar, __ps, __objsize (__s));
   return __wcrtomb_alias (__s, __wchar, __ps);
 }
 
@@ -474,15 +476,15 @@ __fortify_function size_t
 __NTH (mbsrtowcs (wchar_t *__restrict __dst, const char **__restrict __src,
 		  size_t __len, mbstate_t *__restrict __ps))
 {
-  if (__bos (__dst) != (size_t) -1)
+  if (__objsize (__dst) != (size_t) -1)
     {
       if (!__builtin_constant_p (__len))
 	return __mbsrtowcs_chk (__dst, __src, __len, __ps,
-				__bos (__dst) / sizeof (wchar_t));
+				__objsize (__dst) / sizeof (wchar_t));
 
-      if (__len > __bos (__dst) / sizeof (wchar_t))
+      if (__len > __objsize (__dst) / sizeof (wchar_t))
 	return __mbsrtowcs_chk_warn (__dst, __src, __len, __ps,
-				     __bos (__dst) / sizeof (wchar_t));
+				     __objsize (__dst) / sizeof (wchar_t));
     }
   return __mbsrtowcs_alias (__dst, __src, __len, __ps);
 }
@@ -508,13 +510,14 @@ __fortify_function size_t
 __NTH (wcsrtombs (char *__restrict __dst, const wchar_t **__restrict __src,
 		  size_t __len, mbstate_t *__restrict __ps))
 {
-  if (__bos (__dst) != (size_t) -1)
+  if (__objsize (__dst) != (size_t) -1)
     {
       if (!__builtin_constant_p (__len))
-	return __wcsrtombs_chk (__dst, __src, __len, __ps, __bos (__dst));
+	return __wcsrtombs_chk (__dst, __src, __len, __ps, __objsize (__dst));
 
-      if (__len > __bos (__dst))
-	return __wcsrtombs_chk_warn (__dst, __src, __len, __ps, __bos (__dst));
+      if (__len > __objsize (__dst))
+	return __wcsrtombs_chk_warn (__dst, __src, __len, __ps,
+				     __objsize (__dst));
     }
   return __wcsrtombs_alias (__dst, __src, __len, __ps);
 }
@@ -542,15 +545,15 @@ __fortify_function size_t
 __NTH (mbsnrtowcs (wchar_t *__restrict __dst, const char **__restrict __src,
 		   size_t __nmc, size_t __len, mbstate_t *__restrict __ps))
 {
-  if (__bos (__dst) != (size_t) -1)
+  if (__objsize (__dst) != (size_t) -1)
     {
       if (!__builtin_constant_p (__len))
 	return __mbsnrtowcs_chk (__dst, __src, __nmc, __len, __ps,
-				 __bos (__dst) / sizeof (wchar_t));
+				 __objsize (__dst) / sizeof (wchar_t));
 
-      if (__len > __bos (__dst) / sizeof (wchar_t))
+      if (__len > __objsize (__dst) / sizeof (wchar_t))
 	return __mbsnrtowcs_chk_warn (__dst, __src, __nmc, __len, __ps,
-				      __bos (__dst) / sizeof (wchar_t));
+				      __objsize (__dst) / sizeof (wchar_t));
     }
   return __mbsnrtowcs_alias (__dst, __src, __nmc, __len, __ps);
 }
@@ -578,15 +581,15 @@ __fortify_function size_t
 __NTH (wcsnrtombs (char *__restrict __dst, const wchar_t **__restrict __src,
 		   size_t __nwc, size_t __len, mbstate_t *__restrict __ps))
 {
-  if (__bos (__dst) != (size_t) -1)
+  if (__objsize (__dst) != (size_t) -1)
     {
       if (!__builtin_constant_p (__len))
 	return __wcsnrtombs_chk (__dst, __src, __nwc, __len, __ps,
-				 __bos (__dst));
+				 __objsize (__dst));
 
-      if (__len > __bos (__dst))
+      if (__len > __objsize (__dst))
 	return __wcsnrtombs_chk_warn (__dst, __src, __nwc, __len, __ps,
-				      __bos (__dst));
+				      __objsize (__dst));
     }
   return __wcsnrtombs_alias (__dst, __src, __nwc, __len, __ps);
 }
-- 
2.29.2


^ permalink raw reply related	[flat|nested] 14+ messages in thread

* Re: [PATCH v6 0/2] _FORTIFY_SOURCE=3
  2020-12-19  6:33 [PATCH v6 0/2] _FORTIFY_SOURCE=3 Siddhesh Poyarekar via Libc-alpha
  2020-12-19  6:33 ` [PATCH 1/2] string: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size Siddhesh Poyarekar via Libc-alpha
  2020-12-19  6:33 ` [PATCH 2/2] nonstring: " Siddhesh Poyarekar via Libc-alpha
@ 2020-12-22 13:00 ` Siddhesh Poyarekar
  2020-12-22 21:49   ` Adhemerval Zanella via Libc-alpha
  2 siblings, 1 reply; 14+ messages in thread
From: Siddhesh Poyarekar @ 2020-12-22 13:00 UTC (permalink / raw
  To: Siddhesh Poyarekar, libc-alpha; +Cc: fweimer, jakub

On 12/19/20 12:03 PM, Siddhesh Poyarekar via Libc-alpha wrote:
> This patchset implements a new fortification level, _FORTIFY_SOURCE=3.
> This level allows size information to be dynamic, which may potentially
> have a noticeable performance impact.  It uses the
> __builtin_dynamic_object_size builtin available in clang to expand
> coverage of fortifications at the expense of some performance.
> 
> Patch 1/2 implements the base support and support for functions that
> have builtins of string functions.  Additionally, the patch also
> describes the use case and tradeoffs.
> 
> Patch 2/2 adds support for non-string functions that are
> fortification-ready for levels 1 and 2.

Any more comments on this?  I believe I have fixed all the outstanding 
issues that were pointed out during previous reviews.

Siddhesh

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH v6 0/2] _FORTIFY_SOURCE=3
  2020-12-22 13:00 ` [PATCH v6 0/2] _FORTIFY_SOURCE=3 Siddhesh Poyarekar
@ 2020-12-22 21:49   ` Adhemerval Zanella via Libc-alpha
  0 siblings, 0 replies; 14+ messages in thread
From: Adhemerval Zanella via Libc-alpha @ 2020-12-22 21:49 UTC (permalink / raw
  To: Siddhesh Poyarekar, Siddhesh Poyarekar, libc-alpha; +Cc: fweimer, jakub



On 22/12/2020 10:00, Siddhesh Poyarekar wrote:
> On 12/19/20 12:03 PM, Siddhesh Poyarekar via Libc-alpha wrote:
>> This patchset implements a new fortification level, _FORTIFY_SOURCE=3.
>> This level allows size information to be dynamic, which may potentially
>> have a noticeable performance impact.  It uses the
>> __builtin_dynamic_object_size builtin available in clang to expand
>> coverage of fortifications at the expense of some performance.
>>
>> Patch 1/2 implements the base support and support for functions that
>> have builtins of string functions.  Additionally, the patch also
>> describes the use case and tradeoffs.
>>
>> Patch 2/2 adds support for non-string functions that are
>> fortification-ready for levels 1 and 2.
> 
> Any more comments on this?  I believe I have fixed all the outstanding issues that were pointed out during previous reviews.
> 
> Siddhesh

I will check this out tomorrow, but it seems ok skimming through it.

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH 1/2] string: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size
  2020-12-19  6:33 ` [PATCH 1/2] string: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size Siddhesh Poyarekar via Libc-alpha
@ 2020-12-28 16:44   ` Adhemerval Zanella via Libc-alpha
  2020-12-29 15:14     ` Siddhesh Poyarekar via Libc-alpha
  0 siblings, 1 reply; 14+ messages in thread
From: Adhemerval Zanella via Libc-alpha @ 2020-12-28 16:44 UTC (permalink / raw
  To: Siddhesh Poyarekar, libc-alpha; +Cc: fweimer, jakub



On 19/12/2020 03:33, Siddhesh Poyarekar via Libc-alpha wrote:
> Introduce a new _FORTIFY_SOURCE level of 3 to enable additional
> fortifications that may have a potential performance impact.  At the
> moment this level of fortification involves the use of the
> __builtin_dynamic_object_size builtin whenever the compiler supports
> it.
> 
> This change enhances fortified string functions to use
> __builtin_dynamic_object_size under _FORTIFY_SOURCE=3 whenever the
> compiler supports it.


For previous discussion I couldn't really grap what is the GCC intention
regarding this new builtin. Would it willing to implement with the same
semantic as LLVM has done or depending of result when glibc starts to 
provide it GCC will either change its semantic or not implement at all?

If the former, using _FORTIFY_SOURCE=3 should be fine.  However, if it
is the latter I think it would be better to add it as another and different
FORTIFY flag ( _FORTIFY_SOURCE_DYNAMIC or something like that).  

I really want to avoid the issue where developers would not see the
expected code generation when using _FORTIFY_SOURCE=3 with gcc or the worse,
where _FORTIFY_SOURCE=3 would have different semantic depending of the 
compiler used.

> 
> __builtin_dynamic_object_size
> -----------------------------
> 
> __builtin_dynamic_object_size is an LLVM builtin that is similar to
> __builtin_object_size.  In addition to what __builtin_object_size
> does, i.e. replace the builtin call with a constant object size,
> __builtin_dynamic_object_size will replace the call site with an
> expression that evaluates to the object size, thus expanding its
> applicability.  In practice, __builtin_dynamic_object_size evaluates
> these expressions through malloc/calloc calls that it can associate
> with the object being evaluated.
> 
> A simple motivating example is below; -D_FORTIFY_SOURCE=2 would miss
> this and emit memcpy, but -D_FORTIFY_SOURCE=3 with the help of
> __builtin_dynamic_object_size is able to emit __memcpy_chk with the
> allocation size expression passed into the function:
> 
> void *copy_obj (const void *src, size_t alloc, size_t copysize)
> {
>   void *obj = malloc (alloc);
>   memcpy (obj, src, copysize);
> 
>   return obj;
> }
> 
> Limitations
> -----------
> 
> If the object was allocated elsewhere that the compiler cannot see, or
> if it was allocated in the function with a function that the compiler
> does not recognize as an allocator then __builtin_dynamic_object_size
> also returns -1.
> 
> Further, the expression used to compute object size may be non-trivial
> and may potentially incur a noticeable performance impact.  These
> fortifications are hence enabled at a new _FORTIFY_SOURCE level to
> allow developers to make a choice on the tradeoff according to their
> environment.
> 
> Other Changes
> -------------
> 
> The _FORTIFY_SOURCE macro soup in features.h now warns about
> unsupported fortification levels.  For example, it will warn about
> _FORTIFY_SOURCE=3 and over for llvm older than 9.0 and for gcc and
> _FORTIFY_SOURCE=4 will result in a warning on all compilers with an
> indication of which level has been selected.

This should be in a different patch, where glibc would handle not support
_FORTIFY_SOURCE levels and emit the expected warnings.

> 
> Co-authored-by: Paul Eggert <eggert@cs.ucla.edu>
> ---
>  NEWS                            |  6 ++++++
>  include/features.h              |  8 ++++++++
>  include/string.h                |  5 +++--
>  manual/creature.texi            |  3 ++-
>  misc/sys/cdefs.h                |  9 +++++++++
>  string/bits/string_fortified.h  | 22 +++++++++++-----------
>  string/bits/strings_fortified.h |  4 ++--
>  7 files changed, 41 insertions(+), 16 deletions(-)
> 
> diff --git a/NEWS b/NEWS
> index 86e05fb023..8e02dbd0f7 100644
> --- a/NEWS
> +++ b/NEWS
> @@ -28,6 +28,12 @@ Major new features:
>    The 32-bit RISC-V port requires at least Linux 5.4, GCC 7.1 and binutils
>    2.28.
>  
> +* A new fortification level _FORTIFY_SOURCE=3 is available.  At this level,
> +  glibc may use additional checks that may have an additional performance
> +  overhead.  At present these checks are available only on LLVM 9 and later.
> +  The latest GCC available at this time (10.2) does not support this level of
> +  fortification.
> +
>  Deprecated and removed features, and other changes affecting compatibility:
>  
>  * The mallinfo function is marked deprecated.  Callers should call

Ok.

> diff --git a/include/features.h b/include/features.h
> index f3e62d3362..066eb0eecd 100644
> --- a/include/features.h
> +++ b/include/features.h
> @@ -397,7 +397,15 @@
>  #  warning _FORTIFY_SOURCE requires compiling with optimization (-O)
>  # elif !__GNUC_PREREQ (4, 1)
>  #  warning _FORTIFY_SOURCE requires GCC 4.1 or later
> +# elif _FORTIFY_SOURCE > 2 && __glibc_clang_prereq (9, 0)
> +#  if _FORTIFY_SOURCE > 3
> +#   warning _FORTIFY_SOURCE > 3 is treated like 3 on this platform
> +#  endif
> +#  define __USE_FORTIFY_LEVEL 3
>  # elif _FORTIFY_SOURCE > 1
> +#  if _FORTIFY_SOURCE > 2
> +#   warning _FORTIFY_SOURCE > 2 is treated like 2 on this platform
> +#  endif
>  #  define __USE_FORTIFY_LEVEL 2
>  # else
>  #  define __USE_FORTIFY_LEVEL 1

As before, I think the _FORTIFY_LEVEL value check and warning should be in
separated patch.

> diff --git a/include/string.h b/include/string.h
> index 7d344d77d4..841ee05a1d 100644
> --- a/include/string.h
> +++ b/include/string.h
> @@ -123,10 +123,11 @@ libc_hidden_proto (__strerror_l)
>  void __explicit_bzero_chk_internal (void *, size_t, size_t)
>    __THROW __nonnull ((1)) attribute_hidden;
>  # define explicit_bzero(buf, len) \
> -  __explicit_bzero_chk_internal (buf, len, __bos0 (buf))
> +  __explicit_bzero_chk_internal (buf, len, __objsize0 (buf))
>  #elif !IS_IN (nonlib)
>  void __explicit_bzero_chk (void *, size_t, size_t) __THROW __nonnull ((1));
> -# define explicit_bzero(buf, len) __explicit_bzero_chk (buf, len, __bos0 (buf))
> +# define explicit_bzero(buf, len) __explicit_bzero_chk (buf, len,	      \
> +							__objsize0 (buf))
>  #endif
>  
>  libc_hidden_builtin_proto (memchr)
> diff --git a/manual/creature.texi b/manual/creature.texi
> index be5050468b..31208ccb2b 100644
> --- a/manual/creature.texi
> +++ b/manual/creature.texi
> @@ -254,7 +254,8 @@ included.
>  @standards{GNU, (none)}
>  If this macro is defined to @math{1}, security hardening is added to
>  various library functions.  If defined to @math{2}, even stricter
> -checks are applied.
> +checks are applied. If defined to @math{3}, @theglibc{} may also use
> +checks that may have an additional performance overhead.
>  @end defvr
>  
>  @defvr Macro _REENTRANT
> diff --git a/misc/sys/cdefs.h b/misc/sys/cdefs.h
> index a06f1cfd91..ca51a5c3ad 100644
> --- a/misc/sys/cdefs.h
> +++ b/misc/sys/cdefs.h
> @@ -127,6 +127,15 @@
>  #define __bos(ptr) __builtin_object_size (ptr, __USE_FORTIFY_LEVEL > 1)
>  #define __bos0(ptr) __builtin_object_size (ptr, 0)
>  
> +/* Use __builtin_dynamic_object_size at _FORTIFY_SOURCE=3 when available.  */
> +#if __USE_FORTIFY_LEVEL == 3 && __glibc_clang_prereq (9, 0)
> +# define __objsize0(__o) __builtin_dynamic_object_size (__o, 0)
> +# define __objsize(__o) __builtin_dynamic_object_size (__o, 1)
> +#else
> +# define __objsize0(__o) __bos0 (__o)
> +# define __objsize(__o) __bos (__o)
> +#endif
> +
>  #if __GNUC_PREREQ (4,3)

I think from previous version that Florian suggested renamed this internal macros
to __glibc_objsize[0].

>  # define __warnattr(msg) __attribute__((__warning__ (msg)))
>  # define __errordecl(name, msg) \
> diff --git a/string/bits/string_fortified.h b/string/bits/string_fortified.h
> index 4c1aeb45f1..c9f9197aef 100644
> --- a/string/bits/string_fortified.h
> +++ b/string/bits/string_fortified.h
> @@ -26,13 +26,13 @@ __fortify_function void *
>  __NTH (memcpy (void *__restrict __dest, const void *__restrict __src,
>  	       size_t __len))
>  {
> -  return __builtin___memcpy_chk (__dest, __src, __len, __bos0 (__dest));
> +  return __builtin___memcpy_chk (__dest, __src, __len, __objsize0 (__dest));
>  }
>  
>  __fortify_function void *
>  __NTH (memmove (void *__dest, const void *__src, size_t __len))
>  {
> -  return __builtin___memmove_chk (__dest, __src, __len, __bos0 (__dest));
> +  return __builtin___memmove_chk (__dest, __src, __len, __objsize0 (__dest));
>  }
>  
>  #ifdef __USE_GNU
> @@ -40,7 +40,7 @@ __fortify_function void *
>  __NTH (mempcpy (void *__restrict __dest, const void *__restrict __src,
>  		size_t __len))
>  {
> -  return __builtin___mempcpy_chk (__dest, __src, __len, __bos0 (__dest));
> +  return __builtin___mempcpy_chk (__dest, __src, __len, __objsize0 (__dest));
>  }
>  #endif
>  
> @@ -53,7 +53,7 @@ __NTH (mempcpy (void *__restrict __dest, const void *__restrict __src,
>  __fortify_function void *
>  __NTH (memset (void *__dest, int __ch, size_t __len))
>  {
> -  return __builtin___memset_chk (__dest, __ch, __len, __bos0 (__dest));
> +  return __builtin___memset_chk (__dest, __ch, __len, __objsize0 (__dest));
>  }
>  
>  #ifdef __USE_MISC
> @@ -65,21 +65,21 @@ void __explicit_bzero_chk (void *__dest, size_t __len, size_t __destlen)
>  __fortify_function void
>  __NTH (explicit_bzero (void *__dest, size_t __len))
>  {
> -  __explicit_bzero_chk (__dest, __len, __bos0 (__dest));
> +  __explicit_bzero_chk (__dest, __len, __objsize0 (__dest));
>  }
>  #endif
>  
>  __fortify_function char *
>  __NTH (strcpy (char *__restrict __dest, const char *__restrict __src))
>  {
> -  return __builtin___strcpy_chk (__dest, __src, __bos (__dest));
> +  return __builtin___strcpy_chk (__dest, __src, __objsize (__dest));
>  }
>  
>  #ifdef __USE_GNU
>  __fortify_function char *
>  __NTH (stpcpy (char *__restrict __dest, const char *__restrict __src))
>  {
> -  return __builtin___stpcpy_chk (__dest, __src, __bos (__dest));
> +  return __builtin___stpcpy_chk (__dest, __src, __objsize (__dest));
>  }
>  #endif
>  
> @@ -88,14 +88,14 @@ __fortify_function char *
>  __NTH (strncpy (char *__restrict __dest, const char *__restrict __src,
>  		size_t __len))
>  {
> -  return __builtin___strncpy_chk (__dest, __src, __len, __bos (__dest));
> +  return __builtin___strncpy_chk (__dest, __src, __len, __objsize (__dest));
>  }
>  
>  #if __GNUC_PREREQ (4, 7) || __glibc_clang_prereq (2, 6)
>  __fortify_function char *
>  __NTH (stpncpy (char *__dest, const char *__src, size_t __n))
>  {
> -  return __builtin___stpncpy_chk (__dest, __src, __n, __bos (__dest));
> +  return __builtin___stpncpy_chk (__dest, __src, __n, __objsize (__dest));
>  }
>  #else
>  extern char *__stpncpy_chk (char *__dest, const char *__src, size_t __n,
> @@ -118,7 +118,7 @@ __NTH (stpncpy (char *__dest, const char *__src, size_t __n))
>  __fortify_function char *
>  __NTH (strcat (char *__restrict __dest, const char *__restrict __src))
>  {
> -  return __builtin___strcat_chk (__dest, __src, __bos (__dest));
> +  return __builtin___strcat_chk (__dest, __src, __objsize (__dest));
>  }
>  
>  
> @@ -126,7 +126,7 @@ __fortify_function char *
>  __NTH (strncat (char *__restrict __dest, const char *__restrict __src,
>  		size_t __len))
>  {
> -  return __builtin___strncat_chk (__dest, __src, __len, __bos (__dest));
> +  return __builtin___strncat_chk (__dest, __src, __len, __objsize (__dest));
>  }
>  
>  #endif /* bits/string_fortified.h */

Ok.

> diff --git a/string/bits/strings_fortified.h b/string/bits/strings_fortified.h
> index d4091f4f69..122199e036 100644
> --- a/string/bits/strings_fortified.h
> +++ b/string/bits/strings_fortified.h
> @@ -22,13 +22,13 @@
>  __fortify_function void
>  __NTH (bcopy (const void *__src, void *__dest, size_t __len))
>  {
> -  (void) __builtin___memmove_chk (__dest, __src, __len, __bos0 (__dest));
> +  (void) __builtin___memmove_chk (__dest, __src, __len, __objsize0 (__dest));
>  }
>  
>  __fortify_function void
>  __NTH (bzero (void *__dest, size_t __len))
>  {
> -  (void) __builtin___memset_chk (__dest, '\0', __len, __bos0 (__dest));
> +  (void) __builtin___memset_chk (__dest, '\0', __len, __objsize0 (__dest));
>  }
>  
>  #endif
> 

Ok.

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH 2/2] nonstring: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size
  2020-12-19  6:33 ` [PATCH 2/2] nonstring: " Siddhesh Poyarekar via Libc-alpha
@ 2020-12-28 17:36   ` Adhemerval Zanella via Libc-alpha
  2020-12-29 14:04     ` Siddhesh Poyarekar via Libc-alpha
  2020-12-29 14:26     ` Jakub Jelinek via Libc-alpha
  0 siblings, 2 replies; 14+ messages in thread
From: Adhemerval Zanella via Libc-alpha @ 2020-12-28 17:36 UTC (permalink / raw
  To: Siddhesh Poyarekar, libc-alpha; +Cc: fweimer, jakub



On 19/12/2020 03:33, Siddhesh Poyarekar via Libc-alpha wrote:
> These fortified functions use, roughly, the following idiom to
> implement fortifications:
> 
>   if (__builtin_dynamic_object_size (obj) != -1)
>     {
>       __fortified_chk ();
>       return;
>     }
>   __unfortified ();

Reading the D93015, it should be:

  if (__builtin_dynamic_object_size (obj, 0 or 1) != -1ULL)

right?

The __builtin_dynamic_object_size seems to be a 64-bit integer.
How does it play in 32-bit targets? Would clang optimize the check
when dynamic one need to be emitted?

> 
> LLVM is currently unable to fold the conditional; a patch has been
> proposed[1] to fix this.
> 
> Due to this limitation in llvm, these fortifications have a higher
> performance cost than those in the first patch.
> 
> [1] https://reviews.llvm.org/D93015

I think you can state that this has been implemented on LLVM.

> ---
>  io/bits/poll2.h       |  16 +++---
>  libio/bits/stdio.h    |   2 +-
>  libio/bits/stdio2.h   |  53 ++++++++---------
>  posix/bits/unistd.h   | 112 +++++++++++++++++++-----------------
>  socket/bits/socket2.h |  18 +++---
>  stdlib/bits/stdlib.h  |  37 ++++++------
>  wcsmbs/bits/wchar2.h  | 131 +++++++++++++++++++++---------------------
>  7 files changed, 189 insertions(+), 180 deletions(-)
> 
> diff --git a/io/bits/poll2.h b/io/bits/poll2.h
> index dca49717db..ce107b8e50 100644
> --- a/io/bits/poll2.h
> +++ b/io/bits/poll2.h
> @@ -35,12 +35,12 @@ extern int __REDIRECT (__poll_chk_warn, (struct pollfd *__fds, nfds_t __nfds,
>  __fortify_function int
>  poll (struct pollfd *__fds, nfds_t __nfds, int __timeout)
>  {
> -  if (__bos (__fds) != (__SIZE_TYPE__) -1)
> +  if (__objsize (__fds) != (__SIZE_TYPE__) -1)
>      {
>        if (! __builtin_constant_p (__nfds))
> -	return __poll_chk (__fds, __nfds, __timeout, __bos (__fds));
> -      else if (__bos (__fds) / sizeof (*__fds) < __nfds)
> -	return __poll_chk_warn (__fds, __nfds, __timeout, __bos (__fds));
> +	return __poll_chk (__fds, __nfds, __timeout, __objsize (__fds));
> +      else if (__objsize (__fds) / sizeof (*__fds) < __nfds)
> +	return __poll_chk_warn (__fds, __nfds, __timeout, __objsize (__fds));
>      }
>  
>    return __poll_alias (__fds, __nfds, __timeout);

Same for first patch, I recall that Florian has suggested using __glibc_objsize.

The rest looks ok.

> @@ -65,13 +65,13 @@ __fortify_function int
>  ppoll (struct pollfd *__fds, nfds_t __nfds, const struct timespec *__timeout,
>         const __sigset_t *__ss)
>  {
> -  if (__bos (__fds) != (__SIZE_TYPE__) -1)
> +  if (__objsize (__fds) != (__SIZE_TYPE__) -1)
>      {
>        if (! __builtin_constant_p (__nfds))
> -	return __ppoll_chk (__fds, __nfds, __timeout, __ss, __bos (__fds));
> -      else if (__bos (__fds) / sizeof (*__fds) < __nfds)
> +	return __ppoll_chk (__fds, __nfds, __timeout, __ss, __objsize (__fds));
> +      else if (__objsize (__fds) / sizeof (*__fds) < __nfds)
>  	return __ppoll_chk_warn (__fds, __nfds, __timeout, __ss,
> -				 __bos (__fds));
> +				 __objsize (__fds));
>      }
>  
>    return __ppoll_alias (__fds, __nfds, __timeout, __ss);
> diff --git a/libio/bits/stdio.h b/libio/bits/stdio.h
> index 6745571ed5..6d1f0f9fc9 100644
> --- a/libio/bits/stdio.h
> +++ b/libio/bits/stdio.h
> @@ -31,7 +31,7 @@
>  
>  
>  #ifdef __USE_EXTERN_INLINES
> -/* For -D_FORTIFY_SOURCE{,=2} bits/stdio2.h will define a different
> +/* For -D_FORTIFY_SOURCE{,=2,=3} bits/stdio2.h will define a different
>     inline.  */
>  # if !(__USE_FORTIFY_LEVEL > 0 && defined __fortify_function)
>  /* Write formatted output to stdout from argument list ARG.  */> diff --git a/libio/bits/stdio2.h b/libio/bits/stdio2.h
> index ff9202c2cb..b5e804ca13 100644
> --- a/libio/bits/stdio2.h
> +++ b/libio/bits/stdio2.h
> @@ -36,11 +36,11 @@ __fortify_function int
>  __NTH (sprintf (char *__restrict __s, const char *__restrict __fmt, ...))
>  {
>    return __builtin___sprintf_chk (__s, __USE_FORTIFY_LEVEL - 1,
> -				  __bos (__s), __fmt, __va_arg_pack ());
> +				  __objsize (__s), __fmt, __va_arg_pack ());
>  }
>  #elif !defined __cplusplus
>  # define sprintf(str, ...) \
> -  __builtin___sprintf_chk (str, __USE_FORTIFY_LEVEL - 1, __bos (str), \
> +  __builtin___sprintf_chk (str, __USE_FORTIFY_LEVEL - 1, __objsize (str), \
>  			   __VA_ARGS__)
>  #endif
>  
> @@ -49,7 +49,7 @@ __NTH (vsprintf (char *__restrict __s, const char *__restrict __fmt,
>  		 __gnuc_va_list __ap))
>  {
>    return __builtin___vsprintf_chk (__s, __USE_FORTIFY_LEVEL - 1,
> -				   __bos (__s), __fmt, __ap);
> +				   __objsize (__s), __fmt, __ap);
>  }
>  
>  #if defined __USE_ISOC99 || defined __USE_UNIX98
> @@ -68,12 +68,12 @@ __NTH (snprintf (char *__restrict __s, size_t __n,
>  		 const char *__restrict __fmt, ...))
>  {
>    return __builtin___snprintf_chk (__s, __n, __USE_FORTIFY_LEVEL - 1,
> -				   __bos (__s), __fmt, __va_arg_pack ());
> +				   __objsize (__s), __fmt, __va_arg_pack ());
>  }
>  # elif !defined __cplusplus
>  #  define snprintf(str, len, ...) \
> -  __builtin___snprintf_chk (str, len, __USE_FORTIFY_LEVEL - 1, __bos (str), \
> -			    __VA_ARGS__)
> +  __builtin___snprintf_chk (str, len, __USE_FORTIFY_LEVEL - 1,		      \
> +			    __objsize (str), __VA_ARGS__)
>  # endif
>  
>  __fortify_function int
> @@ -81,7 +81,7 @@ __NTH (vsnprintf (char *__restrict __s, size_t __n,
>  		  const char *__restrict __fmt, __gnuc_va_list __ap))
>  {
>    return __builtin___vsnprintf_chk (__s, __n, __USE_FORTIFY_LEVEL - 1,
> -				    __bos (__s), __fmt, __ap);
> +				    __objsize (__s), __fmt, __ap);
>  }
>  
>  #endif
> @@ -237,8 +237,8 @@ extern char *__REDIRECT (__gets_warn, (char *__str), gets)
>  __fortify_function __wur char *
>  gets (char *__str)
>  {
> -  if (__bos (__str) != (size_t) -1)
> -    return __gets_chk (__str, __bos (__str));
> +  if (__objsize (__str) != (size_t) -1)
> +    return __gets_chk (__str, __objsize (__str));
>    return __gets_warn (__str);
>  }
>  #endif
> @@ -259,13 +259,13 @@ extern char *__REDIRECT (__fgets_chk_warn,
>  __fortify_function __wur __attr_access ((__write_only__, 1, 2)) char *
>  fgets (char *__restrict __s, int __n, FILE *__restrict __stream)
>  {
> -  if (__bos (__s) != (size_t) -1)
> +  if (__objsize (__s) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__n) || __n <= 0)
> -	return __fgets_chk (__s, __bos (__s), __n, __stream);
> +	return __fgets_chk (__s, __objsize (__s), __n, __stream);
>  
> -      if ((size_t) __n > __bos (__s))
> -	return __fgets_chk_warn (__s, __bos (__s), __n, __stream);
> +      if ((size_t) __n > __objsize (__s))
> +	return __fgets_chk_warn (__s, __objsize (__s), __n, __stream);
>      }
>    return __fgets_alias (__s, __n, __stream);
>  }
> @@ -289,15 +289,16 @@ __fortify_function __wur size_t
>  fread (void *__restrict __ptr, size_t __size, size_t __n,
>         FILE *__restrict __stream)
>  {
> -  if (__bos0 (__ptr) != (size_t) -1)
> +  if (__objsize0 (__ptr) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__size)
>  	  || !__builtin_constant_p (__n)
>  	  || (__size | __n) >= (((size_t) 1) << (8 * sizeof (size_t) / 2)))
> -	return __fread_chk (__ptr, __bos0 (__ptr), __size, __n, __stream);
> +	return __fread_chk (__ptr, __objsize0 (__ptr), __size, __n, __stream);
>  
> -      if (__size * __n > __bos0 (__ptr))
> -	return __fread_chk_warn (__ptr, __bos0 (__ptr), __size, __n, __stream);
> +      if (__size * __n > __objsize0 (__ptr))
> +	return __fread_chk_warn (__ptr, __objsize0 (__ptr), __size, __n,
> +				 __stream);
>      }
>    return __fread_alias (__ptr, __size, __n, __stream);
>  }
> @@ -319,13 +320,13 @@ extern char *__REDIRECT (__fgets_unlocked_chk_warn,
>  __fortify_function __wur __attr_access ((__write_only__, 1, 2)) char *
>  fgets_unlocked (char *__restrict __s, int __n, FILE *__restrict __stream)
>  {
> -  if (__bos (__s) != (size_t) -1)
> +  if (__objsize (__s) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__n) || __n <= 0)
> -	return __fgets_unlocked_chk (__s, __bos (__s), __n, __stream);
> +	return __fgets_unlocked_chk (__s, __objsize (__s), __n, __stream);
>  
> -      if ((size_t) __n > __bos (__s))
> -	return __fgets_unlocked_chk_warn (__s, __bos (__s), __n, __stream);
> +      if ((size_t) __n > __objsize (__s))
> +	return __fgets_unlocked_chk_warn (__s, __objsize (__s), __n, __stream);
>      }
>    return __fgets_unlocked_alias (__s, __n, __stream);
>  }
> @@ -352,17 +353,17 @@ __fortify_function __wur size_t
>  fread_unlocked (void *__restrict __ptr, size_t __size, size_t __n,
>  		FILE *__restrict __stream)
>  {
> -  if (__bos0 (__ptr) != (size_t) -1)
> +  if (__objsize0 (__ptr) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__size)
>  	  || !__builtin_constant_p (__n)
>  	  || (__size | __n) >= (((size_t) 1) << (8 * sizeof (size_t) / 2)))
> -	return __fread_unlocked_chk (__ptr, __bos0 (__ptr), __size, __n,
> +	return __fread_unlocked_chk (__ptr, __objsize0 (__ptr), __size, __n,
>  				     __stream);
>  
> -      if (__size * __n > __bos0 (__ptr))
> -	return __fread_unlocked_chk_warn (__ptr, __bos0 (__ptr), __size, __n,
> -					  __stream);
> +      if (__size * __n > __objsize0 (__ptr))
> +	return __fread_unlocked_chk_warn (__ptr, __objsize0 (__ptr), __size,
> +					  __n, __stream);
>      }
>  
>  # ifdef __USE_EXTERN_INLINES
> diff --git a/posix/bits/unistd.h b/posix/bits/unistd.h
> index 725a83eb0d..e1c44da01c 100644
> --- a/posix/bits/unistd.h
> +++ b/posix/bits/unistd.h
> @@ -35,13 +35,13 @@ extern ssize_t __REDIRECT (__read_chk_warn,
>  __fortify_function __wur ssize_t
>  read (int __fd, void *__buf, size_t __nbytes)
>  {
> -  if (__bos0 (__buf) != (size_t) -1)
> +  if (__objsize0 (__buf) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__nbytes))
> -	return __read_chk (__fd, __buf, __nbytes, __bos0 (__buf));
> +	return __read_chk (__fd, __buf, __nbytes, __objsize0 (__buf));
>  
> -      if (__nbytes > __bos0 (__buf))
> -	return __read_chk_warn (__fd, __buf, __nbytes, __bos0 (__buf));
> +      if (__nbytes > __objsize0 (__buf))
> +	return __read_chk_warn (__fd, __buf, __nbytes, __objsize0 (__buf));
>      }
>    return __read_alias (__fd, __buf, __nbytes);
>  }
> @@ -77,14 +77,15 @@ extern ssize_t __REDIRECT (__pread64_chk_warn,
>  __fortify_function __wur ssize_t
>  pread (int __fd, void *__buf, size_t __nbytes, __off_t __offset)
>  {
> -  if (__bos0 (__buf) != (size_t) -1)
> +  if (__objsize0 (__buf) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__nbytes))
> -	return __pread_chk (__fd, __buf, __nbytes, __offset, __bos0 (__buf));
> +	return __pread_chk (__fd, __buf, __nbytes, __offset,
> +			    __objsize0 (__buf));
>  
> -      if ( __nbytes > __bos0 (__buf))
> +      if ( __nbytes > __objsize0 (__buf))
>  	return __pread_chk_warn (__fd, __buf, __nbytes, __offset,
> -				 __bos0 (__buf));
> +				 __objsize0 (__buf));
>      }
>    return __pread_alias (__fd, __buf, __nbytes, __offset);
>  }
> @@ -92,14 +93,15 @@ pread (int __fd, void *__buf, size_t __nbytes, __off_t __offset)
>  __fortify_function __wur ssize_t
>  pread (int __fd, void *__buf, size_t __nbytes, __off64_t __offset)
>  {
> -  if (__bos0 (__buf) != (size_t) -1)
> +  if (__objsize0 (__buf) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__nbytes))
> -	return __pread64_chk (__fd, __buf, __nbytes, __offset, __bos0 (__buf));
> +	return __pread64_chk (__fd, __buf, __nbytes, __offset,
> +			      __objsize0 (__buf));
>  
> -      if ( __nbytes > __bos0 (__buf))
> +      if ( __nbytes > __objsize0 (__buf))
>  	return __pread64_chk_warn (__fd, __buf, __nbytes, __offset,
> -				   __bos0 (__buf));
> +				   __objsize0 (__buf));
>      }
>  
>    return __pread64_alias (__fd, __buf, __nbytes, __offset);
> @@ -110,14 +112,15 @@ pread (int __fd, void *__buf, size_t __nbytes, __off64_t __offset)
>  __fortify_function __wur ssize_t
>  pread64 (int __fd, void *__buf, size_t __nbytes, __off64_t __offset)
>  {
> -  if (__bos0 (__buf) != (size_t) -1)
> +  if (__objsize0 (__buf) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__nbytes))
> -	return __pread64_chk (__fd, __buf, __nbytes, __offset, __bos0 (__buf));
> +	return __pread64_chk (__fd, __buf, __nbytes, __offset,
> +			      __objsize0 (__buf));
>  
> -      if ( __nbytes > __bos0 (__buf))
> +      if ( __nbytes > __objsize0 (__buf))
>  	return __pread64_chk_warn (__fd, __buf, __nbytes, __offset,
> -				   __bos0 (__buf));
> +				   __objsize0 (__buf));
>      }
>  
>    return __pread64_alias (__fd, __buf, __nbytes, __offset);
> @@ -145,13 +148,13 @@ __fortify_function __nonnull ((1, 2)) __wur ssize_t
>  __NTH (readlink (const char *__restrict __path, char *__restrict __buf,
>  		 size_t __len))
>  {
> -  if (__bos (__buf) != (size_t) -1)
> +  if (__objsize (__buf) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__len))
> -	return __readlink_chk (__path, __buf, __len, __bos (__buf));
> +	return __readlink_chk (__path, __buf, __len, __objsize (__buf));
>  
> -      if ( __len > __bos (__buf))
> -	return __readlink_chk_warn (__path, __buf, __len, __bos (__buf));
> +      if ( __len > __objsize (__buf))
> +	return __readlink_chk_warn (__path, __buf, __len, __objsize (__buf));
>      }
>    return __readlink_alias (__path, __buf, __len);
>  }
> @@ -179,14 +182,15 @@ __fortify_function __nonnull ((2, 3)) __wur ssize_t
>  __NTH (readlinkat (int __fd, const char *__restrict __path,
>  		   char *__restrict __buf, size_t __len))
>  {
> -  if (__bos (__buf) != (size_t) -1)
> +  if (__objsize (__buf) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__len))
> -	return __readlinkat_chk (__fd, __path, __buf, __len, __bos (__buf));
> +	return __readlinkat_chk (__fd, __path, __buf, __len,
> +				 __objsize (__buf));
>  
> -      if (__len > __bos (__buf))
> +      if (__len > __objsize (__buf))
>  	return __readlinkat_chk_warn (__fd, __path, __buf, __len,
> -				      __bos (__buf));
> +				      __objsize (__buf));
>      }
>    return __readlinkat_alias (__fd, __path, __buf, __len);
>  }
> @@ -206,13 +210,13 @@ extern char *__REDIRECT_NTH (__getcwd_chk_warn,
>  __fortify_function __wur char *
>  __NTH (getcwd (char *__buf, size_t __size))
>  {
> -  if (__bos (__buf) != (size_t) -1)
> +  if (__objsize (__buf) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__size))
> -	return __getcwd_chk (__buf, __size, __bos (__buf));
> +	return __getcwd_chk (__buf, __size, __objsize (__buf));
>  
> -      if (__size > __bos (__buf))
> -	return __getcwd_chk_warn (__buf, __size, __bos (__buf));
> +      if (__size > __objsize (__buf))
> +	return __getcwd_chk_warn (__buf, __size, __objsize (__buf));
>      }
>    return __getcwd_alias (__buf, __size);
>  }
> @@ -227,8 +231,8 @@ extern char *__REDIRECT_NTH (__getwd_warn, (char *__buf), getwd)
>  __fortify_function __nonnull ((1)) __attribute_deprecated__ __wur char *
>  __NTH (getwd (char *__buf))
>  {
> -  if (__bos (__buf) != (size_t) -1)
> -    return __getwd_chk (__buf, __bos (__buf));
> +  if (__objsize (__buf) != (size_t) -1)
> +    return __getwd_chk (__buf, __objsize (__buf));
>    return __getwd_warn (__buf);
>  }
>  #endif
> @@ -248,13 +252,13 @@ extern size_t __REDIRECT_NTH (__confstr_chk_warn,
>  __fortify_function size_t
>  __NTH (confstr (int __name, char *__buf, size_t __len))
>  {
> -  if (__bos (__buf) != (size_t) -1)
> +  if (__objsize (__buf) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__len))
> -	return __confstr_chk (__name, __buf, __len, __bos (__buf));
> +	return __confstr_chk (__name, __buf, __len, __objsize (__buf));
>  
> -      if (__bos (__buf) < __len)
> -	return __confstr_chk_warn (__name, __buf, __len, __bos (__buf));
> +      if (__objsize (__buf) < __len)
> +	return __confstr_chk_warn (__name, __buf, __len, __objsize (__buf));
>      }
>    return __confstr_alias (__name, __buf, __len);
>  }
> @@ -273,13 +277,13 @@ extern int __REDIRECT_NTH (__getgroups_chk_warn,
>  __fortify_function int
>  __NTH (getgroups (int __size, __gid_t __list[]))
>  {
> -  if (__bos (__list) != (size_t) -1)
> +  if (__objsize (__list) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__size) || __size < 0)
> -	return __getgroups_chk (__size, __list, __bos (__list));
> +	return __getgroups_chk (__size, __list, __objsize (__list));
>  
> -      if (__size * sizeof (__gid_t) > __bos (__list))
> -	return __getgroups_chk_warn (__size, __list, __bos (__list));
> +      if (__size * sizeof (__gid_t) > __objsize (__list))
> +	return __getgroups_chk_warn (__size, __list, __objsize (__list));
>      }
>    return __getgroups_alias (__size, __list);
>  }
> @@ -300,13 +304,13 @@ extern int __REDIRECT_NTH (__ttyname_r_chk_warn,
>  __fortify_function int
>  __NTH (ttyname_r (int __fd, char *__buf, size_t __buflen))
>  {
> -  if (__bos (__buf) != (size_t) -1)
> +  if (__objsize (__buf) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__buflen))
> -	return __ttyname_r_chk (__fd, __buf, __buflen, __bos (__buf));
> +	return __ttyname_r_chk (__fd, __buf, __buflen, __objsize (__buf));
>  
> -      if (__buflen > __bos (__buf))
> -	return __ttyname_r_chk_warn (__fd, __buf, __buflen, __bos (__buf));
> +      if (__buflen > __objsize (__buf))
> +	return __ttyname_r_chk_warn (__fd, __buf, __buflen, __objsize (__buf));
>      }
>    return __ttyname_r_alias (__fd, __buf, __buflen);
>  }
> @@ -326,13 +330,13 @@ extern int __REDIRECT (__getlogin_r_chk_warn,
>  __fortify_function int
>  getlogin_r (char *__buf, size_t __buflen)
>  {
> -  if (__bos (__buf) != (size_t) -1)
> +  if (__objsize (__buf) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__buflen))
> -	return __getlogin_r_chk (__buf, __buflen, __bos (__buf));
> +	return __getlogin_r_chk (__buf, __buflen, __objsize (__buf));
>  
> -      if (__buflen > __bos (__buf))
> -	return __getlogin_r_chk_warn (__buf, __buflen, __bos (__buf));
> +      if (__buflen > __objsize (__buf))
> +	return __getlogin_r_chk_warn (__buf, __buflen, __objsize (__buf));
>      }
>    return __getlogin_r_alias (__buf, __buflen);
>  }
> @@ -354,13 +358,13 @@ extern int __REDIRECT_NTH (__gethostname_chk_warn,
>  __fortify_function int
>  __NTH (gethostname (char *__buf, size_t __buflen))
>  {
> -  if (__bos (__buf) != (size_t) -1)
> +  if (__objsize (__buf) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__buflen))
> -	return __gethostname_chk (__buf, __buflen, __bos (__buf));
> +	return __gethostname_chk (__buf, __buflen, __objsize (__buf));
>  
> -      if (__buflen > __bos (__buf))
> -	return __gethostname_chk_warn (__buf, __buflen, __bos (__buf));
> +      if (__buflen > __objsize (__buf))
> +	return __gethostname_chk_warn (__buf, __buflen, __objsize (__buf));
>      }
>    return __gethostname_alias (__buf, __buflen);
>  }
> @@ -384,13 +388,13 @@ extern int __REDIRECT_NTH (__getdomainname_chk_warn,
>  __fortify_function int
>  __NTH (getdomainname (char *__buf, size_t __buflen))
>  {
> -  if (__bos (__buf) != (size_t) -1)
> +  if (__objsize (__buf) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__buflen))
> -	return __getdomainname_chk (__buf, __buflen, __bos (__buf));
> +	return __getdomainname_chk (__buf, __buflen, __objsize (__buf));
>  
> -      if (__buflen > __bos (__buf))
> -	return __getdomainname_chk_warn (__buf, __buflen, __bos (__buf));
> +      if (__buflen > __objsize (__buf))
> +	return __getdomainname_chk_warn (__buf, __buflen, __objsize (__buf));
>      }
>    return __getdomainname_alias (__buf, __buflen);
>  }
> diff --git a/socket/bits/socket2.h b/socket/bits/socket2.h
> index c0421ce244..7f11cbeba9 100644
> --- a/socket/bits/socket2.h
> +++ b/socket/bits/socket2.h
> @@ -33,13 +33,13 @@ extern ssize_t __REDIRECT (__recv_chk_warn,
>  __fortify_function ssize_t
>  recv (int __fd, void *__buf, size_t __n, int __flags)
>  {
> -  if (__bos0 (__buf) != (size_t) -1)
> +  if (__objsize0 (__buf) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__n))
> -	return __recv_chk (__fd, __buf, __n, __bos0 (__buf), __flags);
> +	return __recv_chk (__fd, __buf, __n, __objsize0 (__buf), __flags);
>  
> -      if (__n > __bos0 (__buf))
> -	return __recv_chk_warn (__fd, __buf, __n, __bos0 (__buf), __flags);
> +      if (__n > __objsize0 (__buf))
> +	return __recv_chk_warn (__fd, __buf, __n, __objsize0 (__buf), __flags);
>      }
>    return __recv_alias (__fd, __buf, __n, __flags);
>  }
> @@ -64,14 +64,14 @@ __fortify_function ssize_t
>  recvfrom (int __fd, void *__restrict __buf, size_t __n, int __flags,
>  	  __SOCKADDR_ARG __addr, socklen_t *__restrict __addr_len)
>  {
> -  if (__bos0 (__buf) != (size_t) -1)
> +  if (__objsize0 (__buf) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__n))
> -	return __recvfrom_chk (__fd, __buf, __n, __bos0 (__buf), __flags,
> +	return __recvfrom_chk (__fd, __buf, __n, __objsize0 (__buf), __flags,
>  			       __addr, __addr_len);
> -      if (__n > __bos0 (__buf))
> -	return __recvfrom_chk_warn (__fd, __buf, __n, __bos0 (__buf), __flags,
> -				    __addr, __addr_len);
> +      if (__n > __objsize0 (__buf))
> +	return __recvfrom_chk_warn (__fd, __buf, __n, __objsize0 (__buf),
> +				    __flags, __addr, __addr_len);
>      }
>    return __recvfrom_alias (__fd, __buf, __n, __flags, __addr, __addr_len);
>  }
> diff --git a/stdlib/bits/stdlib.h b/stdlib/bits/stdlib.h
> index 9134d3f36b..3cb1bd9721 100644
> --- a/stdlib/bits/stdlib.h
> +++ b/stdlib/bits/stdlib.h
> @@ -36,13 +36,14 @@ extern char *__REDIRECT_NTH (__realpath_chk_warn,
>  __fortify_function __wur char *
>  __NTH (realpath (const char *__restrict __name, char *__restrict __resolved))
>  {
> -  if (__bos (__resolved) != (size_t) -1)
> +  if (__objsize (__resolved) != (size_t) -1)
>      {
>  #if defined _LIBC_LIMITS_H_ && defined PATH_MAX
> -      if (__bos (__resolved) < PATH_MAX)
> -	return __realpath_chk_warn (__name, __resolved, __bos (__resolved));
> +      if (__objsize (__resolved) < PATH_MAX)
> +	return __realpath_chk_warn (__name, __resolved,
> +				    __objsize (__resolved));
>  #endif
> -      return __realpath_chk (__name, __resolved, __bos (__resolved));
> +      return __realpath_chk (__name, __resolved, __objsize (__resolved));
>      }
>  
>    return __realpath_alias (__name, __resolved);
> @@ -64,12 +65,12 @@ extern int __REDIRECT_NTH (__ptsname_r_chk_warn,
>  __fortify_function int
>  __NTH (ptsname_r (int __fd, char *__buf, size_t __buflen))
>  {
> -  if (__bos (__buf) != (size_t) -1)
> +  if (__objsize (__buf) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__buflen))
> -	return __ptsname_r_chk (__fd, __buf, __buflen, __bos (__buf));
> -      if (__buflen > __bos (__buf))
> -	return __ptsname_r_chk_warn (__fd, __buf, __buflen, __bos (__buf));
> +	return __ptsname_r_chk (__fd, __buf, __buflen, __objsize (__buf));
> +      if (__buflen > __objsize (__buf))
> +	return __ptsname_r_chk_warn (__fd, __buf, __buflen, __objsize (__buf));
>      }
>    return __ptsname_r_alias (__fd, __buf, __buflen);
>  }
> @@ -90,8 +91,8 @@ __NTH (wctomb (char *__s, wchar_t __wchar))
>  #if defined MB_LEN_MAX && MB_LEN_MAX != __STDLIB_MB_LEN_MAX
>  # error "Assumed value of MB_LEN_MAX wrong"
>  #endif
> -  if (__bos (__s) != (size_t) -1 && __STDLIB_MB_LEN_MAX > __bos (__s))
> -    return __wctomb_chk (__s, __wchar, __bos (__s));
> +  if (__objsize (__s) != (size_t) -1 && __STDLIB_MB_LEN_MAX > __objsize (__s))
> +    return __wctomb_chk (__s, __wchar, __objsize (__s));
>    return __wctomb_alias (__s, __wchar);
>  }
>  
> @@ -116,15 +117,15 @@ __fortify_function size_t
>  __NTH (mbstowcs (wchar_t *__restrict __dst, const char *__restrict __src,
>  		 size_t __len))
>  {
> -  if (__bos (__dst) != (size_t) -1)
> +  if (__objsize (__dst) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__len))
>  	return __mbstowcs_chk (__dst, __src, __len,
> -			       __bos (__dst) / sizeof (wchar_t));
> +			       __objsize (__dst) / sizeof (wchar_t));
>  
> -      if (__len > __bos (__dst) / sizeof (wchar_t))
> +      if (__len > __objsize (__dst) / sizeof (wchar_t))
>  	return __mbstowcs_chk_warn (__dst, __src, __len,
> -				     __bos (__dst) / sizeof (wchar_t));
> +				     __objsize (__dst) / sizeof (wchar_t));
>      }
>    return __mbstowcs_alias (__dst, __src, __len);
>  }
> @@ -149,12 +150,12 @@ __fortify_function size_t
>  __NTH (wcstombs (char *__restrict __dst, const wchar_t *__restrict __src,
>  		 size_t __len))
>  {
> -  if (__bos (__dst) != (size_t) -1)
> +  if (__objsize (__dst) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__len))
> -	return __wcstombs_chk (__dst, __src, __len, __bos (__dst));
> -      if (__len > __bos (__dst))
> -	return __wcstombs_chk_warn (__dst, __src, __len, __bos (__dst));
> +	return __wcstombs_chk (__dst, __src, __len, __objsize (__dst));
> +      if (__len > __objsize (__dst))
> +	return __wcstombs_chk_warn (__dst, __src, __len, __objsize (__dst));
>      }
>    return __wcstombs_alias (__dst, __src, __len);
>  }
> diff --git a/wcsmbs/bits/wchar2.h b/wcsmbs/bits/wchar2.h
> index 86e8e23e76..6a67b4bc1c 100644
> --- a/wcsmbs/bits/wchar2.h
> +++ b/wcsmbs/bits/wchar2.h
> @@ -39,15 +39,15 @@ __fortify_function wchar_t *
>  __NTH (wmemcpy (wchar_t *__restrict __s1, const wchar_t *__restrict __s2,
>  		size_t __n))
>  {
> -  if (__bos0 (__s1) != (size_t) -1)
> +  if (__objsize0 (__s1) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__n))
>  	return __wmemcpy_chk (__s1, __s2, __n,
> -			      __bos0 (__s1) / sizeof (wchar_t));
> +			      __objsize0 (__s1) / sizeof (wchar_t));
>  
> -      if (__n > __bos0 (__s1) / sizeof (wchar_t))
> +      if (__n > __objsize0 (__s1) / sizeof (wchar_t))
>  	return __wmemcpy_chk_warn (__s1, __s2, __n,
> -				   __bos0 (__s1) / sizeof (wchar_t));
> +				   __objsize0 (__s1) / sizeof (wchar_t));
>      }
>    return __wmemcpy_alias (__s1, __s2, __n);
>  }
> @@ -67,15 +67,15 @@ extern wchar_t *__REDIRECT_NTH (__wmemmove_chk_warn,
>  __fortify_function wchar_t *
>  __NTH (wmemmove (wchar_t *__s1, const wchar_t *__s2, size_t __n))
>  {
> -  if (__bos0 (__s1) != (size_t) -1)
> +  if (__objsize0 (__s1) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__n))
>  	return __wmemmove_chk (__s1, __s2, __n,
> -			       __bos0 (__s1) / sizeof (wchar_t));
> +			       __objsize0 (__s1) / sizeof (wchar_t));
>  
> -      if (__n > __bos0 (__s1) / sizeof (wchar_t))
> +      if (__n > __objsize0 (__s1) / sizeof (wchar_t))
>  	return __wmemmove_chk_warn (__s1, __s2, __n,
> -				    __bos0 (__s1) / sizeof (wchar_t));
> +				    __objsize0 (__s1) / sizeof (wchar_t));
>      }
>    return __wmemmove_alias (__s1, __s2, __n);
>  }
> @@ -100,15 +100,15 @@ __fortify_function wchar_t *
>  __NTH (wmempcpy (wchar_t *__restrict __s1, const wchar_t *__restrict __s2,
>  		 size_t __n))
>  {
> -  if (__bos0 (__s1) != (size_t) -1)
> +  if (__objsize0 (__s1) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__n))
>  	return __wmempcpy_chk (__s1, __s2, __n,
> -			       __bos0 (__s1) / sizeof (wchar_t));
> +			       __objsize0 (__s1) / sizeof (wchar_t));
>  
> -      if (__n > __bos0 (__s1) / sizeof (wchar_t))
> +      if (__n > __objsize0 (__s1) / sizeof (wchar_t))
>  	return __wmempcpy_chk_warn (__s1, __s2, __n,
> -				    __bos0 (__s1) / sizeof (wchar_t));
> +				    __objsize0 (__s1) / sizeof (wchar_t));
>      }
>    return __wmempcpy_alias (__s1, __s2, __n);
>  }
> @@ -128,14 +128,15 @@ extern wchar_t *__REDIRECT_NTH (__wmemset_chk_warn,
>  __fortify_function wchar_t *
>  __NTH (wmemset (wchar_t *__s, wchar_t __c, size_t __n))
>  {
> -  if (__bos0 (__s) != (size_t) -1)
> +  if (__objsize0 (__s) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__n))
> -	return __wmemset_chk (__s, __c, __n, __bos0 (__s) / sizeof (wchar_t));
> +	return __wmemset_chk (__s, __c, __n,
> +			      __objsize0 (__s) / sizeof (wchar_t));
>  
> -      if (__n > __bos0 (__s) / sizeof (wchar_t))
> +      if (__n > __objsize0 (__s) / sizeof (wchar_t))
>  	return __wmemset_chk_warn (__s, __c, __n,
> -				   __bos0 (__s) / sizeof (wchar_t));
> +				   __objsize0 (__s) / sizeof (wchar_t));
>      }
>    return __wmemset_alias (__s, __c, __n);
>  }
> @@ -151,8 +152,8 @@ extern wchar_t *__REDIRECT_NTH (__wcscpy_alias,
>  __fortify_function wchar_t *
>  __NTH (wcscpy (wchar_t *__restrict __dest, const wchar_t *__restrict __src))
>  {
> -  if (__bos (__dest) != (size_t) -1)
> -    return __wcscpy_chk (__dest, __src, __bos (__dest) / sizeof (wchar_t));
> +  if (__objsize (__dest) != (size_t) -1)
> +    return __wcscpy_chk (__dest, __src, __objsize (__dest) / sizeof (wchar_t));
>    return __wcscpy_alias (__dest, __src);
>  }
>  
> @@ -167,8 +168,8 @@ extern wchar_t *__REDIRECT_NTH (__wcpcpy_alias,
>  __fortify_function wchar_t *
>  __NTH (wcpcpy (wchar_t *__restrict __dest, const wchar_t *__restrict __src))
>  {
> -  if (__bos (__dest) != (size_t) -1)
> -    return __wcpcpy_chk (__dest, __src, __bos (__dest) / sizeof (wchar_t));
> +  if (__objsize (__dest) != (size_t) -1)
> +    return __wcpcpy_chk (__dest, __src, __objsize (__dest) / sizeof (wchar_t));
>    return __wcpcpy_alias (__dest, __src);
>  }
>  
> @@ -191,14 +192,14 @@ __fortify_function wchar_t *
>  __NTH (wcsncpy (wchar_t *__restrict __dest, const wchar_t *__restrict __src,
>  		size_t __n))
>  {
> -  if (__bos (__dest) != (size_t) -1)
> +  if (__objsize (__dest) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__n))
>  	return __wcsncpy_chk (__dest, __src, __n,
> -			      __bos (__dest) / sizeof (wchar_t));
> -      if (__n > __bos (__dest) / sizeof (wchar_t))
> +			      __objsize (__dest) / sizeof (wchar_t));
> +      if (__n > __objsize (__dest) / sizeof (wchar_t))
>  	return __wcsncpy_chk_warn (__dest, __src, __n,
> -				   __bos (__dest) / sizeof (wchar_t));
> +				   __objsize (__dest) / sizeof (wchar_t));
>      }
>    return __wcsncpy_alias (__dest, __src, __n);
>  }
> @@ -222,14 +223,14 @@ __fortify_function wchar_t *
>  __NTH (wcpncpy (wchar_t *__restrict __dest, const wchar_t *__restrict __src,
>  		size_t __n))
>  {
> -  if (__bos (__dest) != (size_t) -1)
> +  if (__objsize (__dest) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__n))
>  	return __wcpncpy_chk (__dest, __src, __n,
> -			      __bos (__dest) / sizeof (wchar_t));
> -      if (__n > __bos (__dest) / sizeof (wchar_t))
> +			      __objsize (__dest) / sizeof (wchar_t));
> +      if (__n > __objsize (__dest) / sizeof (wchar_t))
>  	return __wcpncpy_chk_warn (__dest, __src, __n,
> -				   __bos (__dest) / sizeof (wchar_t));
> +				   __objsize (__dest) / sizeof (wchar_t));
>      }
>    return __wcpncpy_alias (__dest, __src, __n);
>  }
> @@ -245,8 +246,8 @@ extern wchar_t *__REDIRECT_NTH (__wcscat_alias,
>  __fortify_function wchar_t *
>  __NTH (wcscat (wchar_t *__restrict __dest, const wchar_t *__restrict __src))
>  {
> -  if (__bos (__dest) != (size_t) -1)
> -    return __wcscat_chk (__dest, __src, __bos (__dest) / sizeof (wchar_t));
> +  if (__objsize (__dest) != (size_t) -1)
> +    return __wcscat_chk (__dest, __src, __objsize (__dest) / sizeof (wchar_t));
>    return __wcscat_alias (__dest, __src);
>  }
>  
> @@ -263,9 +264,9 @@ __fortify_function wchar_t *
>  __NTH (wcsncat (wchar_t *__restrict __dest, const wchar_t *__restrict __src,
>  		size_t __n))
>  {
> -  if (__bos (__dest) != (size_t) -1)
> +  if (__objsize (__dest) != (size_t) -1)
>      return __wcsncat_chk (__dest, __src, __n,
> -			  __bos (__dest) / sizeof (wchar_t));
> +			  __objsize (__dest) / sizeof (wchar_t));
>    return __wcsncat_alias (__dest, __src, __n);
>  }
>  
> @@ -285,18 +286,18 @@ __fortify_function int
>  __NTH (swprintf (wchar_t *__restrict __s, size_t __n,
>  		 const wchar_t *__restrict __fmt, ...))
>  {
> -  if (__bos (__s) != (size_t) -1 || __USE_FORTIFY_LEVEL > 1)
> +  if (__objsize (__s) != (size_t) -1 || __USE_FORTIFY_LEVEL > 1)
>      return __swprintf_chk (__s, __n, __USE_FORTIFY_LEVEL - 1,
> -			   __bos (__s) / sizeof (wchar_t),
> +			   __objsize (__s) / sizeof (wchar_t),
>  			   __fmt, __va_arg_pack ());
>    return __swprintf_alias (__s, __n, __fmt, __va_arg_pack ());
>  }
>  #elif !defined __cplusplus
>  /* XXX We might want to have support in gcc for swprintf.  */
>  # define swprintf(s, n, ...) \
> -  (__bos (s) != (size_t) -1 || __USE_FORTIFY_LEVEL > 1			      \
> +  (__objsize (s) != (size_t) -1 || __USE_FORTIFY_LEVEL > 1		      \
>     ? __swprintf_chk (s, n, __USE_FORTIFY_LEVEL - 1,			      \
> -		     __bos (s) / sizeof (wchar_t), __VA_ARGS__)		      \
> +		     __objsize (s) / sizeof (wchar_t), __VA_ARGS__)	      \
>     : swprintf (s, n, __VA_ARGS__))
>  #endif
>  
> @@ -315,9 +316,9 @@ __fortify_function int
>  __NTH (vswprintf (wchar_t *__restrict __s, size_t __n,
>  		  const wchar_t *__restrict __fmt, __gnuc_va_list __ap))
>  {
> -  if (__bos (__s) != (size_t) -1 || __USE_FORTIFY_LEVEL > 1)
> +  if (__objsize (__s) != (size_t) -1 || __USE_FORTIFY_LEVEL > 1)
>      return __vswprintf_chk (__s, __n,  __USE_FORTIFY_LEVEL - 1,
> -			    __bos (__s) / sizeof (wchar_t), __fmt, __ap);
> +			    __objsize (__s) / sizeof (wchar_t), __fmt, __ap);
>    return __vswprintf_alias (__s, __n, __fmt, __ap);
>  }
>  
> @@ -383,14 +384,14 @@ extern wchar_t *__REDIRECT (__fgetws_chk_warn,
>  __fortify_function __wur wchar_t *
>  fgetws (wchar_t *__restrict __s, int __n, __FILE *__restrict __stream)
>  {
> -  if (__bos (__s) != (size_t) -1)
> +  if (__objsize (__s) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__n) || __n <= 0)
> -	return __fgetws_chk (__s, __bos (__s) / sizeof (wchar_t),
> +	return __fgetws_chk (__s, __objsize (__s) / sizeof (wchar_t),
>  			     __n, __stream);
>  
> -      if ((size_t) __n > __bos (__s) / sizeof (wchar_t))
> -	return __fgetws_chk_warn (__s, __bos (__s) / sizeof (wchar_t),
> +      if ((size_t) __n > __objsize (__s) / sizeof (wchar_t))
> +	return __fgetws_chk_warn (__s, __objsize (__s) / sizeof (wchar_t),
>  				  __n, __stream);
>      }
>    return __fgetws_alias (__s, __n, __stream);
> @@ -414,14 +415,15 @@ extern wchar_t *__REDIRECT (__fgetws_unlocked_chk_warn,
>  __fortify_function __wur wchar_t *
>  fgetws_unlocked (wchar_t *__restrict __s, int __n, __FILE *__restrict __stream)
>  {
> -  if (__bos (__s) != (size_t) -1)
> +  if (__objsize (__s) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__n) || __n <= 0)
> -	return __fgetws_unlocked_chk (__s, __bos (__s) / sizeof (wchar_t),
> +	return __fgetws_unlocked_chk (__s, __objsize (__s) / sizeof (wchar_t),
>  				      __n, __stream);
>  
> -      if ((size_t) __n > __bos (__s) / sizeof (wchar_t))
> -	return __fgetws_unlocked_chk_warn (__s, __bos (__s) / sizeof (wchar_t),
> +      if ((size_t) __n > __objsize (__s) / sizeof (wchar_t))
> +	return __fgetws_unlocked_chk_warn (__s,
> +					   __objsize (__s) / sizeof (wchar_t),
>  					   __n, __stream);
>      }
>    return __fgetws_unlocked_alias (__s, __n, __stream);
> @@ -447,8 +449,8 @@ __NTH (wcrtomb (char *__restrict __s, wchar_t __wchar,
>  #if defined MB_LEN_MAX && MB_LEN_MAX != __WCHAR_MB_LEN_MAX
>  # error "Assumed value of MB_LEN_MAX wrong"
>  #endif
> -  if (__bos (__s) != (size_t) -1 && __WCHAR_MB_LEN_MAX > __bos (__s))
> -    return __wcrtomb_chk (__s, __wchar, __ps, __bos (__s));
> +  if (__objsize (__s) != (size_t) -1 && __WCHAR_MB_LEN_MAX > __objsize (__s))
> +    return __wcrtomb_chk (__s, __wchar, __ps, __objsize (__s));
>    return __wcrtomb_alias (__s, __wchar, __ps);
>  }
>  
> @@ -474,15 +476,15 @@ __fortify_function size_t
>  __NTH (mbsrtowcs (wchar_t *__restrict __dst, const char **__restrict __src,
>  		  size_t __len, mbstate_t *__restrict __ps))
>  {
> -  if (__bos (__dst) != (size_t) -1)
> +  if (__objsize (__dst) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__len))
>  	return __mbsrtowcs_chk (__dst, __src, __len, __ps,
> -				__bos (__dst) / sizeof (wchar_t));
> +				__objsize (__dst) / sizeof (wchar_t));
>  
> -      if (__len > __bos (__dst) / sizeof (wchar_t))
> +      if (__len > __objsize (__dst) / sizeof (wchar_t))
>  	return __mbsrtowcs_chk_warn (__dst, __src, __len, __ps,
> -				     __bos (__dst) / sizeof (wchar_t));
> +				     __objsize (__dst) / sizeof (wchar_t));
>      }
>    return __mbsrtowcs_alias (__dst, __src, __len, __ps);
>  }
> @@ -508,13 +510,14 @@ __fortify_function size_t
>  __NTH (wcsrtombs (char *__restrict __dst, const wchar_t **__restrict __src,
>  		  size_t __len, mbstate_t *__restrict __ps))
>  {
> -  if (__bos (__dst) != (size_t) -1)
> +  if (__objsize (__dst) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__len))
> -	return __wcsrtombs_chk (__dst, __src, __len, __ps, __bos (__dst));
> +	return __wcsrtombs_chk (__dst, __src, __len, __ps, __objsize (__dst));
>  
> -      if (__len > __bos (__dst))
> -	return __wcsrtombs_chk_warn (__dst, __src, __len, __ps, __bos (__dst));
> +      if (__len > __objsize (__dst))
> +	return __wcsrtombs_chk_warn (__dst, __src, __len, __ps,
> +				     __objsize (__dst));
>      }
>    return __wcsrtombs_alias (__dst, __src, __len, __ps);
>  }
> @@ -542,15 +545,15 @@ __fortify_function size_t
>  __NTH (mbsnrtowcs (wchar_t *__restrict __dst, const char **__restrict __src,
>  		   size_t __nmc, size_t __len, mbstate_t *__restrict __ps))
>  {
> -  if (__bos (__dst) != (size_t) -1)
> +  if (__objsize (__dst) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__len))
>  	return __mbsnrtowcs_chk (__dst, __src, __nmc, __len, __ps,
> -				 __bos (__dst) / sizeof (wchar_t));
> +				 __objsize (__dst) / sizeof (wchar_t));
>  
> -      if (__len > __bos (__dst) / sizeof (wchar_t))
> +      if (__len > __objsize (__dst) / sizeof (wchar_t))
>  	return __mbsnrtowcs_chk_warn (__dst, __src, __nmc, __len, __ps,
> -				      __bos (__dst) / sizeof (wchar_t));
> +				      __objsize (__dst) / sizeof (wchar_t));
>      }
>    return __mbsnrtowcs_alias (__dst, __src, __nmc, __len, __ps);
>  }
> @@ -578,15 +581,15 @@ __fortify_function size_t
>  __NTH (wcsnrtombs (char *__restrict __dst, const wchar_t **__restrict __src,
>  		   size_t __nwc, size_t __len, mbstate_t *__restrict __ps))
>  {
> -  if (__bos (__dst) != (size_t) -1)
> +  if (__objsize (__dst) != (size_t) -1)
>      {
>        if (!__builtin_constant_p (__len))
>  	return __wcsnrtombs_chk (__dst, __src, __nwc, __len, __ps,
> -				 __bos (__dst));
> +				 __objsize (__dst));
>  
> -      if (__len > __bos (__dst))
> +      if (__len > __objsize (__dst))
>  	return __wcsnrtombs_chk_warn (__dst, __src, __nwc, __len, __ps,
> -				      __bos (__dst));
> +				      __objsize (__dst));
>      }
>    return __wcsnrtombs_alias (__dst, __src, __nwc, __len, __ps);
>  }
> 

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH 2/2] nonstring: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size
  2020-12-28 17:36   ` Adhemerval Zanella via Libc-alpha
@ 2020-12-29 14:04     ` Siddhesh Poyarekar via Libc-alpha
  2020-12-29 14:26     ` Jakub Jelinek via Libc-alpha
  1 sibling, 0 replies; 14+ messages in thread
From: Siddhesh Poyarekar via Libc-alpha @ 2020-12-29 14:04 UTC (permalink / raw
  To: Adhemerval Zanella, libc-alpha; +Cc: fweimer, jakub

On 12/28/20 11:06 PM, Adhemerval Zanella via Libc-alpha wrote:
> 
> 
> On 19/12/2020 03:33, Siddhesh Poyarekar via Libc-alpha wrote:
>> These fortified functions use, roughly, the following idiom to
>> implement fortifications:
>>
>>    if (__builtin_dynamic_object_size (obj) != -1)
>>      {
>>        __fortified_chk ();
>>        return;
>>      }
>>    __unfortified ();
> 
> Reading the D93015, it should be:
> 
>    if (__builtin_dynamic_object_size (obj, 0 or 1) != -1ULL)
> 
> right?

Technically, 0, 1, 2 or 3 but we only use 0 and 1 for _FORTIFY_SOURCE at 
the moment.

> 
> The __builtin_dynamic_object_size seems to be a 64-bit integer.
> How does it play in 32-bit targets? Would clang optimize the check
> when dynamic one need to be emitted?
> 

It should work, but I'll confirm just the same.

>> LLVM is currently unable to fold the conditional; a patch has been
>> proposed[1] to fix this.
>>
>> Due to this limitation in llvm, these fortifications have a higher
>> performance cost than those in the first patch.
>>
>> [1] https://reviews.llvm.org/D93015
> 
> I think you can state that this has been implemented on LLVM.

Given that it's no longer an issue, I suppose it's OK to simply omit this?

Siddhesh

^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH 2/2] nonstring: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size
  2020-12-28 17:36   ` Adhemerval Zanella via Libc-alpha
  2020-12-29 14:04     ` Siddhesh Poyarekar via Libc-alpha
@ 2020-12-29 14:26     ` Jakub Jelinek via Libc-alpha
  1 sibling, 0 replies; 14+ messages in thread
From: Jakub Jelinek via Libc-alpha @ 2020-12-29 14:26 UTC (permalink / raw
  To: Adhemerval Zanella; +Cc: fweimer, Siddhesh Poyarekar, libc-alpha

On Mon, Dec 28, 2020 at 02:36:22PM -0300, Adhemerval Zanella wrote:
> The __builtin_dynamic_object_size seems to be a 64-bit integer.

No.  The builtin returns like __builtin_object_size a size_t.
Whether it is 64-bit or 32-bit integer depends on the ABI.

	Jakub


^ permalink raw reply	[flat|nested] 14+ messages in thread

* Re: [PATCH 1/2] string: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size
  2020-12-28 16:44   ` Adhemerval Zanella via Libc-alpha
@ 2020-12-29 15:14     ` Siddhesh Poyarekar via Libc-alpha
  0 siblings, 0 replies; 14+ messages in thread
From: Siddhesh Poyarekar via Libc-alpha @ 2020-12-29 15:14 UTC (permalink / raw
  To: Adhemerval Zanella, libc-alpha; +Cc: fweimer, jakub

On 12/28/20 10:14 PM, Adhemerval Zanella via Libc-alpha wrote:
> For previous discussion I couldn't really grap what is the GCC intention
> regarding this new builtin. Would it willing to implement with the same
> semantic as LLVM has done or depending of result when glibc starts to
> provide it GCC will either change its semantic or not implement at all?

The original conversation around it is here[1], although the 
conversation is more about extending __builtin_object_size vs 
introducing a new builtin (i.e. the __builtin_dynamic_object_size that 
eventually went into llvm).

My understanding from that conversation is that the gcc community sees 
value in the builtin and is willing to consider it as long as its 
semantics are comprehensively documented.  Right now the only real 
explanation for __builtin_dynamic_object_size is that "it's like 
__builtin_object_size", which is inaccurate and misleading.

I wanted to do this first too, i.e. document 
__builtin_dynamic_object_size semantics and work on getting it included 
in gcc but I couldn't make the gcc stage 1 deadline (which was last 
month) and decided to pick it up in 2021.

> If the former, using _FORTIFY_SOURCE=3 should be fine.  However, if it
> is the latter I think it would be better to add it as another and different
> FORTIFY flag ( _FORTIFY_SOURCE_DYNAMIC or something like that).
> 
> I really want to avoid the issue where developers would not see the
> expected code generation when using _FORTIFY_SOURCE=3 with gcc or the worse,
> where _FORTIFY_SOURCE=3 would have different semantic depending of the
> compiler used.

I don't foresee semantic differences diverging enough to be a 
compatibility issue for developers using _FORTIFY_SOURCE=3.  At worst, 
it could result in developers either seeing performance differences 
(because one compiler emits better code than the other due to the kind 
of information it chooses to glean and retain from the builtin) or is 
able to (or not) fortify functions, again because of how well it can 
deduce object sizes.  Such differences already exist in 
__builtin_object_size.

Does that address your concern?

> This should be in a different patch, where glibc would handle not support
> _FORTIFY_SOURCE levels and emit the expected warnings.

OK.

> I think from previous version that Florian suggested renamed this internal macros
> to __glibc_objsize[0].

Hmm, I missed that.  I'll rename it to __glibc_objsize.

Thanks,
Siddhesh

[1] https://gcc.gnu.org/legacy-ml/gcc/2019-01/msg00188.html

^ permalink raw reply	[flat|nested] 14+ messages in thread

end of thread, other threads:[~2020-12-29 15:14 UTC | newest]

Thread overview: 14+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2020-12-19  6:33 [PATCH v6 0/2] _FORTIFY_SOURCE=3 Siddhesh Poyarekar via Libc-alpha
2020-12-19  6:33 ` [PATCH 1/2] string: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size Siddhesh Poyarekar via Libc-alpha
2020-12-28 16:44   ` Adhemerval Zanella via Libc-alpha
2020-12-29 15:14     ` Siddhesh Poyarekar via Libc-alpha
2020-12-19  6:33 ` [PATCH 2/2] nonstring: " Siddhesh Poyarekar via Libc-alpha
2020-12-28 17:36   ` Adhemerval Zanella via Libc-alpha
2020-12-29 14:04     ` Siddhesh Poyarekar via Libc-alpha
2020-12-29 14:26     ` Jakub Jelinek via Libc-alpha
2020-12-22 13:00 ` [PATCH v6 0/2] _FORTIFY_SOURCE=3 Siddhesh Poyarekar
2020-12-22 21:49   ` Adhemerval Zanella via Libc-alpha
  -- strict thread matches above, loose matches on Subject: below --
2020-12-10 18:13 [PATCH " Siddhesh Poyarekar via Libc-alpha
2020-12-10 18:13 ` [PATCH 1/2] string: _FORTIFY_SOURCE=3 using __builtin_dynamic_object_size Siddhesh Poyarekar via Libc-alpha
2020-12-10 19:10   ` Paul Eggert
2020-12-11  1:36     ` Siddhesh Poyarekar via Libc-alpha
2020-12-11  2:42       ` Paul Eggert

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).