You identifed an interesting problem...
The problem is missing POSIX compatibility in
POSIX distincts bewteen a basic POSIX compatibility level for tiny embedded systems and larger systems (like e.g. Linux) that claim UNIX compatibility. In the latter case, the system needs to implement all so called XSI extensions.
An XSI compatible system would need to expand certain backslash escapes in
bash can be compiled to behave POSIX/XSI compliant (and this is e.g. done on Solaris and MacOS), but this is not done for the
bash binary on Linux. If
bash is compiled for POSIX/XSI compliance, it correctly handles backslash escapes for
echo arguments and your example code would work with such a
bash binary from Solaris or MacOS, because there is no POSIX/XSI escape sequence in your example code.
bash on Linux is not XSI compliant, it does not expand backlash escapes for
echo arguments at all and this is why your example code works with
bash on Linux as well.
dash on the other side claims POSIX/XSI compliance and expands backslash escapes for
echo arguments. If
dash did implement POSIX/XSI compliance correctly, your example code did work with
dash as well. This is because your example code does not contain any POSIX/XSI backslash escape sequence.
echo to expand:
\0nnn for an octal number that represents the related character
Your example code contains the backslash sequences:
\1 for the first sed subexpression
\2 for the second sed subexpression
and this is not part of the POSIX/XSI
echo escape sequences, so the builtin
echo from a POSIX compliant shell is not permitted to expand them.
dash however incorrectly expands
\2 as octal numbers even tough this is forbidden by POSIX. This is why your example code fails with
I recommend you to make a bug-report against
dash and either wait for a fix, or to replace
echo arg by
printf '%s\n' arg. This works even with
dash because the known bug with the builtin
dash does not affect your case.
So we can list the POSIX/XSI bugs from
does not support multy-byte characters.
echo arguments even though this is forbidden
does not expand
printf arguments even though this is required.