cprover
Loading...
Searching...
No Matches
tempfile.cpp
Go to the documentation of this file.
1/*******************************************************************\
2
3Module:
4
5Author: Daniel Kroening
6
7\*******************************************************************/
8
9#include "tempfile.h"
10
11// clang-format off
12// clang-format must not re-order includes here to avoid pragma_push/pragma_pop
13#ifdef _WIN32
14#include <util/pragma_push.def>
15#ifdef _MSC_VER
16#pragma warning(disable:4668)
17 // using #if/#elif on undefined macro
18#pragma warning(disable : 5039)
19// pointer or reference to potentially throwing function passed to extern C
20#endif
21#include <fcntl.h>
22#include <process.h>
23#include <sys/stat.h>
24#include <windows.h>
25#include <io.h>
26#include <tchar.h>
27#define getpid _getpid
28#define open _open
29#define close _close
30#include <util/pragma_pop.def>
31#endif
32// clang-format on
33
34#include <cstdlib>
35#include <cstring>
36
37#include "exception_utils.h"
38#include "file_util.h"
39
40#if defined(__linux__) || \
41 defined(__FreeBSD_kernel__) || \
42 defined(__GNU__) || \
43 defined(__unix__) || \
44 defined(__CYGWIN__) || \
45 defined(__MACH__)
46#include <unistd.h>
47#endif
48
51#ifdef _WIN32
52#define mkstemps my_mkstemps
54{
55 // The template should be of the form tmpXXXXXXsuffix
56
58
59 if(suffix_len<0)
60 return -1;
61
62 if(static_cast<std::size_t>(suffix_len+6)>template_length)
63 return -1; // suffix too long
64
65 char *XXXXXX_pos=
67
68 if(strncmp(XXXXXX_pos, "XXXXXX", 6)!=0)
69 return -1; // XXXXXX missing
70
71 static const char letters_and_numbers[]=
72 "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
73
74 static long long unsigned int random_state;
75 random_state+=getpid()+123;
76
77 for(unsigned attempt = 0; attempt < 1000; ++attempt)
78 {
79 unsigned long long number=random_state;
80
81 for(unsigned i=0; i<6; i++)
82 {
84 number/=62;
85 }
86
87 int fd=open(template_str, O_RDWR|O_CREAT|O_EXCL, 0600);
88 if(fd>=0)
89 return fd; // ok
90
91 random_state+=4321+getpid(); // avoid repeating
92 }
93
94 template_str[0]=0;
95 return -1; // error
96}
97#endif
98
100 const std::string &prefix,
101 const std::string &suffix)
102{
103 #ifdef _WIN32
106
107 dwRetVal=
109 MAX_PATH, // length of the buffer
110 lpTempPathBuffer); // buffer for path
111
112 if(dwRetVal>MAX_PATH || (dwRetVal==0))
113 throw system_exceptiont("Failed to get temporary directory");
114
115 // the path returned by GetTempPath ends with a backslash
116 std::string t_template=
117 std::string(lpTempPathBuffer)+prefix+
118 std::to_string(getpid())+".XXXXXX"+suffix;
119 #else
120 std::string dir="/tmp/";
121 const char *TMPDIR_env=getenv("TMPDIR");
122 if(TMPDIR_env!=nullptr)
124 if(*dir.rbegin()!='/')
125 dir+='/';
126
127 std::string t_template=
128 dir+prefix+std::to_string(getpid())+".XXXXXX"+suffix;
129 #endif
130
131 char *t_ptr=strdup(t_template.c_str());
132
133 int fd=mkstemps(t_ptr, suffix.size());
134
135 if(fd<0)
136 throw system_exceptiont("Failed to open temporary file");
137
138 close(fd);
139
140 std::string result=std::string(t_ptr);
141 free(t_ptr);
142 return result;
143}
144
146{
147 if(!name.empty())
149}
ait supplies three of the four components needed: an abstract interpreter (in this case handling func...
Definition ai.h:564
Thrown when some external system fails unexpectedly.
std::string name
Definition tempfile.h:51
bool file_remove(const std::string &path)
C++17 will allow us to use std::filesystem::remove.
std::string get_temporary_file(const std::string &prefix, const std::string &suffix)
Substitute for mkstemps (OpenBSD standard) for Windows, where it is unavailable.
Definition tempfile.cpp:99