Opened 12 years ago

Closed 12 years ago

#34233 closed defect (fixed)

apple-gcc42 doesn't honor -isysroot correctly

Reported by: jeremyhu (Jeremy Huddleston Sequoia) Owned by: royliu@…
Priority: Normal Milestone:
Component: ports Version: 2.0.4
Keywords: Cc: jeremyhu (Jeremy Huddleston Sequoia)
Port: apple-gcc42

Description (last modified by jeremyhu (Jeremy Huddleston Sequoia))

/opt/local/libexec/apple-gcc42/gcc/i686-apple-darwin10/4.2.1/cc1 -E -quiet -isysroot /Developer/SDKs/MacOSX10.5.sdk test.c | grep usr/include| head -n 1
# 1 "/usr/include/stdio.h" 1 3 4
~ $ /opt/local/libexec/apple-gcc42/gcc/i686-apple-darwin8/4.2.1/cc1 -E -quiet -isysroot /Developer/SDKs/MacOSX10.4u.sdk test.c | grep usr/include| head -n 1
# 1 "/usr/include/stdio.h" 1 3 4

gcc42 (and the rest of the gcc ports) are ok:

~ $ /opt/local/libexec/gcc/i386-apple-darwin8.11.1/4.2.4/cc1 -E -quiet -isysroot /Developer/SDKs/MacOSX10.4u.sdk test.c | grep usr/include| head -n 1
# 1 "/Developer/SDKs/MacOSX10.4u.sdk/usr/include/stdio.h" 1 3 4

---

$ /opt/local/libexec/apple-gcc42/gcc/i686-apple-darwin8/4.2.1/cc1 -v -quiet -E -isysroot /Developer/SDKs/MacOSX10.4u.sdk test.c > /dev/null 
ignoring nonexistent directory "/opt/local/lib/apple-gcc42/gcc/i686-apple-darwin8/4.2.1/../../../../i686-apple-darwin8/include"
#include "..." search starts here:
#include <...> search starts here:
 /usr/local/include
 /opt/local/include
 /opt/local/lib/apple-gcc42/gcc/i686-apple-darwin8/4.2.1/include
 /usr/include
 /Developer/SDKs/MacOSX10.4u.sdk/System/Library/Frameworks (framework directory)
 /Developer/SDKs/MacOSX10.4u.sdk/Library/Frameworks (framework directory)
End of search list.

$ /opt/local/libexec/gcc/i386-apple-darwin8.11.1/4.2.4/cc1 -v -quiet -E -isysroot /Developer/SDKs/MacOSX10.4u.sdk test.c > /dev/null 
ignoring nonexistent directory "/Developer/SDKs/MacOSX10.4u.sdk/opt/local/include"
ignoring nonexistent directory "/opt/local/lib/gcc42/gcc/i386-apple-darwin8.11.1/4.2.4/../../../../i386-apple-darwin8.11.1/include"
#include "..." search starts here:
#include <...> search starts here:
 /opt/local/lib/gcc42/gcc/i386-apple-darwin8.11.1/4.2.4/include
 /Developer/SDKs/MacOSX10.4u.sdk/usr/include
 /Developer/SDKs/MacOSX10.4u.sdk/System/Library/Frameworks
 /Developer/SDKs/MacOSX10.4u.sdk/Library/Frameworks
End of search list.

Attachments (1)

main.log (4.5 MB) - added by royliu@… 12 years ago.
The failed build log.

Change History (19)

comment:1 Changed 12 years ago by jeremyhu (Jeremy Huddleston Sequoia)

Description: modified (diff)

comment:2 Changed 12 years ago by jeremyhu (Jeremy Huddleston Sequoia)

Possibly related to #31948

comment:3 Changed 12 years ago by jeremyhu (Jeremy Huddleston Sequoia)

Cc: jeremyhu@… added
Owner: changed from jeremyhu@… to royliu@…

It looks like we're now not looking in the SDK when we should be.

comment:4 Changed 12 years ago by jeremyhu (Jeremy Huddleston Sequoia)

Description: modified (diff)

comment:5 Changed 12 years ago by jeremyhu (Jeremy Huddleston Sequoia)

I think the real fix is in getting "p->add_sysroot" to be false for the compiler's include path.

comment:6 Changed 12 years ago by royliu@…

Give me a few days lead time -- I barely remember how I patched the compiler's search patch mechanism.

comment:7 Changed 12 years ago by jeremyhu (Jeremy Huddleston Sequoia)

Here's how I updated incpath.patch to work around the issue locally. I'd rather have correct logic for setting 'p->add_sysroot' so we could also apply this patch to the gccXX ports.

--- gcc/c-incpath.c.orig	2012-04-27 11:33:12.000000000 -0700
+++ gcc/c-incpath.c	2012-04-27 11:34:17.000000000 -0700
@@ -164,7 +164,7 @@ add_standard_paths (const char *sysroot,
 	  char *str;
 
 	  /* Should this directory start with the sysroot?  */
-	  if (sysroot && p->add_sysroot)
+	  if (sysroot && p->add_sysroot && strstr(p->fname, "apple-gcc42") == NULL)
 	    str = concat (sysroot, p->fname, NULL);
 	  else
 	    str = update_path (p->fname, p->component);

comment:8 Changed 12 years ago by jeremyhu (Jeremy Huddleston Sequoia)

If you don't come up with the "real" solution soon (namely fixing p->add_sysroot to be false in this case), I'm just going to go with this work around as a stop-gap ... that will fix apple-gcc42, but the gccXX ports will still be broken.

comment:9 Changed 12 years ago by royliu@…

While trying to fix this bug, I ran into a build error. Any ideas? Please find log attached.

Changed 12 years ago by royliu@…

Attachment: main.log added

The failed build log.

comment:10 Changed 12 years ago by royliu@…

Never mind, my bad, please ignore the above.

comment:11 Changed 12 years ago by royliu@…

How about r93183? If you agree, I'm closing.

comment:12 Changed 12 years ago by jeremyhu (Jeremy Huddleston Sequoia)

I don't think that's the right solution. I believe the real fix is figuring out why p->add_sysroot is true and set it to false for the compiler's include path.

comment:13 Changed 12 years ago by royliu@…

Doesn't setting p->add_sysroot back to false imply the default behavior? From your bug report, I got the impression that you wanted the MacPorts gcc-apple-4.2 to search in an Xcode SDK. Unless I am mistaken, the only way to make this happen is to replace /opt/local/include with /user/include.

comment:14 Changed 12 years ago by jeremyhu (Jeremy Huddleston Sequoia)

r93187 has my workaround, since your patch actually made things worse. I don't think you understand how -isysroot works. The sysroot is appended to certain include paths (but not all of them). -isysroot should NOT be appended to the *compiler's* include path because it needs to be found in $prefix (we assume MacPorts doesn't exist in an $SDK). Setting p->add_sysroot to false will cause the sysroot to NOT be appended, so that is what we want to do.

Your change just rewrote the include path to be /usr/include ...

My hack works by forcing that predicate to false based on checking for the "apple-gcc42" substring that will appear in the compiler's include directory, but the real fix is to make sure p->add_sysroot gets set to false for that entry.

comment:15 Changed 12 years ago by jeremyhu (Jeremy Huddleston Sequoia)

Note that *other* paths still have p->add_sysroot set to true, so /usr/include will be properly prepended with the sysroot.

comment:16 Changed 12 years ago by royliu@…

I'm still not understanding how my patch made things worse. There are essentially two types of includes that are being addressed. They look like:

 /Applications/Xcode.app/Contents/Developer/usr/llvm-gcc-4.2/lib/gcc/i686-apple-darwin11/4.2.1/include
 /Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.7.sdk/usr/include

I think the problem arises when Apple provides default compilers. These default compilers are installed in the default prefix, i.e., /usr. Apple also provides SDKs which serve as sysroots. A sysroot is a self-contained, alternate include hierarchy. Naturally, the internal structure of Apple SDKs use the /usr hierarchy to mirror their compiler installations, and it's all good. The MacPorts compiler is installed in /opt/local, and third party libraries are asking for -isysroot to be set to an Apple-provided SDK which uses the /usr hierarchy. This is the crux of the problem. The patch I made attempts to address the above two cases. In the first case, the include directory is compiler-specific, and so we actually want the MacPorts compiler's hierarchy, and drop the sysroot. In the second case, the user's intention is to use a "default" set of includes provided by the SDK. The best way I can think of is to:

  1. Ignore sysroot for the compiler's include directory (the MacPorts compiler directory being invariant over SDKs).
  2. Overwrite /opt/local/include with /usr/include when sysroot is about to be prepended, since that is what your vanilla Apple-provided compiler has access to.

Is this set of policies what you had in mind? If not, what should be the correct set of includes for a MacPorts compiler when -isysroot is specified? If so, then can you give a case where my patch isn't correct?

comment:17 Changed 12 years ago by jeremyhu (Jeremy Huddleston Sequoia)

Use -v with a sample compile, and you will see. The problem is that -I/opt/local/include becomes ${SDKROOT}/usr/include. So a case where this fails is for anything built which wants to use anything from MacPorts.

Without -isysroot, gcc -v shows the search path as:

 /opt/local/include
 /usr/local/include
 /opt/local/lib/apple-gcc42/gcc/i686-apple-darwin12/4.2.1/include
 /usr/include
 /System/Library/Frameworks (framework directory)
 /Library/Frameworks (framework directory)

With -isysroot and my patch, gcc shows it as:

/opt/local/include
/opt/local/lib/apple-gcc42/gcc/i686-apple-darwin12/4.2.1/include
${SDKROOT}/usr/include
${SDKROOT}/System/Library/Frameworks (framework directory)

ie, it looks for /usr/{local/,}include and {/S,}/L/F content inside the SDKROOT but not the compiler's internals. Your patch doesn't match that behavior. It does as you described above. #1 is correct. #2 isn't.

comment:18 Changed 12 years ago by royliu@…

Resolution: fixed
Status: newclosed

Very well. I'm closing this bug for now.

Note: See TracTickets for help on using tickets.