]> git.ipfire.org Git - thirdparty/squid.git/blob - src/errorpage.h
Docs: Copyright updates for 2018 (#114)
[thirdparty/squid.git] / src / errorpage.h
1 /*
2 * Copyright (C) 1996-2018 The Squid Software Foundation and contributors
3 *
4 * Squid software is distributed under GPLv2+ license and includes
5 * contributions from numerous individuals and organizations.
6 * Please see the COPYING and CONTRIBUTORS files for details.
7 */
8
9 /* DEBUG: section 04 Error Generation */
10
11 #ifndef SQUID_ERRORPAGE_H
12 #define SQUID_ERRORPAGE_H
13
14 #include "cbdata.h"
15 #include "comm/forward.h"
16 #include "err_detail_type.h"
17 #include "err_type.h"
18 #include "http/forward.h"
19 #include "http/StatusCode.h"
20 #include "ip/Address.h"
21 #include "SquidString.h"
22 /* auth/UserRequest.h is empty unless USE_AUTH is defined */
23 #include "auth/UserRequest.h"
24 #if USE_OPENSSL
25 #include "ssl/ErrorDetail.h"
26 #endif
27
28 /// error page callback
29 typedef void ERCB(int fd, void *, size_t);
30
31 /**
32 \defgroup ErrorPageAPI Error Pages API
33 \ingroup Components
34 \section ErrorPageStringCodes Error Page % codes for text insertion.
35 *
36 \verbatim
37 a - User identity x
38 B - URL with FTP %2f hack x
39 c - Squid error code x
40 d - seconds elapsed since request received x
41 D - Error details x
42 e - errno x
43 E - strerror() x
44 f - FTP request line x
45 F - FTP reply line x
46 g - FTP server message x
47 h - cache hostname x
48 H - server host name x
49 i - client IP address x
50 I - server IP address x
51 l - HREF link for CSS stylesheet inclusion x
52 L - HREF link for more info/contact x
53 M - Request Method x
54 m - Error message returned by auth helper x
55 o - Message returned external acl helper x
56 p - URL port # x
57 P - Protocol x
58 R - Full HTTP Request x
59 S - squid signature from ERR_SIGNATURE x
60 s - caching proxy software with version x
61 t - local time x
62 T - UTC x
63 U - URL without password x
64 u - URL with password x
65 w - cachemgr email address x
66 W - error data (to be included in the mailto links)
67 x - error name x
68 z - dns server error message x
69 Z - Preformatted error message x
70 \endverbatim
71 */
72
73 class MemBuf;
74 class StoreEntry;
75 class wordlist;
76
77 /// \ingroup ErrorPageAPI
78 class ErrorState
79 {
80 CBDATA_CLASS(ErrorState);
81
82 public:
83 ErrorState(err_type type, Http::StatusCode, HttpRequest * request);
84 ErrorState() = delete; // not implemented.
85 ~ErrorState();
86
87 /// Creates a general request forwarding error with the right http_status.
88 static ErrorState *NewForwarding(err_type, HttpRequestPointer &);
89
90 /**
91 * Allocates and initializes an error response
92 */
93 HttpReply *BuildHttpReply(void);
94
95 /// set error type-specific detail code
96 void detailError(int dCode) {detailCode = dCode;}
97
98 private:
99 /**
100 * Locates error page template to be used for this error
101 * and constructs the HTML page content from it.
102 */
103 MemBuf *BuildContent(void);
104
105 /**
106 * Convert the given template string into textual output
107 *
108 * \param text The string to be converted
109 * \param allowRecursion Whether to convert codes which output may contain codes
110 */
111 MemBuf *ConvertText(const char *text, bool allowRecursion);
112
113 /**
114 * Generates the Location: header value for a deny_info error page
115 * to be used for this error.
116 */
117 void DenyInfoLocation(const char *name, HttpRequest *request, MemBuf &result);
118
119 /**
120 * Map the Error page and deny_info template % codes into textual output.
121 *
122 * Several of the codes produce blocks of non-URL compatible results.
123 * When processing the deny_info location URL they will be skipped.
124 *
125 * \param token The token following % which need to be converted
126 * \param building_deny_info_url Perform special deny_info actions, such as URL-encoding and token skipping.
127 * \ allowRecursion True if the codes which do recursions should converted
128 */
129 const char *Convert(char token, bool building_deny_info_url, bool allowRecursion);
130
131 /**
132 * CacheManager / Debug dump of the ErrorState object.
133 * Writes output into the given MemBuf.
134 \retval 0 successful completion.
135 */
136 int Dump(MemBuf * mb);
137
138 public:
139 err_type type = ERR_NONE;
140 int page_id = ERR_NONE;
141 char *err_language = nullptr;
142 Http::StatusCode httpStatus;
143 #if USE_AUTH
144 Auth::UserRequest::Pointer auth_user_request;
145 #endif
146 HttpRequestPointer request;
147 char *url = nullptr;
148 int xerrno = 0;
149 unsigned short port = 0;
150 String dnsError; ///< DNS lookup error message
151 time_t ttl = 0;
152
153 Ip::Address src_addr;
154 char *redirect_url = nullptr;
155 ERCB *callback;
156 void *callback_data = nullptr;
157
158 struct {
159 wordlist *server_msg = nullptr;
160 char *request = nullptr;
161 char *reply = nullptr;
162 char *cwd_msg = nullptr;
163 MemBuf *listing = nullptr;
164 } ftp;
165
166 char *request_hdrs = nullptr;
167 char *err_msg = nullptr; /* Preformatted error message from the cache */
168
169 #if USE_OPENSSL
170 Ssl::ErrorDetail *detail = nullptr;
171 #endif
172 /// type-specific detail about the transaction error;
173 /// overwrites xerrno; overwritten by detail, if any.
174 int detailCode = ERR_DETAIL_NONE;
175 };
176
177 /**
178 \ingroup ErrorPageAPI
179 *
180 * This function finds the error messages formats, and stores
181 * them in error_text[]
182 *
183 \par Global effects:
184 * error_text[] - is modified
185 */
186 void errorInitialize(void);
187
188 /// \ingroup ErrorPageAPI
189 void errorClean(void);
190
191 /**
192 * \ingroup ErrorPageAPI
193 *
194 * This function generates a error page from the info contained
195 * by err and then sends it to the client.
196 * The callback function errorSendComplete() is called after
197 * the page has been written to the client (clientConn).
198 * errorSendComplete() deallocates err. We need to add
199 * err to the cbdata because comm_write() requires it
200 * for all callback data pointers.
201 *
202 \note normally errorSend() should only be called from
203 * routines in ssl.c and pass.c, where we don't have any
204 * StoreEntry's. In client_side.c we must allocate a StoreEntry
205 * for errors and use errorAppendEntry() to account for
206 * persistent/pipeline connections.
207 *
208 \param clientConn socket where page object is to be written
209 \param err This object is destroyed after use in this function.
210 */
211 void errorSend(const Comm::ConnectionPointer &conn, ErrorState *err);
212
213 /**
214 \ingroup ErrorPageAPI
215 *
216 * This function generates a error page from the info contained
217 * by err and then stores the text in the specified store
218 * entry.
219 * This function should only be called by "server
220 * side routines" which need to communicate errors to the
221 * client side. It should also be called from client_side.c
222 * because we now support persistent connections, and
223 * cannot assume that we can immediately write to the socket
224 * for an error.
225 *
226 \param entry ??
227 \param err This object is destroyed after use in this function.
228 */
229 void errorAppendEntry(StoreEntry *entry, ErrorState *err);
230
231 /// \ingroup ErrorPageAPI
232 err_type errorReservePageId(const char *page_name);
233
234 const char *errorPageName(int pageId); ///< error ID to string
235
236 /**
237 \ingroup ErrorPageAPI
238 *
239 * loads text templates used for error pages and details;
240 * supports translation of templates
241 */
242 class TemplateFile
243 {
244 public:
245 TemplateFile(const char *name, const err_type code);
246 virtual ~TemplateFile() {}
247
248 /// return true if the data loaded from disk without any problem
249 bool loaded() const {return wasLoaded;}
250
251 /**
252 * Load the page_name template from a file which probably exist at:
253 * (a) admin specified custom directory (error_directory)
254 * (b) default language translation directory (error_default_language)
255 * (c) English sub-directory where errors should ALWAYS exist
256 */
257 bool loadDefault();
258
259 /**
260 * Load an error template for a given HTTP request. This function examines the
261 * Accept-Language header and select the first available template. If the default
262 * template selected (eg because of a "Accept-Language: *"), or not available
263 * template found this function return false.
264 */
265 bool loadFor(const HttpRequest *request);
266
267 /**
268 * Load the file given by "path". It uses the "parse()" method.
269 * On success return true and sets the "defined" member
270 */
271 bool loadFromFile(const char *path);
272
273 /// The language used for the template
274 const char *language() {return errLanguage.termedBuf();}
275
276 bool silent; ///< Whether to print error messages on cache.log file or not. It is user defined.
277
278 protected:
279 /// Used to parse (if parsing required) the template data .
280 virtual bool parse(const char *buf, int len, bool eof) = 0;
281
282 /**
283 * Try to load the "page_name" template for a given language "lang"
284 * from squid errors directory
285 \return true on success false otherwise
286 */
287 bool tryLoadTemplate(const char *lang);
288
289 bool wasLoaded; ///< True if the template data read from disk without any problem
290 String errLanguage; ///< The error language of the template.
291 String templateName; ///< The name of the template
292 err_type templateCode; ///< The internal code for this template.
293 };
294
295 /**
296 * Parses the Accept-Language header value and return one language item on
297 * each call.
298 * Will ignore any whitespace, q-values, and detectably invalid language
299 * codes in the header.
300 *
301 * \param hdr is the Accept-Language header value
302 * \param lang a buffer to store parsed language code in
303 * \param langlen the length of the lang buffer
304 * \param pos is used to store the offset state of parsing. Must be "0" on first call.
305 * Will be altered to point at the start of next field-value.
306 * \return true if something looking like a language token has been placed in lang, false otherwise
307 */
308 bool strHdrAcptLangGetItem(const String &hdr, char *lang, int langLen, size_t &pos);
309
310 #endif /* SQUID_ERRORPAGE_H */
311