remove struct stat from interfaces
This commit is contained in:
@@ -37,12 +37,13 @@ public:
|
||||
{
|
||||
}
|
||||
virtual FsTreeWalker::Status
|
||||
processone(const string &, const struct stat *, FsTreeWalker::CbFlag);
|
||||
processone(const string &, const struct PathStat *, FsTreeWalker::CbFlag);
|
||||
DesktopDb::AppMap *m_appdefs;
|
||||
};
|
||||
|
||||
FsTreeWalker::Status FstCb::processone(const string& fn, const struct stat *,
|
||||
FsTreeWalker::CbFlag flg)
|
||||
struct PathStat;
|
||||
FsTreeWalker::Status FstCb::processone(
|
||||
const string& fn, const struct PathStat*, FsTreeWalker::CbFlag flg)
|
||||
{
|
||||
if (flg != FsTreeWalker::FtwRegular)
|
||||
return FsTreeWalker::FtwOk;
|
||||
|
||||
+13
-14
@@ -21,7 +21,6 @@
|
||||
#include <dirent.h>
|
||||
#include <errno.h>
|
||||
#include <fnmatch.h>
|
||||
#include "safesysstat.h"
|
||||
#include <cstring>
|
||||
#include <algorithm>
|
||||
|
||||
@@ -228,8 +227,7 @@ static inline int slashcount(const string& p)
|
||||
return n;
|
||||
}
|
||||
|
||||
FsTreeWalker::Status FsTreeWalker::walk(const string& _top,
|
||||
FsTreeWalkerCB& cb)
|
||||
FsTreeWalker::Status FsTreeWalker::walk(const string& _top, FsTreeWalkerCB& cb)
|
||||
{
|
||||
string top = (data->options & FtwNoCanon) ? _top : path_canon(_top);
|
||||
|
||||
@@ -238,7 +236,7 @@ FsTreeWalker::Status FsTreeWalker::walk(const string& _top,
|
||||
}
|
||||
|
||||
data->basedepth = slashcount(top); // Only used for breadthxx
|
||||
struct stat st;
|
||||
struct PathStat st;
|
||||
// We always follow symlinks at this point. Makes more sense.
|
||||
if (path_fileprops(top, &st) == -1) {
|
||||
// Note that we do not return an error if the stat call
|
||||
@@ -343,19 +341,19 @@ FsTreeWalker::Status FsTreeWalker::walk(const string& _top,
|
||||
// This means that we always go into the top 'walk()' parameter if it is a
|
||||
// directory, even if norecurse is set. Bug or Feature ?
|
||||
FsTreeWalker::Status FsTreeWalker::iwalk(const string &top,
|
||||
struct stat *stp,
|
||||
struct PathStat *stp,
|
||||
FsTreeWalkerCB& cb)
|
||||
{
|
||||
Status status = FtwOk;
|
||||
bool nullpush = false;
|
||||
|
||||
// Tell user to process the top entry itself
|
||||
if (S_ISDIR(stp->st_mode)) {
|
||||
if (stp->pst_type == PathStat::PST_DIR) {
|
||||
if ((status = cb.processone(top, stp, FtwDirEnter)) &
|
||||
(FtwStop|FtwError)) {
|
||||
return status;
|
||||
}
|
||||
} else if (S_ISREG(stp->st_mode)) {
|
||||
} else if (stp->pst_type == PathStat::PST_REGULAR) {
|
||||
return cb.processone(top, stp, FtwRegular);
|
||||
} else {
|
||||
return status;
|
||||
@@ -377,7 +375,7 @@ FsTreeWalker::Status FsTreeWalker::iwalk(const string &top,
|
||||
// For now, we'll ignore the "other kind of cycle" part and only monitor
|
||||
// this is FtwFollow is set
|
||||
if (data->options & FtwFollow) {
|
||||
DirId dirid(stp->st_dev, stp->st_ino);
|
||||
DirId dirid(stp->pst_dev, stp->pst_ino);
|
||||
if (data->donedirs.find(dirid) != data->donedirs.end()) {
|
||||
LOGINFO("Not processing [" << top <<
|
||||
"] (already seen as other path)\n");
|
||||
@@ -420,7 +418,7 @@ FsTreeWalker::Status FsTreeWalker::iwalk(const string &top,
|
||||
struct DIRENT *ent;
|
||||
while (errno = 0, ((ent = READDIR(d)) != 0)) {
|
||||
string fn;
|
||||
struct stat st;
|
||||
struct PathStat st;
|
||||
#ifdef _WIN32
|
||||
string sdname;
|
||||
if (!wchartoutf8(ent->d_name, sdname)) {
|
||||
@@ -468,7 +466,7 @@ FsTreeWalker::Status FsTreeWalker::iwalk(const string &top,
|
||||
continue;
|
||||
}
|
||||
|
||||
if (S_ISDIR(st.st_mode)) {
|
||||
if (st.pst_type == PathStat::PST_DIR) {
|
||||
if (!o_nowalkfn.empty() && path_exists(path_cat(fn, o_nowalkfn))) {
|
||||
continue;
|
||||
}
|
||||
@@ -498,7 +496,8 @@ FsTreeWalker::Status FsTreeWalker::iwalk(const string &top,
|
||||
if ((status = cb.processone(top, &st, FtwDirReturn))
|
||||
& (FtwStop|FtwError))
|
||||
goto out;
|
||||
} else if (S_ISREG(st.st_mode) || S_ISLNK(st.st_mode)) {
|
||||
} else if (st.pst_type == PathStat::PST_REGULAR ||
|
||||
st.pst_type == PathStat::PST_SYMLINK) {
|
||||
// Filtering patterns match ?
|
||||
if (!data->onlyNames.empty()) {
|
||||
if (!inOnlyNames(dname))
|
||||
@@ -536,14 +535,14 @@ int64_t fsTreeBytes(const string& topdir)
|
||||
class bytesCB : public FsTreeWalkerCB {
|
||||
public:
|
||||
FsTreeWalker::Status processone(const string &path,
|
||||
const struct stat *st,
|
||||
const struct PathStat *st,
|
||||
FsTreeWalker::CbFlag flg) {
|
||||
if (flg == FsTreeWalker::FtwDirEnter ||
|
||||
flg == FsTreeWalker::FtwRegular) {
|
||||
#ifdef _WIN32
|
||||
totalbytes += st->st_size;
|
||||
totalbytes += st->pst_size;
|
||||
#else
|
||||
totalbytes += st->st_blocks * 512;
|
||||
totalbytes += st->pst_blocks * 512;
|
||||
#endif
|
||||
}
|
||||
return FsTreeWalker::FtwOk;
|
||||
|
||||
+19
-23
@@ -19,13 +19,10 @@
|
||||
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#ifndef NO_NAMESPACES
|
||||
using std::string;
|
||||
using std::vector;
|
||||
#endif
|
||||
|
||||
struct PathStat;
|
||||
|
||||
class FsTreeWalkerCB;
|
||||
struct stat;
|
||||
|
||||
/**
|
||||
* Class implementing a unix directory recursive walk.
|
||||
@@ -44,8 +41,7 @@ class FsTreeWalker {
|
||||
// to not use the flag, which can be set from rclconfig by adding
|
||||
// a value to the config file (skippedPathsNoFnmPathname)
|
||||
static bool o_useFnmPathname;
|
||||
static void setNoFnmPathname()
|
||||
{
|
||||
static void setNoFnmPathname() {
|
||||
o_useFnmPathname = false;
|
||||
}
|
||||
|
||||
@@ -53,8 +49,7 @@ class FsTreeWalker {
|
||||
// directories as if they were in skippedPaths) if the file exists
|
||||
// inside the directory.
|
||||
static std::string o_nowalkfn;
|
||||
static void setNoWalkFn(const std::string& nowalkfn)
|
||||
{
|
||||
static void setNoWalkFn(const std::string& nowalkfn) {
|
||||
o_nowalkfn = nowalkfn;
|
||||
}
|
||||
|
||||
@@ -97,34 +92,35 @@ class FsTreeWalker {
|
||||
* @param cb the function object that will be called back for every
|
||||
* file-system object (called both at entry and exit for directories).
|
||||
*/
|
||||
Status walk(const string &dir, FsTreeWalkerCB& cb);
|
||||
Status walk(const std::string &dir, FsTreeWalkerCB& cb);
|
||||
/** Get explanation for error */
|
||||
string getReason();
|
||||
std::string getReason();
|
||||
int getErrCnt();
|
||||
|
||||
/**
|
||||
* Add a pattern (file or dir) to be ignored (ie: #* , *~)
|
||||
*/
|
||||
bool addSkippedName(const string &pattern);
|
||||
bool addSkippedName(const std::string &pattern);
|
||||
/** Set the ignored patterns set */
|
||||
bool setSkippedNames(const vector<string> &patterns);
|
||||
bool setSkippedNames(const std::vector<std::string> &patterns);
|
||||
/** Set the exclusive patterns set */
|
||||
bool setOnlyNames(const vector<string> &patterns);
|
||||
bool setOnlyNames(const std::vector<std::string> &patterns);
|
||||
|
||||
/** Same for skipped paths: this are paths, not names, under which we
|
||||
do not descend (ie: /home/me/.recoll) */
|
||||
bool addSkippedPath(const string &path);
|
||||
bool addSkippedPath(const std::string &path);
|
||||
/** Set the ignored paths list */
|
||||
bool setSkippedPaths(const vector<string> &patterns);
|
||||
bool setSkippedPaths(const std::vector<std::string> &patterns);
|
||||
|
||||
/** Test if path/name should be skipped. This can be used independently of
|
||||
* an actual tree walk */
|
||||
bool inSkippedPaths(const string& path, bool ckparents = false);
|
||||
bool inSkippedNames(const string& name);
|
||||
bool inOnlyNames(const string& name);
|
||||
bool inSkippedPaths(const std::string& path, bool ckparents = false);
|
||||
bool inSkippedNames(const std::string& name);
|
||||
bool inOnlyNames(const std::string& name);
|
||||
|
||||
private:
|
||||
Status iwalk(const string &dir, struct stat *stp, FsTreeWalkerCB& cb);
|
||||
Status iwalk(const std::string &dir, struct PathStat *stp,
|
||||
FsTreeWalkerCB& cb);
|
||||
class Internal;
|
||||
Internal *data;
|
||||
};
|
||||
@@ -134,11 +130,11 @@ class FsTreeWalkerCB {
|
||||
virtual ~FsTreeWalkerCB() {}
|
||||
// Only st_mtime, st_ctime, st_size, st_mode (filetype bits: dir/reg/lnk),
|
||||
virtual FsTreeWalker::Status
|
||||
processone(const string &, const struct stat *, FsTreeWalker::CbFlag)
|
||||
= 0;
|
||||
processone(const std::string&, const struct PathStat *,
|
||||
FsTreeWalker::CbFlag) = 0;
|
||||
};
|
||||
|
||||
// Utility function. Somewhat like du.
|
||||
int64_t fsTreeBytes(const string& topdir);
|
||||
int64_t fsTreeBytes(const std::string& topdir);
|
||||
|
||||
#endif /* _FSTREEWALK_H_INCLUDED_ */
|
||||
|
||||
+35
-14
@@ -684,11 +684,12 @@ bool path_makepath(const string& ipath, int mode)
|
||||
return true;
|
||||
}
|
||||
|
||||
bool path_isdir(const string& path)
|
||||
bool path_isdir(const string& path, bool follow)
|
||||
{
|
||||
struct STATBUF st;
|
||||
SYSPATH(path, syspath);
|
||||
if (LSTAT(syspath, &st) < 0) {
|
||||
int ret = follow ? STAT(syspath, &st) : LSTAT(syspath, &st);
|
||||
if (ret < 0) {
|
||||
return false;
|
||||
}
|
||||
if (S_ISDIR(st.st_mode)) {
|
||||
@@ -697,6 +698,20 @@ bool path_isdir(const string& path)
|
||||
return false;
|
||||
}
|
||||
|
||||
bool path_isfile(const string& path, bool follow)
|
||||
{
|
||||
struct STATBUF st;
|
||||
SYSPATH(path, syspath);
|
||||
int ret = follow ? STAT(syspath, &st) : LSTAT(syspath, &st);
|
||||
if (ret < 0) {
|
||||
return false;
|
||||
}
|
||||
if (S_ISREG(st.st_mode)) {
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
long long path_filesize(const string& path)
|
||||
{
|
||||
struct STATBUF st;
|
||||
@@ -707,30 +722,36 @@ long long path_filesize(const string& path)
|
||||
return (long long)st.st_size;
|
||||
}
|
||||
|
||||
int path_fileprops(const std::string path, struct stat *stp, bool follow)
|
||||
int path_fileprops(const std::string path, struct PathStat *stp, bool follow)
|
||||
{
|
||||
if (!stp) {
|
||||
if (nullptr == stp) {
|
||||
return -1;
|
||||
}
|
||||
memset(stp, 0, sizeof(struct stat));
|
||||
memset(stp, 0, sizeof(struct PathStat));
|
||||
struct STATBUF mst;
|
||||
SYSPATH(path, syspath);
|
||||
int ret = follow ? STAT(syspath, &mst) : LSTAT(syspath, &mst);
|
||||
if (ret != 0) {
|
||||
return ret;
|
||||
}
|
||||
stp->st_size = mst.st_size;
|
||||
stp->st_mode = mst.st_mode;
|
||||
stp->st_mtime = mst.st_mtime;
|
||||
stp->pst_size = mst.st_size;
|
||||
stp->pst_mode = mst.st_mode;
|
||||
stp->pst_mtime = mst.st_mtime;
|
||||
#ifdef _WIN32
|
||||
stp->st_ctime = mst.st_mtime;
|
||||
stp->pst_ctime = mst.st_mtime;
|
||||
#else
|
||||
stp->st_ino = mst.st_ino;
|
||||
stp->st_dev = mst.st_dev;
|
||||
stp->st_ctime = mst.st_ctime;
|
||||
stp->st_blocks = mst.st_blocks;
|
||||
stp->st_blksize = mst.st_blksize;
|
||||
stp->pst_ino = mst.st_ino;
|
||||
stp->pst_dev = mst.st_dev;
|
||||
stp->pst_ctime = mst.st_ctime;
|
||||
stp->pst_blocks = mst.st_blocks;
|
||||
stp->pst_blksize = mst.st_blksize;
|
||||
#endif
|
||||
switch (mst.st_mode & S_IFMT) {
|
||||
case S_IFDIR: stp->pst_type = PathStat::PST_DIR;break;
|
||||
case S_IFLNK: stp->pst_type = PathStat::PST_SYMLINK;break;
|
||||
case S_IFREG: stp->pst_type = PathStat::PST_REGULAR;break;
|
||||
default: stp->pst_type = PathStat::PST_OTHER;break;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
+17
-6
@@ -20,6 +20,7 @@
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <set>
|
||||
#include <cstdint>
|
||||
|
||||
// Must be called in main thread before starting other threads
|
||||
extern void pathut_init_mt();
|
||||
@@ -66,7 +67,9 @@ extern std::string url_parentfolder(const std::string& url);
|
||||
extern std::string url_gpath(const std::string& url);
|
||||
|
||||
/// Stat parameter and check if it's a directory
|
||||
extern bool path_isdir(const std::string& path);
|
||||
extern bool path_isdir(const std::string& path, bool follow = false);
|
||||
/// Stat parameter and check if it's a regular file
|
||||
extern bool path_isfile(const std::string& path, bool follow = false);
|
||||
|
||||
/// Retrieve file size
|
||||
extern long long path_filesize(const std::string& path);
|
||||
@@ -79,8 +82,19 @@ extern long long path_filesize(const std::string& path);
|
||||
/// all systems. st_dev and st_ino are set for special posix usage.
|
||||
/// The rest is zeroed.
|
||||
/// @ret 0 for success
|
||||
struct stat;
|
||||
extern int path_fileprops(const std::string path, struct stat *stp,
|
||||
struct PathStat {
|
||||
enum PstType {PST_REGULAR, PST_SYMLINK, PST_DIR, PST_OTHER};
|
||||
PstType pst_type;
|
||||
int64_t pst_size;
|
||||
uint64_t pst_mode;
|
||||
int64_t pst_mtime;
|
||||
int64_t pst_ctime;
|
||||
uint64_t pst_ino;
|
||||
uint64_t pst_dev;
|
||||
uint64_t pst_blocks;
|
||||
uint64_t pst_blksize;
|
||||
};
|
||||
extern int path_fileprops(const std::string path, struct PathStat *stp,
|
||||
bool follow = true);
|
||||
|
||||
/// Check that path is traversable and last element exists
|
||||
@@ -150,9 +164,6 @@ public:
|
||||
/// Convert \ separators to /
|
||||
void path_slashize(std::string& s);
|
||||
void path_backslashize(std::string& s);
|
||||
#include "safeunistd.h"
|
||||
#else
|
||||
#include <unistd.h>
|
||||
#endif
|
||||
|
||||
/// Lock/pid file class. This is quite close to the pidfile_xxx
|
||||
|
||||
Reference in New Issue
Block a user