[vte/vte-next] stream: file: Use O_TMPFILE when available



commit 3d4d73f9dc176f9846e53449aa970cddf6295684
Author: Christian Persch <chpe gnome org>
Date:   Sat Sep 28 11:38:49 2013 +0200

    stream: file: Use O_TMPFILE when available
    
    https://bugzilla.gnome.org/show_bug.cgi?id=704705
    (cherry picked from commit c80fe16c3019eeb0686023b2968199e4d84a2676)

 src/Makefile.am      |    2 +
 src/vtestream-file.h |   17 +++------
 src/vteutils.c       |   86 ++++++++++++++++++++++++++++++++++++++++++++++++++
 src/vteutils.h       |   30 +++++++++++++++++
 4 files changed, 124 insertions(+), 11 deletions(-)
---
diff --git a/src/Makefile.am b/src/Makefile.am
index 401742b..6f0b5ba 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -81,6 +81,8 @@ libvte_ VTE_API_MAJOR_VERSION@_ VTE_API_MINOR_VERSION@_la_SOURCES = \
        vtetypebuiltins.h \
        vteunistr.c \
        vteunistr.h \
+       vteutils.c \
+       vteutils.h \
        vteversion.h
        $(NULL)
 
diff --git a/src/vtestream-file.h b/src/vtestream-file.h
index fd80ccd..8bc8bf3 100644
--- a/src/vtestream-file.h
+++ b/src/vtestream-file.h
@@ -25,6 +25,7 @@
 
 #include <gio/gunixinputstream.h>
 
+#include "vteutils.h"
 
 #ifndef HAVE_PREAD
 #define pread _pread
@@ -185,21 +186,15 @@ static inline void
 _vte_file_stream_ensure_fd0 (VteFileStream *stream)
 {
        gint fd;
-       gchar *file_name;
+
        if (G_LIKELY (stream->fd[0]))
                return;
 
-       fd = g_file_open_tmp ("vteXXXXXX", &file_name, NULL);
-       if (fd != -1) {
-               unlink (file_name);
-               g_free (file_name);
-       }
-
-       fcntl (fd, F_SETFL, O_NOATIME);
-
-       stream->fd[0] = dup (fd); /* we do the dup to make sure ->fd[0] is not 0 */
+        fd = _vte_mkstemp ();
+        if (fd == -1)
+                return;
 
-       close (fd);
+        stream->fd[0] = fd;
 }
 
 static void
diff --git a/src/vteutils.c b/src/vteutils.c
new file mode 100644
index 0000000..7615f51
--- /dev/null
+++ b/src/vteutils.c
@@ -0,0 +1,86 @@
+/*
+ * Copyright © 2013 Christian Persch
+ *
+ * This is free software; you can redistribute it and/or modify it under
+ * the terms of the GNU Library General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public
+ * License along with this program; if not, write to the Free Software
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ */
+
+#include "config.h"
+
+#ifndef _GNU_SOURCE
+#define _GNU_SOURCE /* for O_TMPFILE */
+#endif
+
+#include "vteutils.h"
+
+#include <fcntl.h>
+#include <unistd.h>
+#include <errno.h>
+
+#include <glib.h>
+
+#ifndef O_BINARY
+#define O_BINARY 0
+#endif
+
+/* Temporary define until glibc release catches up */
+#ifdef __linux__
+#ifndef O_TMPFILE
+#ifndef __O_TMPFILE
+#define __O_TMPFILE     020000000
+#endif
+#define O_TMPFILE (__O_TMPFILE | O_DIRECTORY)
+#endif
+#endif
+
+int
+_vte_mkstemp (void)
+{
+        int fd;
+        gchar *file_name;
+
+#ifdef O_TMPFILE
+        fd = open (g_get_tmp_dir (),
+                   O_TMPFILE | O_EXCL | O_RDWR | O_BINARY | O_NOATIME,
+                   0600);
+        if (fd != -1)
+                goto done;
+
+        /* Try again with g_file_open_tmp */
+#endif
+
+        fd = g_file_open_tmp ("vteXXXXXX", &file_name, NULL);
+        if (fd == -1)
+                return -1;
+
+        unlink (file_name);
+        g_free (file_name);
+
+        do { } while (fcntl (fd, F_SETFL, O_NOATIME) == -1 && errno == EINTR);
+
+#ifdef O_TMPFILE
+ done:
+#endif
+
+        /* make sure fd is not 0 */
+        if (G_UNLIKELY (fd == 0)) {
+                int new_fd;
+
+                new_fd = dup (fd);
+                close (fd);
+                fd = new_fd;
+        }
+
+        return fd;
+}
diff --git a/src/vteutils.h b/src/vteutils.h
new file mode 100644
index 0000000..3415e76
--- /dev/null
+++ b/src/vteutils.h
@@ -0,0 +1,30 @@
+/*
+ * Copyright © 2013 Christian Persch
+ *
+ * This is free software; you can redistribute it and/or modify it under
+ * the terms of the GNU Library General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public
+ * License along with this program; if not, write to the Free Software
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ */
+
+#ifndef __VTE_UTILS_H__
+#define __VTE_UTILS_H__
+
+#include <glib.h>
+
+G_BEGIN_DECLS
+
+int _vte_mkstemp (void);
+
+G_END_DECLS
+
+#endif /* __VTE_UTILS_H__ */


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