CC: | kwilliams [...] cpan.org |
Subject: | Build failure: undefined SYSTEM_LOCALTIME_MIN under Win32/MSVC |
Build of latest Time::y2038 CPAN fails for me under Windows Vista
and MSVC 2008 Express.
I managed to fix the issues, but I'm not sure if the applied patches
are right to the point. I'll describe errors and fixes tried.
1) perl Build.PL fails with the following error message:
Generating script 'C:\Users\Cosimo\AppData\Local\Temp\compilet.ccs'
cl -nologo -c @"C:\Users\Cosimo\AppData\Local\Temp\compilet.ccs" -
Fo"C:\Users\Cosimo\AppData\Local\Temp\compilet.obj" "C:\Users\Cosimo
\AppData\Local\Temp\compilet.c" compilet.c
Generating script 'C:\Users\Cosimo\AppData\Local\Temp\compilet.lds'
link @"C:\Users\Cosimo\AppData\Local\Temp\compilet.lds" -out:"C:
\Users\Cosimo\AppData\Local\Temp\compilet.dll"
Creating library C:\Users\Cosimo\AppData\Local\Temp\compilet.lib
and object C:\Users\Cosimo\AppData\Local\Temp\compilet.exp
mt -nologo -manifest "C:\Users\Cosimo\AppData\Local\Temp
\compilet.dll.manifest" -outputresource:"C:\Users\Cosimo\AppData\Local
\Temp\compilet.dll";2
Checking whether your kit is complete...
Looks good
Checking prerequisites...
Looks good
Building a program to test the range of your system time
functions...
Generating script 'check_max.ccs'
cl -nologo -c @"check_max.ccs" -Fo"check_max.obj" "check_max.c"
check_max.c
link -o check_max.exe check_max.obj
Microsoft (R) Incremental Linker Version 9.00.21022.08
Copyright (C) Microsoft Corporation. All rights reserved.
LINK : warning LNK4044: unrecognized option '/o'; ignored
check_max.exe : fatal error LNK1107: invalid or corrupt file:
cannot read at 0x248
error building check_max.exe from check_max.obj at c:/dev/perl510/
lib/ExtUtils/CBuilder/Base.pm line 213.
The problem is that MSVC wants `link /OUT:file.exe file.c' instead of
`link -o file.exe file.c'
I tracked this issue down to ExtUtils::CBuilder. Adding the following
overridden method in
ExtUtils::CBuilder::Platform::Windows seems to do the trick.
# Special case for MSVC linker
sub arg_exec_file {
my ($self, $file) = @_;
my $arg_exec_file;
# MSVC linker wants /OUT:file.exe
if ($self->_compiler_type eq 'MSVC') {
$arg_exec_file = "/OUT:$file";
}
# Normal behavior
else {
$arg_exec_file = $self->SUPER::arg_exec_file($file);
}
return $arg_exec_file;
}
2) Applying 1) allows to correctly pass the first step.
However, build fails with a syntax error:
C:\.cpan\build\Time-y2038-20081106-3Bmqot>Build
Generating script 'y2038\time64.ccs'
cl -nologo -c @"y2038\time64.ccs" -Fo"y2038\time64.obj"
"y2038\time64.c"
time64.c
y2038\time64.c(174) : warning C4244: '=' : conversion from 'Year'
to 'int', possible loss of data
y2038\time64.c(179) : warning C4244: '=' : conversion from 'Year'
to 'int', possible loss of data
y2038\time64.c(433) : warning C4244: '=' : conversion from 'Year'
to 'int', possible loss of data
y2038\time64.c(438) : warning C4244: '=' : conversion from 'Year'
to 'int', possible loss of data
y2038\time64.c(620) : error C2059: syntax error : ')'
y2038\time64.c(633) : error C2059: syntax error : 'if'
y2038\time64.c(638) : error C2065: 'gm_tm' : undeclared identifier
y2038\time64.c(638) : error C2224: left of '.tm_year' must have
struct/union type
y2038\time64.c(640) : error C2059: syntax error : 'if'
y2038\time64.c(648) : error C2065: 'gm_tm' : undeclared identifier
y2038\time64.c(648) : warning C4133: 'function' : incompatible
types - from 'int *' to 'const TM64 *'
y2038\time64.c(648) : error C2099: initializer is not a constant
y2038\time64.c(649) : error C2059: syntax error : 'if'
y2038\time64.c(654) : error C2143: syntax error : missing ')'
before '&'
y2038\time64.c(654) : error C2143: syntax error : missing '{'
before '&'
y2038\time64.c(654) : error C2059: syntax error : '&'
y2038\time64.c(654) : error C2059: syntax error : ')'
y2038\time64.c(656) : error C2143: syntax error : missing '{'
before '->'
y2038\time64.c(656) : error C2059: syntax error : '->'
y2038\time64.c(657) : error C2059: syntax error : 'if'
y2038\time64.c(668) : error C2065: 'local_tm' : undeclared
identifier
y2038\time64.c(668) : error C2223: left of '->tm_mon' must point to
struct/union
y2038\time64.c(668) : error C2065: 'gm_tm' : undeclared identifier
y2038\time64.c(668) : error C2224: left of '.tm_mon' must have
struct/union type
y2038\time64.c(673) : error C2059: syntax error : 'if'
y2038\time64.c(680) : error C2059: syntax error : 'if'
y2038\time64.c(690) : error C2059: syntax error : 'if'
y2038\time64.c(693) : error C2059: syntax error : 'type'
y2038\time64.c(695) : error C2059: syntax error : 'return'
y2038\time64.c(696) : error C2059: syntax error : '}'
error building dll file from 'y2038/time64.c' at c:/dev/perl510/lib/
ExtUtils/CBuilder/Platform/Windows.pm line 159.
Again, tracking down the issue reveals a problem in the preprocessed
source code:
/* SHOULD_USE_SYSTEM_LOCALTIME */
/* SYSTEM_LOCALTIME_MIN is missing */
if ( ((*time) <= 32535244799 && (*time) >= ) {
safe_time = *time;
// ...
return local_tm;
}
and in y2038/time64_config.h:
#define SYSTEM_LOCALTIME_MAX 32535244799
#define SYSTEM_LOCALTIME_MIN
#define SYSTEM_GMTIME_MAX 32535291599
#define SYSTEM_GMTIME_MIN -43200
SYSTEM_LOCALTIME_MIN is defined but empty, so this causes the syntax
error.
The following ugly patch to Build.PL works for me:
--- Build.PL.orig Sun Nov 09 12:01:02 2008
+++ Build.PL Sun Nov 09 12:01:50 2008
@@ -40,7 +40,10 @@
# Windows lies about being able to handle just a little bit of
# negative time.
for my $key (qw(gmtime_min localtime_min)) {
- if( -10_000 < $limits{$key} && $limits{$key} < 0 ) {
+ if( ! defined $limits{$key} ) {
+ $limits{$key} = 0;
+ }
+ elsif( -10_000 < $limits{$key} && $limits{$key} < 0 ) {
$limits{$key} = 0;
}
}
That's it.
Subject: | eu-cb.patch |
# Special case for MSVC linker
sub arg_exec_file {
my ($self, $file) = @_;
my $arg_exec_file;
# MSVC linker wants /OUT:file.exe
if ($self->_compiler_type eq 'MSVC') {
$arg_exec_file = "/OUT:$file";
}
# Normal behavior
else {
$arg_exec_file = $self->SUPER::arg_exec_file($file);
}
return $arg_exec_file;
}
Subject: | y2038time64_preprocess.c |
// SHOULD_USE_SYSTEM_LOCALTIME
if ( ((*time) <= 32535244799 && (*time) >= ) {
safe_time = *time;
((void)0);
fake_localtime_r(&safe_time, &safe_date);
copy_tm_to_TM(&safe_date, local_tm);
(void)( (!!(check_tm(local_tm))) || (_wassert(L"check_tm(local_tm)", L"y2038\\time64.c", 628), 0) );
return local_tm;
}
if( gmtime64_r(time, &gm_tm) == ((void *)0) ) {
((void)0);
return ((void *)0);
}
Subject: | time-y2038-buildpl.patch |
--- Build.PL.orig Sun Nov 09 12:01:02 2008
+++ Build.PL Sun Nov 09 12:01:50 2008
@@ -40,7 +40,10 @@
# Windows lies about being able to handle just a little bit of
# negative time.
for my $key (qw(gmtime_min localtime_min)) {
- if( -10_000 < $limits{$key} && $limits{$key} < 0 ) {
+ if( ! defined $limits{$key} ) {
+ $limits{$key} = 0;
+ }
+ elsif( -10_000 < $limits{$key} && $limits{$key} < 0 ) {
$limits{$key} = 0;
}
}