in reply to Clean smoke-test install for Inline based modules using Inline::MakeMaker

In Makefile.PL ensure that the following directive gets passed to WriteMakefile():

CONFIGURE_REQUIRES => { 'Inline::MakeMaker' => 0.45, 'ExtUtils::MakeMaker' => 6.62, },

This is a directive that only alters the way that make dist composes the META.yml and META.json files. In specific, those files will contain a configure_requires section. The various install tools (cpan, cpanm, and cpanp) will read the META.yml file, see what the "configure" requirements are, pull them in, and install them prior to executing Makefile.PL. At that point Makefile.PL will run cleanly as it will have access to the versions of ExtUtils::MakeMaker and Inline::MakeMaker that will allow a trouble-free install. As an added benefit, by causing EU::MM to upgrade (if necessary), the warning about not recognizing the CONFIGURE_REQUIRES directive goes away.

The directive really has no effect on the target system. All the primary effects take place at the time the distribution is composed and packed up. The fact that everything will now work on the target system is because the distribution was built in a more failsafe way.

As proof of concept refer to Math::Prime::FastSieve version 0.04. The smoke tests have begun trickling in, and with 18 of them I haven't yet seen an "UNKNOWN".

To assist the next guy who comes along the docs for Inline should probably contain the following modification in the Writing Modules with Inline section:

The following text:

Finally, you need to modify the Makefile.PL. Simply change: use ExtUtils::MakeMaker; to use Inline::MakeMaker;

Should say:

Finally, you need to make the following modifications to Makefile. +PL. Change: use ExtUtils::MakeMaker; to use Inline::MakeMaker; And add the following directive to WriteMakefile(): CONFIGURE_REQUIRES => { 'Inline::MakeMaker' => 0.45, 'ExtUtils::MakeMaker' => 6.62, },

My rationale for wanting to get a clean "one touch" install is this: If someone attempts to install a module and it fails, they may just move on to some other module, even if the one they chose initially would have been a very good choice had they gone through the extra steps of figuring out why it's not installing. I feel that part of the responsibility for quality insurance that an author takes on is that his module should install successfully using common conventions, without expecting the user to sift through a screen-full of error messages. It's sort of "putting your best foot forward."

As for "Why base a module on Inline?" Well, it's documented in the Inline POD as being a capability. There are tools such as InlineX::CPP2XS that will convert a module with Inline::CPP dependency to an XS module. But that may not exist for Java, Python, etc. So by ironing out the details, all Inline-dependency authors benefit.

On the down-side of requiring an Inline dependency in a module, there is yet another dependency for the user to deal with. Sort of like pulling in Moose for a trivial task, except the only performance penalty with Inline-based modules is paid at install time. Compiletime for code using an Inline-based module won't be impacted negatively in any measurable way. But on the other hand, making the Inline suite of tools more bullet proof could facilitate increased innovation in writing Perl extensions, as the barrier to entry is lower than writing pure XS.

But all of this is just how I rationalize the endeavor in my own mind, when the real reason is that I've been having fun with it. That's how it should be, right? :)


Dave

  • Comment on Re: (solved) Clean smoke-test install for Inline based modules using Inline::MakeMaker
  • Select or Download Code

Replies are listed 'Best First'.
Re^2: (solved) Clean smoke-test install for Inline based modules using Inline::MakeMaker
by BrowserUk (Patriarch) on Dec 15, 2011 at 17:48 UTC

    Math::Prime::FastSieve still doesn't install for me. I used cpan this time and it seems to have done the right thing by all the dependencies, but the compileation of the module itself fails with:

    t/01basic.t ... Microsoft (R) Program Maintenance Utility Version 9.00.21022.08 Copyright (C) Microsoft Corporation. All rights reserved. C:\Perl64\bin\perl.exe C:\Perl64\lib\ExtUtils\xsubpp -typemap + "C:\Perl64\lib\ExtUtils\typemap" -typemap "C:\Perl64\cpan\build\Inli +ne-CPP-0.33-uracNj\_Inline\build\_01basic_t_5cd2\CPP.map" _01basic_t +_5cd2.xs > _01basic_t_5cd2.xsc && C:\Perl64\bin\perl.exe -MExtUtils:: +Command -e "mv" -- _01basic_t_5cd2.xsc _01basic_t_5cd2.c cl -TP -c -I"C:/Perl64/cpan/build/Inline-CPP-0.33-uracNj/t" +-nologo -GF -W3 -MD -Zi -DNDEBUG -Ox -GL -Wp64 -fp:precise -DWIN32 -D +_CONSOLE -DNO_STRICT -DHAVE_DES_FCRYPT -DWIN64 -DCONSERVATIVE -DUSE_S +ITECUSTOMIZE -DPRIVLIB_LAST_IN_INC -DPERL_IMPLICIT_CONTEXT -DPERL_IMP +LICIT_SYS -DUSE_PERLIO -DPERL_MSVCRT_READFIX -MD -Zi -DNDEBUG -Ox -GL + -Wp64 -fp:precise -DVERSION=\"0.00\" -DXS_VERSION=\"0.00\" "-IC +:\Perl64\lib\CORE" _01basic_t_5cd2.c cl : Command line warning D9035 : option 'Wp64' has been deprecated an +d will be removed in a future release cl : Command line warning D9035 : option 'Wp64' has been deprecated an +d will be removed in a future release _01basic_t_5cd2.c _01basic_t_5cd2.xs(2) : fatal error C1083: Cannot open include file: ' +iostream.h': No such file or directory NMAKE : fatal error U1077: '"c:\Program Files (x86)\Microsoft Visual S +tudio 9.0\VC\Bin\amd64\cl.EXE"' : return code '0x2' Stop. A problem was encountered while attempting to compile and install your + Inline CPP code. The command that failed was: c:\PROGRA~2\MICROS~1.0\VC\Bin\amd64\nmake.exe > out.make 2>&1 The build directory was: C:\Perl64\cpan\build\Inline-CPP-0.33-uracNj\_Inline\build\_01basic_t_5 +cd2 To debug the problem, cd to the build directory, and inspect the outpu +t files. at t/01basic.t line 64 BEGIN failed--compilation aborted at t/01basic.t line 64. t/01basic.t ... Dubious, test returned 2 (wstat 512, 0x200) Failed 10/10 subtests ...

    From the error message: _01basic_t_5cd2.xs(2) : fatal error C1083: Cannot open include file: 'iostream.h': No such file or directory and a little googling, it looks like this is a common problem centred around using: #include <iostream.h>

    rather than the (MS?) preferred:<code>#include <iostream></c>


    With the rise and rise of 'Social' network sites: 'Computers are making people easier to use everyday'
    Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
    "Science is about questioning the status quo. Questioning authority".
    In the absence of evidence, opinion is indistinguishable from prejudice.

    The start of some sanity?

      Thanks for that report. That has to be an Inline::CPP issue, so a separate problem. syphilis and I thought we had solved it a couple weeks ago, but it looks like more attention is required. I'll get to work on it. You must be in the 7% that are still having problems with Inline::CPP. My goal there is to get that module to the point that it installs for all systems that Inline::C installs for (assuming they have a C++ compiler), which would be about 98%.

      More details: The problem is related to how C++ has evolved and standardized. As I'm sure you know better than I, before a standard was adopted C++ headers usually had the .h extension. More recently (which really isn't all that recent now) C++ standardized around headers without the .h extension. Inline::CPP automatically includes <iostream>, or <iostream.h>. It's supposed to detect which is required, and for the majority of systems it seems to get it right. It looks like in your case it's guessing wrong. Now that I know it's still an issue I can turn my sights on it again. It's enough of a sore-spot that I'm almost inclined to eliminate the automatic inclusion of <iostream>, but that wouldn't really solve the problem of distributing code based on Inline::CPP, as it just forces module authors to try to figure out how to decide between '.h' or no '.h' themselves.


      Dave

        The test in Inline::CPP.pm is

        my $iostream = "iostream"; # $iostream .= ".h" unless $o->{ILSM}{STD_IOSTREAM}; if($o->{ILSM}{MAKEFILE}{CC} =~ /^cl/) { $iostream .= ".h" unless $o->{ILSM}{STD_IOSTREAM}; } $o->{ILSM}{AUTO_INCLUDE} =~ s|%iostream%|$iostream|g;

        Ie. If the compiler command is 'cl' append '.h'. But, according to MS, all their compilers since VS 2003 now only supply the newer standard extension-less standard header files.

        I have Microsoft (R) C/C++ Optimizing Compiler Version 15.00.21022.08 for x64 which I memory serves equates to VS 2008; internal version 9; File format version 10. (Damn I wish they'd use ONE bloody name for things!), so I think the above test will need to be more selective.


        With the rise and rise of 'Social' network sites: 'Computers are making people easier to use everyday'
        Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
        "Science is about questioning the status quo. Questioning authority".
        In the absence of evidence, opinion is indistinguishable from prejudice.

        The start of some sanity?

Re^2: (solved) Clean smoke-test install for Inline based modules using Inline::MakeMaker
by syphilis (Archbishop) on Dec 15, 2011 at 23:26 UTC
    As an added benefit, by causing EU::MM to upgrade (if necessary), the warning about not recognizing the CONFIGURE_REQUIRES directive goes away.

    I gather that's the *only* reason for adding the EU::MM requirement - I don't see that it could serve any other purpose.
    No problem with any of that but I'll specify '6.52' instead of '6.62'. According to the EU::MM Changes file 6.52 would be the earliest stable version to be aware of the CONFIGURE_REQUIRES option. It so happens that I have 6.52 on one of my builds of perl, and it doesn't complain about the option. (Version 6.48 *does* complain.)

    I'll wait for a week in case there are any more developments, then I'll upload your suggested amendment to github so that it's sitting there in readiness for the next Inline release.
    It's unlikely I'll forget about it, but please ping me if I do :-)

    Cheers,
    Rob

      Yes, that's the only reason. Perhaps it's not a very good reason, as a warning wouldn't cause an install failure anyway, right? Might not be worth forcing people to upgrade EU::MM just to squelch a warning.

      However, it would be worth mentioning in the POD for Inline that the CONFIGURE_REQUIRES directive requires that the person creating the distribution have EU::MM version 6.56 (or whatever it was) installed on his system.

      Opinions?


      Dave

        Opinions?

        I think we could recommend that CONFIGURE_REQUIRES include EU::MM in addition to Inline::MakeMaker - but then explain why we've included EU::MM, and let people make up their own mind as to whether they wish to do the same.

        Should CONFIGURE_REQUIRES specify Inline::MakeMaker or should it specify Inline ?
        I guess it doesn't matter much (you won't get one without the other) so long as Inline gets found and installed. I'll leave that part as is unless someone wants to convince me that it should be changed to specify 'Inline'.

        Cheers,
        Rob

        I'd be inclined to put those sort of directions in a dev-readme.txt file (perhaps in the /t folder) or maybe as a "For maintainers" section in the README file rather than cluttering the POD with stuff that isn't pertinent to users.

        True laziness is hard work