Project

General

Profile

Bug #5218

posix definition of NULL

Added by Richard PALO about 6 years ago. Updated about 2 months ago.

Status:
Closed
Priority:
Normal
Assignee:
Category:
-
Start date:
2016-01-27
Due date:
% Done:

100%

Estimated time:
(Total: 0.00 h)
Difficulty:
Medium
Tags:
needs-triage
Gerrit CR:

Description

Coming across bizarre compile errors now and then with gcc4.9.1 involving NULL not being defined as (void*)0... such as the following:

--- liblangtag_la-lt-ext-module.lo ---
lt-ext-module.c: In function 'lt_ext_module_load':
lt-ext-module.c:255:4: error: missing sentinel in function call [-Werror=format=]
    lt_string_append_filename(fullname, path, filename, NULL);
    ^
cc1: some warnings being treated as errors

Naturally for this case I can either suppress the warning being turned into an error, or
change the null to '(void*)NULL' which lead me to verify the definitions.

In both unistd.h and iso/iso_stddef.h :

#ifndef NULL
#if defined(_LP64)
#define NULL    0L
#else
#define NULL    0
#endif
#endif

From what I can gather, Posix says that stddef.h should:

NULL
    Null pointer constant. The macro shall expand to an integer constant expression with the value 0 cast to type void *. 

ref: http://pubs.opengroup.org/onlinepubs/9699919799/basedefs/stddef.h.html

I notice that netbsd defines in /usr/include/sys/null.h

/*
 * Written by Klaus Klein <kleink@NetBSD.org>, December 22, 1999.
 * Public domain.
 */

#ifndef _SYS_NULL_H_
#define _SYS_NULL_H_
#ifndef NULL
#if !defined(__GNUG__) || __GNUG__ < 2 || (__GNUG__ == 2 && __GNUC_MINOR__ < 90
)
#if !defined(__cplusplus)
#define NULL    ((void *)0)
#else
#define NULL    0
#endif /* !__cplusplus */
#else
#define NULL    __null
#endif
#endif
#endif /* _SYS_NULL_H_ */

since Garrett is working on the latest Posix stuff, perhaps this definition could be cleaned up.

We're not the only distro having problems, as searching for 'NULL fixincludes' can find...


Files

0001-5218-posix-definition-of-NULL.patch (13.9 KB) 0001-5218-posix-definition-of-NULL.patch Richard PALO, 2014-10-11 05:15 PM
il_5218.patch (33 KB) il_5218.patch Richard PALO, 2014-12-14 10:44 PM

Subtasks

Feature #6582: initial reorg adding sys/null.h for 5218Closed2016-01-27

Actions
Bug #6609: NULL pointer constant issues in uts/intelClosed2016-02-06

Actions
Bug #6610: NULL pointer constant issues in uts/i86xpvClosed2016-02-06

Actions
Bug #6611: NULL pointer constant issues in uts/i86pcClosed2016-02-06

Actions
Bug #6612: NULL pointer constant issues in uts/common/fsClosed2016-02-06

Actions
Bug #6613: NULL pointer constant issues in uts/common/osClosed2016-02-06

Actions
Bug #6614: NULL pointer constant issues in uts/common/ioClosed2016-02-06

Actions
Bug #6615: diverse NULL pointer constant issues in uts/common/Closed2016-02-06

Actions
Bug #6616: NULL pointer constant issues in commonClosed2016-02-06

Actions
Bug #6617: NULL pointer constant issues in ucbcmdResolved2016-02-07

Actions
Bug #6625: cleanup warnings in usr/src/ucbcmd/chownClosed2016-02-07

Actions
Bug #6618: NULL pointer constant issues in test/Closed2016-02-06

Actions
Bug #6619: NULL pointer constant issues in lib/cfgadm_pluginsClosed2016-02-06

Actions
Bug #6620: NULL pointer constant issues in lib/libcClosed2016-02-06

Actions
Bug #6621: NULL pointer constant issues in lib/lvmClosed2016-02-06

Actions
Bug #6622: diverse NULL pointer constant issues in lib/Closed2016-02-06

Actions
Bug #6626: NULL pointer constant issues in cmd/mdbClosed2016-02-07

Actions
Bug #6627: NULL pointer constant issues in cmd/sgsClosed2019-01-20

Actions
Bug #10266: NULL pointer constant issues in sgs/librtld_dbClosedGergő Mihály Doma2019-01-20

Actions
Bug #6628: NULL pointer constant issues in cmd/fs.dClosed2016-02-07

Actions
Bug #6629: NULL pointer constant issues under cmd/cmd-inetClosed2016-02-07

Actions
Bug #6630: NULL pointer constant issues in cmd/lvmClosed2016-02-07

Actions
Bug #6631: NULL pointer constant issues in cmd/svr4pkgClosed2016-02-07

Actions
Bug #6632: NULL pointer constant issues in cmd/lpClosed2016-02-07

Actions
Bug #6633: diverse NULL pointer constant issues in cmd/Closed2016-02-07

Actions
Bug #6634: NULL pointer constant issues in cmd/{abi,ypcmd,nscd,mailx,fm,cmd-crypto}Closed2016-02-07

Actions
Bug #6635: NULL pointer constant issues in cmd/{svc,picl,bnu,syseventd,rcm_daemon,hal,avs]Resolved2016-02-07

Actions
Bug #6636: NULL pointer constant issues in cmd/{truss,tic,stat,refer,print,oamuser,krb5,isns}Closed2016-02-07

Actions
#1

Updated by Richard PALO about 6 years ago

I guess I should be complete and add the following from the above reference:

Rationale:
The ISO C standard does not require the NULL macro to include the cast to type void * and specifies that the NULL macro be implementation-defined. POSIX.1-2008 requires the cast and therefore need not be implementation-defined.

and (referring to the part after "Null pointer constant."):

Extension to the ISO C standard
The functionality described is an extension to the ISO C standard. Application developers may make use of an extension as it is supported on all POSIX.1-2008-conforming systems.

With each function or header from the ISO C standard, a statement to the effect that "any conflict is unintentional" is included. That is intended to refer to a direct conflict. POSIX.1-2008 acts in part as a profile of the ISO C standard, and it may choose to further constrain behaviors allowed to vary by the ISO C standard. Such limitations and other compatible differences are not considered conflicts, even if a CX mark is missing. The markings are for information only.

Where additional semantics apply to a function or header, the material is identified by use of the CX margin legend.

#2

Updated by Richard PALO about 6 years ago

I'm using the attached to test on omnios in order to create an appropriate fixincludes for gcc treating with and without this update.
The updated NULL defines are adapted from the FreeBSD tree.

#3

Updated by Rich Lowe about 6 years ago

In illumos, we have many definitions of NULL, with all 3 possible values (maybe even 4, actually).

From memory, we have at least 0, 0L, (void *)0, and I think we also have (caddr_t)0, too.
It would be fantastic if we had one, correct, NULL definition in the entire source tree.

What would your changes look like if you also removed all the other (possibly conditional) definitions of NULL?

Otherwise you're still somewhat victim of which headers are included in which order (I've been bitten by this, certainly).

#4

Updated by Richard PALO about 6 years ago

I like the idea of one file as in NetBSD or FreeBSD so I have no problem creating, for example, sys/null.h.

As to the other actual NULL definitions, I don't see NULL defined as (caddr_t)0, it seems to be used directly in the gate...

from usr/src :

richard@omnis:/home/richard/src/illumos-gate/usr/src$ git grep '^\\#define[[:blank:]]NULL[[:blank:]]'
cmd/audio/include/libaudio.h:#define    NULL    0
cmd/backup/dump/lftw.c:#define    NULL 0
cmd/cmd-inet/usr.bin/pppdump/zlib.c:#define NULL    ((void *) 0)
cmd/cron/elm.c:#define    NULL        0        /* a null pointer     */
cmd/csh/sh.h:#define    NULL    0
cmd/lms/SyncLib/Include/Lock.h:#define NULL 0
cmd/lms/SyncLib/Include/Thread.h:#define NULL 0
cmd/lvm/rpc.metamedd/med_hash.h:#define    NULL    0
cmd/mdb/common/libstand/sys/salib.h:#define    NULL    (0)
cmd/mdb/common/mdb/mdb_modapi.h:#define    NULL    0L
cmd/mdb/common/mdb/mdb_modapi.h:#define    NULL    0
cmd/setuname/setuname.c:#define    NULL        (0)
cmd/sgs/rtld/common/_a.out.h:#define    NULL    0
cmd/sh/pwd.c:#define    NULL    0
cmd/spell/malloc.c:#define NULL 0
cmd/svr4pkg/libinst/pathdup.c:#define    NULL    0
cmd/vi/port/ex.h:#define    NULL    0
cmd/ypcmd/yp_b_subr.c:#define    NULL    0
cmd/ypcmd/ypcat.c:#define    NULL 0
cmd/ypcmd/yppoll.c:#define    NULL 0
cmd/ypcmd/ypset.c:#define    NULL 0
cmd/ypcmd/ypsym.h:#define    NULL 0
cmd/ypcmd/ypv1_xdr.c:#define    NULL 0
common/acpica/include/actypes.h:#define NULL                            (void *) 0
common/bzip2/bzlib_private.h:#define NULL 0
common/net/dhcp/octet.c:#define    NULL        0
common/net/wanboot/auxutil.h:#define    NULL ((void *) 0)
common/util/getoptstr.c:#define    NULL    ((void *)0)
common/util/string.c:#define    NULL    0l
grub/grub-0.97/lib/getopt1.c:#define NULL 0
grub/grub-0.97/netboot/etherboot.h:#define NULL    ((void *)0)
grub/grub-0.97/netboot/grub.h:#define NULL    ((void *)0)
grub/grub-0.97/stage2/dir.h:#define NULL 0
grub/grub-0.97/stage2/shared.h:#define NULL         ((void *) 0)
head/fmtmsg.h:#define    NULL    _NULL
head/iso/locale_iso.h:#define    NULL    0L
head/iso/locale_iso.h:#define    NULL    0
head/iso/stddef_iso.h:#define    NULL    ((void *)0)
head/iso/stddef_iso.h:#define    NULL    nullptr
head/iso/stddef_iso.h:#define    NULL    __null
head/iso/stddef_iso.h:#define    NULL    0L
head/iso/stddef_iso.h:#define    NULL    0
head/iso/stdio_iso.h:#define    NULL    0L
head/iso/stdio_iso.h:#define    NULL    0
head/iso/stdlib_iso.h:#define    NULL    0L
head/iso/stdlib_iso.h:#define    NULL    0
head/iso/string_iso.h:#define    NULL    0L
head/iso/string_iso.h:#define    NULL    0
head/iso/time_iso.h:#define    NULL    0L
head/iso/time_iso.h:#define    NULL    0
head/iso/wchar_iso.h:#define    NULL    0L
head/iso/wchar_iso.h:#define    NULL    0
head/mon.h:#define    NULL    0L
head/mon.h:#define    NULL    0
head/rpcsvc/dbm.h:#define    NULL    ((char *)0)
head/unistd.h:#define    NULL    ((void *)0)
head/unistd.h:#define    NULL    nullptr
head/unistd.h:#define    NULL    __null
head/unistd.h:#define    NULL    0L
head/unistd.h:#define    NULL    0
lib/krb5/plugins/kdb/db2/libdb2/include/db-int.h:#define    NULL        0
lib/libadm/common/getdev.c:#define    NULL            0
lib/libadm/inc/devtab.h:#define    NULL    (0)
lib/libast/amd64/include/ast/ast_stdio.h:#define NULL        0
lib/libast/amd64/include/ast/sfio.h:#define NULL        0
lib/libast/amd64/src/lib/libast/FEATURE/stdio:#define NULL        0
lib/libast/amd64/src/lib/libast/ast_stdio.h:#define NULL        0
lib/libast/common/include/sfio.h:#define NULL        0
lib/libast/i386/include/ast/ast_stdio.h:#define NULL        0
lib/libast/i386/include/ast/sfio.h:#define NULL        0
lib/libast/i386/src/lib/libast/FEATURE/stdio:#define NULL        0
lib/libast/i386/src/lib/libast/ast_stdio.h:#define NULL        0
lib/libast/sparc/include/ast/ast_stdio.h:#define NULL        0
lib/libast/sparc/include/ast/sfio.h:#define NULL        0
lib/libast/sparc/src/lib/libast/FEATURE/stdio:#define NULL        0
lib/libast/sparc/src/lib/libast/ast_stdio.h:#define NULL        0
lib/libast/sparcv9/include/ast/ast_stdio.h:#define NULL        0
lib/libast/sparcv9/include/ast/sfio.h:#define NULL        0
lib/libast/sparcv9/src/lib/libast/FEATURE/stdio:#define NULL        0
lib/libast/sparcv9/src/lib/libast/ast_stdio.h:#define NULL        0
lib/libbc/csu/common/mon.h:#define NULL    0
lib/libbc/inc/5include/stdio.h:#define    NULL        0
lib/libbc/inc/5include/stdlib.h:#define    NULL        0
lib/libbc/inc/5include/time.h:#define    NULL    0
lib/libbc/inc/include/dirent.h:#define    NULL    0
lib/libbc/inc/include/locale.h:#define    NULL        0
lib/libbc/inc/include/stdio.h:#define    NULL    0
lib/libbc/inc/include/string.h:#define    NULL        0
lib/libbc/inc/include/sys/dir.h:#define NULL 0
lib/libbc/inc/include/sys/param.h:#define    NULL    0
lib/libbc/inc/include/unistd.h:#define    NULL    0
lib/libbc/libc/gen/common/ftw.c:#define NULL 0
lib/libbc/libc/gen/common/getenv.c:#define NULL    0
lib/libbc/libc/gen/common/index.c:#define    NULL    0
lib/libbc/libc/gen/common/mallint.h:#define NULL        0
lib/libbc/libc/gen/common/rindex.c:#define NULL 0
lib/libbc/libc/gen/common/strchr.c:#define    NULL    0
lib/libbc/libc/gen/common/strpbrk.c:#define    NULL    (char *) 0
lib/libbc/libc/gen/common/strptime.c:#define NULL    0
lib/libbc/libc/gen/common/strrchr.c:#define NULL 0
lib/libbc/libc/gen/common/strtok.c:#define    NULL    (char*)0
lib/libbc/libc/gen/common/tfind.c:#define    NULL    0
lib/libc/port/gen/mallint.h:#define    NULL        (0)
lib/libmalloc/common/mallint.h:#define    NULL    (char *)0
lib/libmapmalloc/common/textmem.c:#define    NULL        (0)
lib/libpkg/common/nhash.h:#define    NULL    0
lib/watchmalloc/common/mallint.h:#define    NULL        (0)
stand/lib/sa/stddef.h:#define    NULL    0
stand/lib/sa/stdio.h:#define    NULL    0
stand/lib/sa/string.h:#define    NULL    0        /* defined here as per ISO C */
ucbhead/dbm.h:#define    NULL    ((char *) 0)
ucbhead/stdio.h:#define    NULL        0
ucbhead/sys/dir.h:#define    NULL 0
ucbhead/sys/param.h:#define    NULL    0L
ucbhead/sys/param.h:#define    NULL    0
uts/common/avs/ns/nsctl.h:#define    NULL        0
uts/common/fs/nfs/nfs_strerror.c:#define    NULL    0
uts/common/os/iscsiboot_prop.c:#define    NULL    0
uts/common/rpc/types.h:#define    NULL    0
uts/common/sys/param.h:#define    NULL    0L
uts/common/sys/param.h:#define    NULL    0
uts/common/sys/sysevent.h:#define    NULL    0L
uts/common/sys/sysevent.h:#define    NULL    0
uts/i86pc/os/ibft.c:#define    NULL    0

There does seem to be more cleanup possible, although I'm not sure that all these cases are really necessary.
#5

Updated by Richard PALO about 6 years ago

Seems there is also this rogue case!

lib/libxcurses/h/mks.h:#define       NULL    (M_NULL)

#6

Updated by Richard PALO almost 6 years ago

I'd like to advance on this if there's interest getting it committed.

A couple of things please:
- consensus on using a single file for NULL definition and then the name (sys/null.h or sys/_null.h?)
- single big patchset including updates to the files (above) using NULL ?

#7

Updated by Richard PALO almost 6 years ago

Attached is the patchset with new file sys/null.h

This found a number of new surprises...

Since the majority of the file is gleaned from FreeBSD sys/_null.h,
so I cited the original author. Is the illumos licensing compatible with FreeBSD?

I guess I suggest attacking any other files defining NULL separately, upon need.
No sense fixing something that may not be broke.

#8

Updated by Gary Mills almost 6 years ago

I'm testing this change on the SPARC platform. So far, I've found hundreds of warnings from the gcc compiler and thousands of errors from the Studio compiler, all during the build.

#9

Updated by Robert Mustacchi about 2 months ago

  • Status changed from New to Closed
  • Assignee set to Toomas Soome

This work was ultimately finished up by a collection of a number of different people. Toomas in particular took the charge on wrangling the rest of x86 and SPARC into place with help from a number of different folks. At this point, we can say that we have the definition of NULL that this work set out to complete! The original sys/null.h was added in #6582. From there, the POSIX definition was added in #8017. It was enabled by default for all of x86 in #11112 and SPARC in #12661. While there are still some cases where commands have redefined NULL on their own in a few place, the more egregious cases like mdb_modapi.h have been cleaned up. Thanks all!

Also available in: Atom PDF