aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--doc/dns.html9
-rw-r--r--doc/ftp.html57
-rw-r--r--doc/http.html29
-rw-r--r--doc/index.html101
-rw-r--r--doc/introduction.html77
-rw-r--r--doc/ltn12.html41
-rw-r--r--doc/mime.html15
-rw-r--r--doc/reference.html1
-rw-r--r--doc/smtp.html9
-rw-r--r--doc/socket.html11
-rw-r--r--etc/b64.lua6
-rw-r--r--etc/tftp.lua2
-rw-r--r--src/ltn12.lua8
-rw-r--r--src/smtp.lua33
-rw-r--r--test/mimetest.lua2
15 files changed, 256 insertions, 145 deletions
diff --git a/doc/dns.html b/doc/dns.html
index 226a604..fa4c230 100644
--- a/doc/dns.html
+++ b/doc/dns.html
@@ -36,7 +36,7 @@
36<h2 id=dns>DNS</h2> 36<h2 id=dns>DNS</h2>
37 37
38<p> 38<p>
39Name resolution function return <em>all</em> information returned by the 39Name resolution functions return <em>all</em> information obtained from the
40resolver in a table of the form: 40resolver in a table of the form:
41</p> 41</p>
42 42
@@ -59,14 +59,9 @@ socket.dns.<b>gethostname()</b>
59</p> 59</p>
60 60
61<p class=description> 61<p class=description>
62Returns the standard host name for the machine. 62Returns the standard host name for the machine as a string.
63</p> 63</p>
64 64
65<p class=return>
66The function returns a string with the host name.
67</p>
68
69
70<!-- tohostname +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> 65<!-- tohostname +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ -->
71 66
72<p class=name id=tohostname> 67<p class=name id=tohostname>
diff --git a/doc/ftp.html b/doc/ftp.html
index e834f07..9fda02b 100644
--- a/doc/ftp.html
+++ b/doc/ftp.html
@@ -35,39 +35,46 @@
35 35
36<p> 36<p>
37FTP (File Transfer Protocol) is a protocol used to transfer files 37FTP (File Transfer Protocol) is a protocol used to transfer files
38between hosts. The module <tt>ftp.lua</tt> offers simple FTP support. 38between hosts. The <tt>ftp</tt> namespace offers thorough support
39Applications can easily download and upload files. 39to FTP, under a simple interface. The implementation conforms to
40The implementation conforms to
41<a href="http://www.cs.princeton.edu/~diego/rfc/rfc0959.txt">RFC 959</a>. 40<a href="http://www.cs.princeton.edu/~diego/rfc/rfc0959.txt">RFC 959</a>.
42</p> 41</p>
43 42
44<p> 43<p>
45URLs MUST conform to
46<a href="http://www.cs.princeton.edu/~diego/rfc/rfc1738.txt">RFC
471738</a>, that is, an URL is a string in the form:
48</p>
49
50<blockquote>
51<tt>
52[ftp://][&lt;user&gt;[:&lt;password&gt;]@]&lt;host&gt;[:&lt;port&gt;][/&lt;path&gt;][<i>type</i>=a|i]</tt>
53</blockquote>
54
55<p>
56High level functions are provided supporting the most common operations. 44High level functions are provided supporting the most common operations.
57These high level functions are implemented on top of a lower level 45These high level functions are implemented on top of a lower level
58interface. By using the low-level interface, users can easily create their 46interface. Using the low-level interface, users can easily create their
59own functions to access <em>any</em> operation supported by the FTP 47own functions to access <em>any</em> operation supported by the FTP
60protocol. For that, check the implementation. 48protocol. For that, check the implementation.
61</p> 49</p>
62 50
63<p> 51<p>
64To use some of the functions in this module, a good understanding of 52To really benefit from this module, a good understanding of
65<a href="http://lua-users.org/wiki/FiltersSourcesAndSinks"> 53<a href="http://lua-users.org/wiki/FiltersSourcesAndSinks">
66LTN012, Filters sources and sinks</a> is necessary. 54LTN012, Filters sources and sinks</a> is necessary.
67</p> 55</p>
68 56
57<p class=description> To obtain the <tt>ftp</tt> namespace, run:
58</p>
59
60<pre class=example>
61-- loads the FTP module and any libraries it requires
62local ftp = require("ftp")
63</pre>
64
69<p> 65<p>
70The following constants can be set to control the default behaviour of 66URLs MUST conform to
67<a href="http://www.cs.princeton.edu/~diego/rfc/rfc1738.txt">RFC
681738</a>, that is, an URL is a string in the form:
69</p>
70
71<blockquote>
72<tt>
73[ftp://][&lt;user&gt;[:&lt;password&gt;]@]&lt;host&gt;[:&lt;port&gt;][/&lt;path&gt;][<i>type</i>=a|i]</tt>
74</blockquote>
75
76<p>
77The following constants in the namespace can be set to control the default behavior of
71the FTP module: 78the FTP module:
72</p> 79</p>
73 80
@@ -78,6 +85,7 @@ the FTP module:
78<li> <tt>USER</tt>: default anonymous user; 85<li> <tt>USER</tt>: default anonymous user;
79</ul> 86</ul>
80 87
88
81<!-- ftp.get ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> 89<!-- ftp.get ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ -->
82 90
83<p class=name id=get> 91<p class=name id=get>
@@ -116,7 +124,7 @@ optional arguments are the following:
116authentication. Defaults to "<tt>ftp:anonymous@anonymous.org</tt>"; 124authentication. Defaults to "<tt>ftp:anonymous@anonymous.org</tt>";
117<li><tt>command</tt>: The FTP command used to obtain data. Defaults to 125<li><tt>command</tt>: The FTP command used to obtain data. Defaults to
118"<tt>retr</tt>", but see example below; 126"<tt>retr</tt>", but see example below;
119<li><tt>port</tt>: The port to contacct the server at. Defaults to 21; 127<li><tt>port</tt>: The port to used for the control connection. Defaults to 21;
120<li><tt>type</tt>: The transfer mode. Can take values "<tt>i</tt>" or 128<li><tt>type</tt>: The transfer mode. Can take values "<tt>i</tt>" or
121"<tt>a</tt>". Defaults to whatever is the server default; 129"<tt>a</tt>". Defaults to whatever is the server default;
122<li><tt>step</tt>: LTN12 pump step function used to pass data from the 130<li><tt>step</tt>: LTN12 pump step function used to pass data from the
@@ -192,9 +200,9 @@ optional arguments are the following:
192<ul> 200<ul>
193<li><tt>user</tt>, <tt>password</tt>: User name and password used for 201<li><tt>user</tt>, <tt>password</tt>: User name and password used for
194authentication. Defaults to "<tt>ftp:anonymous@anonymous.org</tt>"; 202authentication. Defaults to "<tt>ftp:anonymous@anonymous.org</tt>";
195<li><tt>command</tt>: The FTP command used to obtain data. Defaults to 203<li><tt>command</tt>: The FTP command used to send data. Defaults to
196"<tt>retr</tt>", but see example below; 204"<tt>stor</tt>", but see example below;
197<li><tt>port</tt>: The port to contacct the server at. Defaults to 21; 205<li><tt>port</tt>: The port to used for the control connection. Defaults to 21;
198<li><tt>type</tt>: The transfer mode. Can take values "<tt>i</tt>" or 206<li><tt>type</tt>: The transfer mode. Can take values "<tt>i</tt>" or
199"<tt>a</tt>". Defaults to whatever is the server default; 207"<tt>a</tt>". Defaults to whatever is the server default;
200<li><tt>step</tt>: LTN12 pump step function used to pass data from the 208<li><tt>step</tt>: LTN12 pump step function used to pass data from the
@@ -213,7 +221,8 @@ local ftp = require("ftp")
213-- Log as user "diego" on server "ftp.tecgraf.puc-rio.br", 221-- Log as user "diego" on server "ftp.tecgraf.puc-rio.br",
214-- using password "nehab", and store a file "README" with contents 222-- using password "nehab", and store a file "README" with contents
215-- "wrong password, of course" 223-- "wrong password, of course"
216f, e = ftp.put("ftp://diego:nehab@ftp.tecgraf.puc-rio.br/README", "wrong password, of course") 224f, e = ftp.put("ftp://diego:nehab@ftp.tecgraf.puc-rio.br/README",
225 "wrong password, of course")
217</pre> 226</pre>
218 227
219<pre class=example> 228<pre class=example>
@@ -222,8 +231,8 @@ local ftp = require("ftp")
222local ltn12 = require("ltn12") 231local ltn12 = require("ltn12")
223 232
224-- Log as user "diego" on server "ftp.tecgraf.puc-rio.br", 233-- Log as user "diego" on server "ftp.tecgraf.puc-rio.br",
225-- using password "nehab", and append to the file "LOG", sending the 234-- using password "nehab", and append to the remote file "LOG", sending the
226-- contents of a local file 235-- contents of the local file "LOCAL-LOG"
227f, e = ftp.put{ 236f, e = ftp.put{
228 host = "ftp.tecgraf.puc-rio.br", 237 host = "ftp.tecgraf.puc-rio.br",
229 user = "diego", 238 user = "diego",
diff --git a/doc/http.html b/doc/http.html
index bda3088..0fc04cd 100644
--- a/doc/http.html
+++ b/doc/http.html
@@ -37,8 +37,9 @@
37 37
38<p> 38<p>
39HTTP (Hyper Text Transfer Protocol) is the protocol used to exchange 39HTTP (Hyper Text Transfer Protocol) is the protocol used to exchange
40information between web-browsers and servers. The <tt>http.lua</tt> 40information between web-browsers and servers. The <tt>http</tt>
41module offers support for the client side of the HTTP protocol (i.e., 41namespace offers full support for the client side of the HTTP
42protocol (i.e.,
42the facilities that would be used by a web-browser implementation). The 43the facilities that would be used by a web-browser implementation). The
43implementation conforms to the HTTP/1.1 standard, 44implementation conforms to the HTTP/1.1 standard,
44<a href="http://www.cs.princeton.edu/~diego/rfc/rfc2616.txt">RFC 45<a href="http://www.cs.princeton.edu/~diego/rfc/rfc2616.txt">RFC
@@ -47,11 +48,20 @@ implementation conforms to the HTTP/1.1 standard,
47 48
48<p> 49<p>
49The module exports functions that provide HTTP functionality in different 50The module exports functions that provide HTTP functionality in different
50levels of abstraction, from the simple <a 51levels of abstraction, from the simple
51href="#get"><tt>get</tt></a> function to the generic, LTN12 based <a 52<a href="#get"><tt>get</tt></a> function, through the generic
52href="#request"><tt>request</tt></a> function. 53LTN12 based <a href="#request"><tt>request</tt></a> function, down to
54even lower-level if you bother to look through the source code.
53</p> 55</p>
54 56
57<p class=description> To obtain the <tt>ftp</tt> namespace, run:
58</p>
59
60<pre class=example>
61-- loads the HTTP module and any libraries it requires
62local http = require("http")
63</pre>
64
55<p> 65<p>
56URLs must conform to 66URLs must conform to
57<a href="http://www.cs.princeton.edu/~diego/rfc/rfc1738.txt">RFC 67<a href="http://www.cs.princeton.edu/~diego/rfc/rfc1738.txt">RFC
@@ -189,12 +199,12 @@ http.<b>request{</b><br>
189</p> 199</p>
190 200
191<p class=description> 201<p class=description>
192Performs the generic HTTP request, controled by a request table. 202Performs the generic HTTP request, controlled by a request table.
193</p> 203</p>
194 204
195<p class=parameters> 205<p class=parameters>
196The most important parameters are the <tt>url</tt> and the <em>simple</em> LTN12 <tt>sink</tt> that will receive the downloaded content. 206The most important parameters are the <tt>url</tt> and the <em>simple</em> LTN12 <tt>sink</tt> that will receive the downloaded content.
197Any part of the <tt>url</tt> can be overriden by including 207Any part of the <tt>url</tt> can be overridden by including
198the appropriate field in the request table. 208the appropriate field in the request table.
199If authentication information is provided, the function 209If authentication information is provided, the function
200uses the Basic Authentication Scheme (see <a href="#authentication">note</a>) 210uses the Basic Authentication Scheme (see <a href="#authentication">note</a>)
@@ -231,8 +241,8 @@ respt = {<br>
231</tt></blockquote> 241</tt></blockquote>
232 242
233<p class=return> 243<p class=return>
234Even when there was failure (URL not found, for example), the 244Even when the server fails to provide the contents of the requested URL (URL not found, for example), the
235function usually succeeds retrieving a message body (a web page informing the 245it usually returns a message body (a web page informing the
236URL was not found or some other useless page). To make sure the 246URL was not found or some other useless page). To make sure the
237operation was successful, check the returned status <tt>code</tt>. For 247operation was successful, check the returned status <tt>code</tt>. For
238a list of the possible values and their meanings, refer to <a 248a list of the possible values and their meanings, refer to <a
@@ -261,7 +271,6 @@ respt = http.request {
261-- ["content-Type"] = "text/html" 271-- ["content-Type"] = "text/html"
262-- } 272-- }
263</pre> 273</pre>
264</blockquote>
265 274
266<p class=note id=authentication> 275<p class=note id=authentication>
267Note: Some URLs are protected by their 276Note: Some URLs are protected by their
diff --git a/doc/index.html b/doc/index.html
index 7a3afa8..888bc92 100644
--- a/doc/index.html
+++ b/doc/index.html
@@ -37,22 +37,30 @@
37 37
38<p> 38<p>
39LuaSocket is a <a href="http://www.lua.org">Lua</a> extension library 39LuaSocket is a <a href="http://www.lua.org">Lua</a> extension library
40that is composed by two parts: a C layer that provides support for the TCP 40that is composed by two parts: a C core that provides support for the TCP
41and UDP transport layers, and a set of Lua modules that add support for 41and UDP transport layers, and a set of Lua modules that add support for
42the SMTP (sending e-mails), HTTP (WWW access) and FTP (uploading and 42functionality commonly needed by applications that deal with the Internet.
43downloading files) protocols and other functionality commonly needed by
44applications that deal with the Internet.
45</p> 43</p>
46 44
47<p> 45<p>
48Network support has been implemented so that it is both efficient and 46The core support has been implemented so that it is both efficient and
49simple to use. LuaSocket can be used by any Lua application once it has 47simple to use. The core can be used by any Lua application once it has
50been properly initialized by the interpreter running the 48been properly initialized by the interpreter running the
51Lua application. The code has been tested and runs well on several Windows 49Lua application. The code has been tested and runs well on several Windows
52and Unix platforms. 50and Unix platforms.
53</p> 51</p>
54 52
55<p> 53<p>
54The most used modules implement the SMTP (sending e-mails), HTTP
55(WWW access) and FTP (uploading and downloading files) client
56protocols. These provide a very natural and generic interface to the e
57functionality covered by the protocols.
58In addition, you will find that the MIME (common encodings), URL (anything you
59could possible want to do with one) and LTN12 (filters, sinks, sources
60and pumps) modules can be very handy.
61</p>
62
63<p>
56The library is available under the same 64The library is available under the same
57<a href="http://www.lua.org/copyright.html"> 65<a href="http://www.lua.org/copyright.html">
58terms and conditions</a> as the Lua language, the MIT license. The idea is 66terms and conditions</a> as the Lua language, the MIT license. The idea is
@@ -112,10 +120,10 @@ option, and should be able to run the automatic test procedures.
112<h2 id=thanks>Special thanks</h2> 120<h2 id=thanks>Special thanks</h2>
113 121
114<p> 122<p>
115Throughout LuaSocket's history, many people gave sugestions that helped 123Throughout LuaSocket's history, many people gave suggestions that helped
116improve it. For that, I thank the Lua comunity. 124improve it. For that, I thank the Lua community.
117Special thanks go to 125Special thanks go to
118David Burgess, who has pushed the library to a new level of quality and 126David Burgess, who has helped push the library to a new level of quality and
119from whom I have learned a lot of stuff that doesn't show up in RFCs. 127from whom I have learned a lot of stuff that doesn't show up in RFCs.
120Special thanks also to Carlos Cassino, who played a big part in the 128Special thanks also to Carlos Cassino, who played a big part in the
121extensible design seen in the C core of LuaSocket 2.0. 129extensible design seen in the C core of LuaSocket 2.0.
@@ -127,28 +135,47 @@ extensible design seen in the C core of LuaSocket 2.0.
127 135
128 136
129<p> 137<p>
130Everything is new! Many changes for 2.0 happened in the C layer, which 138<em>Everything</em> is new! Many changes for 2.0 happened in the C layer,
131has been almost completely rewritten. The code has been ported to Lua 5.0 139which has been almost completely rewritten. The code has been ported to
132and greatly improved. There have also been some API changes 140Lua 5.0 and greatly improved. There have also been some API changes
133that made the interface simpler and more consistent. Here are some of 141that made the interface simpler and more consistent. Here are some of
134the changes that made it into version 2.0: 142the changes that made it into version 2.0:
135</p> 143</p>
136 144
137<ul> 145<ul>
138<li> Major C code rewrite. Code is modular and extensible. Hopefully, next 146<li> Major C code rewrite. Code is modular and extensible. Hopefully, other
139 versions will include code for local domain sockets, file descriptors, 147 developers will be motivated to provide code for SSL, local domain
140 pipes (on Unix) and named pipes (on windows) as a bonus; 148 sockets, file descriptors, pipes (on Unix) and named pipes etc;
141 149
142<li> Following the Lua 5.0 trend, all functions provided by the library are 150<li> Everything that is exported by the library is exported inside
143 in namespaces. These should be obtained with calls to the 151 namespaces. These should be obtained with calls to the
144 <tt>require</tt> function. Functions such as 152 <tt>require</tt> function;
153
154<li> Functions such as
145 send/receive/timeout/close etc do not exist anymore as stand-alone 155 send/receive/timeout/close etc do not exist anymore as stand-alone
146 functions. They are now only available as methods of the appropriate 156 functions. They are now only available as methods of the appropriate
147 objects; 157 objects;
148 158
149<li> All functions return a non-nil value as first return value if successful. 159<li> All functions return a non-nil value as first return value if successful.
150 All functions return <b><tt>nil</tt></b> followed by error message 160 All functions return <b><tt>nil</tt></b> followed by error message
151 in case of error; 161 in case of error. This made the library much easier to use;
162
163<li> Greatly reduced the number of times the C select is called
164 during data transfers, by calling only on failure. This might
165 improve a lot the maximum throughput;
166
167<li> TCP has been changed to become more uniform. It's possible to first
168 create a TCP object,
169 then connect or bind if needed, and finally use I/O functions.
170 <tt>socket.connect</tt> and <tt>socket.bind</tt> functions are still
171 provided for simplicity;
172
173<li> This allows for setting a timeout value before connecting;
174
175<li> And also allows binding to a local address before connecting;
176
177<li> New <tt>socket.dns.gethostname</tt> function and <tt>shutdown</tt>
178 method;
152 179
153<li> Better error messages and parameter checking; 180<li> Better error messages and parameter checking;
154 181
@@ -157,20 +184,9 @@ the changes that made it into version 2.0:
157<li> UDP connected sockets can break association with peer by calling 184<li> UDP connected sockets can break association with peer by calling
158 <tt>setpeername</tt> with address '<tt>*</tt>'; 185 <tt>setpeername</tt> with address '<tt>*</tt>';
159 186
160<li> TCP has been changed to become more uniform. First create an object, 187<li> Sets returned by <tt>socket.select</tt> are associative;
161 then connect or bind if needed, and finally use I/O functions. The
162 <tt>socket.connect</tt> and <tt>socket.bind</tt> functions are still
163 provided for simplicity, but they just call <tt>socket.tcp</tt> followed
164 by the <tt>connect</tt> or <tt>bind/listen</tt> methods;
165
166<li> Greatly reduced the number of times select is called during data
167 transfers, by calling only on failure;
168
169<li> TCP can set timeout value before connecting and also bind to local
170 address before connecting;
171 188
172<li> <tt>socket.select</tt> returns associative sets and checks if 189<li> Select checks if sockets have buffered data and returns immediately;
173 sockets had buffered data;
174 190
175<li> <tt>socket.sleep</tt> and <tt>socket.time</tt> are now part of the 191<li> <tt>socket.sleep</tt> and <tt>socket.time</tt> are now part of the
176 library and are supported. They used to be available only when 192 library and are supported. They used to be available only when
@@ -182,7 +198,7 @@ the changes that made it into version 2.0:
182 high-level modules; 198 high-level modules;
183 199
184<li> Socket options interface has been improved. TCP objects also 200<li> Socket options interface has been improved. TCP objects also
185 support socket options and many other options were added. 201 support socket options and many new options were added.
186 202
187</ul> 203</ul>
188 204
@@ -191,12 +207,23 @@ Lots of changes in the Lua modules, too!
191</p> 207</p>
192 208
193<ul> 209<ul>
210<li> Every module loads only the modules that it needs. There is no waste
211of memory. LuaSocket core takes only 20k of memory;
212
194<li> New MIME and LTN12 modules make all other modules much more powerful; 213<li> New MIME and LTN12 modules make all other modules much more powerful;
214
195<li> Support for multipart messages in the SMTP module; 215<li> Support for multipart messages in the SMTP module;
196<li> The old callback mechanism of FTP and HTTP has been replaced with LTN12 sources and sinks, 216
197with advantage; 217<li> The old callback mechanism of FTP and HTTP has been replaced with LTN12 sources and sinks, with advantage;
218
219<li> Common implementation for low-level FTP and SMTP;
220
198<li> FTP, HTTP, and SMTP are implemented in multiple levels in such a way 221<li> FTP, HTTP, and SMTP are implemented in multiple levels in such a way
199that users will have no problems extending the functionality. 222that users will have no problems extending the functionality to satisfy
223personal needs;
224
225<li> SMTP knows how to perform LOGIN and PLAIN authentication.
226
200</ul> 227</ul>
201 228
202<!-- incompatible +++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> 229<!-- incompatible +++++++++++++++++++++++++++++++++++++++++++++++++++++++ -->
@@ -208,7 +235,7 @@ that users will have no problems extending the functionality.
208<li> The introduction of namespaces affects all programs that use LuaSocket, 235<li> The introduction of namespaces affects all programs that use LuaSocket,
209specially code that relies on global functions. These are no longer 236specially code that relies on global functions. These are no longer
210available. Note that even the support modules (<tt>http</tt>, <tt>smtp</tt> 237available. Note that even the support modules (<tt>http</tt>, <tt>smtp</tt>
211etc) are independent now and should be "<tt>require</tt>ed"; 238etc) are independent now and should be "<tt>require</tt>"d;
212 239
213<li> FTP, SMTP and HTTP are completely new; I am sure you will 240<li> FTP, SMTP and HTTP are completely new; I am sure you will
214agree the new stuff is better; 241agree the new stuff is better;
diff --git a/doc/introduction.html b/doc/introduction.html
index 86c552b..59d1956 100644
--- a/doc/introduction.html
+++ b/doc/introduction.html
@@ -36,13 +36,21 @@
36<h2>Introduction</h2> 36<h2>Introduction</h2>
37 37
38<p> 38<p>
39LuaSocket is a <a href="http://www.lua.org">Lua</a> extension library
40that is composed by two parts: a C core that provides support for the TCP
41and UDP transport layers, and a set of Lua modules that add support for
42the SMTP (sending e-mails), HTTP (WWW access) and FTP (uploading and
43downloading files) protocols and other functionality commonly needed by
44applications that deal with the Internet. This introduction is about the C
45core.
46</p>
47
48<p>
39Communication in LuaSocket is performed via I/O objects. These can 49Communication in LuaSocket is performed via I/O objects. These can
40represent different network domains. Currently, support is provided for TCP 50represent different network domains. Currently, support is provided for TCP
41and UDP, but nothing prevents other developers from implementing SSL, Local 51and UDP, but nothing prevents other developers from implementing SSL, Local
42Domain, Pipes, File Descriptors etc. I/O objects provide a standard 52Domain, Pipes, File Descriptors etc. I/O objects provide a standard
43interface to I/O across different domains and operating systems. 53interface to I/O across different domains and operating systems.
44LuaSocket&nbsp;2.0 has been rewritten from scratch to simplify the future
45addition of new domains.
46</p> 54</p>
47 55
48<p> 56<p>
@@ -52,8 +60,17 @@ Second, the simplicity and the feel of the Lua language should be
52preserved. To achieve these goals, the LuaSocket API keeps the function names and semantics the C API whenever possible, but their usage in Lua has been greatly simplified. 60preserved. To achieve these goals, the LuaSocket API keeps the function names and semantics the C API whenever possible, but their usage in Lua has been greatly simplified.
53</p> 61</p>
54 62
63
64<p>
65One of the simplifications is the receive pattern capability.
66Applications can read data from stream domains (such as TCP)
67line by line, block by block, or until the connection is closed.
68All I/O reads are buffered and the performance differences between
69different receive patterns are negligible.
70</p>
71
55<p> 72<p>
56One of the simplifications is the timeout control 73Another advantage is the flexible timeout control
57mechanism. As in C, all I/O operations are blocking by default. For 74mechanism. As in C, all I/O operations are blocking by default. For
58example, the <a href=tcp.html#send><tt>send</tt></a>, 75example, the <a href=tcp.html#send><tt>send</tt></a>,
59<a href=tcp.html#receive><tt>receive</tt></a> and 76<a href=tcp.html#receive><tt>receive</tt></a> and
@@ -70,14 +87,6 @@ call might perform several OS calls, so that the two timeout values are
70</p> 87</p>
71 88
72<p> 89<p>
73Another important difference is the receive pattern capability.
74Applications can read data from stream domains (such as TCP)
75line by line, block by block, or until the connection is closed.
76All I/O reads are buffered and the performance differences between
77different receive patterns are negligible.
78</p>
79
80<p>
81Finally, the host name resolution is transparent, meaning that most 90Finally, the host name resolution is transparent, meaning that most
82functions and methods accept both IP addresses and host names. In case a 91functions and methods accept both IP addresses and host names. In case a
83host name is given, the library queries the system's resolver and 92host name is given, the library queries the system's resolver and
@@ -89,13 +98,8 @@ functions from the DNS module are provided to convert between host names and IP
89</p> 98</p>
90 99
91<p> 100<p>
92Previous versions of LuaSocket provided global functions for operating on 101Together, these changes make network programming in LuaSocket much simpler
93I/O objects. To give the library a Lua 5.0 feel, these have been eliminated 102than it is in C, as the following sections will show.
94from LuaSocket 2.0. I/O operations are only available as methods of the
95corresponding I/O objects. Naturally, different I/O objects accept
96different operations. The TCP and UDP objects are
97introduced in the following sections, following a few words about
98initialization.
99</p> 103</p>
100 104
101<!-- initializing +++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> 105<!-- initializing +++++++++++++++++++++++++++++++++++++++++++++++++++++++ -->
@@ -103,13 +107,14 @@ initialization.
103<h3>Initializing the library</h3> 107<h3>Initializing the library</h3>
104 108
105<p> 109<p>
106The core LuaSocket functionality is implemented in C, and usually available as 110The core LuaSocket is almost entirely implemented in C. It is
107a dynamic library which the interpreter can load when required. 111usually available as a dynamic library which the interpreter can load
112with the help of a loader module written in Lua.
108Beginning with version 2.0 and following the Lua 5.0 trend, all LuaSocket 113Beginning with version 2.0 and following the Lua 5.0 trend, all LuaSocket
109functionality is defined inside a tables (or rather a namespaces). No global 114functionality is defined inside tables (or rather a namespaces). No global
110variables are ever created. 115variables are ever created.
111Namespaces are obtained with the <tt>require</tt> Lua function, which loads 116Namespaces are obtained with the <tt>require</tt> Lua function, which loads
112and initializes any required libraries and return the namespace. 117and initializes any required library and returns the namespace.
113For example, the core functionality or LuaSocket is usually available 118For example, the core functionality or LuaSocket is usually available
114from the "<tt>socket</tt>" namespace. 119from the "<tt>socket</tt>" namespace.
115</p> 120</p>
@@ -130,13 +135,14 @@ words, applications communicating through TCP can send and receive data as
130an error free stream of bytes. Data is split in one end and 135an error free stream of bytes. Data is split in one end and
131reassembled transparently on the other end. There are no boundaries in 136reassembled transparently on the other end. There are no boundaries in
132the data transfers. The library allows users to read data from the 137the data transfers. The library allows users to read data from the
133sockets in several different granularity: patterns are available for 138sockets in several different granularities: patterns are available for
134lines, arbitrary sized blocks or "read up to connection closed", all with 139lines, arbitrary sized blocks or "read up to connection closed", all with
135good performance. 140good performance.
136</p> 141</p>
137 142
138<p> 143<p>
139The library distinguishes three types of TCP sockets: master, client and server sockets. 144The library distinguishes three types of TCP sockets: <em>master</em>,
145<em>client</em> and <em>server</em> sockets.
140</p> 146</p>
141 147
142<p> 148<p>
@@ -144,10 +150,11 @@ Master sockets are newly created TCP sockets returned by the function
144<a href=tcp.html#tcp><tt>socket.tcp</tt></a>. A master socket is 150<a href=tcp.html#tcp><tt>socket.tcp</tt></a>. A master socket is
145transformed into a server socket 151transformed into a server socket
146after it is associated with a <em>local</em> address by a call to the 152after it is associated with a <em>local</em> address by a call to the
147<a href=tcp.html#bind><tt>bind</tt></a> method. Conversely, it 153<a href=tcp.html#bind><tt>bind</tt></a> method followed by a call to the
154<a href=tcp.html#listen><tt>listen</tt></a>. Conversely, a master socket
148can be changed into a client socket with the method 155can be changed into a client socket with the method
149<a href=tcp.html#connect><tt>connect</tt></a>, 156<a href=tcp.html#connect><tt>connect</tt></a>,
150that associates it with a <em>remote</em> address. 157which associates it with a <em>remote</em> address.
151</p> 158</p>
152 159
153<p> 160<p>
@@ -158,7 +165,7 @@ client socket object is returned representing this connection. The
158other methods available for server socket objects are 165other methods available for server socket objects are
159<a href=tcp.html#getsockname><tt>getsockname</tt></a>, 166<a href=tcp.html#getsockname><tt>getsockname</tt></a>,
160<a href=tcp.html#setoption><tt>setoption</tt></a>, 167<a href=tcp.html#setoption><tt>setoption</tt></a>,
161<a href=tcp.html#settimeout><tt>settimeout</tt></a> and 168<a href=tcp.html#settimeout><tt>settimeout</tt></a>, and
162<a href=tcp.html#close><tt>close</tt></a>. 169<a href=tcp.html#close><tt>close</tt></a>.
163</p> 170</p>
164 171
@@ -172,7 +179,8 @@ available for client socket objects are
172<a href=tcp.html#getsockname><tt>getsockname</tt></a>, 179<a href=tcp.html#getsockname><tt>getsockname</tt></a>,
173<a href=tcp.html#getpeername><tt>getpeername</tt></a>, 180<a href=tcp.html#getpeername><tt>getpeername</tt></a>,
174<a href=tcp.html#setoption><tt>setoption</tt></a>, 181<a href=tcp.html#setoption><tt>setoption</tt></a>,
175<a href=tcp.html#settimeout><tt>settimeout</tt></a> and 182<a href=tcp.html#settimeout><tt>settimeout</tt></a>,
183<a href=tcp.html#shutdown><tt>shutdown</tt></a>, and
176<a href=tcp.html#close><tt>close</tt></a>. 184<a href=tcp.html#close><tt>close</tt></a>.
177</p> 185</p>
178 186
@@ -185,7 +193,7 @@ A simple echo server, using LuaSocket. The program binds to an ephemeral
185port (one that is chosen by the operating system) on the local host and 193port (one that is chosen by the operating system) on the local host and
186awaits client connections on that port. When a connection is established, 194awaits client connections on that port. When a connection is established,
187the program reads a line from the remote end and sends it back, closing 195the program reads a line from the remote end and sends it back, closing
188the connection immediately after. You can test it using the telnet 196the connection immediately. You can test it using the telnet
189program. 197program.
190</p> 198</p>
191 199
@@ -232,6 +240,12 @@ error correction).
232</p> 240</p>
233 241
234<p> 242<p>
243Note that although no guarantees are made, these days
244networks are so good that, under normal circumstances, few errors
245happen in practice.
246</p>
247
248<p>
235An UDP socket object is created by the 249An UDP socket object is created by the
236<a href=udp.html#udp><tt>socket.udp</tt></a> function. UDP 250<a href=udp.html#udp><tt>socket.udp</tt></a> function. UDP
237sockets do not need to be connected before use. The method 251sockets do not need to be connected before use. The method
@@ -288,14 +302,13 @@ error message.
288 302
289<pre class=example> 303<pre class=example>
290-- change here to the host an port you want to contact 304-- change here to the host an port you want to contact
291host = "localhost" 305local host, port = "localhost", 13
292port = 13
293-- load namespace 306-- load namespace
294local socket = require("socket") 307local socket = require("socket")
295-- convert host name to ip address 308-- convert host name to ip address
296local ip = socket.try(socket.dns.toip(host)) 309local ip = socket.try(socket.dns.toip(host))
297-- create a new UDP object 310-- create a new UDP object
298local udp = socket.udp() 311local udp = socket.try(socket.udp())
299-- contact daytime host 312-- contact daytime host
300socket.try(udp:sendto("anything", ip, port)) 313socket.try(udp:sendto("anything", ip, port))
301-- retrieve the answer and print results 314-- retrieve the answer and print results
diff --git a/doc/ltn12.html b/doc/ltn12.html
index 363ce43..7b379c2 100644
--- a/doc/ltn12.html
+++ b/doc/ltn12.html
@@ -35,13 +35,21 @@
35 35
36<h2 id=ltn12>LTN12</h2> 36<h2 id=ltn12>LTN12</h2>
37 37
38<p> The LTN12 module implements the ideas described in 38<p> The <tt>ltn12</tt> namespace implements the ideas described in
39<a href="http://lua-users.org/wiki/FiltersSourcesAndSinks"> 39<a href="http://lua-users.org/wiki/FiltersSourcesAndSinks">
40LTN012, Filters sources and sinks</a>. This manual simply describe the 40LTN012, Filters sources and sinks</a>. This manual simply describes the
41functions. Please refer to the LTN for a deeper explanation of the 41functions. Please refer to the LTN for a deeper explanation of the
42functionality provided by this module. 42functionality provided by this module.
43</p> 43</p>
44 44
45<p class=description> To obtain the <tt>ltn12</tt> namespace, run:
46</p>
47
48<pre class=example>
49-- loads the LTN21 module
50local ltn12 = require("ltn12")
51</pre>
52
45<!-- filters ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> 53<!-- filters ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ -->
46 54
47<h3 id="filter">Filters</h3> 55<h3 id="filter">Filters</h3>
@@ -68,15 +76,15 @@ The function returns the chained filter.
68</p> 76</p>
69 77
70<p class=note> 78<p class=note>
71The nesting of filters can be arbritrary. For instance, the useless filter 79The nesting of filters can be arbitrary. For instance, the useless filter
72below doesn't do anything but return the data that was passed to it, 80below doesn't do anything but return the data that was passed to it,
73unaltered. 81unaltered.
74</p> 82</p>
75 83
76<pre class=example> 84<pre class=example>
77-- load required modules 85-- load required modules
78ltn12 = require("ltn12") 86local ltn12 = require("ltn12")
79mime = require("mime") 87local mime = require("mime")
80 88
81-- create a silly identity filter 89-- create a silly identity filter
82id = ltn12.filter.chain( 90id = ltn12.filter.chain(
@@ -165,12 +173,7 @@ ltn12.sink.<b>chain(</b>filter, sink<b>)</b>
165</p> 173</p>
166 174
167<p class=description> 175<p class=description>
168Creates a new sink that passes data through a <tt>filter</tt> before sending 176Creates and returns a new sink that passes data through a <tt>filter</tt> before sending it to a given <tt>sink</tt>.
169it to a given <tt>sink</tt>.
170</p>
171
172<p class=return>
173The function returns the new sink.
174</p> 177</p>
175 178
176<!-- error ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> 179<!-- error ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ -->
@@ -180,7 +183,7 @@ ltn12.sink.<b>error(</b>message<b>)</b>
180</p> 183</p>
181 184
182<p class=description> 185<p class=description>
183Creates and returns a sink that aborts transmission with an error 186Creates and returns a sink that aborts transmission with the error
184<tt>message</tt>. 187<tt>message</tt>.
185</p> 188</p>
186 189
@@ -202,7 +205,7 @@ Creates a sink that sends data to a file.
202<p class=return> 205<p class=return>
203The function returns a sink that sends all data to the given <tt>handle</tt> 206The function returns a sink that sends all data to the given <tt>handle</tt>
204and closes the file when done, or a sink that aborts the transmission with 207and closes the file when done, or a sink that aborts the transmission with
205an error <tt>message</tt> 208the error <tt>message</tt>
206</p> 209</p>
207 210
208<p class=note> 211<p class=note>
@@ -258,7 +261,7 @@ efficiently concatenated into a single string.
258</p> 261</p>
259 262
260<p class=return> 263<p class=return>
261The function returns the sink and the table. 264The function returns the sink and the table used to store the chunks.
262</p> 265</p>
263 266
264<pre class=example> 267<pre class=example>
@@ -266,14 +269,14 @@ The function returns the sink and the table.
266local http = require("http") 269local http = require("http")
267local ltn12 = require("ltn12") 270local ltn12 = require("ltn12")
268 271
269-- the http.get function 272-- a simplified http.get function
270function get(u) 273function http.get(u)
271 local t = {} 274 local t = {}
272 local respt = request{ 275 local respt = request{
273 url = u, 276 url = u,
274 sink = ltn12.sink.table(t) 277 sink = ltn12.sink.table(t)
275 } 278 }
276 return table.concat(t), respt.headers, respt.code, respt.error 279 return table.concat(t), respt.headers, respt.code
277end 280end
278</pre> 281</pre>
279 282
@@ -334,7 +337,7 @@ ltn12.source.<b>error(</b>message<b>)</b>
334</p> 337</p>
335 338
336<p class=description> 339<p class=description>
337Creates and returns a source that aborts transmission with an error 340Creates and returns a source that aborts transmission with the error
338<tt>message</tt>. 341<tt>message</tt>.
339</p> 342</p>
340 343
@@ -357,7 +360,7 @@ Creates a source that produces the contents of a file.
357The function returns a source that reads chunks of data from 360The function returns a source that reads chunks of data from
358given <tt>handle</tt> and returns it to the user, 361given <tt>handle</tt> and returns it to the user,
359closing the file when done, or a source that aborts the transmission with 362closing the file when done, or a source that aborts the transmission with
360an error <tt>message</tt> 363the error <tt>message</tt>
361</p> 364</p>
362 365
363<p class=note> 366<p class=note>
diff --git a/doc/mime.html b/doc/mime.html
index 286e41c..791861e 100644
--- a/doc/mime.html
+++ b/doc/mime.html
@@ -36,7 +36,7 @@
36<h2 id=mime>MIME</h2> 36<h2 id=mime>MIME</h2>
37 37
38<p> 38<p>
39The MIME module offers filters that apply and remove common 39The <tt>mime</tt> namespace offers filters that apply and remove common
40content transfer encodings, such as Base64 and Quoted-Printable. 40content transfer encodings, such as Base64 and Quoted-Printable.
41It also provides functions to break text into lines and change 41It also provides functions to break text into lines and change
42the end-of-line convention. 42the end-of-line convention.
@@ -55,6 +55,15 @@ follows the ideas presented in
55LTN012, Filters sources and sinks</a>. 55LTN012, Filters sources and sinks</a>.
56</p> 56</p>
57 57
58<p class=description> To obtain the <tt>mime</tt> namespace, run:
59</p>
60
61<pre class=example>
62-- loads the MIME module and everything it requires
63local mime = require("mime")
64</pre>
65
66
58<!-- High-level +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> 67<!-- High-level +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ -->
59 68
60<h3 id=high>High-level filters</h3> 69<h3 id=high>High-level filters</h3>
@@ -108,7 +117,7 @@ The function returns the created filter.
108 117
109<p class=name id="encode"> 118<p class=name id="encode">
110mime.<b>encode(</b>"base64"<b>)</b><br> 119mime.<b>encode(</b>"base64"<b>)</b><br>
111mime.<b>encode(</b>"quoted-printable" [, mode])</b> 120mime.<b>encode(</b>"quoted-printable" [, mode]<b>)</b>
112</p> 121</p>
113 122
114<p class=description> 123<p class=description>
@@ -278,7 +287,7 @@ that can be encoded unambiguously. <tt>B</tt> has the remaining bytes of
278<tt>C..D</tt>, <em>before</em> encoding. 287<tt>C..D</tt>, <em>before</em> encoding.
279If <tt>D</tt> is <tt><b>nil</b></tt>, <tt>A</tt> is padded with 288If <tt>D</tt> is <tt><b>nil</b></tt>, <tt>A</tt> is padded with
280the encoding of the remaining bytes of <tt>C</tt>. 289the encoding of the remaining bytes of <tt>C</tt>.
281Throughout encoding, occurences of CRLF are replaced by the 290Throughout encoding, occurrences of CRLF are replaced by the
282<tt>marker</tt>, which itself defaults to CRLF. 291<tt>marker</tt>, which itself defaults to CRLF.
283</p> 292</p>
284 293
diff --git a/doc/reference.html b/doc/reference.html
index ebcfb5b..43aeea5 100644
--- a/doc/reference.html
+++ b/doc/reference.html
@@ -152,7 +152,6 @@
152<a href="socket.html#version">VERSION</a>. 152<a href="socket.html#version">VERSION</a>.
153</blockquote> 153</blockquote>
154</blockquote> 154</blockquote>
155</table>
156 155
157<!-- tcp +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> 156<!-- tcp +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ -->
158 157
diff --git a/doc/smtp.html b/doc/smtp.html
index 03698bf..0fdc4a4 100644
--- a/doc/smtp.html
+++ b/doc/smtp.html
@@ -105,6 +105,8 @@ smtp.<b>send{</b><br>
105&nbsp;&nbsp;from = <i>string</i>,<br> 105&nbsp;&nbsp;from = <i>string</i>,<br>
106&nbsp;&nbsp;rcpt = <i>string</i> or <i>string-table</i>,<br> 106&nbsp;&nbsp;rcpt = <i>string</i> or <i>string-table</i>,<br>
107&nbsp;&nbsp;source = <i>LTN12 source</i>,<br> 107&nbsp;&nbsp;source = <i>LTN12 source</i>,<br>
108&nbsp;&nbsp;[user = <i>string</i>],<br>
109&nbsp;&nbsp;[password = <i>string</i>],<br>
108&nbsp;&nbsp;[server = <i>string</i>],<br> 110&nbsp;&nbsp;[server = <i>string</i>],<br>
109&nbsp;&nbsp;[port = <i>string</i>]<br> 111&nbsp;&nbsp;[port = <i>string</i>]<br>
110&nbsp;&nbsp;[domain = <i>string</i>],<br> 112&nbsp;&nbsp;[domain = <i>string</i>],<br>
@@ -127,7 +129,11 @@ address, or a string
127in case there is just one recipient. 129in case there is just one recipient.
128The contents of the message are given by a <em>simple</em> LTN12 <tt>source</tt>. Several 130The contents of the message are given by a <em>simple</em> LTN12 <tt>source</tt>. Several
129arguments are optional: 131arguments are optional:
132</p>
130<ul> 133<ul>
134<li> <tt>user</tt>, <tt>password</tt>: User and password for
135authentication. The function will attempt LOGIN and PLAIN authentication
136methods if supported by the server (both are unsafe);
131<li> <tt>server</tt>: Server to connect to. Defaults to "localhost"; 137<li> <tt>server</tt>: Server to connect to. Defaults to "localhost";
132<li> <tt>port</tt>: Port to connect to. Defaults to 25; 138<li> <tt>port</tt>: Port to connect to. Defaults to 25;
133<li> <tt>domain</tt>: Domain name used to greet the server; Defaults to the 139<li> <tt>domain</tt>: Domain name used to greet the server; Defaults to the
@@ -135,7 +141,6 @@ local machine host name;
135<li> <tt>step</tt>: LTN12 pump step function used to pass data from the 141<li> <tt>step</tt>: LTN12 pump step function used to pass data from the
136source to the server. Defaults to the LTN12 <tt>pump.step</tt> function. 142source to the server. Defaults to the LTN12 <tt>pump.step</tt> function.
137</ul> 143</ul>
138</p>
139 144
140<p class=return> 145<p class=return>
141If successful, the function returns 1. Otherwise, the function returns 146If successful, the function returns 1. Otherwise, the function returns
@@ -293,7 +298,7 @@ and an epilogue.
293 298
294<p class=return> 299<p class=return>
295The function returns a <em>simple</em> LTN12 source that produces the 300The function returns a <em>simple</em> LTN12 source that produces the
296message contents as defined by <tt>mesgt</tt>. Hopefuly, the following 301message contents as defined by <tt>mesgt</tt>. Hopefully, the following
297example will make things clear. When in doubt, refer to the appropriate RFC 302example will make things clear. When in doubt, refer to the appropriate RFC
298as listed in the introduction. </p> 303as listed in the introduction. </p>
299 304
diff --git a/doc/socket.html b/doc/socket.html
index dbfdaed..b3fbb6e 100644
--- a/doc/socket.html
+++ b/doc/socket.html
@@ -164,7 +164,7 @@ source from a stream socket object.
164</p> 164</p>
165 165
166<p class=parameters> 166<p class=parameters>
167<tt>Mode</tt> defines the behaviour of the source. The following 167<tt>Mode</tt> defines the behavior of the source. The following
168options are available: 168options are available:
169</p> 169</p>
170<ul> 170<ul>
@@ -194,15 +194,16 @@ Throws an exception in case of error.
194</p> 194</p>
195 195
196<p class=parameters> 196<p class=parameters>
197</b>Ret<sub>1</sub>, ret<sub>2</sub> ... ret<sub>N</sub> can be arbitrary 197<tt>Ret</tt><sub>1</sub>, <tt>ret</tt><sub>2</sub> ... <tt>ret</tt><sub>N</sub> can be arbitrary
198arguments, but are usually the return values of a function call that 198arguments, but are usually the return values of a function call that
199nested with the call to <tt>try</tt>. 199nested with the call to <tt>try</tt>.
200</p> 200</p>
201 201
202<p class=return> 202<p class=return>
203The function returns ret<sub>1</sub>, ret<sub>2</sub> ... ret<sub>N</sub> if 203The function returns <tt>ret</tt><sub>1</sub>, <tt>ret</tt><sub>2</sub> ...
204ret<sub>1</sub> is not <tt><b>nil</b></tt>. Otherwise, calls <tt>error</tt> 204<tt>ret</tt><sub>N</sub> if
205passing ret<sub>2</sub>. 205<tt>ret</tt><sub>1</sub> is not <tt><b>nil</b></tt>. Otherwise, calls <tt>error</tt>
206passing <tt>ret</tt><sub>2</sub>.
206</p> 207</p>
207 208
208<pre class=example> 209<pre class=example>
diff --git a/etc/b64.lua b/etc/b64.lua
index 4d5f83e..d74c949 100644
--- a/etc/b64.lua
+++ b/etc/b64.lua
@@ -1,3 +1,9 @@
1-----------------------------------------------------------------------------
2-- Little program to convert to and from Base64
3-- LuaSocket sample files
4-- Author: Diego Nehab
5-- RCS ID: $Id$
6-----------------------------------------------------------------------------
1local ltn12 = require("ltn12") 7local ltn12 = require("ltn12")
2local mime = require("mime") 8local mime = require("mime")
3local source = ltn12.source.file(io.stdin) 9local source = ltn12.source.file(io.stdin)
diff --git a/etc/tftp.lua b/etc/tftp.lua
index 5238de0..6a1a093 100644
--- a/etc/tftp.lua
+++ b/etc/tftp.lua
@@ -71,7 +71,7 @@ local function get_ERROR(dgram)
71end 71end
72 72
73----------------------------------------------------------------------------- 73-----------------------------------------------------------------------------
74-- High level TFTP API 74-- The real work
75----------------------------------------------------------------------------- 75-----------------------------------------------------------------------------
76local function tget(gett) 76local function tget(gett)
77 local retries, dgram, sent, datahost, dataport, code 77 local retries, dgram, sent, datahost, dataport, code
diff --git a/src/ltn12.lua b/src/ltn12.lua
index bb527bd..09771d4 100644
--- a/src/ltn12.lua
+++ b/src/ltn12.lua
@@ -23,6 +23,7 @@ BLOCKSIZE = 2048
23----------------------------------------------------------------------------- 23-----------------------------------------------------------------------------
24-- returns a high level filter that cycles a low-level filter 24-- returns a high level filter that cycles a low-level filter
25function filter.cycle(low, ctx, extra) 25function filter.cycle(low, ctx, extra)
26 assert(low)
26 return function(chunk) 27 return function(chunk)
27 local ret 28 local ret
28 ret, ctx = low(ctx, chunk, extra) 29 ret, ctx = low(ctx, chunk, extra)
@@ -32,6 +33,7 @@ end
32 33
33-- chains two filters together 34-- chains two filters together
34local function chain2(f1, f2) 35local function chain2(f1, f2)
36 assert(f1 and f2)
35 local co = coroutine.create(function(chunk) 37 local co = coroutine.create(function(chunk)
36 while true do 38 while true do
37 local filtered1 = f1(chunk) 39 local filtered1 = f1(chunk)
@@ -95,6 +97,7 @@ end
95 97
96-- turns a fancy source into a simple source 98-- turns a fancy source into a simple source
97function source.simplify(src) 99function source.simplify(src)
100 assert(src)
98 return function() 101 return function()
99 local chunk, err_or_new = src() 102 local chunk, err_or_new = src()
100 src = err_or_new or src 103 src = err_or_new or src
@@ -118,6 +121,7 @@ end
118 121
119-- creates rewindable source 122-- creates rewindable source
120function source.rewind(src) 123function source.rewind(src)
124 assert(src)
121 local t = {} 125 local t = {}
122 return function(chunk) 126 return function(chunk)
123 if not chunk then 127 if not chunk then
@@ -132,6 +136,7 @@ end
132 136
133-- chains a source with a filter 137-- chains a source with a filter
134function source.chain(src, f) 138function source.chain(src, f)
139 assert(src and f)
135 local co = coroutine.create(function() 140 local co = coroutine.create(function()
136 while true do 141 while true do
137 local chunk, err = src() 142 local chunk, err = src()
@@ -186,6 +191,7 @@ end
186 191
187-- turns a fancy sink into a simple sink 192-- turns a fancy sink into a simple sink
188function sink.simplify(snk) 193function sink.simplify(snk)
194 assert(snk)
189 return function(chunk, err) 195 return function(chunk, err)
190 local ret, err_or_new = snk(chunk, err) 196 local ret, err_or_new = snk(chunk, err)
191 if not ret then return nil, err_or_new end 197 if not ret then return nil, err_or_new end
@@ -224,6 +230,7 @@ end
224 230
225-- chains a sink with a filter 231-- chains a sink with a filter
226function sink.chain(f, snk) 232function sink.chain(f, snk)
233 assert(f and snk)
227 return function(chunk, err) 234 return function(chunk, err)
228 local filtered = f(chunk) 235 local filtered = f(chunk)
229 local done = chunk and "" 236 local done = chunk and ""
@@ -248,6 +255,7 @@ end
248 255
249-- pumps all data from a source to a sink, using a step function 256-- pumps all data from a source to a sink, using a step function
250function pump.all(src, snk, step) 257function pump.all(src, snk, step)
258 assert(src and snk)
251 step = step or pump.step 259 step = step or pump.step
252 while true do 260 while true do
253 local ret, err = step(src, snk) 261 local ret, err = step(src, snk)
diff --git a/src/smtp.lua b/src/smtp.lua
index fb76ea4..2ea6097 100644
--- a/src/smtp.lua
+++ b/src/smtp.lua
@@ -11,6 +11,7 @@
11local smtp = requirelib("smtp", "luaopen_smtp", getfenv(1)) 11local smtp = requirelib("smtp", "luaopen_smtp", getfenv(1))
12local socket = require("socket") 12local socket = require("socket")
13local ltn12 = require("ltn12") 13local ltn12 = require("ltn12")
14local mime = require("mime")
14local tp = require("tp") 15local tp = require("tp")
15 16
16----------------------------------------------------------------------------- 17-----------------------------------------------------------------------------
@@ -43,7 +44,7 @@ local metat = { __index = {} }
43function metat.__index:greet(domain) 44function metat.__index:greet(domain)
44 socket.try(self.tp:check("2..")) 45 socket.try(self.tp:check("2.."))
45 socket.try(self.tp:command("EHLO", domain or DOMAIN)) 46 socket.try(self.tp:command("EHLO", domain or DOMAIN))
46 return socket.try(self.tp:check("2..")) 47 return socket.skip(1, socket.try(self.tp:check("2..")))
47end 48end
48 49
49function metat.__index:mail(from) 50function metat.__index:mail(from)
@@ -73,6 +74,32 @@ function metat.__index:close()
73 return socket.try(self.tp:close()) 74 return socket.try(self.tp:close())
74end 75end
75 76
77function metat.__index:login(user, password)
78 socket.try(self.tp:command("AUTH", "LOGIN"))
79 socket.try(self.tp:check("3.."))
80 socket.try(self.tp:command(mime.b64(user)))
81 socket.try(self.tp:check("3.."))
82 socket.try(self.tp:command(mime.b64(password)))
83 return socket.try(self.tp:check("2.."))
84end
85
86function metat.__index:plain(user, password)
87 local auth = "PLAIN " .. mime.b64("\0" .. user .. "\0" .. password)
88 socket.try(self.tp:command("AUTH", auth))
89 return socket.try(self.tp:check("2.."))
90end
91
92function metat.__index:auth(user, password, ext)
93 if not user or not password then return 1 end
94 if string.find(ext, "AUTH[^\n]+LOGIN") then
95 return self:login(user, password)
96 elseif string.find(ext, "AUTH[^\n]+PLAIN") then
97 return self:plain(user, password)
98 else
99 socket.try(nil, "authentication not supported")
100 end
101end
102
76-- send message or throw an exception 103-- send message or throw an exception
77function metat.__index:send(mailt) 104function metat.__index:send(mailt)
78 self:mail(mailt.from) 105 self:mail(mailt.from)
@@ -205,10 +232,10 @@ end
205--------------------------------------------------------------------------- 232---------------------------------------------------------------------------
206-- High level SMTP API 233-- High level SMTP API
207----------------------------------------------------------------------------- 234-----------------------------------------------------------------------------
208socket.protect = function(a) return a end
209send = socket.protect(function(mailt) 235send = socket.protect(function(mailt)
210 local con = open(mailt.server, mailt.port) 236 local con = open(mailt.server, mailt.port)
211 con:greet(mailt.domain) 237 local ext = con:greet(mailt.domain)
238 con:auth(mailt.user, mailt.password, ext)
212 con:send(mailt) 239 con:send(mailt)
213 con:quit() 240 con:quit()
214 return con:close() 241 return con:close()
diff --git a/test/mimetest.lua b/test/mimetest.lua
index 808c402..2d5bce6 100644
--- a/test/mimetest.lua
+++ b/test/mimetest.lua
@@ -8,7 +8,7 @@ local qptest = "qptest.bin"
8local eqptest = "qptest.bin2" 8local eqptest = "qptest.bin2"
9local dqptest = "qptest.bin3" 9local dqptest = "qptest.bin3"
10 10
11local b64test = "luasocket.so" 11local b64test = "luasocket.dylib"
12local eb64test = "b64test.bin" 12local eb64test = "b64test.bin"
13local db64test = "b64test.bin2" 13local db64test = "b64test.bin2"
14 14