blob: 79eb1f8957287411dda39629031b9c850aa528a0 [file] [log] [blame]
Benny Prijono9033e312005-11-21 02:08:39 +00001/* $Id$ */
2/*
3 * Copyright (C)2003-2006 Benny Prijono <benny@prijono.org>
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18 */
19#include <pj/file_access.h>
20#include <pj/assert.h>
21#include <pj/errno.h>
22#include <windows.h>
23#include <time.h>
24
25/*
26 * pj_file_exists()
27 */
28PJ_DEF(pj_bool_t) pj_file_exists(const char *filename)
29{
30 HANDLE hFile;
31
32 PJ_ASSERT_RETURN(filename != NULL, 0);
33
34 hFile = CreateFile(filename, READ_CONTROL, FILE_SHARE_READ, NULL,
35 OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
36 if (hFile == INVALID_HANDLE_VALUE)
37 return 0;
38
39 CloseHandle(hFile);
40 return PJ_TRUE;
41}
42
43
44/*
45 * pj_file_size()
46 */
47PJ_DEF(pj_off_t) pj_file_size(const char *filename)
48{
49 HANDLE hFile;
50 DWORD sizeLo, sizeHi;
51 pj_off_t size;
52
53 PJ_ASSERT_RETURN(filename != NULL, -1);
54
55 hFile = CreateFile(filename, READ_CONTROL,
56 FILE_SHARE_READ | FILE_SHARE_WRITE, NULL,
57 OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
58 if (hFile == INVALID_HANDLE_VALUE)
59 return -1;
60
61 sizeLo = GetFileSize(hFile, &sizeHi);
62 if (sizeLo == INVALID_FILE_SIZE) {
63 DWORD dwStatus = GetLastError();
64 if (dwStatus != NO_ERROR) {
65 CloseHandle(hFile);
66 return -1;
67 }
68 }
69
70 size = sizeHi;
71 size = (size << 32) + sizeLo;
72
73 CloseHandle(hFile);
74 return size;
75}
76
77
78/*
79 * pj_file_delete()
80 */
81PJ_DEF(pj_status_t) pj_file_delete(const char *filename)
82{
83 PJ_ASSERT_RETURN(filename != NULL, PJ_EINVAL);
84
85 if (DeleteFile(filename) == FALSE)
86 return PJ_RETURN_OS_ERROR(GetLastError());
87
88 return PJ_SUCCESS;
89}
90
91
92/*
93 * pj_file_move()
94 */
95PJ_DEF(pj_status_t) pj_file_move( const char *oldname, const char *newname)
96{
97 BOOL rc;
98
99 PJ_ASSERT_RETURN(oldname!=NULL && newname!=NULL, PJ_EINVAL);
100
101#if PJ_WIN32_WINNT >= 0x0400
102 rc = MoveFileEx(oldname, newname,
103 MOVEFILE_COPY_ALLOWED|MOVEFILE_REPLACE_EXISTING);
104#else
105 rc = MoveFile(oldname, newname);
106#endif
107
108 if (!rc)
109 return PJ_RETURN_OS_ERROR(GetLastError());
110
111 return PJ_SUCCESS;
112}
113
114
115static pj_status_t file_time_to_time_val(const FILETIME *file_time,
116 pj_time_val *time_val)
117{
118 SYSTEMTIME systemTime, localTime;
119 struct tm tm;
120
121 if (!FileTimeToSystemTime(file_time, &systemTime))
122 return -1;
123
124 if (!SystemTimeToTzSpecificLocalTime(NULL, &systemTime, &localTime))
125 return -1;
126
127 memset(&tm, 0, sizeof(struct tm));
128 tm.tm_year = localTime.wYear - 1900;
129 tm.tm_mon = localTime.wMonth - 1;
130 tm.tm_mday = localTime.wDay;
131 tm.tm_hour = localTime.wHour;
132 tm.tm_min = localTime.wMinute;
133 tm.tm_sec = localTime.wSecond;
134 tm.tm_isdst = 0;
135
136 time_val->sec = mktime(&tm);
137 if (time_val->sec == (time_t)-1)
138 return -1;
139
140 time_val->msec = localTime.wMilliseconds;
141
142 return PJ_SUCCESS;
143}
144
145/*
146 * pj_file_getstat()
147 */
148PJ_DEF(pj_status_t) pj_file_getstat(const char *filename, pj_file_stat *stat)
149{
150 HANDLE hFile;
151 DWORD sizeLo, sizeHi;
152 FILETIME creationTime, accessTime, writeTime;
153
154 PJ_ASSERT_RETURN(filename!=NULL && stat!=NULL, PJ_EINVAL);
155
156 hFile = CreateFile(filename, READ_CONTROL, FILE_SHARE_READ, NULL,
157 OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
158 if (hFile == INVALID_HANDLE_VALUE)
159 return PJ_RETURN_OS_ERROR(GetLastError());
160
161 sizeLo = GetFileSize(hFile, &sizeHi);
162 if (sizeLo == INVALID_FILE_SIZE) {
163 DWORD dwStatus = GetLastError();
164 if (dwStatus != NO_ERROR) {
165 CloseHandle(hFile);
166 return PJ_RETURN_OS_ERROR(dwStatus);
167 }
168 }
169
170 stat->size = sizeHi;
171 stat->size = (stat->size << 32) + sizeLo;
172
173 if (GetFileTime(hFile, &creationTime, &accessTime, &writeTime)==FALSE) {
174 DWORD dwStatus = GetLastError();
175 CloseHandle(hFile);
176 return PJ_RETURN_OS_ERROR(dwStatus);
177 }
178
179 CloseHandle(hFile);
180
181 if (file_time_to_time_val(&creationTime, &stat->ctime) != PJ_SUCCESS)
182 return PJ_RETURN_OS_ERROR(GetLastError());
183
184 file_time_to_time_val(&accessTime, &stat->atime);
185 file_time_to_time_val(&writeTime, &stat->mtime);
186
187 return PJ_SUCCESS;
188}
189