mirror of
https://github.com/boostorg/build.git
synced 2026-02-15 13:02:11 +00:00
Windows Boost Jam implementation now uses finer resolution than 1 second when creating timestamps based on the current system time. Since these are never (and should never be!) compared to file system timestamps - this causes no conflicts with file system timestamps still using 1 second resolution at best.
Related stylistic changes: - filetime_to_timestamp() function renamed to timestamp_from_filetime() and moved to the timestamp.c module. - filetime_to_seconds() function moved back to the execnt.c module as a static function as it only used from there after the timestamp_from_filetime() reimplementation in revision [79494]. - filent.h header now empty and removed. [SVN r79511]
This commit is contained in:
@@ -30,13 +30,15 @@
|
||||
* exec_check() - preprocess and validate the command
|
||||
* exec_cmd() - launch an async command execution
|
||||
* exec_wait() - wait for any of the async command processes to terminate
|
||||
*
|
||||
* Internal routines:
|
||||
* filetime_to_seconds() - Windows FILETIME --> number of seconds conversion
|
||||
*/
|
||||
|
||||
#include "jam.h"
|
||||
#ifdef USE_EXECNT
|
||||
#include "execcmd.h"
|
||||
|
||||
#include "filent.h"
|
||||
#include "lists.h"
|
||||
#include "output.h"
|
||||
#include "pathsys.h"
|
||||
@@ -47,6 +49,8 @@
|
||||
#include <errno.h>
|
||||
#include <time.h>
|
||||
|
||||
#define WIN32_LEAN_AND_MEAN
|
||||
#include <windows.h>
|
||||
#include <process.h>
|
||||
#include <tlhelp32.h>
|
||||
|
||||
@@ -663,6 +667,17 @@ static FILETIME negate_FILETIME( FILETIME t )
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* filetime_to_seconds() - Windows FILETIME --> number of seconds conversion
|
||||
*/
|
||||
|
||||
static double filetime_to_seconds( FILETIME const ft )
|
||||
{
|
||||
return ft.dwHighDateTime * ( (double)( 1UL << 31 ) * 2.0 * 1.0e-7 ) +
|
||||
ft.dwLowDateTime * 1.0e-7;
|
||||
}
|
||||
|
||||
|
||||
static void record_times( HANDLE const process, timing_info * const time )
|
||||
{
|
||||
FILETIME creation;
|
||||
@@ -673,8 +688,8 @@ static void record_times( HANDLE const process, timing_info * const time )
|
||||
{
|
||||
time->system = filetime_to_seconds( kernel );
|
||||
time->user = filetime_to_seconds( user );
|
||||
filetime_to_timestamp( creation, &time->start );
|
||||
filetime_to_timestamp( exit, &time->end );
|
||||
timestamp_from_filetime( &time->start, &creation );
|
||||
timestamp_from_filetime( &time->end, &exit );
|
||||
}
|
||||
}
|
||||
|
||||
@@ -850,10 +865,10 @@ static double running_time( HANDLE const process )
|
||||
FILETIME exit;
|
||||
FILETIME kernel;
|
||||
FILETIME user;
|
||||
FILETIME current;
|
||||
if ( GetProcessTimes( process, &creation, &exit, &kernel, &user ) )
|
||||
{
|
||||
/* Compute the elapsed time. */
|
||||
FILETIME current;
|
||||
GetSystemTimeAsFileTime( ¤t );
|
||||
return filetime_to_seconds( add_FILETIME( current,
|
||||
negate_FILETIME( creation ) ) );
|
||||
@@ -907,7 +922,6 @@ static double creation_time( HANDLE const process )
|
||||
FILETIME exit;
|
||||
FILETIME kernel;
|
||||
FILETIME user;
|
||||
FILETIME current;
|
||||
return GetProcessTimes( process, &creation, &exit, &kernel, &user )
|
||||
? filetime_to_seconds( creation )
|
||||
: 0.0;
|
||||
|
||||
@@ -15,10 +15,8 @@
|
||||
* filent.c - scan directories and archives on NT
|
||||
*
|
||||
* External routines:
|
||||
* file_archscan() - scan an archive for files
|
||||
* file_mkdir() - create a directory
|
||||
* filetime_to_seconds() - Windows FILETIME --> number of seconds conversion
|
||||
* filetime_to_timestamp() - Windows FILETIME --> timestamp conversion
|
||||
* file_archscan() - scan an archive for files
|
||||
* file_mkdir() - create a directory
|
||||
*
|
||||
* External routines called only via routines in filesys.c:
|
||||
* file_collect_dir_content_() - collects directory content information
|
||||
@@ -28,7 +26,6 @@
|
||||
|
||||
#include "jam.h"
|
||||
#ifdef OS_NT
|
||||
#include "filent.h"
|
||||
#include "filesys.h"
|
||||
|
||||
#include "object.h"
|
||||
@@ -44,6 +41,9 @@
|
||||
# define _finddata_t ffblk
|
||||
#endif
|
||||
|
||||
#define WIN32_LEAN_AND_MEAN
|
||||
#include <windows.h>
|
||||
|
||||
#include <assert.h>
|
||||
#include <ctype.h>
|
||||
#include <direct.h>
|
||||
@@ -351,45 +351,4 @@ void file_archscan( char const * archive, scanback func, void * closure )
|
||||
close( fd );
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* filetime_to_seconds() - Windows FILETIME --> number of seconds conversion
|
||||
*/
|
||||
|
||||
double filetime_to_seconds( FILETIME const t )
|
||||
{
|
||||
return t.dwHighDateTime * ( (double)( 1UL << 31 ) * 2.0 * 1.0e-7 ) +
|
||||
t.dwLowDateTime * 1.0e-7;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* filetime_to_timestamp() - Windows FILETIME --> timestamp conversion
|
||||
*
|
||||
* Lifted shamelessly from the CPython implementation.
|
||||
*/
|
||||
|
||||
void filetime_to_timestamp( FILETIME const ft, timestamp * const time )
|
||||
{
|
||||
/* Seconds between 1.1.1601 and 1.1.1970 */
|
||||
static __int64 const secs_between_epochs = 11644473600;
|
||||
|
||||
/* We can not simply cast and dereference a FILETIME, since it might not be
|
||||
* aligned properly. __int64 type variables are expected to be aligned to an
|
||||
* 8 byte boundary while FILETIME structures may be aligned to any 4 byte
|
||||
* boundary. Using an incorrectly aligned __int64 variable may cause a
|
||||
* performance penalty on some platforms or even exceptions on others
|
||||
* (documented on MSDN).
|
||||
*/
|
||||
__int64 in;
|
||||
memcpy( &in, &ft, sizeof( in ) );
|
||||
|
||||
/* FILETIME resolution: 100ns. */
|
||||
/* For resolutions finer than 1 second use the following:
|
||||
* nsec = (int)( in % 10000000 ) * 100;
|
||||
*/
|
||||
timestamp_init( time, (time_t)( ( in / 10000000 ) - secs_between_epochs ), 0
|
||||
);
|
||||
}
|
||||
|
||||
#endif /* OS_NT */
|
||||
|
||||
@@ -1,22 +0,0 @@
|
||||
/*
|
||||
* Copyright 2012 Jurko Gospodnetic
|
||||
* Distributed under the Boost Software License, Version 1.0.
|
||||
* (See accompanying file LICENSE_1_0.txt or http://www.boost.org/LICENSE_1_0.txt)
|
||||
*/
|
||||
|
||||
/*
|
||||
* filent.h - Windows specific file routines
|
||||
*/
|
||||
|
||||
#ifndef FILENT_JG20120714_H
|
||||
#define FILENT_JG20120714_H
|
||||
|
||||
#include "timestamp.h"
|
||||
|
||||
#define WIN32_LEAN_AND_MEAN
|
||||
#include <windows.h>
|
||||
|
||||
double filetime_to_seconds( FILETIME const ft );
|
||||
void filetime_to_timestamp( FILETIME const ft, timestamp * const time );
|
||||
|
||||
#endif
|
||||
@@ -69,6 +69,35 @@ static char * time_progress[] =
|
||||
};
|
||||
|
||||
|
||||
#ifdef OS_NT
|
||||
/*
|
||||
* timestamp_from_filetime() - Windows FILETIME --> timestamp conversion
|
||||
*
|
||||
* Lifted shamelessly from the CPython implementation.
|
||||
*/
|
||||
|
||||
void timestamp_from_filetime( timestamp * const t, FILETIME const * const ft )
|
||||
{
|
||||
/* Seconds between 1.1.1601 and 1.1.1970 */
|
||||
static __int64 const secs_between_epochs = 11644473600;
|
||||
|
||||
/* We can not simply cast and dereference a FILETIME, since it might not be
|
||||
* aligned properly. __int64 type variables are expected to be aligned to an
|
||||
* 8 byte boundary while FILETIME structures may be aligned to any 4 byte
|
||||
* boundary. Using an incorrectly aligned __int64 variable may cause a
|
||||
* performance penalty on some platforms or even exceptions on others
|
||||
* (documented on MSDN).
|
||||
*/
|
||||
__int64 in;
|
||||
memcpy( &in, ft, sizeof( in ) );
|
||||
|
||||
/* FILETIME resolution: 100ns. */
|
||||
timestamp_init( t, (time_t)( ( in / 10000000 ) - secs_between_epochs ),
|
||||
(int)( in % 10000000 ) * 100 );
|
||||
}
|
||||
#endif /* OS_NT */
|
||||
|
||||
|
||||
void timestamp_clear( timestamp * const time )
|
||||
{
|
||||
time->secs = time->nsecs = 0;
|
||||
@@ -92,7 +121,16 @@ void timestamp_copy( timestamp * const target, timestamp const * const source )
|
||||
|
||||
void timestamp_current( timestamp * const t )
|
||||
{
|
||||
#ifdef OS_NT
|
||||
/* GetSystemTimeAsFileTime()'s resolution seems to be about 15 ms on Windows
|
||||
* XP and under a millisecond on Windows 7.
|
||||
*/
|
||||
FILETIME ft;
|
||||
GetSystemTimeAsFileTime( &ft );
|
||||
timestamp_from_filetime( t, &ft );
|
||||
#else /* OS_NT */
|
||||
timestamp_init( t, time( 0 ), 0 );
|
||||
#endif /* OS_NT */
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -13,6 +13,11 @@
|
||||
|
||||
#include "object.h"
|
||||
|
||||
#ifdef OS_NT
|
||||
# define WIN32_LEAN_AND_MEAN
|
||||
# include <windows.h>
|
||||
#endif
|
||||
|
||||
#include <time.h>
|
||||
|
||||
typedef struct timestamp
|
||||
@@ -21,17 +26,20 @@ typedef struct timestamp
|
||||
int nsecs;
|
||||
} timestamp;
|
||||
|
||||
void timestamp_clear( timestamp * const time );
|
||||
void timestamp_clear( timestamp * const );
|
||||
int timestamp_cmp( timestamp const * const lhs, timestamp const * const rhs );
|
||||
void timestamp_copy( timestamp * const target, timestamp const * const source );
|
||||
void timestamp_current( timestamp * const time );
|
||||
int timestamp_empty( timestamp const * const time );
|
||||
void timestamp_from_path( timestamp * const time, OBJECT * const path );
|
||||
void timestamp_init( timestamp * const time, time_t const secs, int const nsecs
|
||||
);
|
||||
void timestamp_current( timestamp * const );
|
||||
int timestamp_empty( timestamp const * const );
|
||||
void timestamp_from_path( timestamp * const, OBJECT * const path );
|
||||
void timestamp_init( timestamp * const, time_t const secs, int const nsecs );
|
||||
void timestamp_max( timestamp * const max, timestamp const * const lhs,
|
||||
timestamp const * const rhs );
|
||||
char const * timestamp_str( timestamp const * const time );
|
||||
char const * timestamp_str( timestamp const * const );
|
||||
|
||||
#ifdef OS_NT
|
||||
void timestamp_from_filetime( timestamp * const, FILETIME const * const );
|
||||
#endif
|
||||
|
||||
void timestamp_done();
|
||||
|
||||
|
||||
Reference in New Issue
Block a user