printf %(fmt)T fails with large times in 64-bit linux.

2012-09-17 Thread Eduardo A . Bustamante López
printf %(fmt)T fails when the time given is very large in a 64-bit linux
environment. Looping over the powers of two and feeding it to printf shows
the error, which exits the shell with a SIGSEGV

The problem seems to be in builtins/printf.def, as indicated by the backtrace
attached (gdb.txt).


---

I'm running the latest bash from the git repository:

$ echo $BASH_VERSION
4.2.37(3)-release

$ uname -a
Linux claret 3.4.2-2-ARCH #1 SMP PREEMPT Mon Jun 11 22:27:17 CEST 2012
x86_64 GNU/Linux

$ lsb_release -a
LSB Version:n/a
Distributor ID: archlinux
Description:Arch Linux
Release:rolling
Codename:   n/a


---

The following snippet reproduces the problem:

for i in {56..63}; do
printf '%s ' $i;
bash -c 'printf %\(%s\)T\\n $((2**$1))' _ $i;
done

Sample run:

$ for i in {56..63}; do
> printf '%s ' $i;
> bash -c 'printf %\(%s\)T\\n $((2**$1))' _ $i;
> done
56 Segmentation fault
57 Segmentation fault
58 Segmentation fault
59 Segmentation fault
60 Segmentation fault
61 Segmentation fault
62 Segmentation fault
63 Segmentation fault


---

The simple fix is to check if ``tm == NULL``, and show an error message, or
default to some specific value. A 32-bit machine seems to handle overflow as a
zero. I guess defaulting to zero is one option. I'm not sure which one is the
best approach.

I'm attaching the diff generated by git. It just checks if tm is NULL, and
defaults to zero, but it is only to demonstrate that the bug is there, the code
isn't written correctly.

-- 
Eduardo A. Bustamante López
The program being debugged has been started already.
Start it from the beginning? (y or n) Starting program: 
/home/dualbus/local/bin/bash 

Program received signal SIGSEGV, Segmentation fault.
0x77686450 in __strftime_internal () from /lib/libc.so.6
#0  0x77686450 in __strftime_internal () from /lib/libc.so.6
#1  0x776880d6 in strftime_l () from /lib/libc.so.6
#2  0x0047e1b4 in printf_builtin (list=0x72cc08) at ./printf.def:474
#3  0x0042fdbf in execute_builtin (builtin=builtin@entry=0x47d410 
, flags=flags@entry=0, 
subshell=subshell@entry=0, words=) at execute_cmd.c:4109
#4  0x00431998 in execute_builtin_or_function (flags=0, 
fds_to_close=0x76e208, redirects=, var=0x0, 
builtin=0x47d410 , words=0x72c908) at execute_cmd.c:4534
#5  execute_simple_command (simple_command=, 
pipe_in=pipe_in@entry=-1, pipe_out=pipe_out@entry=-1, 
async=async@entry=0, fds_to_close=fds_to_close@entry=0x76e208) at 
execute_cmd.c:3944
#6  0x004329cf in execute_command_internal (fds_to_close=0x76e208, 
pipe_out=-1, pipe_in=-1, asynchronous=0, 
command=0x76e148) at execute_cmd.c:735
#7  execute_command_internal (command=0x76e148, asynchronous=0, pipe_in=-1, 
pipe_out=-1, fds_to_close=0x76e208)
at execute_cmd.c:522
#8  0x00435a4e in execute_command (command=0x76e148) at 
execute_cmd.c:382
#9  0x0041e01d in reader_loop () at eval.c:152
#10 0x0041c5bd in main (argc=1, argv=0x7fffe258, 
env=0x7fffe268) at shell.c:749
diff --git a/builtins/printf.def b/builtins/printf.def
index 71a7c00..94e5af5 100644
--- a/builtins/printf.def
+++ b/builtins/printf.def
@@ -471,6 +471,11 @@ printf_builtin (list)
sv_tz ("TZ");   /* XXX -- just make sure */
 #endif
tm = localtime (&secs);
+if (tm == NULL)
+  {
+secs = 0;
+tm = localtime (&secs);
+  }
n = strftime (timebuf, sizeof (timebuf), timefmt, tm);
free (timefmt);
if (n == 0)


Re: printf %(fmt)T fails with large times in 64-bit linux.

2012-09-17 Thread Chet Ramey
On 9/17/12 4:33 AM, Eduardo A. Bustamante López wrote:
> printf %(fmt)T fails when the time given is very large in a 64-bit linux
> environment. Looping over the powers of two and feeding it to printf shows
> the error, which exits the shell with a SIGSEGV

Thanks for the report.

-- 
``The lyf so short, the craft so long to lerne.'' - Chaucer
 ``Ars longa, vita brevis'' - Hippocrates
Chet Ramey, ITS, CWRUc...@case.eduhttp://cnswww.cns.cwru.edu/~chet/



Re: square bracket vs. curly brace character ranges

2012-09-17 Thread Greg Wooledge
On Sat, Sep 15, 2012 at 06:12:24PM -0600, Bob Proulx wrote:
> I don't know so I will ask.  Isn't the problem endemic to glibc?  Do
> other libc's such as HP-UX or AIX or other have this same issue?  I am
> out of touch on the details of them these days.

imadev:/tmp/greg$ uname -a
HP-UX imadev B.10.20 A 9000/785 2008897791 two-user license
imadev:/tmp/greg$ echo [a-c]
A a Á á À à Â â Ä ä Å å Ã ã Æ æ B b C c
imadev:/tmp/greg$ locale
LANG=en_US.iso88591
LC_CTYPE="en_US.iso88591"
LC_COLLATE="en_US.iso88591"
...

bash-2.04# uname -a
HP-UX megview1 B.11.11 U 9000/785 532302039 unlimited-user license
bash-2.04# echo [a-c]
a b c
bash-2.04# ksh -c 'echo [a-c]'
a Á á À à Â â Ä ä Å å Ã ã æ B b C c
bash-2.04# locale
LANG=en_US.iso88591
LC_CTYPE="en_US.iso88591"
LC_COLLATE="en_US.iso88591"
...

(I need to build a newer bash on that one some time.  And no, I don't
have anything newer than 11.11.)