On Wed, Jun 16, 2021 at 11:40:08PM -0600, Gavin Howard wrote:

> Hello,
> 
> My name is Gavin Howard. I have developed a new bc(1) and dc(1)
> implementation. [0]
> 
> I propose replacing the current implementations with mine.
> 
> Advantages:
> 
> * Performance. [1]
> * Extensions for ease of use.
> * With build options to remove most extensions, if desired.
> * Compatible with GNU bc.
> * Already used by default in FreeBSD.
> * Fuzzed thoroughly.
> * No exec needed for bc(1) (both programs are contained in the same
>   multi-call binary).
> 
> Expectations met:
> 
> * Already uses pledge(2) and unveil(2).
> * No dependencies beyond C99, POSIX `make`, and POSIX `sh`.
>     * This includes no dependency on editline(3), even though my bc(1)
>       and dc(1) have a history implementation.
> * Thorough test suite.
> * Comprehensive man pages.
> * Locale support.
> 
> Disadvantages:
> 
> * There are incompatibilities with the current bc(1) and dc(1), which
>   are listed below. All users would need to be made aware of these
>   incompatibilities, so they can update scripts, and scripts in `src/`
>   will also need to be updated.
> 
> Incompatibilities (failing tests from `regress/usr.bin`):
> 
> 1. Current bc(1) and dc(1) return 0 for length(a) where a is 0. Mine
>    return 1. This causes my dc(1) to fail `dc/t1.in` and `dc/t28.in`.
> 2. Current dc(1) implements arrays as part of registers. Mine keeps
>    arrays and registers separate. This causes my dc(1) to fail
>    `dc/t1.in` and `dc/t8.in`.
> 3. Current dc(1) does not print a `nul` byte if given the `P` or `a`
>    commands with 0 on the top of the stack. My dc(1) does (because it
>    considers 0 to have one digit, see #1). This causes my dc(1) to fail
>    `dc/t3.in` and `dc/t13.in`.
> 4. Current dc(1) starts with empty registers, and allows the user to pop
>    all items off the register stack. My dc(1) starts with a single item
>    in the register and does not allow the user to remove it.
> 5. Current dc(1) will push an item onto a register stack for the `s`
>    command. My dc(1) does not since one already exists. This, combined
>    with #4, causes my dc(1) to fail `dc/t5.in`
> 6. Current bc(1) and dc(1) have a larger maximum `obase` than mine. This
>    causes my dc(1) to fail `dc/t9.in`.
> 7. Current dc(1) does not reset on errors. My dc(1) does, so it fails
>    `dc/t12.in`.
> 8. Current dc(1) allows register names with any character. My dc(1)
>    requires non-control characters and has a different way of doing
>    extended registers. This causes my dc(1) to fail `dc/t15.in`,
>    `dc/t16.in`, `dc/t19.in`, `dc/t21.in`, and `dc/t23.in`.
> 9. Current bc(1) is a frontend to dc(1). Mine are combined into the same
>    binary and generate and run bytecode. This means that my bc(1) fails
>    all of the bc(1) regression tests (which generate dc(1) code) and
>    does not have the `-c` option.
> 
> Notes:
> 
> My dc(1) also fails `dc/t10.in` because it doesn't have the `!` command,
> but https://github.com/openbsd/src/commit/dc405aa075 makes it appear as
> though the current dc(1) does not have the `!` command either.
> 
> In https://youtu.be/gvmGfpMgny4?t=1277 , Bob Beck said that unveil(2)
> must not be used on command-line arguments, so I use unveil(2) after all
> command-line files are executed.
> 
> Current version is 4.0.2. I am planning to release version 4.1.0 soon,
> but held off in case you are interested and had feedback that might
> help.
> 
> I am willing to help maintain them if they are put into OpenBSD, but I
> am also willing to pass them off to whoever you wish, should you wish to
> do so.
> 
> I do have a mirror on GitHub.
> 
> If you are not interested, feel free to ignore this email.
> 
> Regardless, thank you for your time.
> 
> Gavin Howard
> 
> [0]: https://git.yzena.com/gavin/bc
> [1]: https://git.yzena.com/gavin/bc/src/branch/master/manuals/benchmarks.md
> 

I think it is interesting. As for the incompatibilites, my memory says
I followed the original dc and bc when deciding on those (GNU chose to
differs in these cases). Bit it has been 18 years since I wrote the
current versions, so I might misrememeber.

As for moving to your version, I have no opinion yet. I have some
attachment to the current code, but not so strong that I am opposing
replacement upfront. OTOH the current implementaion is almost
maintainance free for many years already. So I dunno.

I'll take a look at your code soon and maybe other devs have opinions.

        -Otto

Reply via email to