1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185
|
////////////////////////////////////////////////////////////////////////////////
// This source file is part of the ZipArchive library source distribution and
// is Copyrighted 2000 - 2007 by Artpol Software - Tadeusz Dracz
//
// This program is free software; you can redistribute it and/or
// modify it under the terms of the GNU General Public License
// as published by the Free Software Foundation; either version 2
// of the License, or (at your option) any later version.
//
// For the licensing details refer to the License.txt file.
//
// Web Site: http://www.artpol-software.com
////////////////////////////////////////////////////////////////////////////////
#include "stdafx.h"
#if defined _MSC_VER && _MSC_VER < 1300
// STL warnings
#pragma warning (push, 3)
#endif
#include "DirEnumerator.h"
#include "FileFilter.h"
#include <queue>
#if defined __GNUC__ && !defined __MINGW32__
#include <sys/stat.h>
#include <dirent.h>
#else
#include <io.h>
#ifdef __BORLANDC__
#ifndef _tfindfirsti64
#define _tfindfirsti64 __tfindfirsti64
#endif
#ifndef _tfindnexti64
#define _tfindnexti64 __tfindnexti64
#endif
#ifndef _tfinddatai64_t
#define _tfinddatai64_t __tfinddatai64_t
#endif
#endif
#endif
namespace ZipArchiveLib
{
#if defined __GNUC__ && !defined __MINGW32__
#define ZIP_ENUMERATOR_FOR_GNUC
#endif
bool CDirEnumerator::Start(CFileFilter& filter)
{
OnEnumerationBegin();
std::queue<CZipString> dirs;
dirs.push(CZipString(m_lpszDirectory));
bool ret = true;
do
{
m_szCurrentDirectory = dirs.front();
dirs.pop();
CZipPathComponent::AppendSeparator(m_szCurrentDirectory);
EnterDirectory();
#ifdef ZIP_ENUMERATOR_FOR_GNUC
DIR* dp = opendir(m_szCurrentDirectory);
if (dp)
{
while (true)
{
struct dirent* entry = readdir(dp);
if (!entry)
break;
CZipString path(m_szCurrentDirectory + entry->d_name);
#if !defined __APPLE__ && !defined __CYGWIN__
struct stat64 sStats;
if (stat64(path, &sStats) == -1)
#else
struct stat sStats;
if (stat(path, &sStats) == -1)
#endif
continue;
LPCTSTR name = entry->d_name;
CFileInfo info;
info.m_uAttributes = sStats.st_mode;
#else
CZipString szFullFileName = m_szCurrentDirectory + _T("*");
_tfinddatai64_t ffInfo;
#if _MSC_VER > 1200
intptr_t hFile;
#else
long hFile;
#endif
if( (hFile = _tfindfirsti64( (LPTSTR)(LPCTSTR)szFullFileName, &ffInfo )) != -1L )
{
do
{
LPCTSTR name = ffInfo.name;
CFileInfo info;
info.m_uAttributes = ffInfo.attrib;
#endif
bool isDir;
if (ZipPlatform::IsDirectory(info.m_uAttributes))
{
if (!m_bRecursive || IsDots(name))
continue;
isDir = true;
}
else
isDir = false;
#ifdef ZIP_ENUMERATOR_FOR_GNUC
info.m_uSize = (ZIP_FILE_USIZE)sStats.st_size;
info.m_uCreateTime = sStats.st_ctime;
info.m_uModTime = sStats.st_mtime;
info.m_uAccessTime = sStats.st_atime;
#else
info.m_uSize = (ZIP_FILE_USIZE)ffInfo.size;
info.m_uCreateTime = ffInfo.time_create;
info.m_uModTime = ffInfo.time_write;
info.m_uAccessTime = ffInfo.time_access;
CZipString path(m_szCurrentDirectory + ffInfo.name);
#endif
if (isDir)
{
bool bAllow;
if (filter.HandlesFile(info))
bAllow = filter.Evaluate(path, name, info);
else
// examine directory, if the filter cannot decide
bAllow = true;
if (bAllow)
dirs.push(path);
}
else
{
bool bAllow;
if (filter.HandlesFile(info))
bAllow = filter.Evaluate(path, name, info);
else
// skip file, if the filter cannot decide
bAllow = false;
if (bAllow && !Process(path, info))
{
ret = false;
break;
}
}
#ifdef ZIP_ENUMERATOR_FOR_GNUC
}
closedir(dp);
}
#else
}
while (_tfindnexti64(hFile, &ffInfo) == 0L);
_findclose(hFile);
}
#endif
ExitDirectory();
}
while(!dirs.empty() && ret);
OnEnumerationEnd(ret);
return ret;
}
bool CDirEnumerator::IsDots(LPCTSTR lpszName)
{
CZipString name(lpszName);
return name.Compare(_T(".")) == 0 || name.Compare(_T("..")) == 0;
}
} // namespace
#if defined _MSC_VER && _MSC_VER < 1300
// STL warnings
#pragma warning (pop)
#endif
|