xref: /netbsd-src/external/bsd/fetch/dist/libfetch/fetch.3 (revision 466a16a118933bd295a8a104f095714fadf9cf68)
1.\"-
2.\" Copyright (c) 1998-2004 Dag-Erling Co�dan Sm�rgrav
3.\" All rights reserved.
4.\"
5.\" Redistribution and use in source and binary forms, with or without
6.\" modification, are permitted provided that the following conditions
7.\" are met:
8.\" 1. Redistributions of source code must retain the above copyright
9.\"    notice, this list of conditions and the following disclaimer.
10.\" 2. Redistributions in binary form must reproduce the above copyright
11.\"    notice, this list of conditions and the following disclaimer in the
12.\"    documentation and/or other materials provided with the distribution.
13.\"
14.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
15.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17.\" ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
18.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
19.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
20.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
21.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
22.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
23.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
24.\" SUCH DAMAGE.
25.\"
26.\" $FreeBSD: fetch.3,v 1.64 2007/12/18 11:03:26 des Exp $
27.\" $NetBSD: fetch.3,v 1.1.1.3 2008/10/29 16:18:13 joerg Exp $
28.\"
29.Dd April 25, 2008
30.Dt FETCH 3
31.Os
32.Sh NAME
33.Nm fetchMakeURL ,
34.Nm fetchParseURL ,
35.Nm fetchCopyURL ,
36.Nm fetchFreeURL ,
37.Nm fetchXGetURL ,
38.Nm fetchGetURL ,
39.Nm fetchPutURL ,
40.Nm fetchStatURL ,
41.Nm fetchListURL ,
42.Nm fetchXGet ,
43.Nm fetchGet ,
44.Nm fetchPut ,
45.Nm fetchStat ,
46.Nm fetchList ,
47.Nm fetchXGetFile ,
48.Nm fetchGetFile ,
49.Nm fetchPutFile ,
50.Nm fetchStatFile ,
51.Nm fetchListFile ,
52.Nm fetchXGetHTTP ,
53.Nm fetchGetHTTP ,
54.Nm fetchPutHTTP ,
55.Nm fetchStatHTTP ,
56.Nm fetchListHTTP ,
57.Nm fetchXGetFTP ,
58.Nm fetchGetFTP ,
59.Nm fetchPutFTP ,
60.Nm fetchStatFTP ,
61.Nm fetchListFTP
62.Nm fetchInitURLList ,
63.Nm fetchFreeURLList ,
64.Nm fetchUnquotePath ,
65.Nm fetchUnquoteFilename ,
66.Nm fetchStringifyURL ,
67.Nm fetch
68.Nd file transfer functions
69.Sh LIBRARY
70.Lb libfetch
71.Sh SYNOPSIS
72.In stdio.h
73.In fetch.h
74.Ft struct url *
75.Fn fetchMakeURL "const char *scheme" "const char *host" "int port" "const char *doc" "const char *user" "const char *pwd"
76.Ft struct url *
77.Fn fetchParseURL "const char *URL"
78.Ft struct url *
79.Fn fetchCopyURL "const struct url *u"
80.Ft void
81.Fn fetchFreeURL "struct url *u"
82.Ft fetchIO *
83.Fn fetchXGetURL "const char *URL" "struct url_stat *us" "const char *flags"
84.Ft fetchIO *
85.Fn fetchGetURL "const char *URL" "const char *flags"
86.Ft fetchIO *
87.Fn fetchPutURL "const char *URL" "const char *flags"
88.Ft int
89.Fn fetchStatURL "const char *URL" "struct url_stat *us" "const char *flags"
90.Ft int
91.Fn fetchListURL "struct url_list *list" "const char *URL" "const char *flags"
92.Ft fetchIO *
93.Fn fetchXGet "struct url *u" "struct url_stat *us" "const char *flags"
94.Ft fetchIO *
95.Fn fetchGet "struct url *u" "const char *flags"
96.Ft fetchIO *
97.Fn fetchPut "struct url *u" "const char *flags"
98.Ft int
99.Fn fetchStat "struct url *u" "struct url_stat *us" "const char *flags"
100.Ft int
101.Fn fetchList "struct url_list *list" "struct url *u" "const char *flags"
102.Ft fetchIO *
103.Fn fetchXGetFile "struct url *u" "struct url_stat *us" "const char *flags"
104.Ft fetchIO *
105.Fn fetchGetFile "struct url *u" "const char *flags"
106.Ft fetchIO *
107.Fn fetchPutFile "struct url *u" "const char *flags"
108.Ft int
109.Fn fetchStatFile "struct url *u" "struct url_stat *us" "const char *flags"
110.Ft int
111.Fn fetchListFile "struct url_list *list" "struct url *u" "const char *flags"
112.Ft fetchIO *
113.Fn fetchXGetHTTP "struct url *u" "struct url_stat *us" "const char *flags"
114.Ft fetchIO *
115.Fn fetchGetHTTP "struct url *u" "const char *flags"
116.Ft fetchIO *
117.Fn fetchPutHTTP "struct url *u" "const char *flags"
118.Ft int
119.Fn fetchStatHTTP "struct url *u" "struct url_stat *us" "const char *flags"
120.Ft int
121.Fn fetchListHTTP "struct url_list *list" "struct url *u" "const char *flags"
122.Ft fetchIO *
123.Fn fetchXGetFTP "struct url *u" "struct url_stat *us" "const char *flags"
124.Ft fetchIO *
125.Fn fetchGetFTP "struct url *u" "const char *flags"
126.Ft fetchIO *
127.Fn fetchPutFTP "struct url *u" "const char *flags"
128.Ft int
129.Fn fetchStatFTP "struct url *u" "struct url_stat *us" "const char *flags"
130.Ft int
131.Fn fetchListFTP "struct url_list *list" "struct url *u" "const char *flags"
132.Ft void
133.Fn fetchInitURLList "struct url_list *ul"
134.Ft void
135.Fn fetchFreeURLList "struct url_list *ul"
136.Ft char *
137.Fn fetchUnquotePath "struct url *u"
138.Ft char *
139.Fn fetchUnquoteFilename "struct url *u"
140.Ft char *
141.Fn fetchStringifyURL "const struct url *u"
142.Sh DESCRIPTION
143These functions implement a high-level library for retrieving and
144uploading files using Uniform Resource Locators (URLs).
145.Pp
146.Fn fetchParseURL
147takes a URL in the form of a null-terminated string and splits it into
148its components function according to the Common Internet Scheme Syntax
149detailed in RFC 1738.
150A regular expression which produces this syntax is:
151.Bd -literal
152    \*[Lt]scheme\*[Gt]:(//(\*[Lt]user\*[Gt](:\*[Lt]pwd\*[Gt])?@)?\*[Lt]host\*[Gt](:\*[Lt]port\*[Gt])?)?/(\*[Lt]document\*[Gt])?
153.Ed
154.Pp
155If the URL does not seem to begin with a scheme name, it is assumed to be a local path.
156Only absolute path names are accepted.
157.Pp
158Note that some components of the URL are not necessarily relevant to
159all URL schemes.
160For instance, the file scheme only needs the
161.Aq scheme
162and
163.Aq document
164components.
165.Fn fetchParseURL
166quotes any unsafe character in the URL automatically.
167This is not done by
168.Fn fetchMakeURL .
169.Fn fetchCopyURL
170copies an existing
171.Vt url
172structure.
173.Pp
174.Fn fetchMakeURL ,
175.Fn fetchParseURL ,
176and
177.Fn fetchCopyURL
178return a pointer to a
179.Vt url
180structure, which is defined as follows in
181.In fetch.h :
182.Bd -literal
183#define URL_SCHEMELEN 16
184#define URL_USERLEN 256
185#define URL_PWDLEN 256
186#define URL_HOSTLEN 255
187
188struct url {
189    char	 scheme[URL_SCHEMELEN + 1];
190    char	 user[URL_USERLEN + 1];
191    char	 pwd[URL_PWDLEN + 1];
192    char	 host[URL_HOSTLEN + 1];
193    int		 port;
194    char	*doc;
195    off_t	 offset;
196    size_t	 length;
197};
198.Ed
199.Pp
200The pointer returned by
201.Fn fetchMakeURL ,
202.Fn fetchCopyURL ,
203and
204.Fn fetchParseURL
205should be freed using
206.Fn fetchFreeURL .
207.Pp
208.Fn fetchXGetURL ,
209.Fn fetchGetURL ,
210and
211.Fn fetchPutURL
212constitute the recommended interface to the
213.Nm fetch
214library.
215They examine the URL passed to them to determine the transfer
216method, and call the appropriate lower-level functions to perform the
217actual transfer.
218.Fn fetchXGetURL
219also returns the remote document's metadata in the
220.Vt url_stat
221structure pointed to by the
222.Fa us
223argument.
224.Pp
225The
226.Fa flags
227argument is a string of characters which specify transfer options.
228The
229meaning of the individual flags is scheme-dependent, and is detailed
230in the appropriate section below.
231.Pp
232.Fn fetchStatURL
233attempts to obtain the requested document's metadata and fill in the
234structure pointed to by its second argument.
235The
236.Vt url_stat
237structure is defined as follows in
238.In fetch.h :
239.Bd -literal
240struct url_stat {
241    off_t	 size;
242    time_t	 atime;
243    time_t	 mtime;
244};
245.Ed
246.Pp
247If the size could not be obtained from the server, the
248.Fa size
249field is set to \-1.
250If the modification time could not be obtained from the server, the
251.Fa mtime
252field is set to the epoch.
253If the access time could not be obtained from the server, the
254.Fa atime
255field is set to the modification time.
256.Pp
257.Fn fetchListURL
258attempts to list the contents of the directory pointed to by the URL provided.
259The pattern can be a simple glob-like expression as hint.
260Callers should not depend on the server to filter names.
261If successful, it appends the list of entries to the
262.Vt url_list
263structure.
264The
265.Vt url_list
266structure is defined as follows in
267.In fetch.h :
268.Bd -literal
269struct url_list {
270    size_t	length;
271    size_t	alloc_size;
272    struct url	*urls;
273};
274.Ed
275.Pp
276The list should be initialized by calling
277.Fn fetchInitURLList
278and the entries be freed by calling
279.Fn fetchFreeURLList .
280.Pp
281.Fn fetchStringifyURL
282returns the URL as string.
283.Fn fetchUnquotePath
284returns the path name part of the URL with any quoting undone.
285Query arguments and fragment identifiers are not included.
286.Fn fetchUnquoteFilename
287returns the last component of the path name as returned by
288.Fn fetchUnquotePath .
289.Fn fetchStringifyURL ,
290.Fn fetchUnquotePath ,
291and
292.Fn fetchUnquoteFilename
293return a string that should be deallocated with
294.Fn free
295after use.
296.Pp
297.Fn fetchXGet ,
298.Fn fetchGet ,
299.Fn fetchPut ,
300and
301.Fn fetchStat
302are similar to
303.Fn fetchXGetURL ,
304.Fn fetchGetURL ,
305.Fn fetchPutURL ,
306and
307.Fn fetchStatURL ,
308except that they expect a pre-parsed URL in the form of a pointer to
309a
310.Vt struct url
311rather than a string.
312.Pp
313All of the
314.Fn fetchXGetXXX ,
315.Fn fetchGetXXX ,
316and
317.Fn fetchPutXXX
318functions return a pointer to a stream which can be used to read or
319write data from or to the requested document, respectively.
320Note that
321although the implementation details of the individual access methods
322vary, it can generally be assumed that a stream returned by one of the
323.Fn fetchXGetXXX
324or
325.Fn fetchGetXXX
326functions is read-only, and that a stream returned by one of the
327.Fn fetchPutXXX
328functions is write-only.
329.Sh FILE SCHEME
330.Fn fetchXGetFile ,
331.Fn fetchGetFile ,
332and
333.Fn fetchPutFile
334provide access to documents which are files in a locally mounted file
335system.
336Only the
337.Aq document
338component of the URL is used.
339.Pp
340.Fn fetchXGetFile
341and
342.Fn fetchGetFile
343do not accept any flags.
344.Pp
345.Fn fetchPutFile
346accepts the
347.Ql a
348(append to file) flag.
349If that flag is specified, the data written to
350the stream returned by
351.Fn fetchPutFile
352will be appended to the previous contents of the file, instead of
353replacing them.
354.Sh FTP SCHEME
355.Fn fetchXGetFTP ,
356.Fn fetchGetFTP ,
357and
358.Fn fetchPutFTP
359implement the FTP protocol as described in RFC 959.
360.Pp
361By default
362.Nm libfetch
363will attempt to use passive mode first and only fallback to active mode
364if the server reports a syntax error.
365If the
366.Ql a
367(active) flag is specified, a passive connection is not tried and active mode
368is used directly.
369.Pp
370If the
371.Ql l
372(low) flag is specified, data sockets will be allocated in the low (or
373default) port range instead of the high port range (see
374.Xr ip 4 ) .
375.Pp
376If the
377.Ql d
378(direct) flag is specified,
379.Fn fetchXGetFTP ,
380.Fn fetchGetFTP ,
381and
382.Fn fetchPutFTP
383will use a direct connection even if a proxy server is defined.
384.Pp
385If no user name or password is given, the
386.Nm fetch
387library will attempt an anonymous login, with user name "anonymous"
388and password "anonymous@\*[Lt]hostname\*[Gt]".
389.Sh HTTP SCHEME
390The
391.Fn fetchXGetHTTP ,
392.Fn fetchGetHTTP ,
393and
394.Fn fetchPutHTTP
395functions implement the HTTP/1.1 protocol.
396With a little luck, there is
397even a chance that they comply with RFC 2616 and RFC 2617.
398.Pp
399If the
400.Ql d
401(direct) flag is specified,
402.Fn fetchXGetHTTP ,
403.Fn fetchGetHTTP ,
404and
405.Fn fetchPutHTTP
406will use a direct connection even if a proxy server is defined.
407.Pp
408Since there seems to be no good way of implementing the HTTP PUT
409method in a manner consistent with the rest of the
410.Nm fetch
411library,
412.Fn fetchPutHTTP
413is currently unimplemented.
414.Sh AUTHENTICATION
415Apart from setting the appropriate environment variables and
416specifying the user name and password in the URL or the
417.Vt struct url ,
418the calling program has the option of defining an authentication
419function with the following prototype:
420.Pp
421.Ft int
422.Fn myAuthMethod "struct url *u"
423.Pp
424The callback function should fill in the
425.Fa user
426and
427.Fa pwd
428fields in the provided
429.Vt struct url
430and return 0 on success, or any other value to indicate failure.
431.Pp
432To register the authentication callback, simply set
433.Va fetchAuthMethod
434to point at it.
435The callback will be used whenever a site requires authentication and
436the appropriate environment variables are not set.
437.Pp
438This interface is experimental and may be subject to change.
439.Sh RETURN VALUES
440.Fn fetchParseURL
441returns a pointer to a
442.Vt struct url
443containing the individual components of the URL.
444If it is
445unable to allocate memory, or the URL is syntactically incorrect,
446.Fn fetchParseURL
447returns a
448.Dv NULL
449pointer.
450.Pp
451The
452.Fn fetchStat
453functions return 0 on success and \-1 on failure.
454.Pp
455All other functions return a stream pointer which may be used to
456access the requested document, or
457.Dv NULL
458if an error occurred.
459.Pp
460The following error codes are defined in
461.In fetch.h :
462.Bl -tag -width 18n
463.It Bq Er FETCH_ABORT
464Operation aborted
465.It Bq Er FETCH_AUTH
466Authentication failed
467.It Bq Er FETCH_DOWN
468Service unavailable
469.It Bq Er FETCH_EXISTS
470File exists
471.It Bq Er FETCH_FULL
472File system full
473.It Bq Er FETCH_INFO
474Informational response
475.It Bq Er FETCH_MEMORY
476Insufficient memory
477.It Bq Er FETCH_MOVED
478File has moved
479.It Bq Er FETCH_NETWORK
480Network error
481.It Bq Er FETCH_OK
482No error
483.It Bq Er FETCH_PROTO
484Protocol error
485.It Bq Er FETCH_RESOLV
486Resolver error
487.It Bq Er FETCH_SERVER
488Server error
489.It Bq Er FETCH_TEMP
490Temporary error
491.It Bq Er FETCH_TIMEOUT
492Operation timed out
493.It Bq Er FETCH_UNAVAIL
494File is not available
495.It Bq Er FETCH_UNKNOWN
496Unknown error
497.It Bq Er FETCH_URL
498Invalid URL
499.El
500.Pp
501The accompanying error message includes a protocol-specific error code
502and message, e.g.\& "File is not available (404 Not Found)"
503.Sh ENVIRONMENT
504.Bl -tag -width ".Ev FETCH_BIND_ADDRESS"
505.It Ev FETCH_BIND_ADDRESS
506Specifies a host name or IP address to which sockets used for outgoing
507connections will be bound.
508.It Ev FTP_LOGIN
509Default FTP login if none was provided in the URL.
510.It Ev FTP_PASSIVE_MODE
511If set to anything but
512.Ql no ,
513forces the FTP code to use passive mode.
514.It Ev FTP_PASSWORD
515Default FTP password if the remote server requests one and none was
516provided in the URL.
517.It Ev FTP_PROXY
518URL of the proxy to use for FTP requests.
519The document part is ignored.
520FTP and HTTP proxies are supported; if no scheme is specified, FTP is
521assumed.
522If the proxy is an FTP proxy,
523.Nm libfetch
524will send
525.Ql user@host
526as user name to the proxy, where
527.Ql user
528is the real user name, and
529.Ql host
530is the name of the FTP server.
531.Pp
532If this variable is set to an empty string, no proxy will be used for
533FTP requests, even if the
534.Ev HTTP_PROXY
535variable is set.
536.It Ev ftp_proxy
537Same as
538.Ev FTP_PROXY ,
539for compatibility.
540.It Ev HTTP_AUTH
541Specifies HTTP authorization parameters as a colon-separated list of
542items.
543The first and second item are the authorization scheme and realm
544respectively; further items are scheme-dependent.
545Currently, only basic authorization is supported.
546.Pp
547Basic authorization requires two parameters: the user name and
548password, in that order.
549.Pp
550This variable is only used if the server requires authorization and
551no user name or password was specified in the URL.
552.It Ev HTTP_PROXY
553URL of the proxy to use for HTTP requests.
554The document part is ignored.
555Only HTTP proxies are supported for HTTP requests.
556If no port number is specified, the default is 3128.
557.Pp
558Note that this proxy will also be used for FTP documents, unless the
559.Ev FTP_PROXY
560variable is set.
561.It Ev http_proxy
562Same as
563.Ev HTTP_PROXY ,
564for compatibility.
565.It Ev HTTP_PROXY_AUTH
566Specifies authorization parameters for the HTTP proxy in the same
567format as the
568.Ev HTTP_AUTH
569variable.
570.Pp
571This variable is used if and only if connected to an HTTP proxy, and
572is ignored if a user and/or a password were specified in the proxy
573URL.
574.It Ev HTTP_REFERER
575Specifies the referrer URL to use for HTTP requests.
576If set to
577.Dq auto ,
578the document URL will be used as referrer URL.
579.It Ev HTTP_USER_AGENT
580Specifies the User-Agent string to use for HTTP requests.
581This can be useful when working with HTTP origin or proxy servers that
582differentiate between user agents.
583.It Ev NETRC
584Specifies a file to use instead of
585.Pa ~/.netrc
586to look up login names and passwords for FTP sites.
587See
588.Xr ftp 1
589for a description of the file format.
590This feature is experimental.
591.It Ev NO_PROXY
592Either a single asterisk, which disables the use of proxies
593altogether, or a comma- or whitespace-separated list of hosts for
594which proxies should not be used.
595.It Ev no_proxy
596Same as
597.Ev NO_PROXY ,
598for compatibility.
599.El
600.Sh EXAMPLES
601To access a proxy server on
602.Pa proxy.example.com
603port 8080, set the
604.Ev HTTP_PROXY
605environment variable in a manner similar to this:
606.Pp
607.Dl HTTP_PROXY=http://proxy.example.com:8080
608.Pp
609If the proxy server requires authentication, there are
610two options available for passing the authentication data.
611The first method is by using the proxy URL:
612.Pp
613.Dl HTTP_PROXY=http://\*[Lt]user\*[Gt]:\*[Lt]pwd\*[Gt]@proxy.example.com:8080
614.Pp
615The second method is by using the
616.Ev HTTP_PROXY_AUTH
617environment variable:
618.Bd -literal -offset indent
619HTTP_PROXY=http://proxy.example.com:8080
620HTTP_PROXY_AUTH=basic:*:\*[Lt]user\*[Gt]:\*[Lt]pwd\*[Gt]
621.Ed
622.Pp
623To disable the use of a proxy for an HTTP server running on the local
624host, define
625.Ev NO_PROXY
626as follows:
627.Bd -literal -offset indent
628NO_PROXY=localhost,127.0.0.1
629.Ed
630.Sh SEE ALSO
631.\" .Xr fetch 1 ,
632.\" .Xr ftpio 3 ,
633.Xr ftp 1 ,
634.Xr ip 4
635.Rs
636.%A J. Postel
637.%A J. K. Reynolds
638.%D October 1985
639.%B File Transfer Protocol
640.%O RFC 959
641.Re
642.Rs
643.%A P. Deutsch
644.%A A. Emtage
645.%A A. Marine
646.%D May 1994
647.%T How to Use Anonymous FTP
648.%O RFC 1635
649.Re
650.Rs
651.%A T. Berners-Lee
652.%A L. Masinter
653.%A M. McCahill
654.%D December 1994
655.%T Uniform Resource Locators (URL)
656.%O RFC 1738
657.Re
658.Rs
659.%A R. Fielding
660.%A J. Gettys
661.%A J. Mogul
662.%A H. Frystyk
663.%A L. Masinter
664.%A P. Leach
665.%A T. Berners-Lee
666.%D January 1999
667.%B Hypertext Transfer Protocol -- HTTP/1.1
668.%O RFC 2616
669.Re
670.Rs
671.%A J. Franks
672.%A P. Hallam-Baker
673.%A J. Hostetler
674.%A S. Lawrence
675.%A P. Leach
676.%A A. Luotonen
677.%A L. Stewart
678.%D June 1999
679.%B HTTP Authentication: Basic and Digest Access Authentication
680.%O RFC 2617
681.Re
682.Sh HISTORY
683The
684.Nm fetch
685library first appeared in
686.Fx 3.0 .
687.Sh AUTHORS
688.An -nosplit
689The
690.Nm fetch
691library was mostly written by
692.An Dag-Erling Sm\(/orgrav Aq des@FreeBSD.org
693with numerous suggestions from
694.An Jordan K. Hubbard Aq jkh@FreeBSD.org ,
695.An Eugene Skepner Aq eu@qub.com
696and other
697.Fx
698developers.
699It replaces the older
700.Nm ftpio
701library written by
702.An Poul-Henning Kamp Aq phk@FreeBSD.org
703and
704.An Jordan K. Hubbard Aq jkh@FreeBSD.org .
705.Pp
706This manual page was written by
707.An Dag-Erling Sm\(/orgrav Aq des@FreeBSD.org .
708.Sh BUGS
709Some parts of the library are not yet implemented.
710The most notable
711examples of this are
712.Fn fetchPutHTTP
713and FTP proxy support.
714.Pp
715There is no way to select a proxy at run-time other than setting the
716.Ev HTTP_PROXY
717or
718.Ev FTP_PROXY
719environment variables as appropriate.
720.Pp
721.Nm libfetch
722does not understand or obey 305 (Use Proxy) replies.
723.Pp
724Error numbers are unique only within a certain context; the error
725codes used for FTP and HTTP overlap, as do those used for resolver and
726system errors.
727For instance, error code 202 means "Command not
728implemented, superfluous at this site" in an FTP context and
729"Accepted" in an HTTP context.
730.Pp
731.Fn fetchStatFTP
732does not check that the result of an MDTM command is a valid date.
733.Pp
734The man page is incomplete, poorly written and produces badly
735formatted text.
736.Pp
737The error reporting mechanism is unsatisfactory.
738.Pp
739Some parts of the code are not fully reentrant.
740