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