Skip Menu |

This queue is for tickets about the Module-Build CPAN distribution.

Report information
The Basics
Id: 48918
Status: resolved
Priority: 0/
Queue: Module-Build

People
Owner: Nobody in particular
Requestors: EWILHELM [...] cpan.org
frequency [...] cpan.org
Cc: module-build [...] perl.org
AdminCc:

Bug Information
Severity: Normal
Broken in: (no value)
Fixed in: 0.36



CC: module-build [...] perl.org
Subject: Auto-detecting XS code should imply build_requires ExtUtils::CBuilder
Currently, distributions compiling XS extensions need to explicitly state ExtUtils::CBuilder as a build_requires element. It would be nice if Module::Build would detect this (probably at `./Build dist` time), but such a feature would need an off-switch for use in dual-mode distributions which fallback to a pure-perl module in the absence of a compiler. This wishlist item originated in the following ticket: http://rt.cpan.org/Ticket/Display.html?id=21515
Subject: Feature request: Fail if ExtUtils::CBuilder is build_requires and have_compiler is false
Hi: My distribution (Math::Random::ISAAC::XS) has a test failure which results from a system that has ExtUtils::CBuilder installed, but without any C compiler. Module::Build does not check "have_compiler" anywhere, which results in the build trying to proceed anyway. It appears EUCB then defaults to "cc" as a compiler, which isn't available, thus resulting in a hard test failure. Instead, it would be nice of Module::Build checked this during Build.PL -> Build process, and exits there. Then the test failure would be an NA rather than FAIL. Cheers, Jonathan
Subject: Re: [rt.cpan.org #48918] Feature request: Fail if ExtUtils::CBuilder is build_requires and have_compiler is false
Date: Sun, 23 Aug 2009 10:45:57 -0700
To: bug-Module-Build [...] rt.cpan.org
From: Eric Wilhelm <enobacon [...] gmail.com>
# from Jonathan Yu via RT # on Friday 21 August 2009 12:09: Show quoted text
>My distribution (Math::Random::ISAAC::XS) has a test failure which >results from a system that has ExtUtils::CBuilder installed, but > without any C compiler. Module::Build does not check "have_compiler" > anywhere, which results in the build trying to proceed anyway.
How did ExtUtils::CBuilder get installed if t/01-basic.t didn't pass? Show quoted text
>Instead, it would be >nice of Module::Build checked this during Build.PL -> Build process, >and exits there. Then the test failure would be an NA rather than FAIL.
If this is an error in the cpantester's machine, it should be corrected on their machine. It is unreasonable to expect M::B to workaround pathological cases simply to gloss over a tester's mess. If a real user were to somehow end up in this situation, I think failing in a smoking wreck is the right thing to do because they need to diagnose and fix their EU::CB installation. --Eric
From: frequency [...] cpan.org
Eric: On Sun Aug 23 13:46:21 2009, enobacon@gmail.com wrote: Show quoted text
> # from Jonathan Yu via RT > # on Friday 21 August 2009 12:09: >
> >My distribution (Math::Random::ISAAC::XS) has a test failure which > >results from a system that has ExtUtils::CBuilder installed, but > > without any C compiler. Module::Build does not check "have_compiler" > > anywhere, which results in the build trying to proceed anyway.
> > How did ExtUtils::CBuilder get installed if t/01-basic.t didn't pass?
It's because in t/01-basic.t: # test plan if ( ! $b->have_compiler ) { plan skip_all => "no compiler available for testing"; } else { plan tests => 10; } All tests are skipped if there's no compiler, but it's not a *failure*. That's the point. You should be able to install EUCB even if you don't have a C compiler. I discussed this with David Golden via IRC. Show quoted text
>
> >Instead, it would be > >nice of Module::Build checked this during Build.PL -> Build process, > >and exits there. Then the test failure would be an NA rather than FAIL.
> > If this is an error in the cpantester's machine, it should be corrected > on their machine. It is unreasonable to expect M::B to workaround > pathological cases simply to gloss over a tester's mess.
I'm simply asking M::B to actually test have_compiler before it tries to build things. That's exactly the point of have_compiler. Keep in mind that EUCB is just a Pure Perl module, and doesn't require a C compiler at all. The report in question happened because someone installed EUCB while not having a C compiler, which is perfectly legal behaviour. The problem is how M::B deals with it. Show quoted text
> > If a real user were to somehow end up in this situation, I think failing > in a smoking wreck is the right thing to do because they need to > diagnose and fix their EU::CB installation.
I think failing with a helpful message like "Well, you're trying to build an XS module but you don't have a C compiler. Please install one and try again" is better than "blahblah 'cc' not found" which is an easily understandable message for technical people, but not immediately obvious for people less familiar with Unix/etc. Show quoted text
> > --Eric
ExtUtils::CBuilder is a core module. This means it should be present even for a binary install of perl which might not have a compiler. Thus, the presence of EU::CB alone is not evidence of a compiler. Module::Build might once have intended this as a "feature", but the existence of a have_compiler API clearly implies that it can be installed even when a compiler is missing. However, it's not appropriate for a build_requires on ExtUtils::CBuilder to fail if have_compiler is false because the author may be doing something custom to check for have_compiler manually and install a pure perl version otherwise. So, we need to do something "smart" but not too smart. Maybe that's adding a "needs_compiler" Module::Build property to automate this kind of check. Needs more thought, but thank you Jawnsy for opening a ticket to remind us to figure it out. -- David
Reconsidered options on IRC with jawnsy. New idea: Can't check during configure because EU::CB might be 'build_requires' and not installed. The check has to come during 'Build' and should ideally just be the parts of ACTION_code that attempt to compile XS or C. At that time, we should check have_compiler and die with a useful message if no compiler is available. If we have a compiler, that should get cached in the 'notes' hash so it's persistent. -- David
As discussed on IRC with ewilhelm: * Add "needs_compiler" property. If true, add ExtUtils::CBuilder to 'build_requires' * In Build.PL, check find_xs_files() and 'c_source' property. If we find anything there that will need compiling, set needs_compiler to 1 unless already set explicitly to 0. If things to compile are found and needs_compiler is 1, then check have_c_compiler and warn with a very visible, useful message if none is found. * In compile_c, check have_c_compiler and die with a visible useful mesage if no compiler is found. (This in case someone is doing something nutty and generating .xs from .PL files and we miss that at configure time) * In have_c_compiler, cache the results in the stash, not the properties, because it isn't actually a property, but we do want it to persist per session
CC: module-build [...] perl.org
Subject: Re: [rt.cpan.org #48918] Feature request: Fail if ExtUtils::CBuilder is build_requires and have_compiler is false
Date: Sun, 23 Aug 2009 22:00:05 -0700
To: bug-Module-Build [...] rt.cpan.org
From: Eric Wilhelm <enobacon [...] gmail.com>
# from David Golden via RT # on Sunday 23 August 2009 20:41: Show quoted text
>* In have_c_compiler, cache the results in the stash, not the >properties, because it isn't actually a property, but we do want it to >persist per session
I'm not sure what you mean by "per session", but $self->{stash} is not persisted in _build/. So, it might not be a 'property', but have_c_compiler() should somehow be cached by write_config() because EU::CB's have_compiler() is an expensive operation of attempting to compile a small c program. Thus, if it was true at configure time, we don't want to repeat that effort at build time. I'm guessing that "just stick it in properties" was the easiest way to make this work when it was written. If there is some sort of "internal use only" equivalent of properties, I'm not seeing it. Do we need to add one? I'm inclined to just call it a {_have_c_compiler} or even leave it as a {have_c_compiler} property. --Eric
I'm bumping this to "normal" severity. Even if new features are needed the behavior is a bug and we should fix it.
Patched in repository trunk