Ticket #5850: bbug.cpp

File bbug.cpp, 3.9 KB (added by Ken Harris <kharris@…>, 11 years ago)
Line 
1
2#include "stdafx.h"
3#include <stdlib.h>
4#include <stdio.h>
5#include <string.h>
6#include <sys/utime.h>
7
8#include <boost/filesystem.hpp>
9
10#include <windows.h>
11
12int main(int argc, char *argv[])
13{
14 time_t modtime = time(NULL) - 24 * 60 * 60;
15 FILE *f;
16
17 if (argc < 3) {
18 printf("please provide 2 different test files paths on a network driver, i.e. '<prog> Y:\\afile.txt Y:\\bfile.txt'\n");
19 return 1;
20 }
21 char *boostfile = argv[1];
22 char *utimefile = argv[2];
23 //
24 // demonstrate the problem first
25 //
26 printf("\ntest boost::last_write_time(f,t) to modifty last write time on %s\n", boostfile);
27
28 f = fopen(boostfile,"wb"); fwrite("X",1,1,f); fclose(f);
29 printf("%lld - original last write time\n", boost::filesystem::last_write_time(boostfile));
30
31 f = fopen(boostfile,"r+b"); fwrite("X",1,1,f); fclose(f);
32 boost::filesystem::last_write_time(boostfile, modtime);
33 printf("%lld - last write time after calling boost::last_write_time to modify it\n", boost::filesystem::last_write_time(boostfile));
34
35 f = fopen(boostfile,"r"); fclose(f);
36 printf("%lld [TEST:%s] last write opening for read - Expected %lld\n",
37 boost::filesystem::last_write_time(boostfile),
38 boost::filesystem::last_write_time(boostfile) == modtime ? "PASS" : "FAIL",
39 modtime);
40
41 //
42 // demonstrate the problem expected behavior
43 //
44 printf("\ntest utime() on %s\n", utimefile);
45
46 f = fopen(utimefile,"wb"); fwrite("X",1,1,f); fclose(f);
47 printf("%lld - original last write time\n", boost::filesystem::last_write_time(utimefile));
48
49 f = fopen(utimefile,"r+b"); fwrite("X",1,1,f); fclose(f);
50
51 struct utimbuf u;
52 u.actime = 0;
53 u.modtime = modtime;
54 utime(utimefile, &u);
55
56 printf("%lld - last write time after calling utime() to modify it\n", boost::filesystem::last_write_time(utimefile));
57
58 f = fopen(utimefile,"r"); fclose(f);
59 printf("%lld [TEST:%s] last write opening for read - Expected %lld\n",
60 boost::filesystem::last_write_time(utimefile),
61 boost::filesystem::last_write_time(utimefile) == modtime ? "PASS" : "FAIL",
62 modtime);
63
64 //
65 // demonstrate perhaps how to fix it using FILE_GENERIC_WRITE rather than just FILE_WRITE_ATTRIBUTES
66 //
67 printf("\nshow 'better' windows API usage to modifty last write time on %s\n", boostfile);
68
69 f = fopen(boostfile,"wb"); fwrite("X",1,1,f); fclose(f);
70 printf("%lld original last write time\n", boost::filesystem::last_write_time(boostfile));
71
72 f = fopen(boostfile,"r+b"); fwrite("X",1,1,f); fclose(f);
73
74 // using boost's technique as see in http://svn.boost.org/svn/boost/trunk/libs/filesystem/v3/src/operations.cpp (in last_write_time -- variant that modifies time)
75 // or http://svn.boost.org/svn/boost/trunk/libs/filesystem/v2/src/v2_operations.cpp (in set_file_write_time )
76 {
77 HANDLE h = CreateFileA(boostfile, FILE_GENERIC_WRITE,
78 FILE_SHARE_DELETE | FILE_SHARE_READ | FILE_SHARE_WRITE, 0,
79 OPEN_EXISTING, FILE_FLAG_BACKUP_SEMANTICS, 0);
80
81 FILETIME lwt;
82 __int64 temp = modtime;
83 temp *= 10000000;
84 temp += 116444736000000000LL;
85
86 lwt.dwLowDateTime = static_cast<DWORD>(temp);
87 lwt.dwHighDateTime = static_cast<DWORD>(temp >> 32);
88
89 SetFileTime(h, 0, 0, &lwt);
90 }
91 printf("%lld - last write time after calling native SetFileTime() with a handle with FILE_GENERIC_ACCESS\n", boost::filesystem::last_write_time(boostfile));
92
93 f = fopen(boostfile,"r"); fclose(f);
94 printf("%lld [TEST:%s] last write opening for read - Expected %lld\n",
95 boost::filesystem::last_write_time(boostfile),
96 boost::filesystem::last_write_time(boostfile) == modtime ? "PASS" : "FAIL",
97 modtime);
98
99 return 0;
100}
101