From 7216973fbe3a006daaf469f75df0299ef4959dea Mon Sep 17 00:00:00 2001 From: Brian Fraser Date: Thu, 24 Sep 2020 02:37:10 +0200 Subject: [PATCH] Work around a header name collission on util.h Perl provides a util.h. openpty() comes from a system util.h in OSX. The end result is that the system util.h is unreachable, and so openpty() is never declared. This commit works around this in a nasty and non-portable fashiom. First, it adds a second way of including the header in the XS code: #ifdef UTIL_H_ABS_PATH # define UTIL_H_ABS_PATH #endif And second, it uses an arcane command to figure out the exact header that gcc or clang ended up finding. It's pretty terrible, all things told, but since it'll only really kick in for OSX, the horror is somewhat contained. --- Makefile.PL | 28 ++++++++++++++++++++++++++++ Tty.xs | 4 +++- 2 files changed, 31 insertions(+), 1 deletion(-) diff --git a/Makefile.PL b/Makefile.PL index 3ff081b..5c58ccf 100644 --- a/Makefile.PL +++ b/Makefile.PL @@ -8,6 +8,7 @@ if ( $^O eq 'MSWin32' ) { use strict; use IO::File; +use File::Spec; use Config qw(%Config); my %cfg; @@ -203,6 +204,33 @@ ESQ else { $headers{$h} = undef; $define{"-DHAVE_\U$def"} = $h; + if ( $h eq 'util.h' ) { + # Jump through hoops due to a header clash collision with perl + # The following is highly unportable. + + # First, we need to figure out where the C compiler is looking + # for includes. + my $raw_cc_output = qx($cfg{'cc'} $flags -E -Wp,-v -xc /dev/null 2>&1); + my @cc_output = split /\n+/, $raw_cc_output; + my @inc_paths; + foreach my $maybe_inc_path ( @cc_output ) { + next unless $maybe_inc_path =~ /\A\s+/; + my (undef, $inc_path) = split /\s+/, $maybe_inc_path, 3; + push @inc_paths, $inc_path; + } + + # With the list of include directories, try to find util.h + foreach my $inc_path ( @inc_paths ) { + my $abs_header_path = File::Spec->catfile($inc_path, 'util.h'); + next unless -e $abs_header_path; + # Bingo! Now we need to let the C compiler know, so that our XS + # file will include it. + # Again massively non-portable -- we ideally should be using something + # smart to quote the value. + $define{qq<-DUTIL_H_ABS_PATH=\\"$abs_header_path\\">} = $h if $abs_header_path; + last; + } + } print "FOUND.\n"; unlink "headtest_$def.c", "headtest_$def.log"; } diff --git a/Tty.xs b/Tty.xs index 1e4ac79..53c2b95 100644 --- a/Tty.xs +++ b/Tty.xs @@ -58,7 +58,9 @@ typedef FILE * InOutStream; #endif /* HAVE_UTIL_H */ #ifdef HAVE_UTIL_H -# if ((PATCHLEVEL < 19) && (SUBVERSION < 4)) +# ifdef UTIL_H_ABS_PATH +# include UTIL_H_ABS_PATH +# elif ((PATCHLEVEL < 19) && (SUBVERSION < 4)) # include # endif #endif /* HAVE_UTIL_H */