libzypp 17.31.23
TmpPath.cc
Go to the documentation of this file.
1/*---------------------------------------------------------------------\
2| ____ _ __ __ ___ |
3| |__ / \ / / . \ . \ |
4| / / \ V /| _/ _/ |
5| / /__ | | | | | | |
6| /_____||_| |_| |_| |
7| |
8\---------------------------------------------------------------------*/
13#include <cstdlib>
14#include <cstring>
15#include <cerrno>
16
17#include <iostream>
18
19#include <zypp-core/base/ReferenceCounted.h>
20#include <zypp-core/base/NonCopyable.h>
21#include <zypp-core/base/Logger.h>
22#include <zypp-core/fs/PathInfo.h>
23#include <zypp-core/fs/TmpPath.h>
24
25using std::endl;
26
27namespace zypp {
28 namespace filesystem {
29
31 //
32 // CLASS NAME : TmpPath::Impl
37 {
38 public:
39
40 enum Flags
41 {
42 NoOp = 0,
43 Autodelete = 1L << 0,
44 KeepTopdir = 1L << 1,
45 //
47 };
48
49 public:
50
51 Impl( const Pathname & path_r, Flags flags_r = CtorDefault )
52 : _path( path_r ), _flags( flags_r )
53 {}
54
56 {
57 if ( ! (_flags & Autodelete) || _path.empty() )
58 return;
59
61 if ( ! p.isExist() )
62 return;
63
64 int res = 0;
65 if ( p.isDir() )
66 {
67 if ( _flags & KeepTopdir )
68 res = clean_dir( _path );
69 else
70 res = recursive_rmdir( _path );
71 }
72 else
73 res = unlink( _path );
74
75 if ( res )
76 INT << "TmpPath cleanup error (" << res << ") " << p << endl;
77 else
78 DBG << "TmpPath cleaned up " << p << endl;
79 }
80
81 const Pathname &
82 path() const
83 { return _path; }
84
85 bool autoCleanup() const
86 { return( _flags & Autodelete ); }
87
88 void autoCleanup( bool yesno_r )
89 { _flags = yesno_r ? CtorDefault : NoOp; }
90
91 private:
94 };
96
98 //
99 // CLASS NAME : TmpPath
100 //
102
104 //
105 // METHOD NAME : TmpPath::TmpPath
106 // METHOD TYPE : Constructor
107 //
109 {}
110
112 //
113 // METHOD NAME : TmpPath::TmpPath
114 // METHOD TYPE : Constructor
115 //
116 TmpPath::TmpPath( const Pathname & tmpPath_r )
117 :_impl( tmpPath_r.empty() ? nullptr : new Impl( tmpPath_r ) )
118 {}
119
121 //
122 // METHOD NAME : TmpPath::~TmpPath
123 // METHOD TYPE : Destructor
124 //
126 {
127 // virtual not inlined dtor.
128 }
129
131 //
132 // METHOD NAME : TmpPath::operator const void *
133 // METHOD TYPE :
134 //
135 TmpPath::operator bool() const
136 {
137 return _impl.get();
138 }
139
141 //
142 // METHOD NAME : TmpPath::path
143 // METHOD TYPE : Pathname
144 //
147 {
148 return _impl.get() ? _impl->path() : Pathname();
149 }
150
152 //
153 // METHOD NAME : TmpPath::defaultLocation
154 // METHOD TYPE : const Pathname &
155 //
156 const Pathname &
158 {
159 static Pathname p( getenv("ZYPPTMPDIR") ? getenv("ZYPPTMPDIR") : "/var/tmp" );
160 return p;
161 }
162
164 { return _impl.get() ? _impl->autoCleanup() : false; }
165
166 void TmpPath::autoCleanup( bool yesno_r )
167 { if ( _impl.get() ) _impl->autoCleanup( yesno_r ); }
168
170 //
171 // CLASS NAME : TmpFile
172 //
174
175
177 //
178 // METHOD NAME : TmpFile::TmpFile
179 // METHOD TYPE : Constructor
180 //
181 TmpFile::TmpFile( const Pathname & inParentDir_r,
182 const std::string & prefix_r )
183 {
184 // parent dir must exist
185 if ( filesystem::assert_dir( inParentDir_r ) != 0 )
186 {
187 ERR << "Parent directory '" << inParentDir_r << "' can't be created." << endl;
188 return;
189 }
190
191 // create the temp file
192 Pathname tmpPath = (inParentDir_r + prefix_r).extend( "XXXXXX");
193 char * buf = ::strdup( tmpPath.asString().c_str() );
194 if ( ! buf )
195 {
196 ERR << "Out of memory" << endl;
197 return;
198 }
199
200 int tmpFd = ::mkostemp( buf, O_CLOEXEC );
201 if ( tmpFd != -1 )
202 {
203 // success; create _impl
204 ::close( tmpFd );
205 _impl = RW_pointer<Impl>( new Impl( buf ) );
206 }
207 else
208 ERR << "Cant create '" << buf << "' " << ::strerror( errno ) << endl;
209
210 ::free( buf );
211 }
212
214 //
215 // METHOD NAME : TmpFile::makeSibling
216 // METHOD TYPE : TmpFile
217 //
219 {
220 TmpFile ret( sibling_r.dirname(), sibling_r.basename() );
221 // clone mode if sibling_r exists
222 PathInfo p( sibling_r );
223 if ( p.isFile() )
224 {
225 ::chmod( ret.path().c_str(), p.st_mode() );
226 }
227 return ret;
228 }
229
231 {
232 filesystem::TmpFile tmpFile;
233 ManagedFile mFile ( tmpFile.path(), filesystem::unlink );
234 tmpFile.autoCleanup(false); //cleaned up by ManagedFile
235 return mFile;
236 }
237
239 //
240 // METHOD NAME : TmpFile::defaultPrefix
241 // METHOD TYPE : const std::string &
242 //
243 const std::string &
245 {
246 static std::string p( "TmpFile." );
247 return p;
248 }
249
251 //
252 // CLASS NAME : TmpDir
253 //
255
257 //
258 // METHOD NAME : TmpDir::TmpDir
259 // METHOD TYPE : Constructor
260 //
261 TmpDir::TmpDir( const Pathname & inParentDir_r,
262 const std::string & prefix_r )
263 {
264 // parent dir must exist
265 if ( filesystem::assert_dir( inParentDir_r ) != 0 )
266 {
267 ERR << "Parent directory '" << inParentDir_r << "' can't be created." << endl;
268 return;
269 }
270
271 // create the temp dir
272 Pathname tmpPath = (inParentDir_r + prefix_r).extend( "XXXXXX");
273 char * buf = ::strdup( tmpPath.asString().c_str() );
274 if ( ! buf )
275 {
276 ERR << "Out of memory" << endl;
277 return;
278 }
279
280 char * tmp = ::mkdtemp( buf );
281 if ( tmp )
282 // success; create _impl
283 _impl = RW_pointer<Impl>( new Impl( tmp ) );
284 else
285 ERR << "Cant create '" << tmpPath << "' " << ::strerror( errno ) << endl;
286
287 ::free( buf );
288 }
289
291 //
292 // METHOD NAME : TmpDir::makeSibling
293 // METHOD TYPE : TmpDir
294 //
296 {
297 TmpDir ret( sibling_r.dirname(), sibling_r.basename() );
298 // clone mode if sibling_r exists
299 PathInfo p( sibling_r );
300 if ( p.isDir() )
301 {
302 ::chmod( ret.path().c_str(), p.st_mode() );
303 }
304 return ret;
305 }
306
308 //
309 // METHOD NAME : TmpDir::defaultPrefix
310 // METHOD TYPE : const std::string &
311 //
312 const std::string &
314 {
315 static std::string p( "TmpDir." );
316 return p;
317 }
318
319 } // namespace filesystem
320} // namespace zypp
Base class for reference counted objects.
Wrapper class for stat/lstat.
Definition: PathInfo.h:221
mode_t st_mode() const
Definition: PathInfo.h:326
bool isExist() const
Return whether valid stat info exists.
Definition: PathInfo.h:281
Pathname dirname() const
Return all but the last component od this path.
Definition: Pathname.h:124
const char * c_str() const
String representation.
Definition: Pathname.h:110
const std::string & asString() const
String representation.
Definition: Pathname.h:91
std::string basename() const
Return the last component of this path.
Definition: Pathname.h:128
bool empty() const
Test for an empty path.
Definition: Pathname.h:114
Provide a new empty temporary directory and recursively delete it when no longer needed.
Definition: TmpPath.h:178
static const std::string & defaultPrefix()
Definition: TmpPath.cc:313
TmpDir(const Pathname &inParentDir_r=defaultLocation(), const std::string &prefix_r=defaultPrefix())
Ctor.
Definition: TmpPath.cc:261
static TmpDir makeSibling(const Pathname &sibling_r)
Provide a new empty temporary directory as sibling.
Definition: TmpPath.cc:295
Provide a new empty temporary file and delete it when no longer needed.
Definition: TmpPath.h:128
TmpFile(const Pathname &inParentDir_r=defaultLocation(), const std::string &prefix_r=defaultPrefix())
Ctor.
Definition: TmpPath.cc:181
static TmpFile makeSibling(const Pathname &sibling_r)
Provide a new empty temporary directory as sibling.
Definition: TmpPath.cc:218
static ManagedFile asManagedFile()
Create a temporary file and convert it to a automatically cleaned up ManagedFile.
Definition: TmpPath.cc:230
static const std::string & defaultPrefix()
Definition: TmpPath.cc:244
Clean or delete a directory on destruction.
Definition: TmpPath.cc:37
void autoCleanup(bool yesno_r)
Definition: TmpPath.cc:88
const Pathname & path() const
Definition: TmpPath.cc:82
Impl(const Pathname &path_r, Flags flags_r=CtorDefault)
Definition: TmpPath.cc:51
static const Pathname & defaultLocation()
Definition: TmpPath.cc:157
RW_pointer< Impl > _impl
Definition: TmpPath.h:98
virtual ~TmpPath()
Dtor.
Definition: TmpPath.cc:125
Pathname path() const
Definition: TmpPath.cc:146
TmpPath()
Default Ctor.
Definition: TmpPath.cc:108
bool autoCleanup() const
Whether path is valid and deleted when the last reference drops.
Definition: TmpPath.cc:163
boost::noncopyable NonCopyable
Ensure derived classes cannot be copied.
Definition: NonCopyable.h:26
int chmod(const Pathname &path, mode_t mode)
Like 'chmod'.
Definition: PathInfo.cc:1092
int unlink(const Pathname &path)
Like 'unlink'.
Definition: PathInfo.cc:700
int recursive_rmdir(const Pathname &path)
Like 'rm -r DIR'.
Definition: PathInfo.cc:412
int assert_dir(const Pathname &path, unsigned mode)
Like 'mkdir -p'.
Definition: PathInfo.cc:319
int clean_dir(const Pathname &path)
Like 'rm -r DIR/ *'.
Definition: PathInfo.cc:442
Easy-to use interface to the ZYPP dependency resolver.
Definition: CodePitfalls.doc:2
Wrapper for const correct access via Smart pointer types.
Definition: PtrTypes.h:286
#define nullptr
Definition: Easy.h:55
#define DBG
Definition: Logger.h:95
#define ERR
Definition: Logger.h:98
#define INT
Definition: Logger.h:100