Opened 3 years ago

Closed 3 years ago

Last modified 3 years ago

#61784 closed defect (fixed)

pv is broken in Apple Silicon

Reported by: hpux735 (William Dillon) Owned by: eborisch (Eric A. Borisch)
Priority: Normal Milestone:
Component: ports Version: 2.6.4
Keywords: bigsur, arm64, upstream Cc:
Port: pv

Description

There is a build failure in CI (and my local machine) for pv related to stat64's deprecation. I was able to fix it locally, and it's fairly straight-forward, though it's hackish. The root of the problem is that autoconf is able to determine that the stat64 function exists, and therefore thinks that the structure exists, and doesn't include a set of defines that make it OK. I was able to edit config.h to clear the HAVE_STAT64 flag and the program compiled. I have a message out to the pv author. I'm not quite competent in autotools, and I'm not sure what the right way to fix it is, but it appears that the Portfile already has a patch to deal with stat64, so maybe that could be extended without changing upstream?

% diff fixed/config.h broken/config.h
21a22
> #define HAVE_STAT64 1

Change History (6)

comment:1 Changed 3 years ago by jmroot (Joshua Root)

Owner: set to eborisch
Status: newassigned

comment:2 Changed 3 years ago by mhberger

Hi, I have had a go at a fix and have created a pull request

https://github.com/macports/macports-ports/pull/9800

comment:3 Changed 3 years ago by kencu (Ken)

there's no log or config.log here, so we can't really say what might be going on.

It looks like your PR just removes the flag; although that might well work on one system to fix a build, it doesn't sound like the proper fix, and seems likely to break builds elsewhere...

comment:4 Changed 3 years ago by mhberger

I have done a bit of digging and have come up with something, but not necessarily the ideal soluton.

Basically autoconf takes autoconf/configure.in and creates configure, which then tests for availability of certain functions and then creates #defines indicating availability of certain functions.

e.g. the autoconf function AC_CHECK_FUNCS(stat64) generates bash code in configure which tests for availability of stat64 and if function is available writes #define HAVE_STAT64 1.

This code does this by creating a C program and then compiles, links and runs it.

This C program does not check for the presence of the symbol at compile time, but only at link time. See the code sample below. Changing all occurrences of stat64 to joe and the compiling using gcc -S sample.c works. However gcc sample.c -o sample will fail with a linking error.

On the systems tested, stat64 is defined as a symbol in

xxd /usr/lib/dyld | grep stat64

So the test always return true.

On the Intel Mac, compiling code generates deprecation warnings, but still compiles and runs.

On the Silicon Mac, compiling generates a compile warning.

The code in the pv include ifndef HAVE_STAT64 does not actually evaluate to true, so the redefinition of stat64 to stat does not happen here. Instead it is being catered for in one of the Apple libraries, but generates deprecation warnings.

However, this compile definition is now not working on the Silicon Mac.

So we have to explicitly add a test in for this i.e. # if __arm64__.

Test code generated by configure

/* confdefs.h */
#define PACKAGE_NAME ""
#define PACKAGE_TARNAME ""
#define PACKAGE_VERSION ""
#define PACKAGE_STRING ""
#define PACKAGE_BUGREPORT ""
#define PACKAGE_URL ""
/* end confdefs.h.  */
/* Define stat64 to an innocuous variant, in case <limits.h> declares stat64.
   For example, HP-UX 11i <limits.h> declares gettimeofday.  */
#define stat64 innocuous_stat64

/* System header to define __stub macros and hopefully few prototypes,
    which can conflict with char stat64 (); below.
    Prefer <limits.h> to <assert.h> if __STDC__ is defined, since
    <limits.h> exists even on freestanding compilers.  */

#ifdef __STDC__
# include <limits.h>
#else
# include <assert.h>
#endif

#undef stat64

/* Override any GCC internal prototype to avoid an error.
   Use char because int might match the return type of a GCC
   builtin and then its argument prototype would still apply.  */
#ifdef __cplusplus
extern "C"
#endif
char stat64 ();
/* The GNU C library defines this for functions which it implements
    to always fail with ENOSYS.  Some functions are actually named
    something starting with __ and the normal name is an alias.  */
#if defined __stub_stat64 || defined __stub___stat64
choke me
#endif

int
main ()
{
return stat64 ();
  ;
  return 0;
}
Version 0, edited 3 years ago by mhberger (next)

comment:5 Changed 3 years ago by mhberger <21727+mhberger@…>

Resolution: fixed
Status: assignedclosed

In 3a5dc026ec2e59849cc45a4e21d5978b64a989a0/macports-ports (master):

pv: Fix detection of stat64 in Apple Silicon. (https://github.com/macports/macports-ports/pull/9800)

Fixes: #61784

Take 7. Tidy up logic when configuring cppflags. Thanks @eborisch.

Co-authored-by: Mark Berger <mark.berger@…>

comment:6 Changed 3 years ago by ryandesign (Ryan Carsten Schmidt)

This change is not correct for the universal variant. The port already uses the muniversal portgroup, and the change should be redesigned with that in mind.

Note: See TracTickets for help on using tickets.