]>
git.proxmox.com Git - mirror_edk2.git/blob - Tools/CCode/Source/SetStamp/SetStamp.c
3 Copyright (c) 2004 - 2007, Intel Corporation
4 All rights reserved. This program and the accompanying materials
5 are licensed and made available under the terms and conditions of the BSD License
6 which accompanies this distribution. The full text of the license may be found at
7 http://opensource.org/licenses/bsd-license.php
9 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
10 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
16 Set Date/Time Stamp of Portable Executable (PE) format file
24 #define LINE_MAXLEN 80
29 #define UTILITY_NAME "SetStamp"
32 // Utility version information
34 #define UTILITY_MAJOR_VERSION 0
35 #define UTILITY_MINOR_VERSION 1
45 Displays the standard utility information to SDTOUT
57 printf ( "%s v%d.%d -Utility to set Date/Time Stamp for Portable Executable (PE) format file. \n " , UTILITY_NAME
, UTILITY_MAJOR_VERSION
, UTILITY_MINOR_VERSION
);
58 printf ( "Copyright (c) 1999-2007 Intel Corporation. All rights reserved. \n " );
67 print usage of setstamp command
79 // print usage of command
81 printf ( " \n Usage: SetStamp <PE-File> <TIME-File> \n " );
91 Read the date and time from TIME file. If the date/time string is
92 "NOW NOW", write the current date and time to TIME file and set it to
93 ltime. Else, set the date and time of TIME file to ltime.
96 fp - The pointer of TIME file
104 char buffer
[ LINE_MAXLEN
];
108 if ( fgets ( buffer
, LINE_MAXLEN
, fp
) == NULL
) {
109 printf ( "Error: Cannot read TIME file. \n " );
113 // compare the value with "NOW NOW", write TIME file if equal
115 if ( strncmp ( buffer
, "NOW NOW" , 7 ) == 0 ) {
117 // get system current time and date
121 now
= localtime ( ltime
);
123 printf ( "Error: Cannot get local time. \n " );
127 if ( strftime ( buffer
, LINE_MAXLEN
, "%Y-%m-%d %H:%M:%S" , now
) == 0 ) {
128 printf ( "Error: Cannot format time string. \n " );
134 if ( fseek ( fp
, 0 , SEEK_SET
) != 0 ) {
135 printf ( "Error: Cannot move location of TIME file. \n " );
139 if ( fputs ( buffer
, fp
) == EOF
) {
140 printf ( "Error: Cannot write time string to TIME file. \n " );
144 // ltime has been set as current time and date, return
149 // get the date and time from buffer
161 printf ( "Error: Invaild date or time! \n " );
165 // in struct, Month (0 - 11; Jan = 0). So decrease 1 from it
170 // in struct, Year (current year minus 1900)
171 // and only the dates can be handled from Jan 1, 1970 to Jan 18, 2038
174 // convert 0 -> 100 (2000), 1 -> 101 (2001), ..., 38 -> 138 (2038)
176 if ( stime
. tm_year
<= 38 ) {
177 stime
. tm_year
+= 100 ;
180 // convert 1970 -> 70, 2000 -> 100, ...
182 else if ( stime
. tm_year
>= 1970 ) {
183 stime
. tm_year
-= 1900 ;
186 // convert the date and time to time_t format
188 * ltime
= mktime (& stime
);
189 if (* ltime
== ( time_t ) - 1 ) {
190 printf ( "Error: Invalid date or time! \n " );
206 read data from a specified location of file
210 offset - number of bytes from beginning of file
211 buffer - buffer used to store data
212 size - size of buffer
220 // set file pointer to the specified location of file
222 if ( fseek ( fp
, offset
, SEEK_SET
) != 0 ) {
223 printf ( "Error: Cannot move the current location of the file. \n " );
227 // read data from the file
229 if ( fread ( buffer
, size
, 1 , fp
) != 1 ) {
230 printf ( "Error: Cannot read data from the file. \n " );
246 write data to a specified location of file
250 offset - number of bytes from beginning of file
251 buffer - buffer used to store data
252 size - size of buffer
260 // set file pointer to the specified location of file
262 if ( fseek ( fp
, offset
, SEEK_SET
) != 0 ) {
263 printf ( "Error: Cannot move the current location of the file. \n " );
267 // write data to the file
269 if ( fwrite ( buffer
, size
, 1 , fp
) != 1 ) {
270 perror ( "Error: Cannot write data to the file. \n " );
284 set Date/Time Stamp of the file
288 ltime - time and date
295 unsigned char header
[ 4 ];
296 unsigned long offset
;
297 unsigned long NumberOfRvaAndSizes
;
299 unsigned long lvalue
;
302 // read the header of file
304 if ( ReadFromFile ( fp
, 0 , header
, 2 ) != 0 ) {
308 // "MZ" -- the header of image file (PE)
310 if ( strncmp (( char *) header
, "MZ" , 2 ) != 0 ) {
311 printf ( "Error: Invalid Image file. \n " );
315 // At location 0x3C, the stub has the file offset to the
318 if ( ReadFromFile ( fp
, 0x3C , & offset
, 4 ) != 0 ) {
322 // read the header of optional
324 if ( ReadFromFile ( fp
, offset
, header
, 4 ) != 0 ) {
328 // "PE\0\0" -- the signature of optional header
330 if ( strncmp (( char *) header
, "PE\0\0" , 4 ) != 0 ) {
331 printf ( "Error: Invalid PE format file. \n " );
335 // Add 8 to skip PE signature (4-byte), Machine (2-byte) and
336 // NumberOfSection (2-byte)
340 if ( WriteToFile ( fp
, offset
, & ltime
, 4 ) != 0 ) {
344 // Add 16 to skip COFF file header, and get to optional header.
349 // Check the magic field, 0x10B for PE32 and 0x20B for PE32+
351 if ( ReadFromFile ( fp
, offset
, & nvalue
, 2 ) != 0 ) {
355 // If this is PE32 image file, offset of NumberOfRvaAndSizes is 92.
358 switch ( nvalue
& 0xFFFF ) {
368 printf ( "Error: Sorry! The Magic value is unknown. \n " );
372 // get the value of NumberOfRvaAndSizes
374 if ( ReadFromFile ( fp
, offset
, & NumberOfRvaAndSizes
, 4 ) != 0 ) {
378 // Date/time stamp exists in Export Table, Import Table, Resource Table,
379 // Debug Table and Delay Import Table. And in Import Table and Delay Import
380 // Table, it will be set when bound. So here only set the date/time stamp
381 // of Export Table, Resource Table and Debug Table.
384 // change date/time stamp of Export Table, the offset of Export Table
385 // is 4 + 0 * 8 = 4. And the offset of stamp is 4.
387 if ( NumberOfRvaAndSizes
>= 1 ) {
388 if ( ReadFromFile ( fp
, offset
+ 4 , & lvalue
, 4 ) != 0 ) {
393 if ( WriteToFile ( fp
, lvalue
+ 4 , & ltime
, 4 ) != 0 ) {
399 // change date/time stamp of Resource Table, the offset of Resource Table
400 // is 4 + 2 * 8 = 20. And the offset of stamp is 4.
402 if ( NumberOfRvaAndSizes
>= 3 ) {
403 if ( ReadFromFile ( fp
, offset
+ 20 , & lvalue
, 4 ) != 0 ) {
408 if ( WriteToFile ( fp
, lvalue
+ 4 , & ltime
, 4 ) != 0 ) {
414 // change date/time stamp of Debug Table, offset of Debug Table
415 // is 4 + 6 * 8 = 52. And the offset of stamp is 4.
417 if ( NumberOfRvaAndSizes
>= 7 ) {
418 if ( ReadFromFile ( fp
, offset
+ 52 , & lvalue
, 4 ) != 0 ) {
423 if ( WriteToFile ( fp
, lvalue
+ 4 , & ltime
, 4 ) != 0 ) {
428 // change the date/time stamp of Debug Data
430 if ( ReadFromFile ( fp
, lvalue
+ 24 , & lvalue
, 4 ) != 0 ) {
434 // get the signature of debug data
436 if ( ReadFromFile ( fp
, lvalue
, header
, 2 ) != 0 ) {
440 // "NB" - the signature of Debug Data
441 // Need Review: (From Spec. is "NB05", From .dll is "NB10")
443 if ( strncmp (( char *) header
, "NB" , 2 ) == 0 ) {
444 if ( WriteToFile ( fp
, lvalue
+ 8 , & ltime
, 4 ) != 0 ) {
467 if (( strcmp ( argv
[ 1 ], "-h" ) == 0 ) || ( strcmp ( argv
[ 1 ], "--help" ) == 0 ) ||
468 ( strcmp ( argv
[ 1 ], "-?" ) == 0 ) || ( strcmp ( argv
[ 1 ], "/?" ) == 0 )) {
473 if (( strcmp ( argv
[ 1 ], "-V" ) == 0 ) || ( strcmp ( argv
[ 1 ], "--version" ) == 0 )) {
478 // check the number of parameters
485 // open the TIME file, if not exists, return
487 fp
= fopen ( argv
[ 2 ], "r+" );
492 // get time and date from file
494 if ( GetDateTime ( fp
, & ltime
) != 0 ) {
499 // close the TIME file
506 fp
= fopen ( argv
[ 1 ], "r+b" );
508 printf ( "Error: Cannot open the PE file! \n " );
512 // set time and date stamp to the PE file
514 if ( SetStamp ( fp
, ltime
) != 0 ) {
519 printf ( "Set Date/Time Stamp to %s" , ctime (& ltime
));