Bug 292937 - m4 defn() macro with multiple args concatenates in wrong order
Summary: m4 defn() macro with multiple args concatenates in wrong order
Status: Closed FIXED
Alias: None
Product: Base System
Classification: Unclassified
Component: standards (show other bugs)
Version: 16.0-CURRENT
Hardware: Any Any
: --- Affects Some People
Assignee: Dag-Erling Smørgrav
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2026-02-04 16:27 UTC by eblake
Modified: 2026-02-15 09:27 UTC (History)
1 user (show)

See Also:
des: mfc-stable15+
des: mfc-stable14+
des: mfc-stable13-


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description eblake 2026-02-04 16:27:08 UTC
One reason that BSD's m4 is not yet a drop-in for GNU's m4 in all situations is that the two disagree on the correct output for this command line:

$ echo 'changequote([,])define(a,1)define(b,2)defn([a],[b])' | m4

GNU m4 outputs 12, but BSD m4 outputs 21.  POSIX says https://pubs.opengroup.org/onlinepubs/9799919799/utilities/m4.html "The defining text of the defn macro shall be the quoted definition (using the current quoting strings) of its arguments.".  Since it does not mention reordering those arguments, I argue that BSD's stack-like behavior of multi-argument defn is wrong.  Especially when compared to it's multi-argument dumpdef which does follow argument order.
Comment 1 commit-hook freebsd_committer freebsd_triage 2026-02-07 18:17:56 UTC
A commit in branch main references this bug:

URL: https://cgit.FreeBSD.org/src/commit/?id=25a8168f86a1222388475ce858da405e4d06c1c3

commit 25a8168f86a1222388475ce858da405e4d06c1c3
Author:     Dag-Erling Smørgrav <des@FreeBSD.org>
AuthorDate: 2026-02-07 18:16:21 +0000
Commit:     Dag-Erling Smørgrav <des@FreeBSD.org>
CommitDate: 2026-02-07 18:16:21 +0000

    m4: Change defn processing order

    Currently, defn pushes its arguments on the stack in order, which means
    they are then processed in reverse order.  POSIX does not specify what
    order they are processed in, which arguably suggests that they should be
    processed in the order they are listed.  Push them in reverse order so
    they will be processed in their original order.  This matches GNU m4.

    PR:             292937
    MFC after:      1 week
    Sponsored by:   Klara, Inc.
    Reviewed by:    obiwac, imp
    Differential Revision:  https://reviews.freebsd.org/D55116

 usr.bin/m4/eval.c                       | 2 +-
 usr.bin/m4/tests/Makefile               | 2 ++
 usr.bin/m4/tests/defn.m4 (new)          | 5 +++++
 usr.bin/m4/tests/m4_test.sh             | 9 +++++++++
 usr.bin/m4/tests/regress.defn.out (new) | 1 +
 5 files changed, 18 insertions(+), 1 deletion(-)
Comment 2 commit-hook freebsd_committer freebsd_triage 2026-02-15 08:58:52 UTC
A commit in branch stable/15 references this bug:

URL: https://cgit.FreeBSD.org/src/commit/?id=78c53adf27d542c970eab2595b04d97b129ab2d0

commit 78c53adf27d542c970eab2595b04d97b129ab2d0
Author:     Dag-Erling Smørgrav <des@FreeBSD.org>
AuthorDate: 2026-02-07 18:16:21 +0000
Commit:     Dag-Erling Smørgrav <des@FreeBSD.org>
CommitDate: 2026-02-15 08:57:46 +0000

    m4: Change defn processing order

    Currently, defn pushes its arguments on the stack in order, which means
    they are then processed in reverse order.  POSIX does not specify what
    order they are processed in, which arguably suggests that they should be
    processed in the order they are listed.  Push them in reverse order so
    they will be processed in their original order.  This matches GNU m4.

    PR:             292937
    MFC after:      1 week
    Sponsored by:   Klara, Inc.
    Reviewed by:    obiwac, imp
    Differential Revision:  https://reviews.freebsd.org/D55116

    (cherry picked from commit 25a8168f86a1222388475ce858da405e4d06c1c3)

 usr.bin/m4/eval.c                       | 2 +-
 usr.bin/m4/tests/Makefile               | 2 ++
 usr.bin/m4/tests/defn.m4 (new)          | 5 +++++
 usr.bin/m4/tests/m4_test.sh             | 9 +++++++++
 usr.bin/m4/tests/regress.defn.out (new) | 1 +
 5 files changed, 18 insertions(+), 1 deletion(-)
Comment 3 commit-hook freebsd_committer freebsd_triage 2026-02-15 08:59:57 UTC
A commit in branch stable/14 references this bug:

URL: https://cgit.FreeBSD.org/src/commit/?id=e661c4c4a3a3aef6645dee66e3c34859766b39be

commit e661c4c4a3a3aef6645dee66e3c34859766b39be
Author:     Dag-Erling Smørgrav <des@FreeBSD.org>
AuthorDate: 2026-02-07 18:16:21 +0000
Commit:     Dag-Erling Smørgrav <des@FreeBSD.org>
CommitDate: 2026-02-15 08:58:34 +0000

    m4: Change defn processing order

    Currently, defn pushes its arguments on the stack in order, which means
    they are then processed in reverse order.  POSIX does not specify what
    order they are processed in, which arguably suggests that they should be
    processed in the order they are listed.  Push them in reverse order so
    they will be processed in their original order.  This matches GNU m4.

    PR:             292937
    MFC after:      1 week
    Sponsored by:   Klara, Inc.
    Reviewed by:    obiwac, imp
    Differential Revision:  https://reviews.freebsd.org/D55116

    (cherry picked from commit 25a8168f86a1222388475ce858da405e4d06c1c3)

 usr.bin/m4/eval.c                       | 2 +-
 usr.bin/m4/tests/Makefile               | 2 ++
 usr.bin/m4/tests/defn.m4 (new)          | 5 +++++
 usr.bin/m4/tests/m4_test.sh             | 9 +++++++++
 usr.bin/m4/tests/regress.defn.out (new) | 1 +
 5 files changed, 18 insertions(+), 1 deletion(-)