OSDN Git Service

a7810c751da711135aa9b7e3caa7e501f446aca3
[hmh/hhml.git] / lib / util_file.cc
1 #include "util_file.h"
2 #include "config.h"
3 #include "ustring.h"
4 #include "util_const.h"
5 #include "util_splitter.h"
6 #include "filemacro.h"
7 #include <iostream>
8 #include <sys/types.h>
9 #include <sys/stat.h>
10
11 bool  isPlainFile (const ustring& name) {
12     struct stat  sb;
13
14     if (name.size () > 0 && stat (name.c_str (), &sb) == 0 && S_ISREG (sb.st_mode)) {
15         return true;
16     } else {
17         return false;
18     }
19 }
20
21 bool  isExecutableFile (const ustring& name) {
22     struct stat  sb;
23
24     if (name.size () > 0 && stat (name.c_str (), &sb) == 0 && (sb.st_mode & (S_IXUSR | S_IXGRP | S_IXOTH))) {
25         return true;
26     } else {
27         return false;
28     }
29 }
30
31 bool  isDirectory (const ustring& name) {
32     struct stat  sb;
33
34     if (name.size () > 0 && stat (name.c_str (), &sb) == 0 && S_ISDIR (sb.st_mode)) {
35         return true;
36     } else {
37         return false;
38     }
39 }
40
41 bool  fileSize (const ustring& name, off_t& size) {
42     struct stat  sb;
43
44     if (name.size () > 0 && stat (name.c_str (), &sb) == 0 && S_ISREG (sb.st_mode)) {
45         size = sb.st_size;
46         return true;
47     } else {
48         return false;
49     }
50 }
51
52 bool  readFile (const ustring& filename, ustring& ans, size_t max) {
53     if (filename.size () > 0) {
54         FileMacro  f;
55         off_t  s;
56
57         if (f.openRead (filename.c_str ())) {
58             s = f.size ();
59             if (max > 0 && s > max)
60                 throw (filename + uErrorFileSize);
61             ans.resize (s);
62             if (s > 0)
63                 f.read (&ans.at (0), s);
64             f.close ();
65         } else {
66             return false;
67         }
68     } else {
69         return false;           // NG
70     }
71     return true;                // OK
72 }
73
74 void  writeFile (const ustring& filename, ustring& data) {
75     if (filename.size () > 0) {
76         FileMacro  f;
77         if (f.openWrite (filename.c_str ())) {
78             if (data.size () > 0)
79                 f.write (&data.at (0), data.size ());
80         }
81     }
82 }
83
84 /*
85   top must end with slash.
86 */
87 void  makeSubdir (ustring& top, const ustring& sub) {
88     SplitterCh  sp (sub, '/');
89
90     while (sp.next ()) {
91         top.append (sp.b, sp.u);
92         mkdir (top.c_str (), 0777);
93 #ifdef DEBUG2
94         std::cerr << "mkdir:" << top << "\n";
95 #endif /* DEBUG */
96     }
97 }
98
99 void  shapePath (ustring& path) {
100     static uregex  re1 ("//+");
101     static uregex  re2 ("[^/]+/\\.\\.(/|$)");
102     static uregex  re3 ("(/|^)\\.(/|$)");
103     static uregex  re4 ("^/\\.\\./");
104     umatch  m;
105     uiterator  b, e;
106
107     while (usearch (path, m, re1)) {
108         b = path.begin ();
109         e = path.end ();
110         path = ustring (b, m[0].first + 1).append (m[0].second, e);
111     }
112     while (usearch (path, m, re2)) {
113         if (m[1].first == m[1].second) { // '$'
114             path.resize (m[0].first - path.begin ());
115         } else {                // '/'
116             b = path.begin ();
117             e = path.end ();
118             path = ustring (b, m[0].first).append (m[0].second, e);
119         }
120     }
121     while (usearch (path, m, re3)) {
122         switch (m[0].second - m[0].first) {
123         case 1:
124             goto Bp1;
125         case 2:
126             b = path.begin ();
127             e = path.end ();
128             path = ustring (b, m[0].first).append (m[0].second, e);
129             break;
130         case 3:
131             b = path.begin ();
132             e = path.end ();
133             path = ustring (b, m[0].first).append (m[2].first, e);
134             break;
135         default:;
136             assert (0);
137         }
138     }
139     while (usearch (path, m, re4)) {
140         e = path.end ();
141         path = ustring (m[0].second - 1, e);
142     }
143  Bp1:;
144 }
145
146 bool  isAbsolutePath (const ustring& path) {
147     return (path.length () > 0 && path[0] == '/');
148 }