libcurl docs: improvements all over

This commit is contained in:
Daniel Stenberg
2014-09-19 15:07:58 +02:00
parent 7b85b332cb
commit 3ef73d9a88
5 changed files with 116 additions and 60 deletions

View File

@@ -5,7 +5,7 @@
.\" * | (__| |_| | _ <| |___ .\" * | (__| |_| | _ <| |___
.\" * \___|\___/|_| \_\_____| .\" * \___|\___/|_| \_\_____|
.\" * .\" *
.\" * Copyright (C) 1998 - 2011, Daniel Stenberg, <daniel@haxx.se>, et al. .\" * Copyright (C) 1998 - 2014, Daniel Stenberg, <daniel@haxx.se>, et al.
.\" * .\" *
.\" * This software is licensed as described in the file COPYING, which .\" * This software is licensed as described in the file COPYING, which
.\" * you should have received as part of this distribution. The terms .\" * you should have received as part of this distribution. The terms
@@ -19,7 +19,7 @@
.\" * KIND, either express or implied. .\" * KIND, either express or implied.
.\" * .\" *
.\" ************************************************************************** .\" **************************************************************************
.TH curl_easy_duphandle 3 "18 September 2001" "libcurl 7.9" "libcurl Manual" .TH curl_easy_duphandle 3 "19 Sep 2014" "libcurl" "libcurl Manual"
.SH NAME .SH NAME
curl_easy_duphandle - Clone a libcurl session handle curl_easy_duphandle - Clone a libcurl session handle
.SH SYNOPSIS .SH SYNOPSIS
@@ -47,5 +47,4 @@ in a synchronous way, the input handle may not be in use when cloned.
If this function returns NULL, something went wrong and no valid handle was If this function returns NULL, something went wrong and no valid handle was
returned. returned.
.SH "SEE ALSO" .SH "SEE ALSO"
.BR curl_easy_init "(3)," curl_easy_cleanup "(3)," curl_global_init "(3) .BR curl_easy_init "(3)," curl_easy_cleanup "(3)," curl_global_init "(3)"

View File

@@ -5,7 +5,7 @@
.\" * | (__| |_| | _ <| |___ .\" * | (__| |_| | _ <| |___
.\" * \___|\___/|_| \_\_____| .\" * \___|\___/|_| \_\_____|
.\" * .\" *
.\" * Copyright (C) 1998 - 2011, Daniel Stenberg, <daniel@haxx.se>, et al. .\" * Copyright (C) 1998 - 2014, Daniel Stenberg, <daniel@haxx.se>, et al.
.\" * .\" *
.\" * This software is licensed as described in the file COPYING, which .\" * This software is licensed as described in the file COPYING, which
.\" * you should have received as part of this distribution. The terms .\" * you should have received as part of this distribution. The terms
@@ -39,5 +39,6 @@ This function was added in libcurl 7.12.1
.SH RETURN VALUE .SH RETURN VALUE
Nothing Nothing
.SH "SEE ALSO" .SH "SEE ALSO"
.BR curl_easy_init "(3)," curl_easy_cleanup "(3)," curl_easy_setopt "(3) .BR curl_easy_init "(3)," curl_easy_cleanup "(3)," curl_easy_setopt "(3),"
.BR curl_easy_duphandle "(3)"

View File

@@ -5,7 +5,7 @@
.\" * | (__| |_| | _ <| |___ .\" * | (__| |_| | _ <| |___
.\" * \___|\___/|_| \_\_____| .\" * \___|\___/|_| \_\_____|
.\" * .\" *
.\" * Copyright (C) 1998 - 2011, Daniel Stenberg, <daniel@haxx.se>, et al. .\" * Copyright (C) 1998 - 2014, Daniel Stenberg, <daniel@haxx.se>, et al.
.\" * .\" *
.\" * This software is licensed as described in the file COPYING, which .\" * This software is licensed as described in the file COPYING, which
.\" * you should have received as part of this distribution. The terms .\" * you should have received as part of this distribution. The terms
@@ -19,7 +19,7 @@
.\" * KIND, either express or implied. .\" * KIND, either express or implied.
.\" * .\" *
.\" ************************************************************************** .\" **************************************************************************
.TH libcurl 3 "12 Aug 2003" "libcurl 7.10.7" "libcurl easy interface" .TH libcurl 3 "19 Sep 2014" "libcurl" "libcurl easy interface"
.SH NAME .SH NAME
libcurl-easy \- easy interface overview libcurl-easy \- easy interface overview
.SH DESCRIPTION .SH DESCRIPTION
@@ -33,6 +33,17 @@ without a specified URL as you may have figured out yourself). You might want
to set some callbacks as well that will be called from the library when data to set some callbacks as well that will be called from the library when data
is available etc. \fIcurl_easy_setopt(3)\fP is used for all this. is available etc. \fIcurl_easy_setopt(3)\fP is used for all this.
\fICURLOPT_URL(3)\fP is only option you really must set, as otherwise there
can be no transfer. Another commonly used option is \fICURLOPT_VERBOSE(3)\fP
that will help you see what libcurl is doing under the hood, very useful when
debugging for example. The \fIcurl_easy_setopt(3)\fP man page has a full index
of the over 200 available options.
If you at any point would like to blank all previously set options for a
single easy handle, you can call \fIcurl_easy_reset(3)\fP and you can also
make a clone of an easy handle (with all its set options) using
\fIcurl_easy_duphandle(3)\fP.
When all is setup, you tell libcurl to perform the transfer using When all is setup, you tell libcurl to perform the transfer using
\fIcurl_easy_perform(3)\fP. It will then do the entire operation and won't \fIcurl_easy_perform(3)\fP. It will then do the entire operation and won't
return until it is done (successfully or not). return until it is done (successfully or not).
@@ -42,4 +53,5 @@ transfer, or if you're done, cleanup the session by calling
\fIcurl_easy_cleanup(3)\fP. If you want persistent connections, you don't \fIcurl_easy_cleanup(3)\fP. If you want persistent connections, you don't
cleanup immediately, but instead run ahead and perform other transfers using cleanup immediately, but instead run ahead and perform other transfers using
the same easy handle. the same easy handle.
.SH "SEE ALSO"
.BR curl_easy_init "(3)," curl_easy_cleanup "(3)," curl_easy_setopt "(3)"

View File

@@ -5,7 +5,7 @@
.\" * | (__| |_| | _ <| |___ .\" * | (__| |_| | _ <| |___
.\" * \___|\___/|_| \_\_____| .\" * \___|\___/|_| \_\_____|
.\" * .\" *
.\" * Copyright (C) 1998 - 2011, Daniel Stenberg, <daniel@haxx.se>, et al. .\" * Copyright (C) 1998 - 2014, Daniel Stenberg, <daniel@haxx.se>, et al.
.\" * .\" *
.\" * This software is licensed as described in the file COPYING, which .\" * This software is licensed as described in the file COPYING, which
.\" * you should have received as part of this distribution. The terms .\" * you should have received as part of this distribution. The terms
@@ -20,7 +20,7 @@
.\" * .\" *
.\" ************************************************************************** .\" **************************************************************************
.\" .\"
.TH libcurl-multi 3 "3 Feb 2007" "libcurl 7.16.0" "libcurl multi interface" .TH libcurl-multi 3 "19 Sep 2014" "libcurl" "libcurl multi interface"
.SH NAME .SH NAME
libcurl-multi \- how to use the multi interface libcurl-multi \- how to use the multi interface
.SH DESCRIPTION .SH DESCRIPTION
@@ -43,18 +43,28 @@ complicated for the application.
3. Enable the application to wait for action on its own file descriptors and 3. Enable the application to wait for action on its own file descriptors and
curl's file descriptors simultaneous easily. curl's file descriptors simultaneous easily.
4. Enable event-based handling and scaling transfers up to and beyond
thousands of parallel connections.
.SH "ONE MULTI HANDLE MANY EASY HANDLES" .SH "ONE MULTI HANDLE MANY EASY HANDLES"
To use the multi interface, you must first create a 'multi handle' with To use the multi interface, you must first create a 'multi handle' with
\fIcurl_multi_init(3)\fP. This handle is then used as input to all further \fIcurl_multi_init(3)\fP. This handle is then used as input to all further
curl_multi_* functions. curl_multi_* functions.
Each single transfer is built up with an easy handle. You must create them, With a multi handle and the multi interface you can do any amount of
and setup the appropriate options for each easy handle, as outlined in the simultaneous transfers in parallel. Each single transfer is built up around an
\fIlibcurl(3)\fP man page, using \fIcurl_easy_setopt(3)\fP. easy handle. You must create the easy handles you need, and setup the
appropriate options for each easy handle, as outlined in the \fIlibcurl(3)\fP
man page, using \fIcurl_easy_setopt(3)\fP.
When the easy handle is setup for a transfer, then instead of using There are two flavours of the multi interface, the select() oriented one and
\fIcurl_easy_perform(3)\fP (as when using the easy interface for transfers), the event based one we called multi_socket. You will benefit from reading
you should instead add the easy handle to the multi handle using through the description of both versions to full understand how they work and
differentiate. We start out with the select() oriented version.
When an easy handle is setup for a transfer, then instead of using
\fIcurl_easy_perform(3)\fP like when using the easy interface for transfers,
you should add the easy handle to the multi handle with
\fIcurl_multi_add_handle(3)\fP. The multi handle is sometimes referred to as a \fIcurl_multi_add_handle(3)\fP. The multi handle is sometimes referred to as a
\'multi stack\' because of the fact that it may hold a large amount of easy \'multi stack\' because of the fact that it may hold a large amount of easy
handles. handles.
@@ -71,7 +81,8 @@ application drive. You drive the transfers by invoking
anything available to transfer. It'll use the callbacks and everything else anything available to transfer. It'll use the callbacks and everything else
you have setup in the individual easy handles. It'll transfer data on all you have setup in the individual easy handles. It'll transfer data on all
current transfers in the multi stack that are ready to transfer anything. It current transfers in the multi stack that are ready to transfer anything. It
may be all, it may be none. may be all, it may be none. When there's nothing more to do for now, it
returns back to the calling application.
Your application can acquire knowledge from libcurl when it would like to get Your application can acquire knowledge from libcurl when it would like to get
invoked to transfer data, so that you don't have to busy-loop and call that invoked to transfer data, so that you don't have to busy-loop and call that
@@ -80,7 +91,9 @@ interface using which you can extract fd_sets from libcurl to use in select()
or poll() calls in order to get to know when the transfers in the multi stack or poll() calls in order to get to know when the transfers in the multi stack
might need attention. This also makes it very easy for your program to wait might need attention. This also makes it very easy for your program to wait
for input on your own private file descriptors at the same time or perhaps for input on your own private file descriptors at the same time or perhaps
timeout every now and then, should you want that. timeout every now and then, should you want that. \fIcurl_multi_timeout(3)\fP
also helps you with providing a suitable timeout period for your select()
call.
\fIcurl_multi_perform(3)\fP stores the number of still running transfers in \fIcurl_multi_perform(3)\fP stores the number of still running transfers in
one of its input arguments, and by reading that you can figure out when all one of its input arguments, and by reading that you can figure out when all
@@ -121,21 +134,39 @@ using large numbers of simultaneous connections.
When using this API, you add easy handles to the multi handle just as with the When using this API, you add easy handles to the multi handle just as with the
normal multi interface. Then you also set two callbacks with the normal multi interface. Then you also set two callbacks with the
CURLMOPT_SOCKETFUNCTION and CURLMOPT_TIMERFUNCTION options to CURLMOPT_SOCKETFUNCTION and CURLMOPT_TIMERFUNCTION options to
\fIcurl_multi_setopt(3)\fP. \fIcurl_multi_setopt(3)\fP. They are two callback functions that libcurl will
call with information about what sockets to wait for, and for what activity,
and what the curret timeout time is - if that expires libcurl should be
notified.
The API is then designed to inform your application about which sockets The multi_socket API is designed to inform your application about which
libcurl is currently using and for what activities (read and/or write) on sockets libcurl is currently using and for what activities (read and/or write)
those sockets your application is expected to wait for. on those sockets your application is expected to wait for.
Your application must then make sure to receive all sockets informed about in Your application must make sure to receive all sockets informed about in the
the CURLMOPT_SOCKETFUNCTION callback and make sure it reacts on the given CURLMOPT_SOCKETFUNCTION callback and make sure it reacts on the given activity
activity on them. When a socket has the given activity, you call on them. When a socket has the given activity, you call
\fIcurl_multi_socket_action(3)\fP specifying which socket and action there \fIcurl_multi_socket_action(3)\fP specifying which socket and action there
are. are.
The CURLMOPT_TIMERFUNCTION callback is called to set a timeout. When that The CURLMOPT_TIMERFUNCTION callback is called to set a timeout. When that
timeout expires, your application should call the timeout expires, your application should call the
\fIcurl_multi_socket_action(3)\fP function saying it was due to a timeout. \fIcurl_multi_socket_action(3)\fP function saying it was due to a timeout.
This API is typically used with an event-driven underlying functionality (like
libevent, libev, kqueue, epoll or similar) which which the application
"subscribes" on socket changes. This allows applications and libcurl to much
better scale upward and beyond thousands of simultaneous transfers without
losing performance.
When you've added your initial set of handles, you call
\fIcurl_multi_socket_action(3)\fP with CURL_SOCKET_TIMEOUT set in the sockfd
argument, and you'll get callbacks call that sets you up and you then continue
to call \fIcurl_multi_socket_action(3)\fP accordingly when you get activity on
the sockets you've been asked to wait on, or if the timeout timer expires.
You can poll \fIcurl_multi_info_read(3)\fP to see if any transfer has
completed, as it then has a message saying so.
.SH "BLOCKING" .SH "BLOCKING"
A few areas in the code are still using blocking code, even when used from the A few areas in the code are still using blocking code, even when used from the
multi interface. While we certainly want and intend for these to get fixed in multi interface. While we certainly want and intend for these to get fixed in

View File

@@ -20,7 +20,7 @@
.\" * .\" *
.\" ************************************************************************** .\" **************************************************************************
.\" .\"
.TH libcurl-tutorial 3 "2 Aug 2014" "libcurl" "libcurl programming" .TH libcurl-tutorial 3 "19 Sep 2014" "libcurl" "libcurl programming"
.SH NAME .SH NAME
libcurl-tutorial \- libcurl programming tutorial libcurl-tutorial \- libcurl programming tutorial
.SH "Objective" .SH "Objective"
@@ -137,15 +137,17 @@ rather than at build-time (if possible of course). By calling
struct, your program can figure out exactly what the currently running libcurl struct, your program can figure out exactly what the currently running libcurl
supports. supports.
.SH "Handle the Easy libcurl" .SH "Two Interfaces"
libcurl first introduced the so called easy interface. All operations in the libcurl first introduced the so called easy interface. All operations in the
easy interface are prefixed with 'curl_easy'. easy interface are prefixed with 'curl_easy'. The easy interface lets you do
single transfers with a synchronous and blocking function call.
Recent libcurl versions also offer the multi interface. More about that
interface, what it is targeted for and how to use it is detailed in a separate
chapter further down. You still need to understand the easy interface first,
so please continue reading for better understanding.
libcurl also offers another interface that allows multiple simultaneous
transfers in a single thread, the so called multi interface. More about that
interface is detailed in a separate chapter further down. You still need to
understand the easy interface first, so please continue reading for better
understanding.
.SH "Handle the Easy libcurl"
To use the easy interface, you must first create yourself an easy handle. You To use the easy interface, you must first create yourself an easy handle. You
need one handle for each easy session you want to perform. Basically, you need one handle for each easy session you want to perform. Basically, you
should use one handle for every thread you plan to use for transferring. You should use one handle for every thread you plan to use for transferring. You
@@ -162,13 +164,18 @@ transfer or series of transfers.
You set properties and options for this handle using You set properties and options for this handle using
\fIcurl_easy_setopt(3)\fP. They control how the subsequent transfer or \fIcurl_easy_setopt(3)\fP. They control how the subsequent transfer or
transfers will be made. Options remain set in the handle until set again to transfers will be made. Options remain set in the handle until set again to
something different. Alas, multiple requests using the same handle will use something different. They are sticky. Multiple requests using the same handle
the same options. will use the same options.
If you at any point would like to blank all previously set options for a
single easy handle, you can call \fIcurl_easy_reset(3)\fP and you can also
make a clone of an easy handle (with all its set options) using
\fIcurl_easy_duphandle(3)\fP.
Many of the options you set in libcurl are "strings", pointers to data Many of the options you set in libcurl are "strings", pointers to data
terminated with a zero byte. When you set strings with terminated with a zero byte. When you set strings with
\fIcurl_easy_setopt(3)\fP, libcurl makes its own copy so that they don't \fIcurl_easy_setopt(3)\fP, libcurl makes its own copy so that they don't need
need to be kept around in your application after being set[4]. to be kept around in your application after being set[4].
One of the most basic properties to set in the handle is the URL. You set your One of the most basic properties to set in the handle is the URL. You set your
preferred URL to transfer with \fICURLOPT_URL(3)\fP in a manner similar to: preferred URL to transfer with \fICURLOPT_URL(3)\fP in a manner similar to:
@@ -1295,39 +1302,44 @@ To avoid this problem, you must of course use your common sense. Often, you
can just edit out the sensitive data or just search/replace your true can just edit out the sensitive data or just search/replace your true
information with faked data. information with faked data.
.SH "Multiple Transfers Using the multi Interface" .SH "The multi Interface"
The easy interface as described in detail in this document is a synchronous The easy interface as described in detail in this document is a synchronous
interface that transfers one file at a time and doesn't return until it is interface that transfers one file at a time and doesn't return until it is
done. done.
The multi interface, on the other hand, allows your program to transfer The multi interface, on the other hand, allows your program to transfer
multiple files in both directions at the same time, without forcing you multiple files in both directions at the same time, without forcing you to use
to use multiple threads. The name might make it seem that the multi multiple threads. The name might make it seem that the multi interface is for
interface is for multi-threaded programs, but the truth is almost the multi-threaded programs, but the truth is almost the reverse. The multi
reverse. The multi interface can allow a single-threaded application interface allows a single-threaded application to perform the same kinds of
to perform the same kinds of multiple, simultaneous transfers that multiple, simultaneous transfers that multi-threaded programs can perform. It
multi-threaded programs can perform. It allows many of the benefits allows many of the benefits of multi-threaded transfers without the complexity
of multi-threaded transfers without the complexity of managing and of managing and synchronizing many threads.
synchronizing many threads.
To complicate matters somewhat more, there are even two versions of the multi
interface. The event based one, also called multi_socket and the "normal one"
designed for using with select(). See the libcurl-multi.3 man page for details
on the multi_socket event based API, this description here is for the select()
oriented one.
To use this interface, you are better off if you first understand the basics To use this interface, you are better off if you first understand the basics
of how to use the easy interface. The multi interface is simply a way to make of how to use the easy interface. The multi interface is simply a way to make
multiple transfers at the same time by adding up multiple easy handles into multiple transfers at the same time by adding up multiple easy handles into
a "multi stack". a "multi stack".
You create the easy handles you want and you set all the options just like you You create the easy handles you want, one for each concurrent transfer, and
have been told above, and then you create a multi handle with you set all the options just like you learned above, and then you create a
\fIcurl_multi_init(3)\fP and add all those easy handles to that multi handle multi handle with \fIcurl_multi_init(3)\fP and add all those easy handles to
with \fIcurl_multi_add_handle(3)\fP. that multi handle with \fIcurl_multi_add_handle(3)\fP.
When you've added the handles you have for the moment (you can still add new When you've added the handles you have for the moment (you can still add new
ones at any time), you start the transfers by calling ones at any time), you start the transfers by calling
\fIcurl_multi_perform(3)\fP. \fIcurl_multi_perform(3)\fP.
\fIcurl_multi_perform(3)\fP is asynchronous. It will only execute as little as \fIcurl_multi_perform(3)\fP is asynchronous. It will only perform what can be
possible and then return back control to your program. It is designed to never done now and then return back control to your program. It is designed to never
block. block. You need to keep calling the function until all transfers are
completed.
The best usage of this interface is when you do a select() on all possible The best usage of this interface is when you do a select() on all possible
file descriptors or sockets to know when to call libcurl again. This also file descriptors or sockets to know when to call libcurl again. This also
@@ -1340,11 +1352,12 @@ When you then call select(), it'll return when one of the file handles signal
action and you then call \fIcurl_multi_perform(3)\fP to allow libcurl to do action and you then call \fIcurl_multi_perform(3)\fP to allow libcurl to do
what it wants to do. Take note that libcurl does also feature some time-out what it wants to do. Take note that libcurl does also feature some time-out
code so we advise you to never use very long timeouts on select() before you code so we advise you to never use very long timeouts on select() before you
call \fIcurl_multi_perform(3)\fP, which thus should be called unconditionally call \fIcurl_multi_perform(3)\fP again. \fIcurl_multi_timeout(3)\fP is
every now and then even if none of its file descriptors have signaled provided to help you get a suitable timeout period.
ready. Another precaution you should use: always call
\fIcurl_multi_fdset(3)\fP immediately before the select() call since the Another precaution you should use: always call \fIcurl_multi_fdset(3)\fP
current set of file descriptors may change when calling a curl function. immediately before the select() call since the current set of file descriptors
may change in any curl function invoke.
If you want to stop the transfer of one of the easy handles in the stack, you If you want to stop the transfer of one of the easy handles in the stack, you
can use \fIcurl_multi_remove_handle(3)\fP to remove individual easy can use \fIcurl_multi_remove_handle(3)\fP to remove individual easy