Compiling ImageMagick for Perl
Compiling PerlMagick, the Perl binding for ImageMagick, is a major pain in the neck, as it almost never works out of the box. Check out this blog post to discover an effortless solution to that tedious task. Say goodbye to manual tinkering and compiling headaches and hello to use Image::Magick
!
Table Of Contents
Source Code on GitHub
The accompanying source code repository is on GitHub at https://github.com/gflohr/perlmagick-hint. I will try to keep it up-to-date.
Pre-Requisites
You have to install ImageMagick. It does not matter whether you install a pre-compiled binary or compile it yourself. If you install a pre-compiled binary, please make sure that the C header files are also installed. For example, on RedHat based Linux distributions, you must also install the package ImageMagick-devel
, not just ImageMagick
.
You can verify that everything worked with this command:
$ MagickCore-config --version
That should print the ImageMagick version plus some extra information. See the section Troubleshooting below, in case the command cannot be found or it does not display the version that you expect.
You also need the Perl binding for ImageMagick. You can download it from https://metacpan.org/dist/Image-Magick.
Compiling
Prepare the Sources
Copy the source tarball for ImageMagick/PerlMagick into a directory of your choice. Then:
$ tar xzf ImageMagick-VERSION.tar.gz
$ cd ImageMagick-VERSION
Replace VERSION
with the actual version of ImageMagick for Perl that you have downloaded.
Download the Hint Script
The file that you need can be downloaded from https://github.com/gflohr/perlmagick-hint/blob/main/hint.pl. You must copy that into a directory hints
inside the unpacked source distribution of PerlMagick:
$ mkdir hints
$ cp ~/Downloads/hint.pl hints
Rename the Hint Script
The hint script must follow a certain naming convention. It must consist of Perl's identifier of your operating system plus the usual .pl
extension. You can find out the Perl identifier of your operating system with the following one-liner:
$ perl -e 'print $^O'
darwin
The output darwin
is just an example that you will see on macos. You must now rename the script accordingly:
$ mv hints/hint.pl hints/darwin.pl
Alternatively, you can just execute the hint file. If it finds out that it does not have the correct name or is not inside a directory hints
, it prints an error message:
$ perl hints/hint.pl
Error: Create a directory 'hints' in an unpacked ImageMagick distribution and
store this file as 'hints/darwin.pl'! Then run 'perl Makefile.PL && make &&
make install'!
On other operating systems, you would see something like hints/YOUR-OS.pl
instead of hints/darwin.pl
.
If you have renamed the script to something recognized, it should now output the patched configuration:
$ perl hints/darwin.pl # Replace with the correct name of the script!
Patch configuration:
CCFLAGS = -DMAGICKCORE_HDRI_ENABLE=0 -DMAGICKCORE_QUANTUM_DEPTH=16 -I/opt/local/include/ImageMagick-6
INC =
LDDLFLAGS = -L/opt/local/lib -lMagickCore-6.Q16
LDFLAGS = -L/opt/local/lib -lMagickCore-6.Q16
LIBS = -L/opt/local/lib -lMagickCore-6.Q16 -L/Users/me/perl5/perlbrew/perls/perl-5.34.0/lib/5.34.0/darwin-2level/CORE -L/Users/me/perl5/perlbrew/perls/perl-5.34.0/lib/5.34.0/darwin-2level/CORE
You are now all set and can configure the extension:
$ perl Makefile.PL
Getting ImageMagick configuration from hints.
Generating a Unix-style Makefile
Writing Makefile for Image::Magick
Writing MYMETA.yml and MYMETA.json
Make sure that you see the message "Getting ImageMagick configuration from hints". If not, please check the above instructions again.
If it worked, you can now compile and install:
$ make
$ make install
If you are not using Perlbrew
you have to install with superuser privileges: sudo make install
.
Troubleshooting
ImageMagick 7 from MacPorts
At the time of this writing, MacPorts has two versions of ImageMagick. The port ImageMagick
contains ImageMagick version 6. If you want the newer version 7, you have to install ImageMagick7
instead.
The problem is that the binaries from ImageMagick7
are not included in $PATH
. There are two possible ways to fix that.
One option is to modify $PATH
in the current shell:
$ export PATH="/opt/local/lib/ImageMagick7/bin:$PATH"
$ perl hints/darwin.pl
$ perl Makefile.PL
The other option is to specify the path to the MagickCore-config
binary:
$ export MAGICKCORE_CONFIG=/opt/local/lib/ImageMagick7/bin/MagickCore-config
$ perl hints/darwin.pl
$ perl Makefile.PL
'MagickCore/MagickCore.h' file not found
If you encounter this error you probably do not have the C header files installed. If your vendor has separate development versions of pre-compiled software packages, make sure that you install them as well. In many cases that the name will be that of the normal package with -devel
appended, for example ImageMagick-devel
.
MS-DOS/Windows
The Makefile.PL
that ships with ImageMagick should work out of the box and you do not need a hints file.
Background
When compiling the Perl binding of ImageMagick, you run into two problems at once. The Makefile.PL
that ships with the Perl binding hardcodes the configuration, assuming that you have built and installed the ImageMagick binaries from sources with default configuration parameters. This configuration also works with Homebrew for macos but this is mostly coincidence.
But if you have ImageMagick binaries using another prefix than /usr/local
, the hardcoded configuration is incorrect. It is also incorrect if you disabled HDRI support.
Surprisingly, the Makefile.PL
autodetects the necessary configuration on MS-DOS/MS-Windows but not for POSIX systems. Our hint script described jumps in here and autodetects the configuration for any system.
The other problem is the inflexibility and terrible documentation of ExtUtils::MakeMaker
. You could theoretically successfully configure ImageMagick like this:
$ perl Makefile.PL INC= \
LIBS=`MagickCore-config --libs` \
CCFLAGS=`MagickCore-config --cflags` \
LDFLAGS=`MagickCore-config --ldflags` \
LDDLFLAGS=`MagickCore-config --lddlflags`
But who knows that? Who can remember that? And where is that documented?
The trick with the hints file actually works for every Perl extension, not just ImageMagick. But why is there not a default search path for that hint file, when no os-specific hint file was found? And it also does not work, when you install non-interactively, for example with cpanm
? Well, the answer is that the mechanism is intended to be used by module authors, and not users. But that does not make it any better.
Feedback and Bug Reports
You can provide feedback and bug reports either as GitHub issues at https://github.com/gflohr/perlmagick-hint or in the comments section below.
Leave a comment