Fix T70315: Blender exit with code `-6` with message `Attempt to free NULL pointer`.
authorBastien Montagne <montagne29@wanadoo.fr>
Tue, 1 Oct 2019 18:02:57 +0000 (20:02 +0200)
committerBastien Montagne <montagne29@wanadoo.fr>
Tue, 1 Oct 2019 18:08:04 +0000 (20:08 +0200)
This is not actually fixing the real issue here, PackedFile structs are
never supposed to have a NULL pointer - and in that monster .blend file,
the pointer is not NULL, but the actual data chunk has been lost
somehow, so it gets NULL during read process.

Very unlikely we ever know how such corrupted .blend was created though
(there's probably a fair chance that this is not even due to a bug in
Blender, but rather a glitch in filesystem or something).

So for now, ensure at read time that we get a coherent state (i.e.
remove any read PackedFile that would have a NULL data field), and add a
few asserts in relevant code to check we never get NULL data pointer
here.

source/blender/blenkernel/intern/packedFile.c
source/blender/blenloader/intern/readfile.c

index 8e647757b403e2540924a5cf8aef39ffba4243f8..1085e515b3af8836baa99b93d350c6687434ca61 100644 (file)
@@ -141,7 +141,9 @@ int BKE_packedfile_count_all(Main *bmain)
 void BKE_packedfile_free(PackedFile *pf)
 {
   if (pf) {
-    MEM_freeN(pf->data);
+    BLI_assert(pf->data != NULL);
+
+    MEM_SAFE_FREE(pf->data);
     MEM_freeN(pf);
   }
   else {
@@ -151,6 +153,9 @@ void BKE_packedfile_free(PackedFile *pf)
 
 PackedFile *BKE_packedfile_duplicate(const PackedFile *pf_src)
 {
+  BLI_assert(pf_src != NULL);
+  BLI_assert(pf_src->data != NULL);
+
   PackedFile *pf_dst;
 
   pf_dst = MEM_dupallocN(pf_src);
@@ -161,6 +166,8 @@ PackedFile *BKE_packedfile_duplicate(const PackedFile *pf_src)
 
 PackedFile *BKE_packedfile_new_from_memory(void *mem, int memlen)
 {
+  BLI_assert(mem != NULL);
+
   PackedFile *pf = MEM_callocN(sizeof(*pf), "PackedFile");
   pf->data = mem;
   pf->size = memlen;
@@ -178,7 +185,7 @@ PackedFile *BKE_packedfile_new(ReportList *reports, const char *filename, const
   /* render result has no filename and can be ignored
    * any other files with no name can be ignored too */
   if (filename[0] == '\0') {
-    return NULL;
+    return pf;
   }
 
   // XXX waitcursor(1);
index 609fa9459ee57bab8ff052b637f84025271801b2..545659d06c2bac2299ee22e06fdcd91cd148197c 100644 (file)
@@ -2829,6 +2829,12 @@ static PackedFile *direct_link_packedfile(FileData *fd, PackedFile *oldpf)
 
   if (pf) {
     pf->data = newpackedadr(fd, pf->data);
+    if (pf->data == NULL) {
+      /* We cannot allow a PackedFile with a NULL data field,
+       * the whole code assumes this is not possible. See T70315. */
+      printf("%s: NULL packedfile data, cleaning up...\n", __func__);
+      MEM_SAFE_FREE(pf);
+    }
   }
 
   return pf;