Revision: 77693
http://sourceforge.net/p/brlcad/code/77693
Author: brlcad
Date: 2020-11-05 04:59:07 +0000 (Thu, 05 Nov 2020)
Log Message:
-----------
if mged was run on a database that doesn't mmap and can't be read, it was
crashing due to an already freed mp->buf pointer getting released twice.
uncrashed by making the mappedfile interface handle itself more gracefully.
Modified Paths:
--------------
brlcad/trunk/src/libbu/mappedfile.c
Modified: brlcad/trunk/src/libbu/mappedfile.c
===================================================================
--- brlcad/trunk/src/libbu/mappedfile.c 2020-11-04 23:08:50 UTC (rev 77692)
+++ brlcad/trunk/src/libbu/mappedfile.c 2020-11-05 04:59:07 UTC (rev 77693)
@@ -365,22 +365,20 @@
mp->uses = 1;
mp->buflen = sb.st_size;
mp->modtime = sb.st_mtime;
- mp->buf = MAP_FAILED;
+ mp->buf = NULL;
/* Attempt to memory-map the file */
bu_semaphore_acquire(BU_SEM_SYSCALL);
-#ifdef HAVE_SYS_MMAN_H
+#if defined(HAVE_SYS_MMAN_H)
mp->buf = mmap(NULL, sb.st_size, PROT_READ, MAP_PRIVATE, fd, 0);
-#else
-# ifdef HAVE_WINDOWS_H
+#elif defined(HAVE_WINDOWS_H)
/* FIXME: shouldn't need to preserve handle */
mp->buf = win_mmap(NULL, sb.st_size, PROT_READ, MAP_PRIVATE, fd, 0,
&(mp->handle));
-# endif
#endif /* HAVE_SYS_MMAN_H */
bu_semaphore_release(BU_SEM_SYSCALL);
/* If cannot memory-map, read it in manually */
- if (mp->buf != MAP_FAILED) {
+ if (mp->buf && mp->buf != MAP_FAILED) {
mp->is_mapped = 1;
} else {
ssize_t bytes_to_go = sb.st_size;
@@ -401,7 +399,6 @@
if (UNLIKELY(readval < 0)) {
bu_semaphore_release(BU_SEM_SYSCALL);
perror("read");
- bu_free(mp->buf, name);
goto fail;
} else {
nbytes += readval;
@@ -412,7 +409,6 @@
if (UNLIKELY(nbytes != sb.st_size)) {
perror(name);
- bu_free(mp->buf, name);
goto fail;
}
}
@@ -436,27 +432,29 @@
bu_semaphore_release(BU_SEM_SYSCALL);
}
- if (mp->name)
+ if (mp->name) {
bu_free(mp->name, "mp->name");
- if (mp->appl)
+ mp->name = NULL;
+ }
+ if (mp->appl) {
bu_free(mp->appl, "mp->appl");
+ mp->appl = NULL;
+ }
if (mp->buf) {
- if (mp->is_mapped)
-#ifdef HAVE_SYS_MMAN_H
+ if (mp->is_mapped) {
+ bu_semaphore_acquire(BU_SEM_SYSCALL);
+#if defined(HAVE_SYS_MMAN_H)
munmap(mp->buf, (size_t)mp->buflen);
-#else
-# ifdef HAVE_WINDOWS_H
- win_munmap(mp->buf, (size_t)mp->buflen, mp->handle);
-# endif
+#elif defined(HAVE_WINDOWS_H)
+ win_munmap(mp->buf, (size_t)mp->buflen, mp->handle);
#endif
- else
+ bu_semaphore_release(BU_SEM_SYSCALL);
+ } else if (mp->buf != MAP_FAILED) {
bu_free(mp->buf, name);
+ }
+ mp->buf = NULL;
}
- mp->name = NULL;
- mp->appl = NULL;
- mp->buf = MAP_FAILED;
-
if (UNLIKELY(bu_debug&BU_DEBUG_MAPPED_FILE))
bu_log("bu_open_mapped_file(%s, %s) can't open file\n", name, appl ?
appl: "(NULL)");
This was sent by the SourceForge.net collaborative development platform, the
world's largest Open Source development site.
_______________________________________________
BRL-CAD Source Commits mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/brlcad-commits