Sane C++ Libraries
C++ Platform Abstraction Libraries
Loading...
Searching...
No Matches
FileSystemWatcherErrorFormatter.h
1// Copyright (c) Stefano Cristiano
2// SPDX-License-Identifier: MIT
3#pragma once
4
5#include "../Common/ResultErrorFormatter.h"
6#include "FileSystemWatcherError.h"
7
8namespace SC
9{
12
13namespace detail
14{
15inline bool appendFileSystemWatcherErrorDetail(ResultErrorFormatter& formatter, FileSystemWatcherErrorDetail detail)
16{
17 switch (detail)
18 {
19 case FileSystemWatcherErrorDetail::None: return true;
20 case FileSystemWatcherErrorDetail::AssignWatchPath: formatter.append("assign watch path"); break;
21 case FileSystemWatcherErrorDetail::BuildSubfolderPath: formatter.append("build subfolder path"); break;
22 case FileSystemWatcherErrorDetail::BuildNotificationPath: formatter.append("build notification path"); break;
23 case FileSystemWatcherErrorDetail::BuildFullPath: formatter.append("build full path"); break;
24 case FileSystemWatcherErrorDetail::WatchPathCapacity: formatter.append("watch path capacity"); break;
25 case FileSystemWatcherErrorDetail::WorkerAlreadyStarted: formatter.append("worker already started"); break;
26 case FileSystemWatcherErrorDetail::PosixPthreadCreate: formatter.append("POSIX create thread"); break;
27 case FileSystemWatcherErrorDetail::PosixPthreadJoin: formatter.append("POSIX join thread"); break;
28 case FileSystemWatcherErrorDetail::WindowsCreateThread: formatter.append("Windows create thread"); break;
29 case FileSystemWatcherErrorDetail::WindowsWaitForSingleObject: formatter.append("Windows wait for thread"); break;
30 case FileSystemWatcherErrorDetail::LinuxCreateShutdownPipe: formatter.append("Linux create shutdown pipe"); break;
31 case FileSystemWatcherErrorDetail::LinuxInitializeInotify: formatter.append("Linux initialize inotify"); break;
32 case FileSystemWatcherErrorDetail::LinuxWriteShutdownPipe: formatter.append("Linux write shutdown pipe"); break;
33 case FileSystemWatcherErrorDetail::LinuxInotifyDescriptor: formatter.append("Linux inotify descriptor"); break;
34 case FileSystemWatcherErrorDetail::LinuxRemoveWatch: formatter.append("Linux remove watch"); break;
35 case FileSystemWatcherErrorDetail::LinuxAddRootWatch: formatter.append("Linux add root watch"); break;
36 case FileSystemWatcherErrorDetail::LinuxAddSubdirectoryWatch:
37 formatter.append("Linux add subdirectory watch");
38 break;
39 case FileSystemWatcherErrorDetail::LinuxOpenRootDirectory: formatter.append("Linux open root directory"); break;
40 case FileSystemWatcherErrorDetail::LinuxWatchHandleCapacity: formatter.append("Linux watch handle capacity"); break;
41 case FileSystemWatcherErrorDetail::LinuxPendingDirectoryCapacity:
42 formatter.append("Linux pending directory capacity");
43 break;
44 case FileSystemWatcherErrorDetail::LinuxRelativePathStorage: formatter.append("Linux relative path storage"); break;
45 case FileSystemWatcherErrorDetail::AppleRunLoop: formatter.append("Apple run loop"); break;
46 case FileSystemWatcherErrorDetail::AppleCreateRunLoopSource:
47 formatter.append("Apple create run loop source");
48 break;
49 case FileSystemWatcherErrorDetail::AppleAllocateWatchPaths: formatter.append("Apple allocate watch paths"); break;
50 case FileSystemWatcherErrorDetail::AppleCreateWatchPathString:
51 formatter.append("Apple create watch path string");
52 break;
53 case FileSystemWatcherErrorDetail::AppleCreateWatchPathsArray:
54 formatter.append("Apple create watch paths array");
55 break;
56 case FileSystemWatcherErrorDetail::AppleCreateEventStream: formatter.append("Apple create event stream"); break;
57 case FileSystemWatcherErrorDetail::AppleStartEventStream: formatter.append("Apple start event stream"); break;
58 case FileSystemWatcherErrorDetail::WindowsOpenDirectory: formatter.append("Windows open directory"); break;
59 case FileSystemWatcherErrorDetail::WindowsSubmitDirectoryChanges:
60 formatter.append("Windows submit directory changes");
61 break;
62 default: return false;
63 }
64 return true;
65}
66
67inline ResultErrorFormat formatFileSystemWatcherErrorWithDetails(FileSystemWatcherError error,
69 uint32_t nativeError, Span<char> output)
70{
71 ResultErrorFormatter formatter(output);
72 switch (error)
73 {
74 case FileSystemWatcherError::NotInitialized: formatter.append("Watcher is not initialized"); break;
75 case FileSystemWatcherError::AlreadyWatching: formatter.append("Folder watcher is already watching"); break;
76 case FileSystemWatcherError::NotWatching: formatter.append("Folder watcher is not watching"); break;
77 case FileSystemWatcherError::UnsupportedPathEncoding: formatter.append("Path encoding is not supported"); break;
78 case FileSystemWatcherError::PathPreparationFailed: formatter.append("Failed to prepare path"); break;
79 case FileSystemWatcherError::WatchLimitExceeded: formatter.append("Watch capacity exceeded"); break;
80 case FileSystemWatcherError::BufferTooSmall: formatter.append("Buffer capacity is insufficient"); break;
81 case FileSystemWatcherError::InitializationFailed: formatter.append("Failed to initialize watcher"); break;
82 case FileSystemWatcherError::WatchSetupFailed: formatter.append("Failed to configure watching"); break;
83 case FileSystemWatcherError::StopWatchingFailed: formatter.append("Failed to stop watching"); break;
84 case FileSystemWatcherError::CloseFailed: formatter.append("Failed to close watcher"); break;
85 default: return ResultErrorFormatter::failure(ResultErrorFormatStatus::UnknownError, output);
86 }
87
88 if (detail != FileSystemWatcherErrorDetail::None)
89 {
90 formatter.append(" (detail: ");
91 if (not appendFileSystemWatcherErrorDetail(formatter, detail))
92 return ResultErrorFormatter::failure(ResultErrorFormatStatus::UnknownError, output);
93 if (nativeError != 0)
94 {
95 formatter.append(", native error: ");
96 formatter.append(static_cast<uint64_t>(nativeError));
97 }
98 formatter.append(")");
99 }
100 else if (nativeError != 0)
101 {
102 formatter.append(" (native error: ");
103 formatter.append(static_cast<uint64_t>(nativeError));
104 formatter.append(")");
105 }
106 return formatter.finish();
107}
108} // namespace detail
109
110inline ResultErrorFormat formatFileSystemWatcherError(FileSystemWatcherError error, Span<char> output)
111{
112 return detail::formatFileSystemWatcherErrorWithDetails(error, FileSystemWatcherErrorDetail::None, 0, output);
113}
114
115inline ResultErrorFormat formatFileSystemWatcherError(Result result, Span<char> output)
116{
117 if (result)
118 return ResultErrorFormatter::failure(ResultErrorFormatStatus::NotAnError, output);
119 if (result.category() != FileSystemWatcherResultCategory)
120 return ResultErrorFormatter::failure(ResultErrorFormatStatus::ForeignCategory, output);
121 return formatFileSystemWatcherError(static_cast<FileSystemWatcherError>(result.errorValue()), output);
122}
123
124inline ResultErrorFormat formatFileSystemWatcherError(ResultFileSystemWatcher result, Span<char> output)
125{
126 if (result)
127 return ResultErrorFormatter::failure(ResultErrorFormatStatus::NotAnError, output);
128 if (result.result.category() != FileSystemWatcherResultCategory)
129 return ResultErrorFormatter::failure(ResultErrorFormatStatus::ForeignCategory, output);
130 return detail::formatFileSystemWatcherErrorWithDetails(
131 static_cast<FileSystemWatcherError>(result.result.errorValue()), result.detail, result.nativeError, output);
132}
133
135} // namespace SC
FileSystemWatcherError
Stable portable failures returned by the FileSystemWatcher library.
Definition FileSystemWatcherError.h:14
FileSystemWatcherErrorDetail
Stable backend stages retained as context for a FileSystemWatcher failure.
Definition FileSystemWatcherError.h:30