bug-gnu-utils
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: /dev/fd/n bug in gawk 3.1.5


From: Aharon Robbins
Subject: Re: /dev/fd/n bug in gawk 3.1.5
Date: Thu, 15 Jun 2006 06:00:59 +0300

Andrew,

I think your analysis is pretty much on target. I rearranged some of
this code some time back. I will take a hard look at this as soon
as I can.

The reuse of the buffer is important for things like /dev/user. 

John, thanks for the report and the test case.

Arnold

> Date: Wed, 14 Jun 2006 09:12:44 -0400
> From: "Andrew J. Schorr" <address@hidden>
> Subject: Re: /dev/fd/n bug in gawk 3.1.5
> To: "John H. DuBois III" <address@hidden>
> Cc: address@hidden
>
> On Tue, Jun 13, 2006 at 05:49:58PM -0700, John H. DuBois III wrote:
> > $ cat /dev/fd/4 /dev/fd/5 4<tm1 5<tm2
> > Contents of tm1
> > Contents of tm2
> > $ gawk 1 /dev/fd/4 /dev/fd/5 4<tm1 5<tm2
> > Contents of tm1
> > Contents of tm1
> > 
> > 
> > gawk: (FILENAME=/dev/fd/5 FNR=3) fatal: error reading input file 
> > `/dev/fd/4': Bad file number
>
> This looks like a bug in iop_open to me.  On linux, valgrind shows:
>
> ==4785== Conditional jump or move depends on uninitialised value(s)
> ==4785==    at 0x4A1F3D7: strlen (mac_replace_strmem.c:243)
> ==4785==    by 0x42206E: spec_setup (io.c:1433)
> ==4785==    by 0x423251: iop_open (io.c:1576)
> ==4785==    by 0x4234A2: nextfile (io.c:280)
> ==4785==    by 0x4241A6: do_input (io.c:445)
> ==4785==    by 0x4282A3: main (main.c:595)
> ==4785== 
> ==4785== Invalid write of size 1
> ==4785==    at 0x422082: spec_setup (io.c:1435)
> ==4785==    by 0x423251: iop_open (io.c:1576)
> ==4785==    by 0x4234A2: nextfile (io.c:280)
> ==4785==    by 0x4241A6: do_input (io.c:445)
> ==4785==    by 0x4282A3: main (main.c:595)
> ==4785==  Address 0x4FE4A8A is 0 bytes after a block of size 18 alloc'd
> ==4785==    at 0x4A1D9D6: malloc (vg_replace_malloc.c:149)
> ==4785==    by 0x422ECF: iop_alloc (io.c:2509)
> ==4785==    by 0x424C26: specfdopen (io.c:1457)
> ==4785==    by 0x423297: iop_open (io.c:1578)
> ==4785==    by 0x4234A2: nextfile (io.c:280)
> ==4785==    by 0x4241A6: do_input (io.c:445)
> ==4785==    by 0x4282A3: main (main.c:595)
> ...
>
> And this logic seems problematic to me:
>
> tatic IOBUF *
> iop_open(const char *name, const char *mode, IOBUF *iop)
> {
>         int openfd = INVALID_HANDLE;
>         int flag = 0;
>         static struct internal {
>                 const char *name;
>                 int compare;
>                 int (*fp) P((IOBUF *, const char *, const char *));
>                 IOBUF iob;
>         } table[] = {
>                 { "/dev/fd/",           8,      specfdopen },
>                 { "/dev/stdin",         10,     specfdopen },
>                 { "/dev/stdout",        11,     specfdopen },
>                 { "/dev/stderr",        11,     specfdopen },
>                 { "/inet/",             6,      specfdopen },
>                 { "/dev/pid",           8,      pidopen },
>                 { "/dev/ppid",          9,      pidopen },
>                 { "/dev/pgrpid",        11,     pidopen },
>                 { "/dev/user",          9,      useropen },
>         };
>         int devcount = sizeof(table) / sizeof(table[0]);
> ...
>                         if (STREQN(name, table[i].name, table[i].compare)) {
>                                 iop = & table[i].iob;
>
>                                 if (iop->buf != NULL) {
>                                         spec_setup(iop, 0, FALSE);
>                                         return iop;
>                                 } else if ((*table[i].fp)(iop, name, mode) == 
> 0)
>                                         return iop;
>                                 else {
>                                         warning(_("could not open `%s', mode 
> `%s
> '"),
>                                                 name, mode);
>                                         return NULL;
>                                 }
>                         }
> ...
>
> If I'm not misreading this, it looks like the attempt to open /dev/fd/5 will
> end up using the same static IOBUF that was previously used for /dev/fd/4, and
> I think that iop->buf will not be NULL, since iop_close will not free iop->buf
> (since specfdopen sets the IOP_NO_FREE flag).  And I don't think the 
> spec_setup
> call is doing what's needed (it looks like devopen is not getting called for
> the new file, etc.).  I'm not quite sure how to fix this, since I'm not quite
> understanding at the moment why the static IOBUF is being used in the first
> place.  Is the goal here to handle correctly the case where the same special
> file name is used more than once?  It looks to me like these problems may also
> affect /inet filenames.  Or perhaps I'm just totally confused.
>
> Regards,
> Andy




reply via email to

[Prev in Thread] Current Thread [Next in Thread]