OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2013 Google Inc. | 2 * Copyright 2013 Google Inc. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
6 */ | 6 */ |
7 | 7 |
8 #include "SkOSFile.h" | 8 #include "SkOSFile.h" |
9 | 9 |
10 #include "SkTFitsIn.h" | 10 #include "SkTFitsIn.h" |
(...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
113 } | 113 } |
114 | 114 |
115 void* sk_fmmap(SkFILE* f, size_t* length) { | 115 void* sk_fmmap(SkFILE* f, size_t* length) { |
116 int fileno = sk_fileno(f); | 116 int fileno = sk_fileno(f); |
117 if (fileno < 0) { | 117 if (fileno < 0) { |
118 return NULL; | 118 return NULL; |
119 } | 119 } |
120 | 120 |
121 return sk_fdmmap(fileno, length); | 121 return sk_fdmmap(fileno, length); |
122 } | 122 } |
| 123 |
| 124 //////////////////////////////////////////////////////////////////////////// |
| 125 |
| 126 struct SkOSFileIterData { |
| 127 SkOSFileIterData() : fHandle(0), fPath16(NULL) { } |
| 128 HANDLE fHandle; |
| 129 uint16_t* fPath16; |
| 130 }; |
| 131 SK_COMPILE_ASSERT(sizeof(SkOSFileIterData) <= SkOSFile::Iter::kStorageSize, not_
enough_space); |
| 132 |
| 133 static uint16_t* concat_to_16(const char src[], const char suffix[]) { |
| 134 size_t i, len = strlen(src); |
| 135 size_t len2 = 3 + (suffix ? strlen(suffix) : 0); |
| 136 uint16_t* dst = (uint16_t*)sk_malloc_throw((len + len2) * sizeof(uint16_t)); |
| 137 |
| 138 for (i = 0; i < len; i++) { |
| 139 dst[i] = src[i]; |
| 140 } |
| 141 |
| 142 if (i > 0 && dst[i-1] != '/') { |
| 143 dst[i++] = '/'; |
| 144 } |
| 145 dst[i++] = '*'; |
| 146 |
| 147 if (suffix) { |
| 148 while (*suffix) { |
| 149 dst[i++] = *suffix++; |
| 150 } |
| 151 } |
| 152 dst[i] = 0; |
| 153 SkASSERT(i + 1 <= len + len2); |
| 154 |
| 155 return dst; |
| 156 } |
| 157 |
| 158 SkOSFile::Iter::Iter() { |
| 159 SkNEW_PLACEMENT(fSelf.get(), SkOSFileIterData); |
| 160 } |
| 161 |
| 162 SkOSFile::Iter::Iter(const char path[], const char suffix[]) { |
| 163 SkNEW_PLACEMENT(fSelf.get(), SkOSFileIterData); |
| 164 this->reset(path, suffix); |
| 165 } |
| 166 |
| 167 SkOSFile::Iter::~Iter() { |
| 168 SkOSFileIterData& self = *static_cast<SkOSFileIterData*>(fSelf.get()); |
| 169 sk_free(self.fPath16); |
| 170 if (self.fHandle) { |
| 171 ::FindClose(self.fHandle); |
| 172 } |
| 173 self.~SkOSFileIterData(); |
| 174 } |
| 175 |
| 176 void SkOSFile::Iter::reset(const char path[], const char suffix[]) { |
| 177 SkOSFileIterData& self = *static_cast<SkOSFileIterData*>(fSelf.get()); |
| 178 if (self.fHandle) { |
| 179 ::FindClose(self.fHandle); |
| 180 self.fHandle = 0; |
| 181 } |
| 182 if (NULL == path) { |
| 183 path = ""; |
| 184 } |
| 185 |
| 186 sk_free(self.fPath16); |
| 187 self.fPath16 = concat_to_16(path, suffix); |
| 188 } |
| 189 |
| 190 static bool is_magic_dir(const uint16_t dir[]) { |
| 191 // return true for "." and ".." |
| 192 return dir[0] == '.' && (dir[1] == 0 || (dir[1] == '.' && dir[2] == 0)); |
| 193 } |
| 194 |
| 195 static bool get_the_file(HANDLE handle, SkString* name, WIN32_FIND_DATAW* dataPt
r, bool getDir) { |
| 196 WIN32_FIND_DATAW data; |
| 197 |
| 198 if (NULL == dataPtr) { |
| 199 if (::FindNextFileW(handle, &data)) |
| 200 dataPtr = &data; |
| 201 else |
| 202 return false; |
| 203 } |
| 204 |
| 205 for (;;) { |
| 206 if (getDir) { |
| 207 if ((dataPtr->dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) && |
| 208 !is_magic_dir((uint16_t*)dataPtr->cFileName)) |
| 209 { |
| 210 break; |
| 211 } |
| 212 } else { |
| 213 if (!(dataPtr->dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)) { |
| 214 break; |
| 215 } |
| 216 } |
| 217 if (!::FindNextFileW(handle, dataPtr)) { |
| 218 return false; |
| 219 } |
| 220 } |
| 221 // if we get here, we've found a file/dir |
| 222 if (name) { |
| 223 name->setUTF16((uint16_t*)dataPtr->cFileName); |
| 224 } |
| 225 return true; |
| 226 } |
| 227 |
| 228 bool SkOSFile::Iter::next(SkString* name, bool getDir) { |
| 229 SkOSFileIterData& self = *static_cast<SkOSFileIterData*>(fSelf.get()); |
| 230 WIN32_FIND_DATAW data; |
| 231 WIN32_FIND_DATAW* dataPtr = NULL; |
| 232 |
| 233 if (self.fHandle == 0) { // our first time |
| 234 if (self.fPath16 == NULL || *self.fPath16 == 0) { // check for no path |
| 235 return false; |
| 236 } |
| 237 |
| 238 self.fHandle = ::FindFirstFileW((LPCWSTR)self.fPath16, &data); |
| 239 if (self.fHandle != 0 && self.fHandle != (HANDLE)~0) { |
| 240 dataPtr = &data; |
| 241 } |
| 242 } |
| 243 return self.fHandle != (HANDLE)~0 && get_the_file(self.fHandle, name, dataPt
r, getDir); |
| 244 } |
OLD | NEW |