source: libcf/trunk/src/cf_file.c@ 117

Last change on this file since 117 was 117, checked in by cheese, 11 years ago

#1 more fix and arrange doxygen comments

File size: 5.1 KB
RevLine 
[4]1/**
[28]2 * @file cf_file.c
3 * @author myusgun <myusgun@gmail.com>
[117]4 *
5 * @brief 파일 입출력 구현
[4]6 */
7#include "cf_file.h"
[66]8#include "cf_local.h"
[40]9#include "cf_error.h"
[4]10
[41]11#include <stdio.h>
[90]12#include <fcntl.h>
[41]13#include <errno.h>
14#include <sys/stat.h>
15
[50]16#if defined(_WIN32) || defined(_WIN64)
[4]17# include <io.h>
[55]18# include <direct.h>
[14]19
[41]20# define DELIMITER '\\'
21# define mkdir(a,b) _mkdir (a)
22# define access(a,b) _access (a,b)
23
[43]24# define F_OK 0
25# define W_OK 2
26# define R_OK 4
27
[41]28/*------------------------------*/
[14]29# define S_IWUSR _S_IWRITE
30# define S_IRUSR _S_IREAD
31# define S_IXUSR _S_IEXEC
[41]32/*------------------------------*/
[14]33# define S_IRGRP 0x00000000
34# define S_IWGRP 0x00000000
35# define S_IXGRP 0x00000000
[41]36/*------------------------------*/
[14]37# define S_IROTH 0x00000000
38# define S_IWOTH 0x00000000
39# define S_IXOTH 0x00000000
[41]40/*------------------------------*/
41# define S_IRWXU 0x00000000
[50]42#else // #if defined(_WIN32) || defined(_WIN64)
[4]43# include <unistd.h>
[41]44
45# define DELIMITER '/'
[26]46# define O_BINARY 0x00000000
[50]47#endif // #if defined(_WIN32) || defined(_WIN64)
[4]48
[41]49#define DIRECTORY_MODE S_IRWXU|S_IRGRP|S_IXGRP|S_IROTH|S_IXOTH
50#define FILE_MODE S_IWUSR|S_IRUSR|S_IRGRP|S_IROTH
[15]51
[85]52#define ASSERT_ARGS(x) \
53 if ((x)) \
[55]54 return CF_ERROR_FILE_INVALID_ARGS
55
[90]56static int
57CF_File_Local_ConvertFlag (const CF_FILE_FLAG flag)
58{
59 int result = 0;
60
61 if (flag & CF_FILE_READ) result |= O_RDONLY;
62 if (flag & CF_FILE_WRITE) result |= O_WRONLY;
63 if (flag & CF_FILE_RW) result |= O_RDWR;
64 if (flag & CF_FILE_CREATE) result |= O_CREAT;
65 if (flag & CF_FILE_TRUNC) result |= O_TRUNC;
66 if (flag & CF_FILE_APPEND) result |= O_APPEND;
67
68 return result;
69}
70
[35]71/**
72 * 파일 열기
73 *
74 * @return 성공 시, 파일 디스크립터; 실패 시, 오류 코드
75 *
76 * @param path 파일 경로
77 * @param flag 파일 열기 플래그
78 *
79 * @see CF_FILE_FLAG
80 */
[4]81int
[16]82CF_File_Open (const char * path,
83 const CF_FILE_FLAG flag)
[4]84{
[55]85 int result = 0;
[93]86 int osflag = 0;
[4]87
[55]88 ASSERT_ARGS (path == NULL);
89
[93]90 osflag = CF_File_Local_ConvertFlag (flag) | O_BINARY;
91
92 result = open (path, osflag, FILE_MODE);
[4]93 if (result < 0)
94 return CF_ERROR_FILE_OPEN;
95
96 return result;
97}
98
[35]99/**
100 * 파일 생성
101 *
102 * @return 성공 시, 파일 디스크립터; 실패 시, 오류 코드
103 *
[41]104 * @param path 파일 경로
[35]105 */
[4]106int
107CF_File_Create (const char * path)
108{
[93]109 int result = 0;
110 const int flag = CF_FILE_CREATE|CF_FILE_WRITE|CF_FILE_TRUNC;
[55]111
112 ASSERT_ARGS (path == NULL);
[4]113
[93]114 result = CF_File_Open (path, flag);
[4]115 if (result < 0)
116 return CF_ERROR_FILE_CREATE;
117
118 return result;
119}
120
[35]121/**
122 * 파일 닫기
123 *
124 * @return 성공 시, CF_OK; 실패 시, 오류 코드
125 *
126 * @param fd 파일 디스크립터
127 */
[4]128int
129CF_File_Close (const int fd)
130{
131 int result = 0;
132
[55]133 ASSERT_ARGS (fd < 0);
[4]134
135 result = close (fd);
136 if (result < 0)
137 return CF_ERROR_FILE_CLOSE;
138
139 return CF_OK;
140}
141
[35]142/**
143 * 파일 읽기
144 *
145 * @return 성공 시, 읽은 바이트 수; 실패 시, 오류 코드
146 *
147 * @param fd 파일 디스크립터
148 * @param buf 데이터를 저장할 메모리
149 * @param len 데이터를 저장할 메모리의 크기
150 */
[4]151int
152CF_File_Read (const int fd,
153 void * buf,
154 const size_t len)
155{
[55]156 int result = 0;
157
158 ASSERT_ARGS (fd < 0);
159 ASSERT_ARGS (buf == NULL);
[4]160
[55]161 result = (int) read (fd, buf, len);
[4]162 if (result < 0)
163 return CF_ERROR_FILE_READ;
164
[26]165 return result;
[4]166}
167
[35]168/**
169 * 파일 쓰기
170 *
171 * @return 성공 시, CF_OK; 실패 시, 오류 코드
172 *
173 * @param fd 파일 디스크립터
174 * @param buf 데이터가 저장된 메모리
175 * @param len 쓸 데이터의 길이
176 */
[4]177int
178CF_File_Write (const int fd,
179 const void * buf,
180 const size_t len)
181{
[55]182 int result = 0;
183
184 ASSERT_ARGS (fd < 0);
185 ASSERT_ARGS (buf == NULL);
[4]186
[58]187 result = (int) write (fd, buf, len);
[4]188 if (result != len)
189 return CF_ERROR_FILE_WRITE;
190
191 return CF_OK;
192}
193
[35]194/**
195 * 파일 크기 얻기
196 *
197 * @return 성공 시, 파일 크기; 실패 시, 오류 코드
198 *
[95]199 * @param path 파일 경로
[35]200 */
[4]201int
[94]202CF_File_GetSize (const char * path)
[4]203{
[94]204 int length = 0;
205 int fd = 0;
[4]206
[94]207 ASSERT_ARGS (path == NULL);
[55]208
[94]209 fd = CF_File_Open (path, CF_FILE_READ);
210 if (fd < 0)
211 return CF_ERROR_FILE_OPEN;
212
213 length = (int) lseek (fd, 0, SEEK_END);
214 if (length < 0)
[4]215 return CF_ERROR_FILE_GET_SIZE;
216
[94]217 CF_File_Close (fd);
218
219 return length;
[4]220}
[41]221
222/**
[109]223 * 파일 및 디렉터리 존재 여부 검사
224 *
225 * @return 존재 시, CF_TRUE; 아니면, CF_FALSE
226 *
227 * @param path 파일 및 디렉터리 경로
228 */
229CF_BOOL
230CF_File_Exists (const char * path)
231{
232 return (access (path, F_OK) == 0) ? CF_TRUE : CF_FALSE;
233}
234
235/**
[41]236 * 디렉터리 생성
237 *
238 * @return 성공 시, CF_OK; 실패 시, 오류 코드
239 *
240 * @param path 생성할 디렉터리 경로
241 */
242int
243CF_File_MakeDirectory (const char * path)
244{
245 int result = 0;
246 char fullPath[1024] = {0x00,};
247 char stepPath[256] = {0x00,};
248
249 char * f = fullPath;
250 char * d = stepPath;
251
[55]252 ASSERT_ARGS (path == NULL);
253
[46]254 snprintf (fullPath, sizeof (fullPath) - 1, "%s%c", path, DELIMITER);
[41]255
256 for (*d++ = *f++ ; *f ; *d++ = *f++)
257 {
258 if (*f != DELIMITER)
259 continue;
260
[109]261 if (CF_File_Exists (stepPath))
[41]262 continue;
263
264 result = mkdir (stepPath, DIRECTORY_MODE);
265 if (result && errno != EEXIST)
266 return CF_ERROR_FILE_MAKE_DIRECTORY;
267 }
268
269 return CF_OK;
270}
Note: See TracBrowser for help on using the repository browser.