~emersion/mrsh-dev

1

Invalid read in mrsh_getopt getopt.c:13

Details
Message ID
<20200204005703.ztqchivcy2qceazi@aoi>
DKIM signature
missing
Download raw message
Hi, I sent some messages about this on ##emersion, but I wanted to
reiterate here, since it looks like that channel is not very active.

While working on the read patch, I happened to run mrsh on my macbook
and noticed a bug.  Specifically, if I have a script like this:

#!/bin/mrsh
while getopts "a" opt; do
  do_something
done

And run it like this:

$ ./script.sh -a

I always get the following error:

Assertion failed: (argv[argc] == NULL), function mrsh_getopt, file ../getopt.c, line 13.

If I call the script with no arguments, or 2+ there is no error.  I.e.
it must be called with exactly 1 argument.

The same behavior results if you call a function that calls getopts with
one argument like so:

#!/bin/mrsh
func() { getopts "a" opt; }
func -a

Running valgrind in the above scenario gives us the details:

Invalid read of size 4
   at 0x48544EC: mrsh_getopt (getopt.c:13)
   by 0x4850DB8: builtin_getopts (getopts.c:52)
   by 0x484F1EC: mrsh_run_builtin (builtin.c:109)
   by 0x485FE80: run_builtin (simple_command.c:169)
   by 0x48605EF: run_simple_command (simple_command.c:336)
   by 0x4860E83: run_command (task.c:259)
   by 0x485F4BA: run_pipeline (pipeline.c:35)
   by 0x4861004: run_and_or_list (task.c:291)
   by 0x48612F6: run_command_list_array (task.c:375)
   by 0x4860EAE: run_command (task.c:262)
   by 0x48605A8: run_simple_command (simple_command.c:332)
   by 0x4860E83: run_command (task.c:259)
 Address 0x4ae5f6c is 0 bytes after a block of size 4 alloc'd
   at 0x483665B: malloc (in /usr/lib/valgrind/vgpreload_memcheck-x86-linux.so)
   by 0x485F2B0: push_frame (shell.c:158)
   by 0x4860583: run_simple_command (simple_command.c:328)
   by 0x4860E83: run_command (task.c:259)
   by 0x485F4BA: run_pipeline (pipeline.c:35)
   by 0x4861004: run_and_or_list (task.c:291)
   by 0x48612F6: run_command_list_array (task.c:375)
   by 0x486155A: mrsh_run_program (task.c:432)
   by 0x1094C7: main (main.c:131)

However, on my linux machines, the assertion does not fail.  I believe I
have a fix for this, which I will send shortly if it works out.

- Stone
Details
Message ID
<ohGpVOGICPYnuZECipZLlBu4SDqiZ9qJFdzf6-bVrlj__VH6acDWphOtrDqd7J74I2tgrDzot-99eRTDpnI3BOspikKq9yD651p8Y_yZPwI=@emersion.fr>
In-Reply-To
<20200204005703.ztqchivcy2qceazi@aoi> (view parent)
DKIM signature
missing
Download raw message
On Tuesday, February 4, 2020 1:57 AM, Stone Tickle <lattis@mochiro.moe> wrote:

> Hi, I sent some messages about this on ##emersion, but I wanted to
> reiterate here, since it looks like that channel is not very active.

Sorry about that, I was at FOSDEM the last few days. :)

> While working on the read patch, I happened to run mrsh on my macbook
> and noticed a bug. Specifically, if I have a script like this:
>
> #!/bin/mrsh
> while getopts "a" opt; do
> do_something
> done
>
> And run it like this:
>
> $ ./script.sh -a
>
> I always get the following error:
>
> Assertion failed: (argv[argc] == NULL), function mrsh_getopt, file ../getopt.c, line 13.
>
> If I call the script with no arguments, or 2+ there is no error. I.e.
> it must be called with exactly 1 argument.
>
> The same behavior results if you call a function that calls getopts with
> one argument like so:
>
> #!/bin/mrsh
> func() { getopts "a" opt; }
> func -a
>
> Running valgrind in the above scenario gives us the details:
>
> Invalid read of size 4
> at 0x48544EC: mrsh_getopt (getopt.c:13)
> by 0x4850DB8: builtin_getopts (getopts.c:52)
> by 0x484F1EC: mrsh_run_builtin (builtin.c:109)
> by 0x485FE80: run_builtin (simple_command.c:169)
> by 0x48605EF: run_simple_command (simple_command.c:336)
> by 0x4860E83: run_command (task.c:259)
> by 0x485F4BA: run_pipeline (pipeline.c:35)
> by 0x4861004: run_and_or_list (task.c:291)
> by 0x48612F6: run_command_list_array (task.c:375)
> by 0x4860EAE: run_command (task.c:262)
> by 0x48605A8: run_simple_command (simple_command.c:332)
> by 0x4860E83: run_command (task.c:259)
> Address 0x4ae5f6c is 0 bytes after a block of size 4 alloc'd
> at 0x483665B: malloc (in /usr/lib/valgrind/vgpreload_memcheck-x86-linux.so)
> by 0x485F2B0: push_frame (shell.c:158)
> by 0x4860583: run_simple_command (simple_command.c:328)
> by 0x4860E83: run_command (task.c:259)
> by 0x485F4BA: run_pipeline (pipeline.c:35)
> by 0x4861004: run_and_or_list (task.c:291)
> by 0x48612F6: run_command_list_array (task.c:375)
> by 0x486155A: mrsh_run_program (task.c:432)
> by 0x1094C7: main (main.c:131)
>
> However, on my linux machines, the assertion does not fail. I believe I
> have a fix for this, which I will send shortly if it works out.

Thanks a lot for investigating this issue! I agree and I've pushed your
fix.