Fix TOCTOU race conditions reported by CodeQL and Coverity

CodeQL and Coverity both complained about:

 * lib/libshare/os/linux/smb.c
 * tests/zfs-tests/cmd/mmapwrite.c
 	* twice
 * tests/zfs-tests/tests/functional/tmpfile/tmpfile_002_pos.c
 * tests/zfs-tests/tests/functional/tmpfile/tmpfile_stat_mode.c
	* coverity had a second complaint that CodeQL did not have
 * tests/zfs-tests/cmd/suid_write_to_file.c
	* Coverity had two complaints and CodeQL had one complaint, both
	  differed. The CodeQL complaint is about the main point of the
	  test, so it is not fixable without a hack involving `fork()`.

The issues reported by CodeQL are fixed, with the exception of the last
one, which is deemed to be a false positive that is too much trouble to
wrokaround. The issues reported by Coverity were only fixed if CodeQL
complained about them.

There were issues reported by Coverity in a number of other files that
were not reported by CodeQL, but fixing the CodeQL complaints is
considered a priority since we want to integrate it into a github
workflow, so the remaining Coverity complaints are left for future work.

Reviewed-by: Brian Behlendorf <behlendorf1@llnl.gov>
Signed-off-by: Richard Yao <richard.yao@alumni.stonybrook.edu>
Closes #14098
This commit is contained in:
Richard Yao
2022-10-27 11:03:48 -04:00
committed by Brian Behlendorf
parent 82ad2a06ac
commit 4170ae4ea6
4 changed files with 34 additions and 31 deletions
+15 -4
View File
@@ -90,21 +90,32 @@ smb_retrieve_shares(void)
/* Go through the directory, looking for shares */
while ((directory = readdir(shares_dir))) {
int fd;
if (directory->d_name[0] == '.')
continue;
snprintf(file_path, sizeof (file_path),
"%s/%s", SHARE_DIR, directory->d_name);
if (stat(file_path, &eStat) == -1) {
if ((fd = open(file_path, O_RDONLY | O_CLOEXEC)) == -1) {
rc = SA_SYSTEM_ERR;
goto out;
}
if (!S_ISREG(eStat.st_mode))
continue;
if (stat(file_path, &eStat) == -1) {
close(fd);
rc = SA_SYSTEM_ERR;
goto out;
}
if ((share_file_fp = fopen(file_path, "re")) == NULL) {
if (!S_ISREG(eStat.st_mode)) {
close(fd);
continue;
}
if ((share_file_fp = fdopen(fd, "r")) == NULL) {
close(fd);
rc = SA_SYSTEM_ERR;
goto out;
}