BDE 4.39.x Production Release
Loading...
Searching...
No Matches
bdls_filesystemutil_transitionaluniximputil.h
Go to the documentation of this file.
1/// @file bdls_filesystemutil_transitionaluniximputil.h
2///
3/// The content of this file has been pre-processed for Doxygen.
4///
5
6
7// bdls_filesystemutil_transitionaluniximputil.h -*-C++-*-
8#ifndef INCLUDED_BDLS_FILESYSTEMUTIL_TRANSITIONALUNIXIMPUTIL
9#define INCLUDED_BDLS_FILESYSTEMUTIL_TRANSITIONALUNIXIMPUTIL
10
11#include <bsls_ident.h>
12BSLS_IDENT("$Id: $")
13
14/// @defgroup bdls_filesystemutil_transitionaluniximputil bdls_filesystemutil_transitionaluniximputil
15/// @brief Provide testable `bdls::FilesystemUtil` operations for some Unixes.
16/// @addtogroup bdl
17/// @{
18/// @addtogroup bdls
19/// @{
20/// @addtogroup bdls_filesystemutil_transitionaluniximputil
21/// @{
22///
23/// <h1> Outline </h1>
24/// * <a href="#bdls_filesystemutil_transitionaluniximputil-purpose"> Purpose</a>
25/// * <a href="#bdls_filesystemutil_transitionaluniximputil-classes"> Classes </a>
26/// * <a href="#bdls_filesystemutil_transitionaluniximputil-description"> Description </a>
27/// * <a href="#bdls_filesystemutil_transitionaluniximputil-the-transitional-compilation-environment"> The Transitional-Compilation Environment </a>
28///
29/// # Purpose {#bdls_filesystemutil_transitionaluniximputil-purpose}
30/// Provide testable `bdls::FilesystemUtil` operations for some Unixes.
31///
32/// # Classes {#bdls_filesystemutil_transitionaluniximputil-classes}
33///
34/// - bdls::FileystemUtil_TransitionalUnixImpUtil: testable file-system utilities
35///
36/// @see bdls_filesystemutil, bdls_filesystemutil_unixplatform
37///
38/// # Description {#bdls_filesystemutil_transitionaluniximputil-description}
39/// This subordinate component to @ref bdls_filesystemutil provides a
40/// utlity `struct` template, `bdls::FilesystemUtil_TransitionalUnixImpUtil` for
41/// implementing some of `bdls::FileystemUtil`s functions on Unix platforms in
42/// the transitional-compilation environemnt.
43/// `bdls::FilesystemUtil_TransitionalUnixImpUtil` accesses Unix functions and
44/// types through its template parameter, `UNIX_INTERFACE`, in order to allow
45/// tests to supply mock Unix interfaces.
46///
47/// ## The Transitional-Compilation Environment {#bdls_filesystemutil_transitionaluniximputil-the-transitional-compilation-environment}
48///
49///
50/// Many Unix systems provide a non-standard "transitional-compilation
51/// environment", which is a compilation mode that supports large, 64-bit file
52/// operations in 32-bit (or 64-bit) programs. For more information about this
53/// and other large-file compilation modes, please see the `lfcompile64` and/or
54/// `lfcompile` manual pages provided for the operating system of interest.
55/// Note that some Unix systems may not support a transitional-compilation
56/// environment, and some that do may provide descriptions of this environment
57/// in documentation outside of a `lfcompile64` or `lfcompile` manual page.
58/// Furthermore, some Unix systems natively provide 64-bit file operations for
59/// 32-bit programs, in which case a transitional-compilation environment is not
60/// necessary.
61///
62/// Another subordinate component of @ref bdls_filesystemutil ,
63/// @ref bdls_filesystemutil_unixplatform , is principally concerned with the
64/// detection of the transitional-compilation environment on any Unix platform
65/// supported by the BDE library.
66/// @}
67/** @} */
68/** @} */
69
70/** @addtogroup bdl
71 * @{
72 */
73/** @addtogroup bdls
74 * @{
75 */
76/** @addtogroup bdls_filesystemutil_transitionaluniximputil
77 * @{
78 */
79
80#include <bdlt_datetime.h>
81#include <bdlt_epochutil.h>
82#include <bdlt_timeunitratio.h>
83
84#include <bsls_assert.h>
85
86
87namespace bdls {
88
89 // =============================================
90 // struct FilesystemUtil_TransitionalUnixImpUtil
91 // =============================================
92
93/// This component-private utility `struct` provides a namespace for a suite
94/// of functions that `FilesystemUtil` uses as implementation details.
95/// These functions have a `UNIX_INTERFACE` template parameter, which
96/// provides access to the entities that transitional-compilation
97/// environment Unix systems declare, and that the function implementations
98/// need.
99///
100///
101/// \note Note that, on some Unix platforms and some build configurations, the
102/// `stat` struct does not have an `st_mtime` field, and `st_mtime` is a
103/// macro that emulates the access of the field. Similarly, on some Unix
104/// platforms and some build configurations, the `stat` structure does not
105/// have an `st_mtim` field or the `st_mtim` struct does not have a
106/// `tv_nsec` (or, for some versions of Solaris, `__tv_nsec`) field, in
107/// which case the @ref get_st_mtim_nsec function returns zero. For more
108/// information, please see the specification of the `sys/stat.h` header
109/// from IEEE Std
110/// 1003.1-2017, which provides information about the evolution of the
111/// `stat` struct in the POSIX specification
112/// (https://pubs.opengroup.org/onlinepubs/9699919799.2018edition/).
113///
114/// The program is ill-formed unless the specified `UNIX_INTERFACE` is a
115/// class type that meets the following requirements:
116///
117/// * `UNIX_INTERFACE::off64_t` is a type alias to the `off64_t` type
118/// provided by the `sys/types.h` header.
119/// * `UNIX_INTERFACE::stat64` is a type alias to the `stat64` type
120/// provided by the `sys/stat.h` header.
121/// * `UNIX_INTERFACE::time_t` is a type alias to the `time_t` type
122/// provided by the `sys/types.h` header.
123/// * `UNIX_INTERFACE::get_st_mtim_nsec` is a public, static member
124/// function that has `long (const stat& stat)` type and whose contract
125/// is to return the value of the `st_mtim.tv_nsec` field of the
126/// specified `stat` struct.
127/// * `UNIX_INTERFACE::get_st_mtime` is a public, static member function
128/// that has `time_t (const stat& stat)` type and whose contract is to
129/// return the value of the `st_mtime` field of the specified `stat`
130/// struct.
131/// * `UNIX_INTERFACE::get_st_size` is a public, static member function
132/// that has `off64_t (const stat& stat)` type and whose contract is to
133/// return the value of the `st_size` field of the specified `stat` struct.
134///
135/// \note Note that this function is required in order to
136/// access the data members of a `stat` struct in a manner consistent
137/// with the requirements of @ref get_st_mtime .
138/// * `UNIX_INTERFACE::fstat64` is a public, static member function that
139/// has `int (int fildes, stat64 *buf)` type and whose contract is to
140/// return the result of `::fstat64(fildes, buf)`, where `::fstat64` is
141/// the function provided by the `sys/stat.h` header.
142///
143/// See @ref bdls_filesystemutil_transitionaluniximputil
144template <class UNIX_INTERFACE>
146
147 // TYPES
148
149 /// `FileDescriptor` is an alias for the operating system's native file
150 /// descriptor / file handle type.
151 typedef int FileDescriptor;
152
153 /// `Offset` is an alias for a signed integral type, and represents the
154 /// offset of a location in a file.
155 typedef typename UNIX_INTERFACE::off64_t Offset;
156
157 private:
158 // PRIVATE TYPES
159
160 /// `off_t` is an alias to the `off64_t` type provided by the
161 /// `sys/types.h` header. It is a signed integral type used to
162 /// represent quantities of bytes.
163 typedef typename UNIX_INTERFACE::off64_t off64_t;
164
165 /// `stat64` is an alias to the `stat64` `struct` provided by the
166 /// `sys/stat.h` header.
167 typedef typename UNIX_INTERFACE::stat64 stat64;
168
169 /// `time_t` is an alias to the `time_t` type provided by the `sys/types.h`
170 /// header. It represents a time point as number of seconds since January
171 /// 1st 1970 in Coordinated Universal Time.
172 typedef typename UNIX_INTERFACE::time_t time_t;
173
174 // PRIVATE CLASS METHODS
175
176 /// Return the value of the `st_mtim.nsec` field of the specified `stat`
177 /// struct.
178 static long get_st_mtim_nsec(const stat64& stat);
179
180 /// Return the value of the `st_mtime` data member of the specified `stat`.
181 static time_t get_st_mtime(const stat64& stat);
182
183 /// Return the value of the `st_size` data member of the specified `stat`.
184 ///
185 /// \note Note that this function is provided in order to create a consistent
186 /// interface for accessing the data members of a `stat64` struct with
187 /// @ref get_st_mtime .
188 static off64_t get_st_size(const stat64& stat);
189
190 /// Invoke and return the result of `::fstat64(fildes, buf)` with the
191 /// specified `fildes` and `buf`, where `::fstat64` is the function
192 /// provided by the `sys/stat.h` header.
193 static int fstat64(int fildes, stat64 *buf);
194
195 public:
196 // CLASS METHODS
197
198 /// Return the size, in bytes, of the file with the specified `descriptor`,
199 /// or a negative value if an error occurs.
200 static Offset getFileSize(FileDescriptor descriptor);
201
202 /// Load into the specified `time` the last modification time of the file
203 /// with the specified `descriptor`, as reported by the filesystem. Return 0 on success, and a non-zero value otherwise.
204 ///
205 /// \note Note that the time is
206 /// reported in UTC.
208 FileDescriptor descriptor);
209};
210
211// ============================================================================
212// INLINE DEFINITIONS
213// ============================================================================
214
215 // ---------------------------------------------
216 // struct FilesystemUtil_TransitionalUnixImpUtil
217 // ---------------------------------------------
218
219// PRIVATE CLASS METHODS
220template <class UNIX_INTERFACE>
221long
223 const stat64& stat)
224{
225 return UNIX_INTERFACE::get_st_mtim_nsec(stat);
226}
227
228template <class UNIX_INTERFACE>
229typename UNIX_INTERFACE::time_t
230FilesystemUtil_TransitionalUnixImpUtil<UNIX_INTERFACE>::get_st_mtime(
231 const stat64& stat)
232{
233 return UNIX_INTERFACE::get_st_mtime(stat);
234}
235
236template <class UNIX_INTERFACE>
237typename UNIX_INTERFACE::off64_t
238FilesystemUtil_TransitionalUnixImpUtil<UNIX_INTERFACE>::get_st_size(
239 const stat64& stat)
240{
241 return UNIX_INTERFACE::get_st_size(stat);
242}
243
244template <class UNIX_INTERFACE>
245int FilesystemUtil_TransitionalUnixImpUtil<UNIX_INTERFACE>::fstat64(
246 int fildes,
247 stat64 *buf)
248{
249 return UNIX_INTERFACE::fstat64(fildes, buf);
250}
251
252// CLASS METHODS
253template <class UNIX_INTERFACE>
256 FileDescriptor descriptor)
257{
258 stat64 statResult;
259 const int rc = fstat64(descriptor, &statResult);
260 if (0 != rc) {
261 return -1; // RETURN
262 }
263
264 return get_st_size(statResult);
265}
266
267template <class UNIX_INTERFACE>
269 UNIX_INTERFACE>::getLastModificationTime(bdlt::Datetime *time,
270 FileDescriptor descriptor)
271{
272 stat64 statResult;
273 int rc = fstat64(descriptor, &statResult);
274 if (0 != rc) {
275 return -1; // RETURN
276 }
277
279 rc = result.addSecondsIfValid(get_st_mtime(statResult));
280 if (0 != rc) {
281 return -1; // RETURN
282 }
283
284 long nanoseconds = get_st_mtim_nsec(statResult);
285 BSLS_ASSERT_SAFE((0 <= nanoseconds) &&
286 (nanoseconds <
288 rc = result.addMicrosecondsIfValid(
290 if (0 != rc) {
291 return -1; // RETURN
292 }
293
294 *time = result;
295 return 0;
296}
297
298} // close package namespace
299
300
301#endif
302
303// ----------------------------------------------------------------------------
304// Copyright 2020 Bloomberg Finance L.P.
305//
306// Licensed under the Apache License, Version 2.0 (the "License");
307// you may not use this file except in compliance with the License.
308// You may obtain a copy of the License at
309//
310// http://www.apache.org/licenses/LICENSE-2.0
311//
312// Unless required by applicable law or agreed to in writing, software
313// distributed under the License is distributed on an "AS IS" BASIS,
314// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
315// See the License for the specific language governing permissions and
316// limitations under the License.
317// ----------------------------- END-OF-FILE ----------------------------------
318
319/** @} */
320/** @} */
321/** @} */
Definition bdlt_datetime.h:330
int addMicrosecondsIfValid(bsls::Types::Int64 microseconds)
Definition bdlt_datetime.h:2173
int addSecondsIfValid(bsls::Types::Int64 seconds)
Definition bdlt_datetime.h:2110
#define BSLS_ASSERT_SAFE(X)
Definition bsls_assert.h:1917
#define BSLS_IDENT(str)
BSLS_IDENT() - insert string into .comment binary segment (if supported)
Definition bsls_ident.h:238
Definition bdls_fdstreambuf.h:412
Definition bdls_filesystemutil_transitionaluniximputil.h:145
int FileDescriptor
Definition bdls_filesystemutil_transitionaluniximputil.h:151
static Offset getFileSize(FileDescriptor descriptor)
Definition bdls_filesystemutil_transitionaluniximputil.h:255
UNIX_INTERFACE::off64_t Offset
Definition bdls_filesystemutil_transitionaluniximputil.h:155
static int getLastModificationTime(bdlt::Datetime *time, FileDescriptor descriptor)
Definition bdls_filesystemutil_transitionaluniximputil.h:269
static const Datetime & epoch()
Definition bdlt_epochutil.h:397
static const bsls::Types::Int64 k_NANOSECONDS_PER_SECOND
Definition bdlt_timeunitratio.h:219
static const int k_NANOSECONDS_PER_MICROSECOND_32
Definition bdlt_timeunitratio.h:298