/[svn]/linuxsampler/trunk/src/common/File.cpp
ViewVC logotype

Annotation of /linuxsampler/trunk/src/common/File.cpp

Parent Directory Parent Directory | Revision Log Revision Log


Revision 3082 - (hide annotations) (download)
Mon Jan 9 18:39:35 2017 UTC (7 years, 3 months ago) by schoenebeck
File size: 6614 byte(s)
* Added support for sfz extension opcode 'script' which may be used to
  load real-time instrument script file (NKSP script language).
* Removed code duplication in SFZ file loading code.
* Bumped version (2.0.0.svn37).

1 iliev 1717 /***************************************************************************
2     * *
3 persson 2313 * Copyright (C) 2008 - 2012 Grigor Iliev, Benno Senoner *
4 iliev 1717 * *
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., 51 Franklin St, Fifth Floor, Boston, *
18     * MA 02110-1301 USA *
19     ***************************************************************************/
20    
21     #include "File.h"
22    
23 persson 1726 #include <cstring>
24 iliev 1717 #include <errno.h>
25     #include <sstream>
26 senoner 1911 #include <sys/stat.h>
27 persson 1943 #include <dirent.h>
28 iliev 1717
29     #include "Exception.h"
30 schoenebeck 3082 #include "Path.h"
31 iliev 1717 #include "global_private.h"
32    
33     #if WIN32
34 persson 1943 #include <windows.h>
35 iliev 1717 #else
36     #include <ftw.h>
37     #endif
38    
39     namespace LinuxSampler {
40 persson 1943 #ifdef WIN32
41 persson 2313 const char File::DirSeparator = '\\';
42     const char File::PathSeparator = ';';
43 persson 1943 #else
44 persson 2313 const char File::DirSeparator = '/';
45     const char File::PathSeparator = ':';
46 persson 1943 #endif
47 senoner 1910 Mutex File::DirectoryWalkerMutex;
48 iliev 1717 std::vector<File::DirectoryWalker*> File::DirectoryWalkers;
49     std::string File::DWErrorMsg;
50    
51 schoenebeck 3082 File::File(const Path& path) {
52     bExist = !stat(path.toNativeFSPath().c_str(), &Status);
53     if (!bExist) ErrorMsg = strerror(errno);
54     }
55    
56 iliev 1717 File::File(std::string Path) {
57     bExist = !stat(Path.c_str(), &Status);
58     if(!bExist) ErrorMsg = strerror(errno);
59     }
60    
61     bool File::Exist() {
62     return bExist;
63     }
64    
65     std::string File::GetErrorMsg() {
66     return ErrorMsg;
67     }
68    
69     bool File::IsFile() {
70     if(!Exist()) return false;
71    
72     return S_ISREG(Status.st_mode);
73     }
74    
75     bool File::IsDirectory() {
76     if(!Exist()) return false;
77    
78     return S_ISDIR(Status.st_mode);
79     }
80    
81     unsigned long File::GetSize() {
82     if(!Exist()) return 0;
83    
84 senoner 1910 return Status.st_size;
85 iliev 1717 }
86    
87     FileListPtr File::GetFiles(std::string Dir) {
88     DIR* pDir = opendir(Dir.c_str());
89     if (pDir == NULL) {
90     std::stringstream ss;
91     ss << "Failed to list the directory content of `";
92     ss << Dir << "`: " << strerror(errno);
93     throw Exception(ss.str());
94     }
95    
96     FileListPtr fileList(new std::vector<std::string>);
97    
98     struct dirent* pEnt = readdir(pDir);
99     while (pEnt != NULL) {
100 persson 1943 #ifdef _DIRENT_HAVE_D_TYPE
101     if (pEnt->d_type == DT_REG) {
102 iliev 1717 fileList->push_back(std::string(pEnt->d_name));
103 persson 1943 }
104     #else
105     struct stat s;
106     if (stat((Dir + DirSeparator + pEnt->d_name).c_str(), &s) == 0 && S_ISREG(s.st_mode)) {
107     fileList->push_back(std::string(pEnt->d_name));
108     }
109     #endif
110 iliev 1717 pEnt = readdir(pDir);
111     }
112    
113     if (closedir(pDir)) {
114     std::stringstream ss;
115     ss << "Failed to close directory `" << Dir << "`: ";
116     ss << strerror(errno);
117     throw Exception(ss.str());
118     }
119    
120     return fileList;
121     }
122    
123     void File::WalkDirectoryTree(std::string Dir, DirectoryWalker* pWalker) {
124     dmsg(2,("File: WalkDirectoryTree(Dir=%s)\n", Dir.c_str()));
125     File f = File(Dir);
126     if(!f.Exist()) throw Exception("Fail to stat `" + Dir + "`: " + f.GetErrorMsg());
127     if(!f.IsDirectory()) throw Exception("The specified path is not a directory: " + Dir);
128 persson 1943 #ifdef WIN32
129     WalkDirectoryTreeSub(Dir, pWalker);
130     #else
131 iliev 1717 DirectoryWalkerMutex.Lock();
132     DirectoryWalkers.push_back(pWalker);
133     DWErrorMsg = "Failed to process directory tree: " + Dir;
134    
135     if (ftw(Dir.c_str(), FtwCallback, 10)) {
136     DirectoryWalkers.pop_back();
137     if (DirectoryWalkers.size() == 0) DirectoryWalkerMutex.Unlock();
138     throw Exception(DWErrorMsg);
139     }
140     DirectoryWalkers.pop_back();
141     if (DirectoryWalkers.size() == 0) DirectoryWalkerMutex.Unlock();
142 persson 1943 #endif
143 iliev 1717 }
144    
145 persson 1943 #ifdef WIN32
146     void File::WalkDirectoryTreeSub(String Dir, DirectoryWalker* pWalker) {
147     dmsg(2,("File: WalkDirectoryTreeSub(Dir=%s)\n", Dir.c_str()));
148     DWORD attrs = GetFileAttributes(Dir.c_str());
149     if (attrs == INVALID_FILE_ATTRIBUTES) return;
150 iliev 1717
151 persson 1943 if (attrs & FILE_ATTRIBUTE_DIRECTORY) {
152     pWalker->DirectoryEntry(Dir);
153    
154     std::string::size_type l = Dir.length() - 1;
155     if (Dir[l] == '/') Dir[l] = '\\';
156     else if (Dir[l] != '\\') Dir += '\\';
157    
158     WIN32_FIND_DATA fd;
159     HANDLE h = FindFirstFile((Dir + "*").c_str(), &fd);
160     if (h == INVALID_HANDLE_VALUE) return;
161     do {
162     if (strcmp(fd.cFileName, ".") != 0 &&
163     strcmp(fd.cFileName, "..") != 0) {
164     WalkDirectoryTreeSub(Dir + fd.cFileName, pWalker);
165     }
166     } while (FindNextFile(h, &fd));
167     FindClose(h);
168     } else {
169     pWalker->FileEntry(Dir);
170     }
171     }
172     #else
173 iliev 1717 int File::FtwCallback(const char* fpath, const struct stat* sb, int typeflag) {
174     dmsg(2,("File: FtwCallback(fpath=%s)\n", fpath));
175     try {
176     if (typeflag == FTW_D) DirectoryWalkers.back()->DirectoryEntry(std::string(fpath));
177     else if (typeflag == FTW_F) DirectoryWalkers.back()->FileEntry(std::string(fpath));
178     } catch(Exception e) {
179     e.PrintMessage();
180     DWErrorMsg = e.Message();
181     return -1;
182     }
183    
184     return 0;
185 persson 1943 }
186     #endif
187 iliev 1717 }

  ViewVC Help
Powered by ViewVC