diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/tools/msvc/Genbki.pm | 264 | ||||
-rw-r--r-- | src/tools/msvc/Install.pm | 208 | ||||
-rw-r--r-- | src/tools/msvc/Mkvcbuild.pm | 455 | ||||
-rw-r--r-- | src/tools/msvc/README | 2 | ||||
-rw-r--r-- | src/tools/msvc/Solution.pm | 9 | ||||
-rwxr-xr-x | src/tools/msvc/install.pl | 193 | ||||
-rw-r--r-- | src/tools/msvc/mkvcbuild.pl | 432 | ||||
-rw-r--r-- | src/tools/msvc/vcregress.bat | 2 |
8 files changed, 943 insertions, 622 deletions
diff --git a/src/tools/msvc/Genbki.pm b/src/tools/msvc/Genbki.pm new file mode 100644 index 00000000000..20a9881078b --- /dev/null +++ b/src/tools/msvc/Genbki.pm @@ -0,0 +1,264 @@ +#!/usr/bin/perl +#------------------------------------------------------------------------- +# +# Genbki.pm -- +# perl script which generates .bki files from specially formatted .h +# files. These .bki files are used to initialize the postgres template +# database. +# +# Portions Copyright (c) 1996-2007, PostgreSQL Global Development Group +# Portions Copyright (c) 1994, Regents of the University of California +# +# +# IDENTIFICATION +# $PostgreSQL: pgsql/src/tools/msvc/Genbki.pm,v 1.1 2007/03/17 13:50:42 mha Exp $ +# +#------------------------------------------------------------------------- + +package Genbki; + +use strict; +use warnings; + +use Exporter; +our (@ISA, @EXPORT_OK); +@ISA = qw(Exporter); +@EXPORT_OK = qw(genbki); + +sub genbki +{ + my $version = shift; + my $prefix = shift; + + $version =~ /^(\d+\.\d+)/ || die "Bad format verison $version\n"; + my $majorversion = $1; + + my $pgext = read_file("src/include/pg_config_manual.h"); + $pgext =~ /^#define\s+NAMEDATALEN\s+(\d+)$/mg + || die "Could not read NAMEDATALEN from pg_config_manual.h\n"; + my $namedatalen = $1; + + my $pgauthid = read_file("src/include/catalog/pg_authid.h"); + $pgauthid =~ /^#define\s+BOOTSTRAP_SUPERUSERID\s+(\d+)$/mg + || die "Could not read BOOTSTRAUP_SUPERUSERID from pg_authid.h\n"; + my $bootstrapsuperuserid = $1; + + my $pgnamespace = read_file("src/include/catalog/pg_namespace.h"); + $pgnamespace =~ /^#define\s+PG_CATALOG_NAMESPACE\s+(\d+)$/mg + || die "Could not read PG_CATALOG_NAMESPACE from pg_namespace.h\n"; + my $pgcatalognamespace = $1; + + my $indata = ""; + + while (@_) + { + my $f = shift; + next unless $f; + $indata .= read_file($f); + $indata .= "\n"; + } + + # Strip C comments, from perl FAQ 4.27 + $indata =~ s{/\*.*?\*/}{}gs; + + $indata =~ s{;\s*$}{}gm; + $indata =~ s{^\s+}{}gm; + $indata =~ s{^Oid}{oid}gm; + $indata =~ s{\(Oid}{(oid}gm; + $indata =~ s{^NameData}{name}gm; + $indata =~ s{\(NameData}{(name}g; + $indata =~ s{^TransactionId}{xid}gm; + $indata =~ s{\(TransactionId}{(xid}g; + $indata =~ s{PGUID}{$bootstrapsuperuserid}g; + $indata =~ s{NAMEDATALEN}{$namedatalen}g; + $indata =~ s{PGNSP}{$pgcatalognamespace}g; + + #print $indata; + + my $bki = ""; + my $desc = ""; + my $shdesc = ""; + + my $oid = 0; + my $catalog = 0; + my $reln_open = 0; + my $bootstrap = ""; + my $shared_relation = ""; + my $without_oids = ""; + my $nc = 0; + my $inside = 0; + my @attr; + my @types; + + foreach my $line (split /\n/, $indata) + { + if ($line =~ /^DATA\((.*)\)$/m) + { + my $data = $1; + my @fields = split /\s+/,$data; + if ($#fields >=4 && $fields[0] eq "insert" && $fields[1] eq "OID" && $fields[2] eq "=") + { + $oid = $fields[3]; + } + else + { + $oid = 0; + } + $data =~ s/\s{2,}/ /g; + $bki .= $data . "\n"; + } + elsif ($line =~ /^DESCR\("(.*)"\)$/m) + { + if ($oid != 0) + { + $desc .= sprintf("%d\t%s\t0\t%s\n", $oid, $catalog, $1); + } + } + elsif ($line =~ /^SHDESCR\("(.*)"\)$/m) + { + if ($oid != 0) + { + $shdesc .= sprintf("%d\t%s\t%s\n", $oid, $catalog, $1); + } + } + elsif ($line =~ /^DECLARE_(UNIQUE_)?INDEX\((.*)\)$/m) + { + if ($reln_open) + { + $bki .= "close $catalog\n"; + $reln_open = 0; + } + my $u = $1?" unique":""; + my @fields = split /,/,$2,3; + $fields[2] =~ s/\s{2,}/ /g; + $bki .= "declare$u index $fields[0] $fields[1] $fields[2]\n"; + } + elsif ($line =~ /^DECLARE_TOAST\((.*)\)$/m) + { + if ($reln_open) + { + $bki .= "close $catalog\n"; + $reln_open = 0; + } + my @fields = split /,/,$1; + $bki .= "declare toast $fields[1] $fields[2] on $fields[0]\n"; + } + elsif ($line =~ /^BUILD_INDICES/) + { + $bki .= "build indices\n"; + } + elsif ($line =~ /^CATALOG\((.*)\)(.*)$/m) + { + if ($reln_open) + { + $bki .= "close $catalog\n"; + $reln_open = 0; + } + my $rest = $2; + my @fields = split /,/,$1; + $catalog = $fields[0]; + $oid = $fields[1]; + $bootstrap=$shared_relation=$without_oids=""; + if ($rest =~ /BKI_BOOTSTRAP/) + { + $bootstrap = "bootstrap "; + } + if ($rest =~ /BKI_SHARED_RELATION/) + { + $shared_relation = "shared_relation "; + } + if ($rest =~ /BKI_WITHOUT_OIDS/) + { + $without_oids = "without_oids "; + } + $nc++; + $inside = 1; + next; + } + if ($inside==1) + { + next if ($line =~ /{/); + if ($line =~ /}/) + { + + # Last line + $bki .= "create $bootstrap$shared_relation$without_oids$catalog $oid\n (\n"; + my $first = 1; + for (my $i = 0; $i <= $#attr; $i++) + { + if ($first == 1) + { + $first = 0; + } + else + { + $bki .= ",\n"; + } + $bki .= " " . $attr[$i] . " = " . $types[$i]; + } + $bki .= "\n )\n"; + undef(@attr); + undef(@types); + $reln_open = 1; + $inside = 0; + if ($bootstrap eq "") + { + $bki .= "open $catalog\n"; + } + next; + } + + # inside catalog definition, so keep sucking up attributes + my @fields = split /\s+/,$line; + if ($fields[1] =~ /(.*)\[.*\]/) + { #Array attribute + push @attr, $1; + push @types, $fields[0] . '[]'; + } + else + { + push @attr, $fields[1]; + push @types, $fields[0]; + } + next; + } + } + if ($reln_open == 1) + { + $bki .= "close $catalog\n"; + } + + open(O,">$prefix.bki") || die "Could not write $prefix.bki\n"; + print O "# PostgreSQL $majorversion\n"; + print O $bki; + close(O); + open(O,">$prefix.description") || die "Could not write $prefix.description\n"; + print O $desc; + close(O); + open(O,">$prefix.shdescription") || die "Could not write $prefix.shdescription\n"; + print O $shdesc; + close(O); +} + +sub Usage +{ + print "Usage: genbki.pl <version> <prefix> <input1> [<input2> <input3>...]\n"; + exit(1); +} + +sub read_file +{ + my $filename = shift; + my $F; + my $t = $/; + + undef $/; + open($F, $filename) || die "Could not open file $filename\n"; + my $txt = <$F>; + close($F); + $/ = $t; + + return $txt; +} + +1; diff --git a/src/tools/msvc/Install.pm b/src/tools/msvc/Install.pm new file mode 100644 index 00000000000..0b7a9b1983f --- /dev/null +++ b/src/tools/msvc/Install.pm @@ -0,0 +1,208 @@ +package Install; + +use strict; +use warnings; +use Carp; +use File::Basename; +use File::Copy; + +use Exporter; +our (@ISA,@EXPORT_OK); +@ISA = qw(Exporter); +@EXPORT_OK = qw(Install); + +sub Install +{ + $| = 1; + + my $target = shift; + + chdir("../../..") if (-f "../../../configure"); + my $conf = ""; + if (-d "debug") + { + $conf = "debug"; + } + if (-d "release") + { + $conf = "release"; + } + die "Could not find debug or release binaries" if ($conf eq ""); + print "Installing for $conf\n"; + + EnsureDirectories($target, 'bin','lib','share','share/timezonesets'); + + CopySolutionOutput($conf, $target); + copy($target . '/lib/libpq.dll', $target . '/bin/libpq.dll'); + CopySetOfFiles('config files', "*.sample", $target . '/share/'); + CopySetOfFiles('timezone names', 'src\timezone\tznames\*.txt',$target . '/share/timezonesets/'); + CopyFiles( + 'timezone sets', + $target . '/share/timezonesets/', + 'src/timezone/tznames/', 'Default','Australia','India' + ); + CopySetOfFiles('BKI files', "src\\backend\\catalog\\postgres.*", $target .'/share/'); + CopySetOfFiles('SQL files', "src\\backend\\catalog\\*.sql", $target . '/share/'); + CopyFiles( + 'Information schema data', + $target . '/share/', + 'src/backend/catalog/', 'sql_features.txt' + ); + GenerateConversionScript($target); + GenerateTimezoneFiles($target,$conf); +} + +sub EnsureDirectories +{ + my $target = shift; + mkdir $target unless -d ($target); + while (my $d = shift) + { + mkdir $target . '/' . $d unless -d ($target . '/' . $d); + } +} + +sub CopyFiles +{ + my $what = shift; + my $target = shift; + my $basedir = shift; + + print "Copying $what"; + while (my $f = shift) + { + print "."; + $f = $basedir . $f; + die "No file $f\n" if (!-f $f); + copy($f, $target . basename($f)) + || croak "Could not copy $f to $target". basename($f). " to $target". basename($f) . "\n"; + } + print "\n"; +} + +sub CopySetOfFiles +{ + my $what = shift; + my $spec = shift; + my $target = shift; + my $D; + + print "Copying $what"; + open($D, "dir /b /s $spec |") || croak "Could not list $spec\n"; + while (<$D>) + { + chomp; + next if /regress/; # Skip temporary install in regression subdir + my $tgt = $target . basename($_); + print "."; + copy($_, $tgt) || croak "Could not copy $_: $!\n"; + } + close($D); + print "\n"; +} + +sub CopySolutionOutput +{ + my $conf = shift; + my $target = shift; + my $rem = qr{Project\("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}"\) = "([^"]+)"}; + + my $sln = read_file("pgsql.sln") || croak "Could not open pgsql.sln\n"; + print "Copying build output files..."; + while ($sln =~ $rem) + { + my $pf = $1; + my $dir; + my $ext; + + $sln =~ s/$rem//; + + my $proj = read_file("$pf.vcproj") || croak "Could not open $pf.vcproj\n"; + if ($proj !~ qr{ConfigurationType="([^"]+)"}) + { + croak "Could not parse $pf.vcproj\n"; + } + if ($1 == 1) + { + $dir = "bin"; + $ext = "exe"; + } + elsif ($1 == 2) + { + $dir = "lib"; + $ext = "dll"; + } + else + { + + # Static lib, such as libpgport, only used internally during build, don't install + next; + } + copy("$conf\\$pf\\$pf.$ext","$target\\$dir\\$pf.$ext") || croak "Could not copy $pf.$ext\n"; + print "."; + } + print "\n"; +} + +sub GenerateConversionScript +{ + my $target = shift; + my $sql = ""; + my $F; + + print "Generating conversion proc script..."; + my $mf = read_file('src/backend/utils/mb/conversion_procs/Makefile'); + $mf =~ s{\\\s*[\r\n]+}{}mg; + $mf =~ /^CONVERSIONS\s*=\s*(.*)$/m + || die "Could not find CONVERSIONS line in conversions Makefile\n"; + my @pieces = split /\s+/,$1; + while ($#pieces > 0) + { + my $name = shift @pieces; + my $se = shift @pieces; + my $de = shift @pieces; + my $func = shift @pieces; + my $obj = shift @pieces; + $sql .= "-- $se --> $de\n"; + $sql .= +"CREATE OR REPLACE FUNCTION $func (INTEGER, INTEGER, CSTRING, INTERNAL, INTEGER) RETURNS VOID AS '\$libdir/$obj', '$func' LANGUAGE C STRICT;\n"; + $sql .= "DROP CONVERSION pg_catalog.$name;\n"; + $sql .= "CREATE DEFAULT CONVERSION pg_catalog.$name FOR '$se' TO '$de' FROM $func;\n"; + } + open($F,">$target/share/conversion_create.sql") + || die "Could not write to conversion_create.sql\n"; + print $F $sql; + close($F); + print "\n"; +} + +sub GenerateTimezoneFiles +{ + my $target = shift; + my $conf = shift; + my $mf = read_file("src/timezone/Makefile"); + $mf =~ s{\\\s*[\r\n]+}{}mg; + $mf =~ /^TZDATA\s*:?=\s*(.*)$/m || die "Could not find TZDATA row in timezone makefile\n"; + my @tzfiles = split /\s+/,$1; + unshift @tzfiles,''; + print "Generating timezone files..."; + system("$conf\\zic\\zic -d $target/share/timezone " . join(" src/timezone/data/", @tzfiles)); + print "\n"; +} + +sub read_file +{ + my $filename = shift; + my $F; + my $t = $/; + + undef $/; + open($F, $filename) || die "Could not open file $filename\n"; + my $txt = <$F>; + close($F); + $/ = $t; + + return $txt; +} + +1; diff --git a/src/tools/msvc/Mkvcbuild.pm b/src/tools/msvc/Mkvcbuild.pm new file mode 100644 index 00000000000..84d5889ddda --- /dev/null +++ b/src/tools/msvc/Mkvcbuild.pm @@ -0,0 +1,455 @@ +package Mkvcbuild; + +use Carp; +use Win32; +use strict; +use warnings; +use Project; +use Solution; + +use Exporter; +our (@ISA, @EXPORT_OK); +@ISA = qw(Exporter); +@EXPORT_OK = qw(Mkvcbuild); + +my $solution; +my $libpgport; +my $postgres; +my $libpq; + +my $contrib_defines = {'refint' => 'REFINT_VERBOSE'}; +my @contrib_uselibpq = ('dblink', 'oid2name', 'pgbench', 'vacuumlo'); +my @contrib_uselibpgport = ('oid2name', 'pgbench', 'pg_standby', 'vacuumlo'); +my $contrib_extralibs = {'pgbench' => ['wsock32.lib']}; +my $contrib_extraincludes = {'tsearch2' => ['contrib/tsearch2']}; +my $contrib_extrasource = { + 'cube' => ['cubescan.l','cubeparse.y'], + 'seg' => ['segscan.l','segparse.y'] +}; +my @contrib_excludes = ('pgcrypto'); + +sub mkvcbuild +{ + our $config = shift; + + chdir('..\..\..') if (-d '..\msvc' && -d '..\..\..\src'); + die 'Must run from root or msvc directory' unless (-d 'src\tools\msvc' && -d 'src'); + + $solution = new Solution($config); + + our @pgportfiles = qw( + crypt.c fseeko.c getrusage.c inet_aton.c random.c srandom.c + unsetenv.c getaddrinfo.c gettimeofday.c kill.c open.c rand.c + snprintf.c strlcat.c strlcpy.c copydir.c dirmod.c exec.c noblock.c path.c pipe.c + pgsleep.c pgstrcasecmp.c qsort.c qsort_arg.c sprompt.c thread.c + getopt.c getopt_long.c dirent.c rint.c win32error.c); + + $libpgport = $solution->AddProject('libpgport','lib','misc'); + $libpgport->AddDefine('FRONTEND'); + $libpgport->AddFiles('src\port',@pgportfiles); + + $postgres = $solution->AddProject('postgres','exe','','src\backend'); + $postgres->AddIncludeDir('src\backend'); + $postgres->AddDir('src\backend\port\win32'); + $postgres->AddFile('src\backend\utils\fmgrtab.c'); + $postgres->ReplaceFile('src\backend\port\dynloader.c','src\backend\port\dynloader\win32.c'); + $postgres->ReplaceFile('src\backend\port\pg_sema.c','src\backend\port\win32_sema.c'); + $postgres->ReplaceFile('src\backend\port\pg_shmem.c','src\backend\port\sysv_shmem.c'); + $postgres->AddFiles('src\port',@pgportfiles); + $postgres->AddDir('src\timezone'); + $postgres->AddFiles('src\backend\parser','scan.l','gram.y'); + $postgres->AddFiles('src\backend\bootstrap','bootscanner.l','bootparse.y'); + $postgres->AddFiles('src\backend\utils\misc','guc-file.l'); + $postgres->AddDefine('BUILDING_DLL'); + $postgres->AddLibrary('wsock32.lib ws2_32.lib'); + $postgres->AddLibrary('wldap32.lib') if ($solution->{options}->{ldap}); + $postgres->FullExportDLL('postgres.lib'); + + my $plpgsql = $solution->AddProject('plpgsql','dll','PLs','src\pl\plpgsql\src'); + $plpgsql->AddFiles('src\pl\plpgsql\src','scan.l','gram.y'); + $plpgsql->AddReference($postgres); + + if ($solution->{options}->{perl}) + { + my $plperl = $solution->AddProject('plperl','dll','PLs','src\pl\plperl'); + $plperl->AddIncludeDir($solution->{options}->{perl} . '/lib/CORE'); + $plperl->AddDefine('PLPERL_HAVE_UID_GID'); + if (Solution::IsNewer('src\pl\plperl\SPI.c','src\pl\plperl\SPI.xs')) + { + print 'Building src\pl\plperl\SPI.c...' . "\n"; + system( $solution->{options}->{perl} + . '/bin/perl ' + . $solution->{options}->{perl} + . '/lib/ExtUtils/xsubpp -typemap ' + . $solution->{options}->{perl} + . '/lib/ExtUtils/typemap src\pl\plperl\SPI.xs >src\pl\plperl\SPI.c'); + if ((!(-f 'src\pl\plperl\SPI.c')) || -z 'src\pl\plperl\SPI.c') + { + unlink('src\pl\plperl\SPI.c'); # if zero size + die 'Failed to create SPI.c' . "\n"; + } + } + $plperl->AddReference($postgres); + $plperl->AddLibrary($solution->{options}->{perl} . '\lib\CORE\perl58.lib'); + } + + if ($solution->{options}->{python}) + { + my $plpython = $solution->AddProject('plpython','dll','PLs','src\pl\plpython'); + $plpython->AddIncludeDir($solution->{options}->{python} . '\include'); + $solution->{options}->{python} =~ /\\Python(\d{2})/i + || croak "Could not determine python version from path"; + $plpython->AddLibrary($solution->{options}->{python} . "\\Libs\\python$1.lib"); + $plpython->AddReference($postgres); + } + + if ($solution->{options}->{tcl}) + { + my $pltcl = $solution->AddProject('pltcl','dll','PLs','src\pl\tcl'); + $pltcl->AddIncludeDir($solution->{options}->{tcl} . '\include'); + $pltcl->AddReference($postgres); + $pltcl->AddLibrary($solution->{options}->{tcl} . '\lib\tcl84.lib'); + } + + $libpq = $solution->AddProject('libpq','dll','interfaces','src\interfaces\libpq'); + $libpq->AddDefine('FRONTEND'); + $libpq->AddIncludeDir('src\port'); + $libpq->AddLibrary('wsock32.lib'); + $libpq->AddLibrary('wldap32.lib') if ($solution->{options}->{ldap}); + $libpq->UseDef('src\interfaces\libpq\libpqdll.def'); + $libpq->ReplaceFile('src\interfaces\libpq\libpqrc.c','src\interfaces\libpq\libpq.rc'); + $libpq->AddReference($libpgport); + + my $pgtypes = + $solution->AddProject('libpgtypes','dll','interfaces','src\interfaces\ecpg\pgtypeslib'); + $pgtypes->AddDefine('FRONTEND'); + $pgtypes->AddReference($postgres,$libpgport); + $pgtypes->AddIncludeDir('src\interfaces\ecpg\include'); + + if ($config->{pthread}) + { + my $libecpg = + $solution->AddProject('libecpg','dll','interfaces','src\interfaces\ecpg\ecpglib'); + $libecpg->AddDefine('FRONTEND'); + $libecpg->AddIncludeDir('src\interfaces\ecpg\include'); + $libecpg->AddIncludeDir('src\interfaces\libpq'); + $libecpg->AddIncludeDir('src\port'); + $libecpg->AddLibrary('wsock32.lib'); + $libecpg->AddLibrary($config->{'pthread'} . '\pthreadVC2.lib'); + $libecpg->AddReference($libpq,$pgtypes); + + my $libecpgcompat = + $solution->AddProject('libecpg_compat','dll','interfaces', + 'src\interfaces\ecpg\compatlib'); + $libecpgcompat->AddIncludeDir('src\interfaces\ecpg\include'); + $libecpgcompat->AddIncludeDir('src\interfaces\libpq'); + $libecpgcompat->AddReference($pgtypes,$libecpg); + + my $ecpg = $solution->AddProject('ecpg','exe','interfaces','src\interfaces\ecpg\preproc'); + $ecpg->AddIncludeDir('src\interfaces\ecpg\include'); + $ecpg->AddIncludeDir('src\interfaces\libpq'); + $ecpg->AddFiles('src\interfaces\ecpg\preproc','pgc.l','preproc.y'); + $ecpg->AddDefine('MAJOR_VERSION=4'); + $ecpg->AddDefine('MINOR_VERSION=2'); + $ecpg->AddDefine('PATCHLEVEL=1'); + $ecpg->AddReference($libpgport); + } + else + { + print "Not building ecpg due to lack of pthreads.\n"; + } + + # src/bin + my $initdb = AddSimpleFrontend('initdb', 1); + + my $pgconfig = AddSimpleFrontend('pg_config'); + + my $pgcontrol = AddSimpleFrontend('pg_controldata'); + + my $pgctl = AddSimpleFrontend('pg_ctl', 1); + + my $pgreset = AddSimpleFrontend('pg_resetxlog'); + + my $pgevent = $solution->AddProject('pgevent','dll','bin'); + $pgevent->AddFiles('src\bin\pgevent','pgevent.c','pgmsgevent.rc'); + $pgevent->AddResourceFile('src\bin\pgevent','Eventlog message formatter'); + $pgevent->RemoveFile('src\bin\pgevent\win32ver.rc'); + $pgevent->UseDef('src\bin\pgevent\pgevent.def'); + $pgevent->DisableLinkerWarnings('4104'); + + my $psql = AddSimpleFrontend('psql', 1); + $psql->AddIncludeDir('src\bin\pg_dump'); + $psql->AddFile('src\bin\psql\psqlscan.l'); + + my $pgdump = AddSimpleFrontend('pg_dump', 1); + $pgdump->AddFile('src\bin\pg_dump\pg_dump.c'); + $pgdump->AddFile('src\bin\pg_dump\common.c'); + $pgdump->AddFile('src\bin\pg_dump\pg_dump_sort.c'); + + my $pgdumpall = AddSimpleFrontend('pg_dump', 1); + $pgdumpall->{name} = 'pg_dumpall'; + $pgdumpall->AddFile('src\bin\pg_dump\pg_dumpall.c'); + + my $pgrestore = AddSimpleFrontend('pg_dump', 1); + $pgrestore->{name} = 'pg_restore'; + $pgrestore->AddFile('src\bin\pg_dump\pg_restore.c'); + + my $zic = $solution->AddProject('zic','exe','utils'); + $zic->AddFiles('src\timezone','zic.c','ialloc.c','scheck.c','localtime.c'); + $zic->AddReference($libpgport); + + if ($solution->{options}->{xml}) + { + $contrib_extraincludes->{'xml2'} = [ + $solution->{options}->{xml} . '\include', + $solution->{options}->{xslt} . '\include', + $solution->{options}->{iconv} . '\include' + ]; + + $contrib_extralibs->{'xml2'} = [ + $solution->{options}->{xml} . '\lib\libxml2.lib', + $solution->{options}->{xslt} . '\lib\libxslt.lib' + ]; + } + else + { + push @contrib_excludes,'xml2'; + } + + if (!$solution->{options}->{openssl}) + { + push @contrib_excludes,'sslinfo'; + } + + # Pgcrypto makefile too complex to parse.... + my $pgcrypto = $solution->AddProject('pgcrypto','dll','crypto'); + $pgcrypto->AddFiles( + 'contrib\pgcrypto','pgcrypto.c','px.c','px-hmac.c', + 'px-crypt.c','crypt-gensalt.c','crypt-blowfish.c','crypt-des.c', + 'crypt-md5.c','mbuf.c','pgp.c','pgp-armor.c', + 'pgp-cfb.c','pgp-compress.c','pgp-decrypt.c','pgp-encrypt.c', + 'pgp-info.c','pgp-mpi.c','pgp-pubdec.c','pgp-pubenc.c', + 'pgp-pubkey.c','pgp-s2k.c','pgp-pgsql.c' + ); + if ($solution->{options}->{openssl}) + { + $pgcrypto->AddFiles('contrib\pgcrypto', 'openssl.c','pgp-mpi-openssl.c'); + } + else + { + $pgcrypto->AddFiles( + 'contrib\pgcrypto', 'md5.c','sha1.c','sha2.c', + 'internal.c','internal-sha2.c','blf.c','rijndael.c', + 'fortuna.c','random.c','pgp-mpi-internal.c','imath.c' + ); + } + $pgcrypto->AddReference($postgres); + $pgcrypto->AddLibrary('wsock32.lib'); + + my $D; + opendir($D, 'contrib') || croak "Could not opendir on contrib!\n"; + while (my $d = readdir($D)) + { + next if ($d =~ /^\./); + next unless (-f "contrib/$d/Makefile"); + next if (grep {/^$d$/} @contrib_excludes); + AddContrib($d); + } + closedir($D); + + my $mf = Project::read_file('src\backend\utils\mb\conversion_procs\Makefile'); + $mf =~ s{\\s*[\r\n]+}{}mg; + $mf =~ m{DIRS\s*=\s*(.*)$}m || die 'Could not match in conversion makefile' . "\n"; + foreach my $sub (split /\s+/,$1) + { + my $mf = Project::read_file('src\backend\utils\mb\conversion_procs\\' . $sub . '\Makefile'); + my $p = $solution->AddProject($sub, 'dll', 'conversion procs'); + $p->AddFile('src\backend\utils\mb\conversion_procs\\' . $sub . '\\' . $sub . '.c'); + if ($mf =~ m{^SRCS\s*\+=\s*(.*)$}m) + { + $p->AddFile('src\backend\utils\mb\conversion_procs\\' . $sub . '\\' . $1); + } + $p->AddReference($postgres); + } + + $mf = Project::read_file('src\bin\scripts\Makefile'); + $mf =~ s{\\s*[\r\n]+}{}mg; + $mf =~ m{PROGRAMS\s*=\s*(.*)$}m || die 'Could not match in bin\scripts\Makefile' . "\n"; + foreach my $prg (split /\s+/,$1) + { + my $proj = $solution->AddProject($prg,'exe','bin'); + $mf =~ m{$prg\s*:\s*(.*)$}m || die 'Could not find script define for $prg' . "\n"; + my @files = split /\s+/,$1; + foreach my $f (@files) + { + if ($f =~ /\/keywords\.o$/) + { + $proj->AddFile('src\backend\parser\keywords.c'); + } + else + { + $f =~ s/\.o$/\.c/; + if ($f eq 'dumputils.c') + { + $proj->AddFile('src\bin\pg_dump\dumputils.c'); + } + elsif ($f =~ /print\.c$/) + { # Also catches mbprint.c + $proj->AddFile('src\bin\psql\\' . $f); + } + else + { + $proj->AddFile('src\bin\scripts\\' . $f); + } + } + } + $proj->AddIncludeDir('src\interfaces\libpq'); + $proj->AddIncludeDir('src\bin\pg_dump'); + $proj->AddIncludeDir('src\bin\psql'); + $proj->AddReference($libpq,$libpgport); + $proj->AddResourceFile('src\bin\scripts','PostgreSQL Utility'); + } + + # Regression DLL and EXE + my $regress = $solution->AddProject('regress','dll','misc'); + $regress->AddFile('src\test\regress\regress.c'); + $regress->AddReference($postgres); + + my $pgregress = $solution->AddProject('pg_regress','exe','misc'); + $pgregress->AddFile('src\test\regress\pg_regress.c'); + $pgregress->AddIncludeDir('src\port'); + $pgregress->AddDefine('HOST_TUPLE="i686-pc-win32vc"'); + $pgregress->AddDefine('FRONTEND'); + $pgregress->AddReference($libpgport); + + $solution->Save(); +} + +##################### +# Utility functions # +##################### + +# Add a simple frontend project (exe) +sub AddSimpleFrontend +{ + my $n = shift; + my $uselibpq= shift; + + my $p = $solution->AddProject($n,'exe','bin'); + $p->AddDir('src\bin\\' . $n); + $p->AddDefine('FRONTEND'); + $p->AddReference($libpgport); + if ($uselibpq) + { + $p->AddIncludeDir('src\interfaces\libpq'); + $p->AddReference($libpq); + } + return $p; +} + +# Add a simple contrib project +sub AddContrib +{ + my $n = shift; + my $mf = Project::read_file('contrib\\' . $n . '\Makefile'); + + if ($mf =~ /^MODULE_big/mg) + { + $mf =~ s{\\\s*[\r\n]+}{}mg; + my $proj = $solution->AddProject($n, 'dll', 'contrib'); + $mf =~ /^OBJS\s*=\s*(.*)$/gm || croak "Could not find objects in MODULE_big for $n\n"; + foreach my $o (split /\s+/, $1) + { + $o =~ s/\.o$/.c/; + $proj->AddFile('contrib\\' . $n . '\\' . $o); + } + $proj->AddReference($postgres); + if ($mf =~ /^SUBDIRS\s*:?=\s*(.*)$/mg) + { + foreach my $d (split /\s+/, $1) + { + my $mf2 = Project::read_file('contrib\\' . $n . '\\' . $d . '\Makefile'); + $mf2 =~ s{\\\s*[\r\n]+}{}mg; + $mf2 =~ /^SUBOBJS\s*=\s*(.*)$/gm + || croak "Could not find objects in MODULE_big for $n, subdir $d\n"; + foreach my $o (split /\s+/, $1) + { + $o =~ s/\.o$/.c/; + $proj->AddFile('contrib\\' . $n . '\\' . $d . '\\' . $o); + } + } + } + AdjustContribProj($proj); + return $proj; + } + elsif ($mf =~ /^MODULES\s*=\s*(.*)$/mg) + { + foreach my $mod (split /\s+/, $1) + { + my $proj = $solution->AddProject($mod, 'dll', 'contrib'); + $proj->AddFile('contrib\\' . $n . '\\' . $mod . '.c'); + $proj->AddReference($postgres); + AdjustContribProj($proj); + } + return undef; + } + elsif ($mf =~ /^PROGRAM\s*=\s*(.*)$/mg) + { + my $proj = $solution->AddProject($1, 'exe', 'contrib'); + $mf =~ /^OBJS\s*=\s*(.*)$/gm || croak "Could not find objects in MODULE_big for $n\n"; + foreach my $o (split /\s+/, $1) + { + $o =~ s/\.o$/.c/; + $proj->AddFile('contrib\\' . $n . '\\' . $o); + } + AdjustContribProj($proj); + return $proj; + } + else + { + croak "Could not determine contrib module type for $n\n"; + } +} + +sub AdjustContribProj +{ + my $proj = shift; + my $n = $proj->{name}; + + if ($contrib_defines->{$n}) + { + foreach my $d ($contrib_defines->{$n}) + { + $proj->AddDefine($d); + } + } + if (grep {/^$n$/} @contrib_uselibpq) + { + $proj->AddIncludeDir('src\interfaces\libpq'); + $proj->AddReference($libpq); + } + if (grep {/^$n$/} @contrib_uselibpgport) + { + $proj->AddReference($libpgport); + } + if ($contrib_extralibs->{$n}) + { + foreach my $l (@{$contrib_extralibs->{$n}}) + { + $proj->AddLibrary($l); + } + } + if ($contrib_extraincludes->{$n}) + { + foreach my $i (@{$contrib_extraincludes->{$n}}) + { + $proj->AddIncludeDir($i); + } + } + if ($contrib_extrasource->{$n}) + { + $proj->AddFiles('contrib\\' . $n, @{$contrib_extrasource->{$n}}); + } +} + +1; diff --git a/src/tools/msvc/README b/src/tools/msvc/README index e0123a953f5..71d6f7d1d6b 100644 --- a/src/tools/msvc/README +++ b/src/tools/msvc/README @@ -8,5 +8,5 @@ Notes about code indention -------------------------- If the perl code is modified, use perltidy on it since pgindent won't touch perl code. Use the following commandline: -perltidy -b -bl -nsfs -naws -l=100 *.pl *.pm +perltidy -b -bl -nsfs -naws -l=100 -ole=unix *.pl *.pm diff --git a/src/tools/msvc/Solution.pm b/src/tools/msvc/Solution.pm index 37c098b4fb6..f6699c857f2 100644 --- a/src/tools/msvc/Solution.pm +++ b/src/tools/msvc/Solution.pm @@ -3,6 +3,8 @@ use Carp; use strict; use warnings; +use Genbki; + sub new { my $junk = shift; @@ -266,8 +268,11 @@ EOF if (IsNewer('src/backend/catalog/postgres.bki', "src/include/catalog/$bki")) { print "Generating postgres.bki...\n"; - system("perl src/tools/msvc/genbki.pl $self->{majorver} src/backend/catalog/postgres " - . join(' src/include/catalog/',@allbki)); + Genbki::genbki( + $self->{majorver}, + "src/backend/catalog/postgres", + split(/ /,join(' src/include/catalog/',@allbki)) + ); last; } } diff --git a/src/tools/msvc/install.pl b/src/tools/msvc/install.pl index 00271e50a42..4d7053f52d2 100755 --- a/src/tools/msvc/install.pl +++ b/src/tools/msvc/install.pl @@ -1,202 +1,13 @@ use strict; use warnings; -use Carp; -use File::Basename; -use File::Copy; -$| = 1; +use Install qw(Install); my $target = shift || Usage(); - -chdir("../../..") if (-f "../../../configure"); -my $conf = ""; -if (-d "debug") -{ - $conf = "debug"; -} -if (-d "release") -{ - $conf = "release"; -} -die "Could not find debug or release binaries" if ($conf eq ""); -print "Installing for $conf\n"; - -EnsureDirectories('bin','lib','share','share/timezonesets'); - -CopySolutionOutput($conf, $target); -copy($target . '/lib/libpq.dll', $target . '/bin/libpq.dll'); -CopySetOfFiles('config files', "*.sample", $target . '/share/'); -CopySetOfFiles('timezone names', 'src\timezone\tznames\*.txt', $target . '/share/timezonesets/'); -CopyFiles( - 'timezone sets', - $target . '/share/timezonesets/', - 'src/timezone/tznames/', 'Default','Australia','India' -); -CopySetOfFiles('BKI files', "src\\backend\\catalog\\postgres.*", $target .'/share/'); -CopySetOfFiles('SQL files', "src\\backend\\catalog\\*.sql", $target . '/share/'); -CopyFiles( - 'Information schema data', - $target . '/share/', - 'src/backend/catalog/', 'sql_features.txt' -); -GenerateConversionScript(); -GenerateTimezoneFiles(); +Install($target); sub Usage { print "Usage: install.pl <targetdir>\n"; exit(1); } - -sub EnsureDirectories -{ - mkdir $target unless -d ($target); - while (my $d = shift) - { - mkdir $target . '/' . $d unless -d ($target . '/' . $d); - } -} - -sub CopyFiles -{ - my $what = shift; - my $target = shift; - my $basedir = shift; - - print "Copying $what"; - while (my $f = shift) - { - print "."; - $f = $basedir . $f; - die "No file $f\n" if (!-f $f); - copy($f, $target . basename($f)) - || croak "Could not copy $f to $target" - . basename($f) - . " to $target" - . basename($f) . "\n"; - } - print "\n"; -} - -sub CopySetOfFiles -{ - my $what = shift; - my $spec = shift; - my $target = shift; - my $D; - - print "Copying $what"; - open($D, "dir /b /s $spec |") || croak "Could not list $spec\n"; - while (<$D>) - { - chomp; - next if /regress/; # Skip temporary install in regression subdir - my $tgt = $target . basename($_); - print "."; - copy($_, $tgt) || croak "Could not copy $_: $!\n"; - } - close($D); - print "\n"; -} - -sub CopySolutionOutput -{ - my $conf = shift; - my $target = shift; - my $rem = qr{Project\("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}"\) = "([^"]+)"}; - - my $sln = read_file("pgsql.sln") || croak "Could not open pgsql.sln\n"; - print "Copying build output files..."; - while ($sln =~ $rem) - { - my $pf = $1; - my $dir; - my $ext; - - $sln =~ s/$rem//; - - my $proj = read_file("$pf.vcproj") || croak "Could not open $pf.vcproj\n"; - if ($proj !~ qr{ConfigurationType="([^"]+)"}) - { - croak "Could not parse $pf.vcproj\n"; - } - if ($1 == 1) - { - $dir = "bin"; - $ext = "exe"; - } - elsif ($1 == 2) - { - $dir = "lib"; - $ext = "dll"; - } - else - { - - # Static lib, such as libpgport, only used internally during build, don't install - next; - } - copy("$conf\\$pf\\$pf.$ext","$target\\$dir\\$pf.$ext") || croak "Could not copy $pf.$ext\n"; - print "."; - } - print "\n"; -} - -sub GenerateConversionScript -{ - my $sql = ""; - my $F; - - print "Generating conversion proc script..."; - my $mf = read_file('src/backend/utils/mb/conversion_procs/Makefile'); - $mf =~ s{\\\s*[\r\n]+}{}mg; - $mf =~ /^CONVERSIONS\s*=\s*(.*)$/m - || die "Could not find CONVERSIONS line in conversions Makefile\n"; - my @pieces = split /\s+/,$1; - while ($#pieces > 0) - { - my $name = shift @pieces; - my $se = shift @pieces; - my $de = shift @pieces; - my $func = shift @pieces; - my $obj = shift @pieces; - $sql .= "-- $se --> $de\n"; - $sql .= -"CREATE OR REPLACE FUNCTION $func (INTEGER, INTEGER, CSTRING, INTERNAL, INTEGER) RETURNS VOID AS '\$libdir/$obj', '$func' LANGUAGE C STRICT;\n"; - $sql .= "DROP CONVERSION pg_catalog.$name;\n"; - $sql .= "CREATE DEFAULT CONVERSION pg_catalog.$name FOR '$se' TO '$de' FROM $func;\n"; - } - open($F,">$target/share/conversion_create.sql") - || die "Could not write to conversion_create.sql\n"; - print $F $sql; - close($F); - print "\n"; -} - -sub GenerateTimezoneFiles -{ - my $mf = read_file("src/timezone/Makefile"); - $mf =~ s{\\\s*[\r\n]+}{}mg; - $mf =~ /^TZDATA\s*:?=\s*(.*)$/m || die "Could not find TZDATA row in timezone makefile\n"; - my @tzfiles = split /\s+/,$1; - unshift @tzfiles,''; - print "Generating timezone files..."; - system("$conf\\zic\\zic -d $target/share/timezone " . join(" src/timezone/data/", @tzfiles)); - print "\n"; -} - -sub read_file -{ - my $filename = shift; - my $F; - my $t = $/; - - undef $/; - open($F, $filename) || die "Could not open file $filename\n"; - my $txt = <$F>; - close($F); - $/ = $t; - - return $txt; -} - diff --git a/src/tools/msvc/mkvcbuild.pl b/src/tools/msvc/mkvcbuild.pl index a09838df65a..e8d9922f302 100644 --- a/src/tools/msvc/mkvcbuild.pl +++ b/src/tools/msvc/mkvcbuild.pl @@ -1,438 +1,14 @@ -use Carp; -use Win32; use strict; use warnings; -use Project; -use Solution; + +use Mkvcbuild; chdir('..\..\..') if (-d '..\msvc' && -d '..\..\..\src'); die 'Must run from root or msvc directory' unless (-d 'src\tools\msvc' && -d 'src'); + die 'Could not find config.pl' unless (-f 'src/tools/msvc/config.pl'); our $config; require 'src/tools/msvc/config.pl'; -my $solution = new Solution($config); - -our @pgportfiles = qw( - crypt.c fseeko.c getrusage.c inet_aton.c random.c srandom.c - unsetenv.c getaddrinfo.c gettimeofday.c kill.c open.c rand.c - snprintf.c strlcat.c strlcpy.c copydir.c dirmod.c exec.c noblock.c path.c pipe.c - pgsleep.c pgstrcasecmp.c qsort.c qsort_arg.c sprompt.c thread.c - getopt.c getopt_long.c dirent.c rint.c win32error.c); - -my $libpgport = $solution->AddProject('libpgport','lib','misc'); -$libpgport->AddDefine('FRONTEND'); -$libpgport->AddFiles('src\port',@pgportfiles); - -my $postgres = $solution->AddProject('postgres','exe','','src\backend'); -$postgres->AddIncludeDir('src\backend'); -$postgres->AddDir('src\backend\port\win32'); -$postgres->AddFile('src\backend\utils\fmgrtab.c'); -$postgres->ReplaceFile('src\backend\port\dynloader.c','src\backend\port\dynloader\win32.c'); -$postgres->ReplaceFile('src\backend\port\pg_sema.c','src\backend\port\win32_sema.c'); -$postgres->ReplaceFile('src\backend\port\pg_shmem.c','src\backend\port\sysv_shmem.c'); -$postgres->AddFiles('src\port',@pgportfiles); -$postgres->AddDir('src\timezone'); -$postgres->AddFiles('src\backend\parser','scan.l','gram.y'); -$postgres->AddFiles('src\backend\bootstrap','bootscanner.l','bootparse.y'); -$postgres->AddFiles('src\backend\utils\misc','guc-file.l'); -$postgres->AddDefine('BUILDING_DLL'); -$postgres->AddLibrary('wsock32.lib ws2_32.lib'); -$postgres->AddLibrary('wldap32.lib') if ($solution->{options}->{ldap}); -$postgres->FullExportDLL('postgres.lib'); - -my $plpgsql = $solution->AddProject('plpgsql','dll','PLs','src\pl\plpgsql\src'); -$plpgsql->AddFiles('src\pl\plpgsql\src','scan.l','gram.y'); -$plpgsql->AddReference($postgres); - -if ($solution->{options}->{perl}) -{ - my $plperl = $solution->AddProject('plperl','dll','PLs','src\pl\plperl'); - $plperl->AddIncludeDir($solution->{options}->{perl} . '/lib/CORE'); - $plperl->AddDefine('PLPERL_HAVE_UID_GID'); - if (Solution::IsNewer('src\pl\plperl\SPI.c','src\pl\plperl\SPI.xs')) - { - print 'Building src\pl\plperl\SPI.c...' . "\n"; - system( $solution->{options}->{perl} - . '/bin/perl ' - . $solution->{options}->{perl} - . '/lib/ExtUtils/xsubpp -typemap ' - . $solution->{options}->{perl} - . '/lib/ExtUtils/typemap src\pl\plperl\SPI.xs >src\pl\plperl\SPI.c'); - if ((!(-f 'src\pl\plperl\SPI.c')) || -z 'src\pl\plperl\SPI.c') - { - unlink('src\pl\plperl\SPI.c'); # if zero size - die 'Failed to create SPI.c' . "\n"; - } - } - $plperl->AddReference($postgres); - $plperl->AddLibrary($solution->{options}->{perl} . '\lib\CORE\perl58.lib'); -} - -if ($solution->{options}->{python}) -{ - my $plpython = $solution->AddProject('plpython','dll','PLs','src\pl\plpython'); - $plpython->AddIncludeDir($solution->{options}->{python} . '\include'); - $solution->{options}->{python} =~ /\\Python(\d{2})/i - || croak "Could not determine python version from path"; - $plpython->AddLibrary($solution->{options}->{python} . "\\Libs\\python$1.lib"); - $plpython->AddReference($postgres); -} - -if ($solution->{options}->{tcl}) -{ - my $pltcl = $solution->AddProject('pltcl','dll','PLs','src\pl\tcl'); - $pltcl->AddIncludeDir($solution->{options}->{tcl} . '\include'); - $pltcl->AddReference($postgres); - $pltcl->AddLibrary($solution->{options}->{tcl} . '\lib\tcl84.lib'); -} - -my $libpq = $solution->AddProject('libpq','dll','interfaces','src\interfaces\libpq'); -$libpq->AddDefine('FRONTEND'); -$libpq->AddIncludeDir('src\port'); -$libpq->AddLibrary('wsock32.lib'); -$libpq->AddLibrary('wldap32.lib') if ($solution->{options}->{ldap}); -$libpq->UseDef('src\interfaces\libpq\libpqdll.def'); -$libpq->ReplaceFile('src\interfaces\libpq\libpqrc.c','src\interfaces\libpq\libpq.rc'); - -my $pgtypes = - $solution->AddProject('libpgtypes','dll','interfaces','src\interfaces\ecpg\pgtypeslib'); -$pgtypes->AddDefine('FRONTEND'); -$pgtypes->AddReference($postgres,$libpgport); -$pgtypes->AddIncludeDir('src\interfaces\ecpg\include'); - -if ($config->{pthread}) -{ - my $libecpg = $solution->AddProject('libecpg','dll','interfaces','src\interfaces\ecpg\ecpglib'); - $libecpg->AddDefine('FRONTEND'); - $libecpg->AddIncludeDir('src\interfaces\ecpg\include'); - $libecpg->AddIncludeDir('src\interfaces\libpq'); - $libecpg->AddIncludeDir('src\port'); - $libecpg->AddLibrary('wsock32.lib'); - $libecpg->AddLibrary($config->{'pthread'} . '\pthreadVC2.lib'); - $libecpg->AddReference($libpq,$pgtypes); - - my $libecpgcompat = - $solution->AddProject('libecpg_compat','dll','interfaces','src\interfaces\ecpg\compatlib'); - $libecpgcompat->AddIncludeDir('src\interfaces\ecpg\include'); - $libecpgcompat->AddIncludeDir('src\interfaces\libpq'); - $libecpgcompat->AddReference($pgtypes,$libecpg); - - my $ecpg = $solution->AddProject('ecpg','exe','interfaces','src\interfaces\ecpg\preproc'); - $ecpg->AddIncludeDir('src\interfaces\ecpg\include'); - $ecpg->AddIncludeDir('src\interfaces\libpq'); - $ecpg->AddFiles('src\interfaces\ecpg\preproc','pgc.l','preproc.y'); - $ecpg->AddDefine('MAJOR_VERSION=4'); - $ecpg->AddDefine('MINOR_VERSION=2'); - $ecpg->AddDefine('PATCHLEVEL=1'); - $ecpg->AddReference($libpgport); -} -else -{ - print "Not building ecpg due to lack of pthreads.\n"; -} - -# src/bin -my $initdb = AddSimpleFrontend('initdb', 1); - -my $pgconfig = AddSimpleFrontend('pg_config'); - -my $pgcontrol = AddSimpleFrontend('pg_controldata'); - -my $pgctl = AddSimpleFrontend('pg_ctl', 1); - -my $pgreset = AddSimpleFrontend('pg_resetxlog'); - -my $pgevent = $solution->AddProject('pgevent','dll','bin'); -$pgevent->AddFiles('src\bin\pgevent','pgevent.c','pgmsgevent.rc'); -$pgevent->AddResourceFile('src\bin\pgevent','Eventlog message formatter'); -$pgevent->RemoveFile('src\bin\pgevent\win32ver.rc'); -$pgevent->UseDef('src\bin\pgevent\pgevent.def'); -$pgevent->DisableLinkerWarnings('4104'); - -my $psql = AddSimpleFrontend('psql', 1); -$psql->AddIncludeDir('src\bin\pg_dump'); -$psql->AddFile('src\bin\psql\psqlscan.l'); - -my $pgdump = AddSimpleFrontend('pg_dump', 1); -$pgdump->AddFile('src\bin\pg_dump\pg_dump.c'); -$pgdump->AddFile('src\bin\pg_dump\common.c'); -$pgdump->AddFile('src\bin\pg_dump\pg_dump_sort.c'); - -my $pgdumpall = AddSimpleFrontend('pg_dump', 1); -$pgdumpall->{name} = 'pg_dumpall'; -$pgdumpall->AddFile('src\bin\pg_dump\pg_dumpall.c'); - -my $pgrestore = AddSimpleFrontend('pg_dump', 1); -$pgrestore->{name} = 'pg_restore'; -$pgrestore->AddFile('src\bin\pg_dump\pg_restore.c'); - -my $zic = $solution->AddProject('zic','exe','utils'); -$zic->AddFiles('src\timezone','zic.c','ialloc.c','scheck.c','localtime.c'); -$zic->AddReference($libpgport); - -my $contrib_defines = {'refint' => 'REFINT_VERBOSE'}; -my @contrib_uselibpq = ('dblink', 'oid2name', 'pgbench', 'vacuumlo'); -my @contrib_uselibpgport = ('oid2name', 'pgbench', 'pg_standby', 'vacuumlo'); -my $contrib_extralibs = {'pgbench' => ['wsock32.lib']}; -my $contrib_extraincludes = {'tsearch2' => ['contrib/tsearch2']}; -my $contrib_extrasource = { - 'cube' => ['cubescan.l','cubeparse.y'], - 'seg' => ['segscan.l','segparse.y'] -}; - -my @contrib_excludes = ('pgcrypto'); - -if ($solution->{options}->{xml}) -{ - $contrib_extraincludes->{'xml2'} = [ - $solution->{options}->{xml} . '\include', - $solution->{options}->{xslt} . '\include', - $solution->{options}->{iconv} . '\include' - ]; - - $contrib_extralibs->{'xml2'} = [ - $solution->{options}->{xml} . '\lib\libxml2.lib', - $solution->{options}->{xslt} . '\lib\libxslt.lib' - ]; -} -else -{ - push @contrib_excludes,'xml2'; -} - -if (!$solution->{options}->{openssl}) -{ - push @contrib_excludes,'sslinfo'; -} - -# Pgcrypto makefile too complex to parse.... -my $pgcrypto = $solution->AddProject('pgcrypto','dll','crypto'); -$pgcrypto->AddFiles( - 'contrib\pgcrypto','pgcrypto.c','px.c','px-hmac.c', - 'px-crypt.c','crypt-gensalt.c','crypt-blowfish.c','crypt-des.c', - 'crypt-md5.c','mbuf.c','pgp.c','pgp-armor.c', - 'pgp-cfb.c','pgp-compress.c','pgp-decrypt.c','pgp-encrypt.c', - 'pgp-info.c','pgp-mpi.c','pgp-pubdec.c','pgp-pubenc.c', - 'pgp-pubkey.c','pgp-s2k.c','pgp-pgsql.c' -); -if ($solution->{options}->{openssl}) -{ - $pgcrypto->AddFiles('contrib\pgcrypto', 'openssl.c','pgp-mpi-openssl.c'); -} -else -{ - $pgcrypto->AddFiles( - 'contrib\pgcrypto', 'md5.c','sha1.c','sha2.c', - 'internal.c','internal-sha2.c','blf.c','rijndael.c', - 'fortuna.c','random.c','pgp-mpi-internal.c','imath.c' - ); -} -$pgcrypto->AddReference($postgres); -$pgcrypto->AddLibrary('wsock32.lib'); - -my $D; -opendir($D, 'contrib') || croak "Could not opendir on contrib!\n"; -while (my $d = readdir($D)) -{ - next if ($d =~ /^\./); - next unless (-f "contrib/$d/Makefile"); - next if (grep {/^$d$/} @contrib_excludes); - AddContrib($d); -} -closedir($D); - -my $mf = Project::read_file('src\backend\utils\mb\conversion_procs\Makefile'); -$mf =~ s{\\s*[\r\n]+}{}mg; -$mf =~ m{DIRS\s*=\s*(.*)$}m || die 'Could not match in conversion makefile' . "\n"; -foreach my $sub (split /\s+/,$1) -{ - my $mf = Project::read_file('src\backend\utils\mb\conversion_procs\\' . $sub . '\Makefile'); - my $p = $solution->AddProject($sub, 'dll', 'conversion procs'); - $p->AddFile('src\backend\utils\mb\conversion_procs\\' . $sub . '\\' . $sub . '.c'); - if ($mf =~ m{^SRCS\s*\+=\s*(.*)$}m) - { - $p->AddFile('src\backend\utils\mb\conversion_procs\\' . $sub . '\\' . $1); - } - $p->AddReference($postgres); -} - -$mf = Project::read_file('src\bin\scripts\Makefile'); -$mf =~ s{\\s*[\r\n]+}{}mg; -$mf =~ m{PROGRAMS\s*=\s*(.*)$}m || die 'Could not match in bin\scripts\Makefile' . "\n"; -foreach my $prg (split /\s+/,$1) -{ - my $proj = $solution->AddProject($prg,'exe','bin'); - $mf =~ m{$prg\s*:\s*(.*)$}m || die 'Could not find script define for $prg' . "\n"; - my @files = split /\s+/,$1; - foreach my $f (@files) - { - if ($f =~ /\/keywords\.o$/) - { - $proj->AddFile('src\backend\parser\keywords.c'); - } - else - { - $f =~ s/\.o$/\.c/; - if ($f eq 'dumputils.c') - { - $proj->AddFile('src\bin\pg_dump\dumputils.c'); - } - elsif ($f =~ /print\.c$/) - { # Also catches mbprint.c - $proj->AddFile('src\bin\psql\\' . $f); - } - else - { - $proj->AddFile('src\bin\scripts\\' . $f); - } - } - } - $proj->AddIncludeDir('src\interfaces\libpq'); - $proj->AddIncludeDir('src\bin\pg_dump'); - $proj->AddIncludeDir('src\bin\psql'); - $proj->AddReference($libpq,$libpgport); - $proj->AddResourceFile('src\bin\scripts','PostgreSQL Utility'); -} - -# Regression DLL and EXE -my $regress = $solution->AddProject('regress','dll','misc'); -$regress->AddFile('src\test\regress\regress.c'); -$regress->AddReference($postgres); - -my $pgregress = $solution->AddProject('pg_regress','exe','misc'); -$pgregress->AddFile('src\test\regress\pg_regress.c'); -$pgregress->AddIncludeDir('src\port'); -$pgregress->AddDefine('HOST_TUPLE="i686-pc-win32vc"'); -$pgregress->AddDefine('FRONTEND'); -$pgregress->AddReference($libpgport); - -$solution->Save(); - -##################### -# Utility functions # -##################### - -# Add a simple frontend project (exe) -sub AddSimpleFrontend -{ - my $n = shift; - my $uselibpq= shift; - - my $p = $solution->AddProject($n,'exe','bin'); - $p->AddDir('src\bin\\' . $n); - $p->AddDefine('FRONTEND'); - $p->AddReference($libpgport); - if ($uselibpq) - { - $p->AddIncludeDir('src\interfaces\libpq'); - $p->AddReference($libpq); - } - return $p; -} - -# Add a simple contrib project -sub AddContrib -{ - my $n = shift; - my $mf = Project::read_file('contrib\\' . $n . '\Makefile'); - - if ($mf =~ /^MODULE_big/mg) - { - $mf =~ s{\\\s*[\r\n]+}{}mg; - my $proj = $solution->AddProject($n, 'dll', 'contrib'); - $mf =~ /^OBJS\s*=\s*(.*)$/gm || croak "Could not find objects in MODULE_big for $n\n"; - foreach my $o (split /\s+/, $1) - { - $o =~ s/\.o$/.c/; - $proj->AddFile('contrib\\' . $n . '\\' . $o); - } - $proj->AddReference($postgres); - if ($mf =~ /^SUBDIRS\s*:?=\s*(.*)$/mg) - { - foreach my $d (split /\s+/, $1) - { - my $mf2 = Project::read_file('contrib\\' . $n . '\\' . $d . '\Makefile'); - $mf2 =~ s{\\\s*[\r\n]+}{}mg; - $mf2 =~ /^SUBOBJS\s*=\s*(.*)$/gm - || croak "Could not find objects in MODULE_big for $n, subdir $d\n"; - foreach my $o (split /\s+/, $1) - { - $o =~ s/\.o$/.c/; - $proj->AddFile('contrib\\' . $n . '\\' . $d . '\\' . $o); - } - } - } - AdjustContribProj($proj); - return $proj; - } - elsif ($mf =~ /^MODULES\s*=\s*(.*)$/mg) - { - foreach my $mod (split /\s+/, $1) - { - my $proj = $solution->AddProject($mod, 'dll', 'contrib'); - $proj->AddFile('contrib\\' . $n . '\\' . $mod . '.c'); - $proj->AddReference($postgres); - AdjustContribProj($proj); - } - return undef; - } - elsif ($mf =~ /^PROGRAM\s*=\s*(.*)$/mg) - { - my $proj = $solution->AddProject($1, 'exe', 'contrib'); - $mf =~ /^OBJS\s*=\s*(.*)$/gm || croak "Could not find objects in MODULE_big for $n\n"; - foreach my $o (split /\s+/, $1) - { - $o =~ s/\.o$/.c/; - $proj->AddFile('contrib\\' . $n . '\\' . $o); - } - AdjustContribProj($proj); - return $proj; - } - else - { - croak "Could not determine contrib module type for $n\n"; - } -} - -sub AdjustContribProj -{ - my $proj = shift; - my $n = $proj->{name}; - - if ($contrib_defines->{$n}) - { - foreach my $d ($contrib_defines->{$n}) - { - $proj->AddDefine($d); - } - } - if (grep {/^$n$/} @contrib_uselibpq) - { - $proj->AddIncludeDir('src\interfaces\libpq'); - $proj->AddReference($libpq); - } - if (grep {/^$n$/} @contrib_uselibpgport) - { - $proj->AddReference($libpgport); - } - if ($contrib_extralibs->{$n}) - { - foreach my $l (@{$contrib_extralibs->{$n}}) - { - $proj->AddLibrary($l); - } - } - if ($contrib_extraincludes->{$n}) - { - foreach my $i (@{$contrib_extraincludes->{$n}}) - { - $proj->AddIncludeDir($i); - } - } - if ($contrib_extrasource->{$n}) - { - $proj->AddFiles('contrib\\' . $n, @{$contrib_extrasource->{$n}}); - } -} +Mkvcbuild::mkvcbuild($config); diff --git a/src/tools/msvc/vcregress.bat b/src/tools/msvc/vcregress.bat index c8954499437..af714835669 100644 --- a/src/tools/msvc/vcregress.bat +++ b/src/tools/msvc/vcregress.bat @@ -24,6 +24,8 @@ SET SCHEDULE=parallel SET TEMPPORT=54321 IF NOT "%2"=="" SET SCHEDULE=%2 +SET PERL5LIB=..\..\tools\msvc + if "%what%"=="INSTALLCHECK" ..\..\..\%CONFIG%\pg_regress\pg_regress --psqldir=..\..\..\%CONFIG%\psql --schedule=%SCHEDULE%_schedule --multibyte=SQL_ASCII --load-language=plpgsql --no-locale if "%what%"=="CHECK" ..\..\..\%CONFIG%\pg_regress\pg_regress --psqldir=..\..\..\%CONFIG%\psql --schedule=%SCHEDULE%_schedule --multibyte=SQL_ASCII --load-language=plpgsql --no-locale --temp-install=./tmp_check --top-builddir=%TOPDIR% --temp-port=%TEMPPORT% |