Subject: bug#35713: closed (Re: bug#35713: /dev/stdin problem in cp on Solaris)

From: [email-masked] (GNU bug Tracking System)
Date: Sun, 02 Jun 2019 06:01:02 +0000

Your bug report

#35713: /dev/stdin problem in cp on Solaris

which was filed against the coreutils package, has been closed.

The explanation is attached below, along with your original report.
If you require more details, please reply to [email-masked].

-- 
35713: http://debbugs.gnu.org/cgi/bugreport.cgi?bug=35713
GNU Bug Tracking System
Contact [email-masked] with problems

Subject: Re: bug#35713: /dev/stdin problem in cp on Solaris
From: Paul Eggert <[email-masked]>
To: [email-masked]
Cc: [email-masked],Pádraig Brady <[email-masked]>
Date: Sat, 1 Jun 2019 23:00:46 -0700
List-Id: <debbugs-submit.debbugs.gnu.org>

[email-masked] wrote:

> I tested the patch on both intel and sparc platform and all seems to work 
> without any problem.
> 
> So I guess this can be closed as solved.

Thanks for checking; closing.

Subject: /dev/stdin problem in cp on Solaris
From: [email-masked]
To: [email-masked]
Date: Mon, 13 May 2019 12:24:17 +0200
List-Id: <debbugs-submit.debbugs.gnu.org>

Hi,

We found out that the following simple command fails on Solaris with:

  cat srcfile.txt | /usr/gnu/bin/cp /dev/stdin dstfile.txt
  cp: skipping file '/dev/stdin', as it was replaced while being copied

I found that problem is with SAME_INODE macro. It accepts two 
structures, one from stat and another from fstat function. On Solaris, 
each of these can return a different thing. While stat returns 
information about the /dev/fd/0 file itself (linked by /dev/stdin), 
fstat knows much more from the file descriptor and returns info about 
the pipe that is being used. That results in SAME_INODE failing.

This happens in both Coreutils 8.30 and 8.31 (both intel and sparc) but 
it looks like it was seen first in 8.16.

The easiest fix to this issue I came up with is to disable SAME_INODE 
validation for special devices and pipes (as they won't be moved 
anyway). Patch is attached as well as small program that can show stat 
and fstat differences on Solaris.

Thanks
Jakub

--- src/copy.c
+++ src/copy.c
@@ -1050,11 +1050,18 @@ copy_reg (char const *src_name, char con
      saved ones obtained via a previous call to stat.  */
   if (! SAME_INODE (*src_sb, src_open_sb))
     {
-      error (0, 0,
-             _("skipping file %s, as it was replaced while being copied"),
-             quoteaf (src_name));
-      return_val = false;
-      goto close_src_desc;
+      /* Stat and fstat returns different results on Solaris for devices
+         like /dev/stdin. Confirm that this is not the case.  */
+      mode_t file_type = src_open_sb.st_mode & S_IFMT;
+      if (!(file_type == S_IFBLK || file_type == S_IFCHR ||
+	         file_type == S_IFIFO || file_type == S_IFSOCK))
+        {
+          error (0, 0,
+                 _("skipping file %s, as it was replaced while being copied"),
+                 quoteaf (src_name));
+          return_val = false;
+          goto close_src_desc;
+        }
     }
 
   /* The semantics of the following open calls are mandated