linux-man.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Alejandro Colomar <alx.manpages@gmail.com>
To: mtk.manpages@gmail.com
Cc: Alejandro Colomar <alx.manpages@gmail.com>,
	linux-man@vger.kernel.org, Jens Gustedt <jens.gustedt@loria.fr>,
	Glibc <libc-alpha@sourceware.org>
Subject: [PATCH 2/2] ctime.3, strftime.3, strptime.3, timegm.3: Add [[gnu::nonnull]] to <time.h> prototypes
Date: Wed, 20 Oct 2021 22:22:41 +0200	[thread overview]
Message-ID: <20211020202241.171180-2-alx.manpages@gmail.com> (raw)
In-Reply-To: <20211020202241.171180-1-alx.manpages@gmail.com>

C2X changes the prototypes of <time.h> functions that accept a
pointer that cannot be NULL, to use 'static', which clearly
denotes that passing NULL is Undefined Behavior.

For example, 'time_t mktime(struct tm tm[static 1]);'.

This change is backwards compatible, since array notation is just
syntactic sugar for pointers, and the Undefined Behavior in case
of a pointer already existed (in the wording); it just wasn't
clear from the prototype itself.

However, that forces the use of VLA (array) notation for something
that is *not* an array.  It is cofusing, probably too much for
some programmers not so familiar with the difference between an
array and a pointer, and that happens more than we would like.
Even for programmers that clearly know the difference between an
array and a pointer, this is at least misleading.

That happens because the standard lacks a 'nonnull' attribute, and
only has that (VLA) way of expressing what GCC can express with
'[[gnu::nonnull]]' (a.k.a. '__attribute__((__nonnull__))').

Expressing that NULL pointers shall invoke Undefined Behavior in
the prototype of a function is *way* more readable than having to
read through the whole manual page text, so ideally we should also
follow the standard idea of expressing that.  But we can make use
of more advanced techniques such as the GCC attribute, which help
keep the information that those pointers are actually pointers and
not arrays.

From the 2 different attribute notations, let's use the "C++" one,
which will be part of the standard in C2X (unlike __attribute__),
and is also shorter, which helps keep the SYNOPSIS short (mostly
one-liner prototypes).

See <http://www.open-std.org/JTC1/SC22/WG14/www/docs/n2417.pdf>

Signed-off-by: Alejandro Colomar <alx.manpages@gmail.com>
Cc: Jens Gustedt <jens.gustedt@loria.fr>
Cc: Glibc <libc-alpha@sourceware.org>
---
 man3/ctime.3    | 26 +++++++++++++-------------
 man3/strftime.3 |  1 +
 man3/strptime.3 |  1 +
 man3/timegm.3   |  4 ++--
 4 files changed, 17 insertions(+), 15 deletions(-)

diff --git a/man3/ctime.3 b/man3/ctime.3
index 0620741e9..42021a588 100644
--- a/man3/ctime.3
+++ b/man3/ctime.3
@@ -40,23 +40,23 @@ localtime_r \- transform date and time to broken-down time or ASCII
 .nf
 .B #include <time.h>
 .PP
-.BI "char *asctime(const struct tm *" tm );
-.BI "char *asctime_r(const struct tm *restrict " tm ,
-.BI "                    char " buf "[static restrict 26]);"
+.BI "[[gnu::nonnull]] char *asctime(const struct tm *" tm );
+.BI "[[gnu::nonnull]] char *asctime_r(const struct tm *restrict " tm ,
+.BI "                                     char " buf "[static restrict 26]);"
 .PP
-.BI "char *ctime(const time_t *" timep );
-.BI "char *ctime_r(const time_t *restrict " timep ,
-.BI "                    char " buf "[static restrict 26]);"
+.BI "[[gnu::nonnull]] char *ctime(const time_t *" timep );
+.BI "[[gnu::nonnull]] char *ctime_r(const time_t *restrict " timep ,
+.BI "                                     char " buf "[static restrict 26]);"
 .PP
-.BI "struct tm *gmtime(const time_t *" timep );
-.BI "struct tm *gmtime_r(const time_t *restrict " timep ,
-.BI "                    struct tm *restrict " result );
+.BI "[[gnu::nonnull]] struct tm *gmtime(const time_t *" timep );
+.BI "[[gnu::nonnull]] struct tm *gmtime_r(const time_t *restrict " timep ,
+.BI "                                     struct tm *restrict " result );
 .PP
-.BI "struct tm *localtime(const time_t *" timep );
-.BI "struct tm *localtime_r(const time_t *restrict " timep ,
-.BI "                    struct tm *restrict " result );
+.BI "[[gnu::nonnull]] struct tm *localtime(const time_t *" timep );
+.BI "[[gnu::nonnull]] struct tm *localtime_r(const time_t *restrict " timep ,
+.BI "                                     struct tm *restrict " result );
 .PP
-.BI "time_t mktime(struct tm *" tm );
+.BI "[[gnu::nonnull]] time_t mktime(struct tm *" tm );
 .fi
 .PP
 .RS -4
diff --git a/man3/strftime.3 b/man3/strftime.3
index a24ea720b..715b30edb 100644
--- a/man3/strftime.3
+++ b/man3/strftime.3
@@ -41,6 +41,7 @@ strftime \- format date and time
 .nf
 .B #include <time.h>
 .PP
+.B [[gnu::nonnull]]
 .BI "size_t strftime(char *restrict " s ", size_t " max ,
 .BI "                const char *restrict " format ,
 .BI "                const struct tm *restrict " tm );
diff --git a/man3/strptime.3 b/man3/strptime.3
index d6595d4bf..c1b334d87 100644
--- a/man3/strptime.3
+++ b/man3/strptime.3
@@ -36,6 +36,7 @@ strptime \- convert a string representation of time to a time tm structure
 .BR "#define _XOPEN_SOURCE" "       /* See feature_test_macros(7) */"
 .B #include <time.h>
 .PP
+.B [[gnu::nonnull]]
 .BI "char *strptime(const char *restrict " s ", const char *restrict " format ,
 .BI "               struct tm *restrict " tm );
 .fi
diff --git a/man3/timegm.3 b/man3/timegm.3
index b848e83e1..18b6e4847 100644
--- a/man3/timegm.3
+++ b/man3/timegm.3
@@ -29,8 +29,8 @@ timegm, timelocal \- inverses of gmtime and localtime
 .nf
 .B #include <time.h>
 .PP
-.BI "time_t timelocal(struct tm *" tm );
-.BI "time_t timegm(struct tm *" tm );
+.BI "[[gnu::nonnull]] time_t timelocal(struct tm *" tm );
+.BI "[[gnu::nonnull]] time_t timegm(struct tm *" tm );
 .PP
 .fi
 .RS -4
-- 
2.33.0


  reply	other threads:[~2021-10-20 20:22 UTC|newest]

Thread overview: 10+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2021-10-20 20:22 [PATCH 1/2] ctime.3: Use VLA notation for [as]ctime_r() buffer Alejandro Colomar
2021-10-20 20:22 ` Alejandro Colomar [this message]
2021-10-21  8:13   ` AW: [PATCH 2/2] ctime.3, strftime.3, strptime.3, timegm.3: Add [[gnu::nonnull]] to <time.h> prototypes Walter Harms
2021-10-21  9:01     ` Alejandro Colomar (man-pages)
2021-10-21 17:40       ` Paul Eggert
2021-10-21 20:54         ` Alejandro Colomar (man-pages)
     [not found] ` <20211021092746.78bc82f8@inria.fr>
2021-10-21  9:12   ` [PATCH 1/2] ctime.3: Use VLA notation for [as]ctime_r() buffer Alejandro Colomar (man-pages)
     [not found]   ` <20c1e58b-ba2b-f9df-ab1f-f80725414cf5@gmail.com>
2021-10-21  9:13     ` Alejandro Colomar (man-pages)
     [not found]     ` <5782a3ea-9774-3acb-e365-1e4d03ed3358@gmail.com>
2021-10-21  9:14       ` Alejandro Colomar (man-pages)
     [not found]       ` <20211021110311.52541d69@inria.fr>
     [not found]         ` <ec620c5e-0952-fe16-353c-0210d3bea6e8@gmail.com>
2021-10-21  9:27           ` Alejandro Colomar (man-pages)

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20211020202241.171180-2-alx.manpages@gmail.com \
    --to=alx.manpages@gmail.com \
    --cc=jens.gustedt@loria.fr \
    --cc=libc-alpha@sourceware.org \
    --cc=linux-man@vger.kernel.org \
    --cc=mtk.manpages@gmail.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
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 NNTP newsgroup(s).