omniti-labs / portableumem

This is a port of the Solaris umem memory allocator to other popular operating systems, such as Linux, Windows and BSDish systems (including Darwin/OSX).
Other
30 stars 11 forks source link

error: incompatible pointer to integer conversion assigning to 'int' from 'void *' [-Wint-conversion] #5

Open ryandesign opened 2 weeks ago

ryandesign commented 2 weeks ago

umem 1.0.1 does not build with Apple clang 16 from Xcode 16 on macOS 15. The error is:

vmem_sbrk.c:137:14: error: incompatible pointer to integer conversion assigning to 'int' from 'void *' [-Wint-conversion]
  137 |   brk_result = brk((void *)new_brk);
      |              ^ ~~~~~~~~~~~~~~~~~~~~

This was reported to MacPorts here: https://trac.macports.org/ticket/71087

You define brk_result as an int:

https://github.com/omniti-labs/portableumem/blob/3fc772c78b312bc3f7f063a526f2da62cc5e4e2d/vmem_sbrk.c#L112

and assign the return value of brk to it:

https://github.com/omniti-labs/portableumem/blob/3fc772c78b312bc3f7f063a526f2da62cc5e4e2d/vmem_sbrk.c#L141

But brk is documented to return a void *, not an int.

You then compare the result to 0:

https://github.com/omniti-labs/portableumem/blob/3fc772c78b312bc3f7f063a526f2da62cc5e4e2d/vmem_sbrk.c#L144-L145

But the manpage for brk says:

brk returns a pointer to the new end of memory if successful; otherwise -1 with errno set to indicate why the allocation failed.

so comparing to 0 does not seem correct.

ryandesign commented 2 weeks ago

But brk is documented to return a void *, not an int.

Huh. This appears to be a platform difference.

On macOS, brk returns a void *: the new end of memory if successful or -1 on failure.

However the Open Group says brk returns an int: 0 on success or -1 on failure.

ryandesign commented 2 weeks ago

This is the fix I've added to MacPorts:

--- vmem_sbrk.c.orig    2009-03-05 18:56:48.000000000 -0600
+++ vmem_sbrk.c 2024-10-11 10:55:35.000000000 -0500
@@ -108,7 +108,7 @@
   uintptr_t ret_brk;
   uintptr_t high_brk;
   uintptr_t new_brk;
-  int brk_result;
+  intptr_t brk_result;

 #define ALIGNSZ   16
 #define BRKALIGN(x) (caddr_t)P2ROUNDUP((uintptr_t)(x), ALIGNSZ)
@@ -134,9 +134,9 @@
     return ((void *)-1);
   }

-  brk_result = brk((void *)new_brk);
+  brk_result = (intptr_t)brk((void *)new_brk);

-  if (brk_result != 0)
+  if (brk_result == (intptr_t)-1)
     return ((void *)-1);

   if (actual_size != NULL)

Another option that I've seen some other programs use is to check brk's return type at configure time.

Finally, brk is obsolete and should not be used at all.