You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

101 lines
3.4 KiB

  1. From dce4683cbbe107a95f1f0d45fabc304acfb5d71a Mon Sep 17 00:00:00 2001
  2. From: Andreas Gruenbacher <agruen@gnu.org>
  3. Date: Mon, 15 Jul 2019 16:21:48 +0200
  4. Subject: Don't follow symlinks unless --follow-symlinks is given
  5. * src/inp.c (plan_a, plan_b), src/util.c (copy_to_fd, copy_file,
  6. append_to_file): Unless the --follow-symlinks option is given, open files with
  7. the O_NOFOLLOW flag to avoid following symlinks. So far, we were only doing
  8. that consistently for input files.
  9. * src/util.c (create_backup): When creating empty backup files, (re)create them
  10. with O_CREAT | O_EXCL to avoid following symlinks in that case as well.
  11. ---
  12. src/inp.c | 12 ++++++++++--
  13. src/util.c | 14 +++++++++++---
  14. 2 files changed, 21 insertions(+), 5 deletions(-)
  15. --- a/src/inp.c
  16. +++ b/src/inp.c
  17. @@ -238,8 +238,13 @@ plan_a (char const *filename)
  18. {
  19. if (S_ISREG (instat.st_mode))
  20. {
  21. - int ifd = safe_open (filename, O_RDONLY|binary_transput, 0);
  22. + int flags = O_RDONLY | binary_transput;
  23. size_t buffered = 0, n;
  24. + int ifd;
  25. +
  26. + if (! follow_symlinks)
  27. + flags |= O_NOFOLLOW;
  28. + ifd = safe_open (filename, flags, 0);
  29. if (ifd < 0)
  30. pfatal ("can't open file %s", quotearg (filename));
  31. @@ -340,6 +345,7 @@ plan_a (char const *filename)
  32. static void
  33. plan_b (char const *filename)
  34. {
  35. + int flags = O_RDONLY | binary_transput;
  36. int ifd;
  37. FILE *ifp;
  38. int c;
  39. @@ -353,7 +359,9 @@ plan_b (char const *filename)
  40. if (instat.st_size == 0)
  41. filename = NULL_DEVICE;
  42. - if ((ifd = safe_open (filename, O_RDONLY | binary_transput, 0)) < 0
  43. + if (! follow_symlinks)
  44. + flags |= O_NOFOLLOW;
  45. + if ((ifd = safe_open (filename, flags, 0)) < 0
  46. || ! (ifp = fdopen (ifd, binary_transput ? "rb" : "r")))
  47. pfatal ("Can't open file %s", quotearg (filename));
  48. if (TMPINNAME_needs_removal)
  49. --- a/src/util.c
  50. +++ b/src/util.c
  51. @@ -388,7 +388,7 @@ create_backup (char const *to, const str
  52. try_makedirs_errno = ENOENT;
  53. safe_unlink (bakname);
  54. - while ((fd = safe_open (bakname, O_CREAT | O_WRONLY | O_TRUNC, 0666)) < 0)
  55. + while ((fd = safe_open (bakname, O_CREAT | O_EXCL | O_WRONLY | O_TRUNC, 0666)) < 0)
  56. {
  57. if (errno != try_makedirs_errno)
  58. pfatal ("Can't create file %s", quotearg (bakname));
  59. @@ -579,10 +579,13 @@ create_file (char const *file, int open_
  60. static void
  61. copy_to_fd (const char *from, int tofd)
  62. {
  63. + int from_flags = O_RDONLY | O_BINARY;
  64. int fromfd;
  65. ssize_t i;
  66. - if ((fromfd = safe_open (from, O_RDONLY | O_BINARY, 0)) < 0)
  67. + if (! follow_symlinks)
  68. + from_flags |= O_NOFOLLOW;
  69. + if ((fromfd = safe_open (from, from_flags, 0)) < 0)
  70. pfatal ("Can't reopen file %s", quotearg (from));
  71. while ((i = read (fromfd, buf, bufsize)) != 0)
  72. {
  73. @@ -625,6 +628,8 @@ copy_file (char const *from, char const
  74. else
  75. {
  76. assert (S_ISREG (mode));
  77. + if (! follow_symlinks)
  78. + to_flags |= O_NOFOLLOW;
  79. tofd = create_file (to, O_WRONLY | O_BINARY | to_flags, mode,
  80. to_dir_known_to_exist);
  81. copy_to_fd (from, tofd);
  82. @@ -640,9 +645,12 @@ copy_file (char const *from, char const
  83. void
  84. append_to_file (char const *from, char const *to)
  85. {
  86. + int to_flags = O_WRONLY | O_APPEND | O_BINARY;
  87. int tofd;
  88. - if ((tofd = safe_open (to, O_WRONLY | O_BINARY | O_APPEND, 0)) < 0)
  89. + if (! follow_symlinks)
  90. + to_flags |= O_NOFOLLOW;
  91. + if ((tofd = safe_open (to, to_flags, 0)) < 0)
  92. pfatal ("Can't reopen file %s", quotearg (to));
  93. copy_to_fd (from, tofd);
  94. if (close (tofd) != 0)