diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml new file mode 100644 index 00000000..9abf2b7f --- /dev/null +++ b/.github/workflows/build.yml @@ -0,0 +1,33 @@ +name: Python build +on: + push: + branches: [ master ] + pull_request: + branches: [ master ] + +jobs: + test: + runs-on: windows-latest + + steps: + - uses: actions/checkout@v2 + - run: unzip httpd-2.4.54-win64-VS16.zip + + - uses: ilammy/msvc-dev-cmd@v1 + + + - name: Build APXS + working-directory: ${{ github.workspace }}\apxs_win32 + run: perl -I. Configure.pl --with-apache2=${{ github.workspace }}\Apache24 --with-apache-prog=httpd.exe + + - name: Set up Python ${{ matrix.python-version }} + uses: actions/setup-python@v2 + with: + python-version: '3.10' + + - name: Build mod_python + shell: bash + run: | + ./configure --with-apxs=${{ github.workspace }}/apxs_win32 + make + make install diff --git a/apxs_win32/Configure.pl b/apxs_win32/Configure.pl new file mode 100644 index 00000000..a47427e3 --- /dev/null +++ b/apxs_win32/Configure.pl @@ -0,0 +1,148 @@ +#!C:/Perl/bin/perl +use strict; +use warnings; +use Getopt::Long; +require Win32; +use Config; +use ExtUtils::MakeMaker; +use File::Basename; +use File::Spec::Functions; +require 'util.pl'; + +BEGIN { + die 'This script is intended for Win32' unless $^O =~ /Win32/i; +} + +my ($apache, $help, $progname); +GetOptions( 'with-apache2=s' => \$apache, + 'with-apache-prog=s' => \$progname, + 'help' => \$help, + ) or usage($0); +usage($0) if $help; + +my @path_ext; +path_ext(); +($apache, $progname) = search($apache, $progname); + +push @ARGV, "--with-apache-prog=$progname"; + +for my $file (qw(apxs_win32.pl apr_win32.pl apu_win32.pl) ) { + push @ARGV, "--with-apache2=$apache"; + unless (my $return = do $file) { + die "Cannot parse $file: $@" if $@; + die "Cannot do $file: $!" unless defined $return; + die "Cannot run $file" unless $return; + } +} + +sub search { + my ($apache, $progname) = @_; + + if ($apache) { + die qq{Cannot find the "$apache" directory} unless -d $apache; + if ($progname) { + my $bin = catfile $apache, 'bin', $progname; + die qq{"$bin" appears not to be an executable file} unless (-x $bin); + } + else { + $progname = 'Apache.exe'; + } + if (check_httpd($apache, $progname)) { + $apache = Win32::GetShortPathName($apache); + $apache =~ s!\\$!!; + return ($apache, $progname); + } + else { + die qq{"$apache" appears not to be a suitable Apache2 installation}; + } + } + + for my $binary( qw(Apache.exe httpd.exe) ) { + my ($candidate, $bin); + if ($bin = which($binary)) { + ($candidate = dirname($bin)) =~ s!bin$!!; + if (-d $candidate and check_httpd($candidate, $binary)) { + $apache = $candidate; + $progname = $binary; + last; + } + } + } + + $progname ||= 'Apache.exe'; + + unless ($apache and -d $apache) { + $apache = prompt("Please give the path to your Apache2 installation:", + $apache); + $progname = prompt("Please give the name of your Apache program name:", + $progname); + } + die "Cannot find a suitable Apache2 installation!" + unless ($apache and -d $apache and check_httpd($apache, $progname)); + + $apache = Win32::GetShortPathName($apache); + $apache =~ s!\\$!!; + my $ans = prompt(qq{\nUse "$apache" for your Apache2 directory?}, 'yes'); + unless ($ans =~ /^y/i) { + die <<'END'; + +Please run this configuration script again, and give +the --with-apache2=C:\Path\to\Apache2 option to specify +the desired top-level Apache2 directory and, if necessary, +the --with-apache-prog=httpd.exe to specify the Apache +program name. + +END + } + return ($apache, $progname); +} + +sub drives { + my @drives = (); + eval{require Win32API::File;}; + return map {"$_:\\"} ('C' .. 'Z') if $@; + my @r = Win32API::File::getLogicalDrives(); + return unless @r > 0; + for (@r) { + my $t = Win32API::File::GetDriveType($_); + push @drives, $_ if ($t == 3 or $t == 4); + } + return @drives > 0 ? @drives : undef; +} + +sub path_ext { + if ($ENV{PATHEXT}) { + push @path_ext, split ';', $ENV{PATHEXT}; + for my $ext (@path_ext) { + $ext =~ s/^\.*(.+)$/$1/; + } + } + else { + #Win9X: doesn't have PATHEXT + push @path_ext, qw(com exe bat); + } +} + +sub which { + my $program = shift; + return unless $program; + my @extras = (); + my @drives = drives(); + if (@drives > 0) { + for my $drive (@drives) { + for ('Apache2', 'Program Files/Apache2', + 'Program Files/Apache Group/Apache2') { + my $bin = catfile $drive, $_, 'bin'; + push @extras, $bin if (-d $bin); + } + } + } + my @a = map {catfile($_, $program) } (path(), @extras); + for my $base(@a) { + return $base if -x $base; + for my $ext (@path_ext) { + return "$base.$ext" if -x "$base.$ext"; + } + } + return; +} diff --git a/apxs_win32/README b/apxs_win32/README new file mode 100644 index 00000000..e8e981ba --- /dev/null +++ b/apxs_win32/README @@ -0,0 +1,22 @@ +This distribution contains scripts to install the utilities +apxs, apr-config, and apu-config on Win32 for use with Apache2. +To install, at a DOS prompt run + perl Configure.pl +which will attempt to find your top-level Apache2 directory. +If this is unsuccessful, or the guess is wrong, run + perl Configure.pl --with-apache2=\Path\to\Apache2 +The utilities will be placed under \Path\to\Apache2\bin\. + +If you are building for Apache 2.1-dev/2.2, you will discover +that it's now httpd.exe, not Apache.exe. Specifying + + perl Configure.pl --with-apache-prog=httpd.exe + +will provide the results you hoped for. + +Randy Kobes + +Bill Rowe provided the fixes necessary +for Apache 2.1-dev/2.2. + +July 22, 2005 diff --git a/apxs_win32/apr_win32.pl b/apxs_win32/apr_win32.pl new file mode 100644 index 00000000..a4ba1f8b --- /dev/null +++ b/apxs_win32/apr_win32.pl @@ -0,0 +1,263 @@ +#!perl +use strict; +use warnings; +use Config; +use Getopt::Long; +require Win32; +use ExtUtils::MakeMaker; +use File::Spec::Functions qw(catfile catdir); +require 'util.pl'; + +BEGIN { + die 'This script is intended for Win32' unless $^O =~ /Win32/i; +} + +my $license = <<'END'; +# ==================================================================== +# +# Copyright 2003-2004 The Apache Software Foundation +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# ==================================================================== +# +# APR script designed to allow easy command line access to APR configuration +# parameters. + +END + +my ($prefix, $help); +GetOptions('with-apache2=s' => \$prefix, 'help' => \$help) or usage($0); +usage($0) if $help; + +unless (defined $prefix and -d $prefix) { + $prefix = prompt("Please give the path to your Apache2 installation:", + $prefix); +} +die "Can't find a suitable Apache2 installation!" + unless (-d $prefix and check_apr($prefix)); + +$prefix = Win32::GetShortPathName($prefix); + +my %ap_dir; +foreach (qw(bin lib include build)) { + $ap_dir{$_} = catdir $prefix, $_; +} + +my $apr_version = catfile $ap_dir{include}, 'apr_version.h'; +open(my $inc, $apr_version) + or die "Cannot open $apr_version: $!"; +my %vers; +while (<$inc>) { + if (/define\s+APR_(MAJOR|MINOR|PATCH)_VERSION\s+(\d+)/) { + $vers{$1} = $2; + } +} +close $inc; +my $file = $vers{MAJOR} < 1 ? "apr-config.pl" : "apr-$vers{MAJOR}-config.pl"; +my $dotted = "$vers{MAJOR}.$vers{MINOR}.$vers{PATCH}"; + +my $apr_libname; +opendir(my $dir, $ap_dir{lib}) or die "Cannot opendir $ap_dir{lib}: $!"; +my @libs = grep /^libapr\b\S+lib$/, readdir $dir; +closedir $dir; +die "Unable to find the apr lib" unless ($apr_libname = $libs[0]); + +my %apr_args = (APR_MAJOR_VERSION => $vers{MAJOR}, + APR_DOTTED_VERSION => $dotted, + APR_LIBNAME => $apr_libname, + prefix => $prefix, + exec_prefix => $prefix, + bindir => $ap_dir{bin}, + libdir => $ap_dir{lib}, + datadir => $prefix, + installbuilddir => $ap_dir{build}, + includedir => $ap_dir{include}, + + CC => $Config{cc}, + CPP => $Config{cpp}, + LD => $Config{ld}, + SHELL => $ENV{comspec}, + CPPFLAGS => '', + CFLAGS => q{ /nologo /MD /W3 /O2 /D WIN32 /D _WINDOWS /D NDEBUG }, + LDFLAGS => q{ kernel32.lib /nologo /subsystem:windows /dll }, + LIBS => '', + EXTRA_INCLUDES => '', + APR_SOURCE_DIR => '', + APR_SO_EXT => $Config{dlext}, + APR_LIB_TARGET => '', + ); + +my $apr_usage = << "EOF"; +Usage: apr-$vers{MAJOR}-config [OPTION] + +Known values for OPTION are: + --prefix[=DIR] change prefix to DIR + --bindir print location where binaries are installed + --includedir print location where headers are installed + --libdir print location where libraries are installed + --cc print C compiler name + --cpp print C preprocessor name and any required options + --ld print C linker name + --cflags print C compiler flags + --cppflags print cpp flags + --includes print include information + --ldflags print linker flags + --libs print additional libraries to link against + --srcdir print APR source directory + --installbuilddir print APR build helper directory + --link-ld print link switch(es) for linking to APR + --apr-so-ext print the extensions of shared objects on this platform + --apr-lib-file print the name of the apr lib + --version print the APR version as a dotted triple + --help print this help + +When linking, an application should do something like: + APR_LIBS="\`apr-config --link-ld --libs\`" + +An application should use the results of --cflags, --cppflags, --includes, +and --ldflags in their build process. +EOF + +my $full = catfile $ap_dir{bin}, $file; +open(my $fh, '>', $full) or die "Cannot open $full: $!"; +print $fh <<"END"; +#!$^X +use strict; +use warnings; +use Getopt::Long; +use File::Spec::Functions qw(catfile catdir); + +$license +sub usage { + print << 'EOU'; +$apr_usage +EOU + exit(1); +} + +END + +foreach my $var (keys %apr_args) { + print $fh qq{my \${$var} = q[$apr_args{$var}];\n}; +} +print $fh $_ while ; +close $fh; + +my @args = ('pl2bat', $full); +system(@args) == 0 or die "system @args failed: $?"; +print qq{$file.bat has been created under $ap_dir{bin}.\n\n}; + +__DATA__ + +my %opts = (); +GetOptions(\%opts, + 'prefix:s', + 'bindir', + 'includedir', + 'libdir', + 'cc', + 'cpp', + 'ld', + 'cflags', + 'cppflags', + 'includes', + 'ldflags', + 'libs', + 'srcdir', + 'installbuilddir', + 'link-ld', + 'apr-so-ext', + 'apr-lib-file', + 'version', + 'help' + ) or usage(); + +usage() if ($opts{help} or not %opts); + +if (exists $opts{prefix} and $opts{prefix} eq "") { + print qq{$prefix\n}; + exit(0); +} +my $user_prefix = defined $opts{prefix} ? $opts{prefix} : ''; +my %user_dir; +if ($user_prefix) { + foreach (qw(lib bin include build)) { + $user_dir{$_} = catdir $user_prefix, $_; + } +} +my $flags = ''; + +SWITCH : { + local $\ = "\n"; + $opts{bindir} and do { + print $user_prefix ? $user_dir{bin} : $bindir; + last SWITCH; + }; + $opts{includedir} and do { + print $user_prefix ? $user_dir{include} : $includedir; + last SWITCH; + }; + $opts{libdir} and do { + print $user_prefix ? $user_dir{lib} : $libdir; + last SWITCH; + }; + $opts{installbuilddir} and do { + print $user_prefix ? $user_dir{build} : $installbuilddir; + last SWITCH; + }; + $opts{srcdir} and do { + print $APR_SOURCE_DIR; + last SWITCH; + }; + $opts{cc} and do { + print $CC; + last SWITCH; + }; + $opts{cpp} and do { + print $CPP; + last SWITCH; + }; + $opts{ld} and do { + print $LD; + last SWITCH; + }; + $opts{cflags} and $flags .= " $CFLAGS "; + $opts{cppflags} and $flags .= " $CPPFLAGS "; + $opts{includes} and do { + my $inc = $user_prefix ? $user_dir{include} : $includedir; + $flags .= qq{ /I"$inc" $EXTRA_INCLUDES }; + }; + $opts{ldflags} and $flags .= " $LDFLAGS "; + $opts{libs} and $flags .= " $LIBS "; + $opts{'link-ld'} and do { + my $libpath = $user_prefix ? $user_dir{lib} : $libdir; + $flags .= qq{ /libpath:"$libpath" $APR_LIBNAME }; + }; + $opts{'apr-so-ext'} and do { + print $APR_SO_EXT; + last SWITCH; + }; + $opts{'apr-lib-file'} and do { + my $full_aprlib = $user_prefix ? + (catfile $user_dir{lib}, $APR_LIBNAME) : + (catfile $libdir, $APR_LIBNAME); + print $full_aprlib; + last SWITCH; + }; + $opts{version} and do { + print $APR_DOTTED_VERSION; + last SWITCH; + }; + print $flags if $flags; +} +exit(0); diff --git a/apxs_win32/apu_win32.pl b/apxs_win32/apu_win32.pl new file mode 100644 index 00000000..c860aedc --- /dev/null +++ b/apxs_win32/apu_win32.pl @@ -0,0 +1,265 @@ +#!perl +use strict; +use Config; +use Getopt::Long; +require Win32; +use ExtUtils::MakeMaker; +use File::Spec::Functions qw(catfile catdir); +use warnings; +require 'util.pl'; + +BEGIN { + die 'This script is intended for Win32' unless $^O =~ /Win32/i; +} + +my $license = <<'END'; +# ==================================================================== +# +# Copyright 2003-2004 The Apache Software Foundation +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# ==================================================================== +# +# APR-util script designed to allow easy command line access to APR-util +# configuration parameters. + +END + +my ($prefix, $help); +GetOptions('with-apache2=s' => \$prefix, 'help' => \$help) or usage($0); +usage($0) if $help; + +unless (defined $prefix and -d $prefix) { + $prefix = prompt("Please give the path to your Apache2 installation:", + $prefix); +} +die "Can't find a suitable Apache2 installation!" + unless (-d $prefix and check_apu($prefix)); + +$prefix = Win32::GetShortPathName($prefix); + +my %ap_dir; +foreach (qw(bin lib include build)) { + $ap_dir{$_} = catdir $prefix, $_; +} + +my $apu_version = catfile $ap_dir{include}, 'apu_version.h'; +open(my $inc, $apu_version) + or die "Cannot open $apu_version: $!"; +my %vers; +while (<$inc>) { + if (/define\s+APU_(MAJOR|MINOR|PATCH)_VERSION\s+(\d+)/) { + $vers{$1} = $2; + } +} +close $inc; +my $file = $vers{MAJOR} < 1 ? "apu-config.pl" : "apu-$vers{MAJOR}-config.pl"; + +my $dotted = "$vers{MAJOR}.$vers{MINOR}.$vers{PATCH}"; + +my $aprutil_libname; +opendir(my $dir, $ap_dir{lib}) or die "Cannot opendir $ap_dir{lib}: $!"; +my @libs = grep /^libaprutil\b\S+lib$/, readdir $dir; +closedir $dir; +die "Unable to find the apr lib" unless ($aprutil_libname = $libs[0]); + +my %apu_args = (APRUTIL_MAJOR_VERSION => $vers{MAJOR}, + APRUTIL_DOTTED_VERSION => $dotted, + APRUTIL_LIBNAME => $aprutil_libname, + prefix => $prefix, + exec_prefix => $prefix, + bindir => $ap_dir{bin}, + libdir => $ap_dir{lib}, + datadir => $prefix, + installbuilddir => $ap_dir{build}, + includedir => $ap_dir{include}, + + CC => $Config{cc}, + CPP => $Config{cpp}, + LD => $Config{ld}, + SHELL => $ENV{comspec}, + CPPFLAGS => '', + CFLAGS => q{ /nologo /MD /W3 /O2 /D WIN32 /D _WINDOWS /D NDEBUG }, + LDFLAGS => q{ kernel32.lib /nologo /subsystem:windows /dll }, + LIBS => '', + EXTRA_INCLUDES => '', + APRUTIL_SOURCE_DIR => '', + APRUTIL_SO_EXT => $Config{dlext}, + APRUTIL_LIB_TARGET => '', + ); + +my $apu_usage = << "EOF"; +Usage: apu-$vers{MAJOR}-config [OPTION] + +Known values for OPTION are: + --prefix[=DIR] change prefix to DIR + --bindir print location where binaries are installed + --includedir print location where headers are installed + --libdir print location where libraries are installed + --cc print C compiler name + --cpp print C preprocessor name and any required options + --ld print C linker name + --cflags print C compiler flags + --cppflags print cpp flags + --includes print include information + --ldflags print linker flags + --libs print additional libraries to link against + --srcdir print APR-util source directory + --installbuilddir print APR-util build helper directory + --link-ld print link switch(es) for linking to APR-util + --apu-so-ext print the extensions of shared objects on this platform + --apu-lib-file print the name of the aprutil lib + --version print the APR-util version as a dotted triple + --help print this help + +When linking, an application should do something like: + APU_LIBS="\`apu-config --link-ld --libs\`" + +An application should use the results of --cflags, --cppflags, --includes, +and --ldflags in their build process. +EOF + +my $full = catfile $ap_dir{bin}, $file; +open(my $fh, '>', $full) or die "Cannot open $full: $!"; +print $fh <<"END"; +#!$^X +use strict; +use warnings; +use Getopt::Long; +use File::Spec::Functions qw(catfile catdir); + +$license +sub usage { + print << 'EOU'; +$apu_usage +EOU + exit(1); +} + +END + +foreach my $var (keys %apu_args) { + print $fh qq{my \${$var} = q[$apu_args{$var}];\n}; +} +print $fh $_ while ; +close $fh; + +my @args = ('pl2bat', $full); +system(@args) == 0 or die "system @args failed: $?"; +print qq{$file.bat has been created under $ap_dir{bin}.\n\n}; + +__DATA__ + +my %opts = (); +GetOptions(\%opts, + 'prefix:s', + 'bindir', + 'includedir', + 'libdir', + 'cc', + 'cpp', + 'ld', + 'cflags', + 'cppflags', + 'includes', + 'ldflags', + 'libs', + 'srcdir', + 'installbuilddir', + 'link-ld', + 'apu-so-ext', + 'apu-lib-file', + 'version', + 'help' + ) or usage(); + +usage() if ($opts{help} or not %opts); + +if (exists $opts{prefix} and $opts{prefix} eq "") { + print qq{$prefix\n}; + exit(0); +} +my $user_prefix = defined $opts{prefix} ? $opts{prefix} : ''; +my %user_dir; +if ($user_prefix) { + foreach (qw(lib bin include build)) { + $user_dir{$_} = catdir $user_prefix, $_; + } +} + +my $flags = ''; + +SWITCH : { + local $\ = "\n"; + $opts{bindir} and do { + print $user_prefix ? $user_dir{bin} : $bindir; + last SWITCH; + }; + $opts{includedir} and do { + print $user_prefix ? $user_dir{include} : $includedir; + last SWITCH; + }; + $opts{libdir} and do { + print $user_prefix ? $user_dir{lib} : $libdir; + last SWITCH; + }; + $opts{installbuilddir} and do { + print $user_prefix ? $user_dir{build} : $installbuilddir; + last SWITCH; + }; + $opts{srcdir} and do { + print $APRUTIL_SOURCE_DIR; + last SWITCH; + }; + $opts{cc} and do { + print $CC; + last SWITCH; + }; + $opts{cpp} and do { + print $CPP; + last SWITCH; + }; + $opts{ld} and do { + print $LD; + last SWITCH; + }; + $opts{cflags} and $flags .= " $CFLAGS "; + $opts{cppflags} and $flags .= " $CPPFLAGS "; + $opts{includes} and do { + my $inc = $user_prefix ? $user_dir{include} : $includedir; + $flags .= qq{ /I"$inc" $EXTRA_INCLUDES }; + }; + $opts{ldflags} and $flags .= " $LDFLAGS "; + $opts{libs} and $flags .= " $LIBS "; + $opts{'link-ld'} and do { + my $libpath = $user_prefix ? $user_dir{lib} : $libdir; + $flags .= qq{ /libpath:"$libpath" $APRUTIL_LIBNAME }; + }; + $opts{'apu-so-ext'} and do { + print $APRUTIL_SO_EXT; + last SWITCH; + }; + $opts{'apu-lib-file'} and do { + my $full_apulib = $user_prefix ? + (catfile $user_dir{lib}, $APRUTIL_LIBNAME) : + (catfile $libdir, $APRUTIL_LIBNAME); + print $full_apulib; + last SWITCH; + }; + $opts{version} and do { + print $APRUTIL_DOTTED_VERSION; + last SWITCH; + }; + print $flags if $flags; +} +exit(0); diff --git a/apxs_win32/apxs_win32 b/apxs_win32/apxs_win32 new file mode 100644 index 00000000..4ce93aaa --- /dev/null +++ b/apxs_win32/apxs_win32 @@ -0,0 +1,828 @@ +#!%perlbin% -w +# ==================================================================== +# +# Copyright 2003-2004 The Apache Software Foundation +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +# apxs script designed to allow easy command line access to Apache +# configuration parameters. + +require 5.003; +use strict; +package apxs; +use File::Copy; +use File::Spec::Functions; + +## +## Configuration +## + +my %config_vars = (); + +my $installbuilddir = '%exp_installbuilddir%'; +get_config_vars("$installbuilddir/config_vars.mk",\%config_vars); + +# read the configuration variables once + +my $prefix = get_vars('prefix'); +my $CFG_PREFIX = $prefix; +my $exec_prefix = get_vars('exec_prefix'); +my $datadir = get_vars('datadir'); +my $localstatedir = get_vars('localstatedir'); +my $CFG_TARGET = get_vars('progname'); +my $progname = get_vars('progname'); +my $CFG_SYSCONFDIR = get_vars('sysconfdir'); +my $CFG_SYSCONF = get_vars('sysconf'); +my $CFG_CFLAGS = join ' ', map { get_vars($_) } + qw(SHLTCFLAGS CFLAGS NOTEST_CPPFLAGS EXTRA_CPPFLAGS EXTRA_CFLAGS); +my $includedir = get_vars('includedir'); +my $CFG_INCLUDEDIR = $includedir; +my $libdir = get_vars('libdir'); +my $CFG_LIBDIR = $libdir; +my $CFG_CC = get_vars('CC'); +my $CFG_LD = get_vars('LD'); +my $CFG_LDFLAGS = get_vars('LDFLAGS'); +my $libexecdir = get_vars('libexecdir'); +my $CFG_LIBEXECDIR = $libexecdir; +my $sbindir = get_vars('sbindir'); +my $CFG_SBINDIR = $sbindir; +my $ltflags = $ENV{LTFLAGS}; +my $apr_libname = get_vars('APR_LIBNAME'); +my $aprutil_libname = get_vars('APRUTIL_LIBNAME'); + +$ltflags or $ltflags = '--silent'; + +my %internal_vars = map {$_ => 1} + qw(TARGET CC CFLAGS CFLAGS_SHLIB LD_SHLIB LDFLAGS_SHLIB LIBS_SHLIB + PREFIX SBINDIR INCLUDEDIR LIBEXECDIR SYSCONFDIR SYSCONF); + +my $CP = '%CP%'; +my $CHMOD = '%CHMOD%'; +my $RM_F = '%RM_F%'; +my $TOUCH = '%TOUCH%'; + +## +## parse argument line +## + +# defaults for parameters +my $opt_n = ''; +my $opt_g = ''; +my $opt_c = 0; +my $opt_o = ''; +my @opt_D = (); +my @opt_I = (); +my @opt_L = (); +my @opt_l = (); +my @opt_W = (); +my @opt_S = (); +my $opt_e = 0; +my $opt_i = 0; +my $opt_a = 0; +my $opt_A = 0; +my $opt_q = 0; +my $opt_h = 0; +my $opt_p = 0; +my $opt_v = 0; +my $opt_d = 0; + +# this subroutine is derived from Perl's getopts.pl with the enhancement of +# the "+" metacharacter at the format string to allow a list to be built by +# subsequent occurrences of the same option. +sub Getopts { + my ($argumentative, @ARGV) = @_; + my $errs = 0; + local $_; + + my @args = split / */, $argumentative; + while (@ARGV && ($_ = $ARGV[0]) =~ /^-(.)(.*)/) { + my ($first, $rest) = ($1,$2); + if ($_ =~ m|^--$|) { + shift @ARGV; + last; + } + my $pos = index($argumentative,$first); + if ($pos >= $[) { + if ($pos < $#args && $args[$pos+1] eq ':') { + shift @ARGV; + if ($rest eq '') { + unless (@ARGV) { + error("Incomplete option: $first (needs an argument)"); + $errs++; + } + $rest = shift(@ARGV); + } + eval "\$opt_$first = \$rest;"; + } + elsif ($pos < $#args && $args[$pos+1] eq '+') { + shift @ARGV; + if ($rest eq '') { + unless (@ARGV) { + error("Incomplete option: $first (needs an argument)"); + $errs++; + } + $rest = shift(@ARGV); + } + eval "push(\@opt_$first, \$rest);"; + } + else { + eval "\$opt_$first = 1"; + if ($rest eq '') { + shift(@ARGV); + } + else { + $ARGV[0] = "-$rest"; + } + } + } + else { + error("Unknown option: $first"); + $errs++; + if ($rest ne '') { + $ARGV[0] = "-$rest"; + } + else { + shift(@ARGV); + } + } + } + return ($errs == 0, @ARGV); +} + +sub usage { + print STDERR <<'END'; +Usage: apxs -g [-S =] -n + apxs -q [-v] [-S =] ... + apxs -c [-S =] [-o ] [-D [=]] + [-I ] [-L ] [-l ] [-Wc,] + [-Wl,] [-p] ... + apxs -i [-S =] [-a] [-A] [-n ] ... + apxs -e [-S =] [-a] [-A] [-n ] ... + +END + exit(1); +} + +# option handling +my $rc; +($rc, @ARGV) = &Getopts("qn:gco:I+D+L+l+W+S+eiaApvd", @ARGV); +&usage if ($rc == 0); +&usage if ($#ARGV == -1 and not $opt_g and not $opt_q); +&usage if (not $opt_q and not ($opt_g and $opt_n) + and not $opt_i and not $opt_c and not $opt_e); + +# argument handling +my @args = @ARGV; +my $name = 'unknown'; +$name = $opt_n if ($opt_n ne ''); + +if (@opt_S) { + my ($opt_S); + foreach $opt_S (@opt_S) { + if ($opt_S =~ m/^([^=]+)=(.*)$/) { + my ($var) = $1; + my ($val) = $2; + my $oldval = eval "\$CFG_$var"; + + unless ($var and $oldval) { + print STDERR "apxs:Error: no config variable $var\n"; + &usage; + } + + eval "\$CFG_${var}=\"${val}\""; + } else { + print STDERR "apxs:Error: malformatted -S option\n"; + &usage; + } + } +} + +## +## Initial shared object support check +## +my $httpd = catfile get_vars("sbindir"), get_vars("progname"); +my $envvars = catfile get_vars("sbindir"), "envvars"; + +#allow apxs to be run from the source tree, before installation +if ($0 =~ m:support/apxs$:) { + ($httpd = $0) =~ s:support/apxs$::; +} + +unless (-f $httpd) { + error("$httpd not found or not executable"); + exit 1; +} + +sub get_config_vars{ + my ($file, $rh_config) = @_; + + open IN, $file or die "cannot open $file: $!"; + while (){ + if (/^\s*(.*?)\s*=\s*(.*)$/){ + $rh_config->{$1} = $2; + } + } + close IN; +} + +sub get_vars { + my $result = ''; + my $ok = 0; + my $arg; + foreach $arg (@_) { + if (exists $config_vars{$arg} or exists $config_vars{lc $arg}) { + my $val = exists $config_vars{$arg} + ? $config_vars{$arg} + : $config_vars{lc $arg}; + $val =~ s/[()]//g; + $result .= $val if defined $val; + $result .= ";;"; + $ok = 1; + } + if (not $ok) { + if (exists $internal_vars{$arg} + or exists $internal_vars{lc $arg}) { + my $val = exists $internal_vars{$arg} ? $arg : lc $arg; + $val = eval "\$CFG_$val"; + $result .= $val if defined $val; + $result .= ";;"; + $ok = 1; + } + if (not $ok) { + error("Invalid query string `$arg'"); + exit(1); + } + } + } + $result =~ s|;;$||; + # $result =~ s|:| |; + return $result; +} + +## +## Operation +## + +# helper function for executing a list of +# system command with return code checks +sub execute_cmds { + my (@cmds) = @_; + my ($cmd, $rc); + + foreach $cmd (@cmds) { + notice($cmd); + $rc = system $cmd; + if ($rc) { + error(sprintf "Command failed with rc=%d\n", $rc << 8); + exit 1 ; + } + } +} + +if ($opt_g) { + ## + ## SAMPLE MODULE SOURCE GENERATION + ## + + if (-d $name) { + error("Directory `$name' already exists. Remove first"); + exit(1); + } + + my $data = join('', ); + $data =~ s!__END__.*!!s; + $data =~ s|%NAME%|$name|sg; + $data =~ s|%PROGNAME%|$progname|sg; + $data =~ s|%SYSCONF%|$CFG_SYSCONF|sg; + $data =~ s|%PREFIX%|$prefix|sg; + $data =~ s|%INSTALLBUILDDIR%|$installbuilddir|sg; + + my ($mkf, $src) = ($data =~ m|^(.+)-=\#=-\n(.+)|s); + + notice("Creating [DIR] $name"); + mkdir $name or die "Cannot mkdir $name: $!"; + notice("Creating [FILE] $name/Makefile"); + open(FP, ">${name}/Makefile") or die "Cannot open ${name}/Makefile: $!"; + print FP $mkf; + close(FP); + notice("Creating [FILE] $name/mod_$name.c"); + open(FP, ">${name}/mod_${name}.c") || die; + print FP $src; + close(FP); + notice("Creating [FILE] $name/.deps"); + open(FP, ">${name}/.deps") or die "Cannot open ${name}/.deps: $!"; + close(FP); + + exit(0); +} + +if ($opt_q) { + ## + ## QUERY INFORMATION + ## + my $result; + if ($#args >= 0) { + $result = get_vars(@args); + print "$result\n"; + } else { + # -q without var name prints all variables and their values + + # Additional -v pretty-prints output + if ($opt_v) { + # Variable names in alphabetic order + my @vars = sort {uc($a) cmp uc($b)} keys %config_vars; + + # Make the left column as wide as the longest variable name + my $width = 0; + foreach (@vars) { + my $l = length $_; + $width = $l unless ($l <= $width); + } + + foreach (@vars) { + printf "%-${width}s = %s\n", $_, $config_vars{$_}; + } + } else { + # Unprettified name=value list + foreach (keys %config_vars) { + print "$_=$config_vars{$_}\n"; + } + } + } +} + +my $apr_bindir = get_vars("APR_BINDIR"); +my $apu_bindir = get_vars("APU_BINDIR"); + +my $apr_includedir = qq{-I"$prefix/include"}; +my $apu_includedir = qq{-I$"prefix/include"}; + +if ($opt_c) { + ## + ## SHARED OBJECT COMPILATION + ## + + # split files into sources and objects + my @srcs = (); + my @objs = (); + my $f; + foreach $f (@args) { + if ($f =~ m|\.c$|) { + push(@srcs, $f); + } + else { + push(@objs, $f); + } + } + + # determine output file + my $dso_file; + if ($opt_o eq '') { + if ($#srcs > -1) { + $dso_file = $srcs[0]; + $dso_file =~ s|\.[^.]+$|.so|; + } + elsif ($#objs > -1) { + $dso_file = $objs[0]; + $dso_file =~ s|\.[^.]+$|.so|; + } + else { + $dso_file = "mod_unknown.so"; + } + } + else { + $dso_file = $opt_o; + } + + # create compilation commands + my @cmds = (); + my $opt = ''; + my ($opt_Wc, $opt_I, $opt_D); + foreach $opt_Wc (@opt_W) { + $opt .= "$1 " if ($opt_Wc =~ m|^\s*c,(.*)$|); + } + foreach $opt_I (@opt_I) { + $opt .= qq{ /I"$opt_I" }; + } + foreach $opt_D (@opt_D) { + $opt .= qq{ /D "$opt_D" }; + } + my $cflags = "$CFG_CFLAGS"; + if ($opt_d) { + $cflags =~ s!NDEBUG!DEBUG!; + $cflags .= ' /Zi'; + $cflags =~ s!/MD !/MDd !; + } + my $s; + my $mod; + foreach $s (@srcs) { + my $slo = $s; + $slo =~ s|\.c$|.slo|; + my $lo = $s; + $lo =~ s|\.c$|.lo|; + my $la = $s; + $la =~ s|\.c$|.la|; + my $o = $s; + $o =~ s|\.c$|.o|; + push(@cmds, qq{$CFG_CC $cflags -I"$CFG_INCLUDEDIR" $opt /c /Fo$lo $s}); + unshift(@objs, $lo); + } + + # create link command + my $o; + my $lo; + $opt = ''; + foreach $o (@objs) { + $lo .= " $o"; + } + my ($opt_Wl, $opt_L, $opt_l); + foreach $opt_Wl (@opt_W) { + if ($CFG_CC !~ m/gcc$/) { + $opt .= " $1" if ($opt_Wl =~ m|^\s*l,(.*)$|); + } else { + $opt .= " -W$opt_Wl"; + } + } + foreach $opt_L (@opt_L) { + $opt .= qq{ /libpath:"$opt_L" }; + } + foreach $opt_l (@opt_l) { + $opt_l .= '.lib' unless ($opt_l =~ /\.lib$/); + $opt .= " $opt_l"; + } + + if ($opt_p == 1) { + $opt .= " ".$aprutil_libname." ".$apr_libname; + } + else { + my $apr_ldflags; + $opt .= " $apr_ldflags"; + } + my $ldflags = "$CFG_LDFLAGS"; + if ($opt_d) { + $ldflags .= ' /debug'; + } + push(@cmds, "$CFG_LD $ldflags /out:$dso_file $opt $lo"); + + my $manifest = $dso_file . '.manifest'; + push(@cmds, "if exist $manifest mt.exe /manifest $manifest /outputresource:$dso_file;#2"); + + # execute the commands + &execute_cmds(@cmds); + + # allow one-step compilation and installation + if ($opt_i or $opt_e) { + @args = ( $dso_file ); + } +} + +if ($opt_i or $opt_e) { + ## + ## SHARED OBJECT INSTALLATION + ## + unless (-d $CFG_LIBEXECDIR) { + die "Directory $CFG_LIBEXECDIR not found"; + } + # determine installation commands + # and corresponding LoadModule/AddModule directives + my @lmd = (); + my @amd = (); + my @cmds = (); + my $f; + foreach $f (@args) { + my $end = qr{(\.so|\.la)$}; + if ($f !~ m!$end!) { + error("file $f is not a shared object"); + exit(1); + } + my $t = $f; + $t =~ s|^.+/([^/]+)$|$1|; + $t =~ s|\.la$|\.so|; + (my $libf = $f) =~ s!$end!.lib!; + (my $libt = $t) =~ s!$end!.lib!; + (my $pdbf = $f) =~ s!$end!.pdb!; + (my $pdbt = $t) =~ s!$end!.pdb!; + + if ($opt_i) { + push(@cmds, "$CP $f $CFG_LIBEXECDIR"); + push(@cmds, "$CHMOD 755 $CFG_LIBEXECDIR\\$t"); + if (-f $libf) { + push(@cmds, "$CP $libf $CFG_LIBDIR"); + push(@cmds, "$CHMOD 755 $CFG_LIBDIR\\$libt"); + } + if ($opt_d and -f $pdbf) { + push(@cmds, "$CP $pdbf $CFG_LIBEXECDIR"); + push(@cmds, "$CHMOD 755 $CFG_LIBEXECDIR\\$pdbt"); + } + } + + # determine module symbolname and filename + my $filename = ''; + if ($name eq 'unknown') { + $name = ''; + my $base = $f; + $base =~ s|\.[^.]+$||; + if (-f "$base.c") { + open(FP, "<$base.c"); + my $content = join('', ); + close(FP); + if ($content =~ m|.*module\s+(?:AP_MODULE_DECLARE_DATA\s+)?([a-zA-Z0-9_]+)_module\s*=\s*.*|s) { + $name = "$1"; + $filename = "$base.c"; + $filename =~ s|^[^/]+/||; + } + } + if ($name eq '') { + if ($base =~ m|.*mod_([a-zA-Z0-9_]+)\..+|) { + $name = "$1"; + $filename = $base; + $filename =~ s|^[^/]+/||; + } + } + if ($name eq '') { + error("Sorry, cannot determine bootstrap symbol name"); + error("Please specify one with option `-n'"); + exit(1); + } + } + if ($filename eq '') { + $filename = "mod_${name}.c"; + } + my $dir = $CFG_LIBEXECDIR; + $dir =~ s|^$CFG_PREFIX/?||; + $dir =~ s|(.)$|$1/|; + $dir =~ s|\\|/|g; + $t =~ s|\.la$|.so|; + push(@lmd, + sprintf("LoadModule %-18s %s", "${name}_module", qq{"$dir$t"})); + push(@amd, sprintf("AddModule %s", $filename)); + } + + # execute the commands + &execute_cmds(@cmds); + + # activate module via LoadModule/AddModule directive + if ($opt_a or $opt_A) { + if (not -f "$CFG_SYSCONFDIR/$CFG_SYSCONF") { + error("Config file $CFG_SYSCONFDIR/$CFG_SYSCONF not found"); + exit(1); + } + + open(FP, "<$CFG_SYSCONFDIR/$CFG_SYSCONF") + || die "Cannot open $CFG_SYSCONFDIR/$CFG_SYSCONF: $!"; + my $content = join('', ); + close(FP); + + if ($content !~ m|\n\#?\s*LoadModule\s+|) { + error("Activation failed for custom $CFG_SYSCONFDIR/$CFG_SYSCONF file."); + error("At least one `LoadModule' directive already has to exist."); + exit(1); + } + + my $lmd; + my $c = ''; + $c = '#' if ($opt_A); + foreach $lmd (@lmd) { + my $what = $opt_A ? "preparing" : "activating"; + if ($content !~ m|\n\#?\s*$lmd|) { + # check for open , so that the new LoadModule + # directive always appears *outside* of an . + + my $before = + ($content =~ m|^(.*\n)\#?\s*LoadModule\s+[^\n]+\n|s)[0]; + + # the '()=' trick forces list context and the scalar + # assignment counts the number of list members (aka number + # of matches) then + my $cntopen = () = ($before =~ m|^\s*<[^/].*$|mg); + my $cntclose = () = ($before =~ m|^\s*', $conf_new)) { + print FP $content; + close(FP); + copy($conf, $conf_bak) or + die "Backup of $conf failed: $!"; + copy($conf_new, $conf) or + die "Copying $conf_new to $conf failed: $!"; + unlink $conf_new or + die "Removing $conf_new failed: $!"; + } + else { + notice("unable to open configuration file $conf_new"); + } + } + } +} + +sub error{ + print STDERR "apxs:Error: $_[0].\n"; +} + +sub notice{ + print STDERR "$_[0]\n"; +} + +##EOF## +__DATA__ +## +## Makefile -- Build procedure for sample %NAME% Apache module +## Autogenerated via ``apxs -n %NAME% -g''. +## + +builddir=. +top_srcdir=%PREFIX% +top_builddir=%PREFIX% + +# the used tools +APXS=apxs +APACHECTL=%PROGNAME% -k + +# additional defines, includes and libraries +#DEFS=-Dmy_define=my_value +#INCLUDES=-Imy/include/dir +#LIBS=-Lmy/lib/dir -lmylib + +# the default target +all: local-shared-build + +# install the shared object file into Apache +install: install-modules + +# cleanup +clean: + -@erase mod_%NAME%.lo mod_%NAME%.ilk mod_%NAME%.so mod_%NAME%.lib mod_%NAME%.exp mod_%NAME%.pdb + +# simple test +test: reload + GET http://localhost/%NAME% + +# install and activate shared object by reloading Apache to +# force a reload of the shared object file +reload: install restart + +# the general Apache start/restart/stop +# procedures +start: + $(APACHECTL) start +restart: + $(APACHECTL) restart +stop: + $(APACHECTL) stop + +-=#=- +/* +** mod_%NAME%.c -- Apache sample %NAME% module +** [Autogenerated via ``apxs -n %NAME% -g''] +** +** To play with this sample module first compile it into a +** DSO file and install it into Apache's modules directory +** by running: +** +** $ apxs -c -i mod_%NAME%.c +** +** Then activate it in Apache's %SYSCONF% file for instance +** for the URL /%NAME% in as follows: +** +** # %SYSCONF% +** LoadModule %NAME%_module modules/mod_%NAME%.so +** +** SetHandler %NAME% +** +** +** Then after restarting Apache via +** +** $ apachectl restart +** +** you immediately can request the URL /%NAME% and watch for the +** output of this module. This can be achieved for instance via: +** +** $ lynx -mime_header http://localhost/%NAME% +** +** The output should be similar to the following one: +** +** HTTP/1.1 200 OK +** Date: Tue, 31 Mar 1998 14:42:22 GMT +** Server: Apache/1.3.4 (Unix) +** Connection: close +** Content-Type: text/html +** +** The sample page from mod_%NAME%.c +*/ + +#include "httpd.h" +#include "http_config.h" +#include "http_protocol.h" +#include "ap_config.h" + +/* The sample content handler */ +static int %NAME%_handler(request_rec *r) +{ + if (strcmp(r->handler, "%NAME%")) { + return DECLINED; + } + r->content_type = "text/html"; + + if (!r->header_only) + ap_rputs("The sample page from mod_%NAME%.c\n", r); + return OK; +} + +static void %NAME%_register_hooks(apr_pool_t *p) +{ + ap_hook_handler(%NAME%_handler, NULL, NULL, APR_HOOK_MIDDLE); +} + +/* Dispatch list for API hooks */ +module AP_MODULE_DECLARE_DATA %NAME%_module = { + STANDARD20_MODULE_STUFF, + NULL, /* create per-dir config structures */ + NULL, /* merge per-dir config structures */ + NULL, /* create per-server config structures */ + NULL, /* merge per-server config structures */ + NULL, /* table of config file commands */ + %NAME%_register_hooks /* register hooks */ +}; diff --git a/apxs_win32/apxs_win32.pl b/apxs_win32/apxs_win32.pl new file mode 100644 index 00000000..b932dd04 --- /dev/null +++ b/apxs_win32/apxs_win32.pl @@ -0,0 +1,230 @@ +#!C:/Perl/bin/perl +use strict; +use warnings; +use Getopt::Long; +require Win32; +use Config; +use ExtUtils::MakeMaker; +use File::Spec::Functions; +require 'util.pl'; +my ($apache, $help, $progname); +GetOptions( 'with-apache2=s' => \$apache, + 'with-apache-prog=s' => \$progname, + 'help' => \$help, + ) or usage($0); +usage($0) if $help; + +unless (defined $apache and -d $apache) { + $apache = prompt("Please give the path to your Apache2 installation:", + $apache); +} +die "Can't find a suitable Apache2 installation!" + unless (-d $apache and check_httpd($apache, $progname)); + +$apache = Win32::GetShortPathName($apache); + +my $perl = which('perl'); +my %subs_cfg = ( + '%APACHE2%' => $apache, + '%PROGNAME%' => $progname, + '%AWK%' => which('awk') || which('gawk') || '', + '%CC%' => $Config{cc}, + '%CPP%' => $Config{cpp}, + '%SHELL%' => $ENV{COMSPEC}, + '%LD%' => $Config{ld}, + ); + +my $pat = join '|', keys %subs_cfg; +my $build_dir = catdir $apache, 'build'; +my $cfg_mk = catfile $build_dir, 'config_vars.mk'; +unless (-d $build_dir) { + mkdir $build_dir or die "Cannot mkdir $build_dir: $!"; +} + +my $prefix = $apache; +my $exec_prefix = $prefix; +my $datadir = ${prefix}; +my $localstatedir = ${prefix}; + +my ($aprutil_libname, $apr_libname); +my $libdir = catdir $exec_prefix, 'lib'; +opendir(my $apr_dir, $libdir) or die "Cannot opendir $libdir: $!"; +my @libs = readdir $apr_dir; +closedir $apr_dir; +foreach (@libs) { + if (/^libaprutil\b\S+lib$/) { + $aprutil_libname = $_; + next; + } + if (/^libapr\b\S+lib$/) { + $apr_libname = $_; + next; + } +} +die "Cannot determine apr lib names" + unless ($aprutil_libname and $apr_libname); + +my %dirs = (prefix => $prefix, + exec_prefix => $exec_prefix, + datadir => $datadir, + localstatedir => $localstatedir, + bindir => catdir($exec_prefix, 'bin'), + sbindir => catdir($exec_prefix, 'bin'), + cgidir => catdir($datadir, 'cgi-bin'), + logfiledir => catdir($localstatedir, 'logs'), + mandir => catdir($prefix, 'man'), + libdir => $libdir, + libexecdir => catdir($exec_prefix, 'modules'), + htdocsdir => catdir($datadir, 'htdocs'), + manualdir => catdir($datadir, 'manual'), + includedir => catdir($prefix, 'include'), + errordir => catdir($datadir, 'error'), + iconsdir => catdir($datadir, 'icons'), + sysconfdir => catdir($prefix, 'conf'), + installbuilddir => catdir($datadir, 'build'), + runtimedir => catdir($localstatedir, 'logs'), + proxycachedir => catdir($localstatedir, 'proxy'), + APR_BINDIR => catdir($apache, 'bin'), + APU_BINDIR => catdir($apache, 'bin'), + APR_INCLUDEDIR => catdir($apache, 'include'), + APU_INCLUDEDIR => catdir($apache, 'include'), + APRUTIL_LIBNAME => catfile($libdir, $aprutil_libname), + APR_LIBNAME => catfile($libdir, $apr_libname), + ); + +open(my $cfg, ">$cfg_mk") + or die qq{Cannot open $cfg_mk: $!}; +while () { + if (/^rel_(\S+) = (\S+)/) { + my $dir = $1; next unless $dir; + my $val = $2; + print $cfg $_; + print $cfg "exp_$dir = ", catdir($apache, $val), $/; + next; + } + s/($pat)/$subs_cfg{$1}/; + print $cfg $_; +} +foreach (keys %dirs) { + print $cfg "$_ = $dirs{$_}\n"; +} +close $cfg; + +my %subs_apxs = ( + '%perlbin%' => which('perl'), + '%exp_installbuilddir%' => $build_dir, + '%RM_F%' => qq{$perl -MExtUtils::Command -e rm_f}, + '%CP%' => qq{$perl -MExtUtils::Command -e cp}, + '%CHMOD%' => qq{$perl -MExtUtils::Command -e chmod}, + '%TOUCH%' => qq{$perl -MExtUtils::Command -e touch}, + ); +$pat = join '|', keys %subs_apxs; +my $apxs_out = catfile $apache, 'bin', 'apxs.pl'; +my $apxs_in = 'apxs_win32'; +open(my $out, ">$apxs_out") + or die "Cannot open $apxs_out: $!"; +open(my $in, $apxs_in) + or die "Cannot open $apxs_in: $!"; +while (<$in>) { + s/($pat)/$subs_apxs{$1}/; + print $out $_; +} +close $in; +close $out; + +system ('pl2bat', $apxs_out) == 0 + or die "system pl2bat $apxs_out failed: $?"; +print qq{\napxs.bat has been created under $apache\\bin.\n\n}; + +__DATA__ +exp_exec_prefix = %APACHE2% +rel_exec_prefix = +rel_bindir = bin +rel_sbindir = bin +rel_libdir = lib +rel_libexecdir = modules +rel_sysconfdir = conf +rel_datadir = +rel_installbuilddir = build +rel_errordir = error +rel_iconsdir = icons +rel_htdocsdir = htdocs +rel_manualdir = manual +rel_cgidir = cgi-bin +rel_includedir = include +rel_localstatedir = +rel_runtimedir = logs +rel_logfiledir = logs +rel_proxycachedir = proxy +SHLTCFLAGS = +LTCFLAGS = +MPM_NAME = winnt +MPM_SUBDIR_NAME = winnt +htpasswd_LTFLAGS = +htdigest_LTFLAGS = +rotatelogs_LTFLAGS = +logresolve_LTFLAGS = +htdbm_LTFLAGS = +ab_LTFLAGS = +checkgid_LTFLAGS = +APACHECTL_ULIMIT = +progname = %PROGNAME% +MPM_LIB = server/mpm/winnt/ +OS = win32 +OS_DIR = win32 +BUILTIN_LIBS = +SHLIBPATH_VAR = +OS_SPECIFIC_VARS = +PRE_SHARED_CMDS = +POST_SHARED_CMDS = +shared_build = +AP_LIBS = +AP_BUILD_SRCLIB_DIRS = apr apr-util +AP_CLEAN_SRCLIB_DIRS = apr-util apr +abs_srcdir = +sysconf = httpd.conf +other_targets = +unix_progname = httpd +prefix = %APACHE2% +AWK = %AWK% +CC = %CC% +LD = %LD% +CPP = %CPP% +CXX = +CPPFLAGS = +CFLAGS = /nologo /MD /W3 /O2 /D WIN32 /D _WINDOWS /D NDEBUG +CXXFLAGS = +LTFLAGS = +LDFLAGS = kernel32.lib /nologo /subsystem:windows /dll /libpath:"%APACHE2%\lib" +LT_LDFLAGS = +SH_LDFLAGS = +HTTPD_LDFLAGS = +UTIL_LDFLAGS = +LIBS = +DEFS = +INCLUDES = +NOTEST_CPPFLAGS = +NOTEST_CFLAGS = +NOTEST_CXXFLAGS = +NOTEST_LDFLAGS = +NOTEST_LIBS = +EXTRA_CPPFLAGS = +EXTRA_CFLAGS = +EXTRA_CXXFLAGS = +EXTRA_LDFLAGS = +EXTRA_LIBS = +EXTRA_INCLUDES = +LIBTOOL = +SHELL = %SHELL% +MODULE_DIRS = aaa filters loggers metadata proxy http generators mappers +MODULE_CLEANDIRS = arch/win32 cache echo experimental ssl test dav/main dav/fs +PORT = 80 +nonssl_listen_stmt_1 = +nonssl_listen_stmt_2 = Listen @@Port@@ +CORE_IMPLIB_FILE = +CORE_IMPLIB = +SH_LIBS = +SH_LIBTOOL = +MK_IMPLIB = +INSTALL_PROG_FLAGS = +DSO_MODULES = diff --git a/apxs_win32/util.pl b/apxs_win32/util.pl new file mode 100644 index 00000000..41f0fc97 --- /dev/null +++ b/apxs_win32/util.pl @@ -0,0 +1,84 @@ +use File::Spec::Functions; + +sub usage { + my $script = shift; + print <<"END"; + + Usage: perl $script [--with-apache2=C:\Path\to\Apache2] + perl $script [--with-apache-prog=httpd.exe] + perl $script --help + +Options: + + --with-apache2=C:\Path\to\Apache2 : specify the top-level Apache2 directory + --with-apache-prog=Apache.exe : specify the Apache2 program name + --help : print this help message + +With no options specified, an attempt will be made to find a suitable +Apache2 directory with a program name of "Apache.exe". + +END + exit; +} + +sub check_httpd { + my ($apache, $progname) = @_; + + die qq{No libhttpd library found under $apache/lib} + unless -e qq{$apache/lib/libhttpd.lib}; + + die qq{No httpd header found under $apache/include} + unless -e qq{$apache/include/httpd.h}; + + my $vers = qx{"$apache/bin/$progname" -v}; + die qq{"$apache" does not appear to be version 2} + unless $vers =~ m!Apache/2!; + + return 1; +} + +sub check_apr { + (my $prefix) = @_; + my ($dir); + + my $lib = catdir $prefix, 'lib'; + opendir($dir, $lib) or die qq{Cannot opendir $lib: $!}; + my @libs = grep /^libapr\b\S+lib$/, readdir $dir; + closedir $dir; + die qq{Unable to find apr lib beneath $lib} unless (scalar @libs > 0); + + die qq{No apr.h header found under $prefix/include} + unless -e qq{$prefix/include/apr.h}; + + my $bin = catdir $prefix, 'bin'; + opendir($dir, $bin) or die qq{Cannot opendir $bin: $!}; + my @bins = grep /^libapr\b\S+dll$/, readdir $dir; + closedir $dir; + die qq{Unable to find apr dll beneath $bin} unless (scalar @bins > 0); + + return 1; +} + +sub check_apu { + (my $prefix) = @_; + my ($dir); + + my $lib = catdir $prefix, 'lib'; + opendir($dir, $lib) or die qq{Cannot opendir $lib: $!}; + my @libs = grep /^libaprutil\b\S+lib$/, readdir $dir; + closedir $dir; + die qq{Unable to find aprutil lib beneath $lib} unless (scalar @libs > 0); + + die qq{No apu.h header found under $prefix/include} + unless -e qq{$prefix/include/apu.h}; + + my $bin = catdir $prefix, 'bin'; + opendir($dir, $bin) or die qq{Cannot opendir $bin: $!}; + my @bins = grep /^libaprutil\b\S+dll$/, readdir $dir; + closedir $dir; + die qq{Unable to find aprutil dll beneath $bin} unless (scalar @bins > 0); + + return 1; +} + +1; diff --git a/httpd-2.4.54-win64-VS16.zip b/httpd-2.4.54-win64-VS16.zip new file mode 100644 index 00000000..56f5a0c9 Binary files /dev/null and b/httpd-2.4.54-win64-VS16.zip differ