mirror of
				https://github.com/lunarmodules/luasocket.git
				synced 2025-10-31 10:25:55 +01:00 
			
		
		
		
	Final push for release...
This commit is contained in:
		
							
								
								
									
										11
									
								
								FIX
									
									
									
									
									
								
							
							
						
						
									
										11
									
								
								FIX
									
									
									
									
									
								
							| @@ -1,3 +1,14 @@ | |||||||
|  | fix smtp.send hang on source error | ||||||
|  | add create field to FTP and SMTP and fix HTTP ugliness | ||||||
|  | clean timeout argument to open functions in SMTP, HTTP and FTP | ||||||
|  | eliminate globals from namespaces created by module(). | ||||||
|  |  | ||||||
|  |  | ||||||
|  |  | ||||||
|  |  | ||||||
|  |  | ||||||
|  |  | ||||||
|  |  | ||||||
| url.absolute was not working when base_url was already parsed | url.absolute was not working when base_url was already parsed | ||||||
| http.request was redirecting even when the location header was empty | http.request was redirecting even when the location header was empty | ||||||
| tcp{client}:shutdown() was checking for group instead of class. | tcp{client}:shutdown() was checking for group instead of class. | ||||||
|   | |||||||
							
								
								
									
										36
									
								
								TODO
									
									
									
									
									
								
							
							
						
						
									
										36
									
								
								TODO
									
									
									
									
									
								
							| @@ -1,22 +1,13 @@ | |||||||
|  | new instalation scheme??? | ||||||
|  | test empty socket.select no windows. | ||||||
|  | bug by mathew percival? | ||||||
|  |  | ||||||
|  | arranjar um jeito de fazer multipart/alternative | ||||||
|  |  | ||||||
| what the hell does __unload do? | what the hell does __unload do? | ||||||
| clean timeout argument to open functions in SMTP, HTTP and FTP |  | ||||||
| add create field to FTP and SMTP |  | ||||||
| talk about new create field in HTTP, FTP and SMTP |  | ||||||
| talk about the non-blocking connect in the manual |  | ||||||
| test it on Windows!!! | test it on Windows!!! | ||||||
|  |  | ||||||
| think about a dispatcher. |  | ||||||
|     - it creates a server and receives a function that will do the work on |  | ||||||
|     received connections |  | ||||||
|     - this function is invoked with the client socket |  | ||||||
|     - it calls special send and receive functions that yield on timeout |  | ||||||
|  |  | ||||||
| think about how to extend http, ftp, smtp to use special send and receive |  | ||||||
| functions for non-blocking so they can be used in the context of the |  | ||||||
| dispatcher! |  | ||||||
|  |  | ||||||
| adjust manual for new sock:send returns. |  | ||||||
|  |  | ||||||
| leave code for losers that don't have nanosleep | leave code for losers that don't have nanosleep | ||||||
|  |  | ||||||
| ftp.send/recv return bytes transfered? | ftp.send/recv return bytes transfered? | ||||||
| @@ -41,7 +32,16 @@ testar os options! | |||||||
|   - proteger ou atomizar o conjunto (timedout, receive), (timedout, send) |   - proteger ou atomizar o conjunto (timedout, receive), (timedout, send) | ||||||
|   - inet_ntoa tamb<6D>m <20> uma merda. |   - inet_ntoa tamb<6D>m <20> uma merda. | ||||||
|  |  | ||||||
| eliminate globals from namespaces created by module(). |  | ||||||
|  |  | ||||||
| * BUG NO SET DO TINYIRC!!! SINISTRO. | * BUG NO SET DO TINYIRC!!! SINISTRO. | ||||||
| * _VERSION, _DEBUG, etc. | * _VERSION, _DEBUG, etc. | ||||||
|  | * talk about new create field in HTTP, FTP and SMTP | ||||||
|  | * talk about the non-blocking connect in the manual | ||||||
|  | * think about how to extend http, ftp, smtp to use special send and receive | ||||||
|  | * functions for non-blocking so they can be used in the context of the | ||||||
|  | * dispatcher! | ||||||
|  | * adjust manual for new sock:send returns. | ||||||
|  | * think about a dispatcher. | ||||||
|  |     * - it creates a server and receives a function that will do the work on | ||||||
|  |     * received connections | ||||||
|  |     * - this function is invoked with the client socket | ||||||
|  |     * - it calls special send and receive functions that yield on timeout | ||||||
|   | |||||||
							
								
								
									
										2
									
								
								config
									
									
									
									
									
								
							
							
						
						
									
										2
									
								
								config
									
									
									
									
									
								
							| @@ -21,7 +21,7 @@ LUALIB= | |||||||
| #------ | #------ | ||||||
| # Compat-5.1 directory | # Compat-5.1 directory | ||||||
| # | # | ||||||
| COMPAT=compat-5.1r3 | COMPAT=compat-5.1r4 | ||||||
|  |  | ||||||
| #------ | #------ | ||||||
| # Top of your Lua installation | # Top of your Lua installation | ||||||
|   | |||||||
							
								
								
									
										10
									
								
								doc/ftp.html
									
									
									
									
									
								
							
							
						
						
									
										10
									
								
								doc/ftp.html
									
									
									
									
									
								
							| @@ -106,6 +106,7 @@ ftp.<b>get{</b><br> | |||||||
|   [port = <i>number</i>,]<br> |   [port = <i>number</i>,]<br> | ||||||
|   [type = <i>string</i>,]<br> |   [type = <i>string</i>,]<br> | ||||||
|   [step = <i>LTN12 pump step</i>,]<br> |   [step = <i>LTN12 pump step</i>,]<br> | ||||||
|  |   [create = <i>function</i>]<br> | ||||||
| <b>}</b> | <b>}</b> | ||||||
| </p> | </p> | ||||||
|  |  | ||||||
| @@ -138,7 +139,9 @@ authentication. Defaults to "<tt>ftp:anonymous@anonymous.org</tt>"; | |||||||
| <li><tt>step</tt>:  | <li><tt>step</tt>:  | ||||||
| <a href="http://lua-users.org/wiki/FiltersSourcesAndSinks">LTN12</a> | <a href="http://lua-users.org/wiki/FiltersSourcesAndSinks">LTN12</a> | ||||||
| pump step function used to pass data from the | pump step function used to pass data from the | ||||||
| server to the sink. Defaults to the LTN12 <tt>pump.step</tt> function. | server to the sink. Defaults to the LTN12 <tt>pump.step</tt> function; | ||||||
|  | <li><tt>accept</tt>: An optional function to be used instead of | ||||||
|  | <a href=tcp.html#socket.tcp><tt>socket.tcp</tt></a> when the communications socket is created.  | ||||||
| </ul> | </ul> | ||||||
|  |  | ||||||
| <p class=return> | <p class=return> | ||||||
| @@ -188,6 +191,7 @@ ftp.<b>put{</b><br> | |||||||
|   [port = <i>number</i>,]<br> |   [port = <i>number</i>,]<br> | ||||||
|   [type = <i>string</i>,]<br> |   [type = <i>string</i>,]<br> | ||||||
|   [step = <i>LTN12 pump step</i>,]<br> |   [step = <i>LTN12 pump step</i>,]<br> | ||||||
|  |   [create = <i>function</i>]<br> | ||||||
| <b>}</b> | <b>}</b> | ||||||
| </p> | </p> | ||||||
|  |  | ||||||
| @@ -220,7 +224,9 @@ authentication. Defaults to "<tt>ftp:anonymous@anonymous.org</tt>"; | |||||||
| <li><tt>step</tt>:  | <li><tt>step</tt>:  | ||||||
| <a href="http://lua-users.org/wiki/FiltersSourcesAndSinks">LTN12</a>  | <a href="http://lua-users.org/wiki/FiltersSourcesAndSinks">LTN12</a>  | ||||||
| pump step function used to pass data from the | pump step function used to pass data from the | ||||||
| server to the sink. Defaults to the LTN12 <tt>pump.step</tt> function. | server to the sink. Defaults to the LTN12 <tt>pump.step</tt> function; | ||||||
|  | <li><tt>accept</tt>: An optional function to be used instead of | ||||||
|  | <a href=tcp.html#socket.tcp><tt>socket.tcp</tt></a> when the communications socket is created.  | ||||||
| </ul> | </ul> | ||||||
|  |  | ||||||
| <p class=return> | <p class=return> | ||||||
|   | |||||||
| @@ -131,7 +131,8 @@ http.<b>request{</b><br> | |||||||
|   [source = <i>LTN12 source</i>],<br> |   [source = <i>LTN12 source</i>],<br> | ||||||
|   [step = <i>LTN12 pump step</i>,]<br> |   [step = <i>LTN12 pump step</i>,]<br> | ||||||
|   [proxy = <i>string</i>,]<br> |   [proxy = <i>string</i>,]<br> | ||||||
|   [redirect = <i>boolean</i>]<br> |   [redirect = <i>boolean</i>,]<br> | ||||||
|  |   [create = <i>function</i>]<br> | ||||||
| <b>}</b> | <b>}</b> | ||||||
| </p> | </p> | ||||||
|  |  | ||||||
| @@ -178,7 +179,9 @@ pump step function used to move data. | |||||||
| Defaults to the LTN12 <tt>pump.step</tt> function. | Defaults to the LTN12 <tt>pump.step</tt> function. | ||||||
| <li><tt>proxy</tt>: The URL of a proxy server to use. Defaults to no proxy;  | <li><tt>proxy</tt>: The URL of a proxy server to use. Defaults to no proxy;  | ||||||
| <li><tt>redirect</tt>: Set to <tt><b>false</b></tt> to prevent the  | <li><tt>redirect</tt>: Set to <tt><b>false</b></tt> to prevent the  | ||||||
| function from  automatically following 301 or 302 server redirect messages.  | function from  automatically following 301 or 302 server redirect messages;  | ||||||
|  | <li><tt>accept</tt>: An optional function to be used instead of | ||||||
|  | <a href=tcp.html#socket.tcp><tt>socket.tcp</tt></a> when the communications socket is created.  | ||||||
| </ul> | </ul> | ||||||
|  |  | ||||||
| <p class=return> | <p class=return> | ||||||
|   | |||||||
| @@ -168,6 +168,7 @@ support. | |||||||
| <li> Improved: <tt>tcp:send(data, i, j)</tt> to return <tt>(i+sent-1)</tt>.  This is great for non-blocking I/O, but might break some code; | <li> Improved: <tt>tcp:send(data, i, j)</tt> to return <tt>(i+sent-1)</tt>.  This is great for non-blocking I/O, but might break some code; | ||||||
| <li> Improved: HTTP, SMTP, and FTP functions to accept a new field | <li> Improved: HTTP, SMTP, and FTP functions to accept a new field | ||||||
| <tt>create</tt> that overrides the function used to create socket objects; | <tt>create</tt> that overrides the function used to create socket objects; | ||||||
|  | <li> Fixed: <tt>smtp.send</tt> was hanging on errors returned by LTN12 sources; | ||||||
| <li> Fixed: <tt>url.absolute()</tt> to work when <tt>base_url</tt> is in | <li> Fixed: <tt>url.absolute()</tt> to work when <tt>base_url</tt> is in | ||||||
| parsed form; | parsed form; | ||||||
| <li> Fixed: <tt>http.request()</tt> not to redirect when the location  | <li> Fixed: <tt>http.request()</tt> not to redirect when the location  | ||||||
| @@ -194,7 +195,8 @@ with descriptor 0 to be ignored (Renato Maia); | |||||||
| <li> Fixed: "Bug" that caused <tt>gethostbyname</tt> to crash under VMS | <li> Fixed: "Bug" that caused <tt>gethostbyname</tt> to crash under VMS | ||||||
| (Renato Maia); | (Renato Maia); | ||||||
| <li> Fixed: <tt>tcp:send("")</tt> to return 0 bytes sent (Alexander Marinov); | <li> Fixed: <tt>tcp:send("")</tt> to return 0 bytes sent (Alexander Marinov); | ||||||
| <li> Improved: <tt>socket.DEBUG</tt> and <tt>socket.VERSION</tt> became <tt>socket._DEBUGs</tt> and <tt>socket._VERSION</tt> for uniformity with other libraries. | <li> Improved: <tt>socket.DEBUG</tt> and <tt>socket.VERSION</tt> became <tt>socket._DEBUGs</tt> and <tt>socket._VERSION</tt> for uniformity with other libraries; | ||||||
|  | <li> Improved: <tt>socket.select</tt> now works on empty sets on Windows.  | ||||||
| </ul> | </ul> | ||||||
|  |  | ||||||
| <!-- incompatible +++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> | <!-- incompatible +++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> | ||||||
|   | |||||||
| @@ -71,11 +71,11 @@ Here is the standard LuaSocket distribution directory structure:</p> | |||||||
|  |  | ||||||
| <pre class=example> | <pre class=example> | ||||||
| <ROOT>/compat-5.1.lua | <ROOT>/compat-5.1.lua | ||||||
| <ROOT>/socket.lua |  | ||||||
| <ROOT>/lsocket.dll |  | ||||||
| <ROOT>/mime.lua |  | ||||||
| <ROOT>/lmime.dll |  | ||||||
| <ROOT>/ltn12.lua | <ROOT>/ltn12.lua | ||||||
|  | <ROOT>/mime/init.lua | ||||||
|  | <ROOT>/mime/core.dll | ||||||
|  | <ROOT>/socket/init.lua | ||||||
|  | <ROOT>/socket/core.dll | ||||||
| <ROOT>/socket/http.lua | <ROOT>/socket/http.lua | ||||||
| <ROOT>/socket/tp.lua | <ROOT>/socket/tp.lua | ||||||
| <ROOT>/socket/ftp.lua | <ROOT>/socket/ftp.lua | ||||||
| @@ -83,10 +83,8 @@ Here is the standard LuaSocket distribution directory structure:</p> | |||||||
| <ROOT>/socket/url.lua | <ROOT>/socket/url.lua | ||||||
| </pre> | </pre> | ||||||
|  |  | ||||||
| <p> Naturally, on Unix systems, <tt>lsocket.dll</tt> and <tt>lmime.dll</tt> | <p> Naturally, on Unix systems, <tt>core.dll</tt> | ||||||
| would be replaced by <tt>lsocket.so</tt> and <tt>lmime.so</tt>. In Mac OS | would be replaced by <tt>core.so</tt>. | ||||||
| X, they would be replaced by <tt>lsocket.dylib</tt> and |  | ||||||
| <tt>lmime.dylib</tt>. </p> |  | ||||||
|  |  | ||||||
| <p> In order for the interpreter to find all LuaSocket components, three | <p> In order for the interpreter to find all LuaSocket components, three | ||||||
| environment variables need to be set. The first environment variable tells | environment variables need to be set. The first environment variable tells | ||||||
|   | |||||||
| @@ -142,7 +142,7 @@ Support, Manual"> | |||||||
| <blockquote> | <blockquote> | ||||||
| <a href="socket.html">Socket</a> | <a href="socket.html">Socket</a> | ||||||
| <blockquote> | <blockquote> | ||||||
| <a href="socket.html#_debug">_DEBUG</a>, | <a href="socket.html#debug">_DEBUG</a>, | ||||||
| <a href="dns.html#dns">dns</a>, | <a href="dns.html#dns">dns</a>, | ||||||
| <a href="socket.html#gettime">gettime</a>, | <a href="socket.html#gettime">gettime</a>, | ||||||
| <a href="socket.html#newtry">newtry</a>, | <a href="socket.html#newtry">newtry</a>, | ||||||
| @@ -155,7 +155,7 @@ Support, Manual"> | |||||||
| <a href="tcp.html#tcp">tcp</a>, | <a href="tcp.html#tcp">tcp</a>, | ||||||
| <a href="socket.html#try">try</a>, | <a href="socket.html#try">try</a>, | ||||||
| <a href="udp.html#udp">udp</a>, | <a href="udp.html#udp">udp</a>, | ||||||
| <a href="socket.html#_version">_VERSION</a>. | <a href="socket.html#version">_VERSION</a>. | ||||||
| </blockquote> | </blockquote> | ||||||
| </blockquote> | </blockquote> | ||||||
|  |  | ||||||
|   | |||||||
| @@ -127,6 +127,7 @@ smtp.<b>send{</b><br> | |||||||
|   [port = <i>number</i>,]<br> |   [port = <i>number</i>,]<br> | ||||||
|   [domain = <i>string</i>,]<br> |   [domain = <i>string</i>,]<br> | ||||||
|   [step = <i>LTN12 pump step</i>,]<br> |   [step = <i>LTN12 pump step</i>,]<br> | ||||||
|  |   [create = <i>function</i>]<br> | ||||||
| <b>}</b> | <b>}</b> | ||||||
| </p> | </p> | ||||||
|  |  | ||||||
| @@ -138,6 +139,7 @@ doesn't have a simple interface. However, see the | |||||||
| a very powerful way to define the message contents. | a very powerful way to define the message contents. | ||||||
| </p> | </p> | ||||||
|  |  | ||||||
|  |  | ||||||
| <p class=parameters> | <p class=parameters> | ||||||
| The sender is given by the e-mail address in the <tt>from</tt> field.  | The sender is given by the e-mail address in the <tt>from</tt> field.  | ||||||
| <tt>Rcpt</tt> is a Lua table with one entry for each recipient e-mail | <tt>Rcpt</tt> is a Lua table with one entry for each recipient e-mail | ||||||
| @@ -158,7 +160,9 @@ local machine host name; | |||||||
| <li> <tt>step</tt>:  | <li> <tt>step</tt>:  | ||||||
| <a href="http://lua-users.org/wiki/FiltersSourcesAndSinks">LTN12</a>  | <a href="http://lua-users.org/wiki/FiltersSourcesAndSinks">LTN12</a>  | ||||||
| pump step function used to pass data from the | pump step function used to pass data from the | ||||||
| source to the server. Defaults to the LTN12 <tt>pump.step</tt> function. | source to the server. Defaults to the LTN12 <tt>pump.step</tt> function; | ||||||
|  | <li><tt>accept</tt>: An optional function to be used instead of | ||||||
|  | <a href=tcp.html#socket.tcp><tt>socket.tcp</tt></a> when the communications socket is created.  | ||||||
| </ul> | </ul> | ||||||
|  |  | ||||||
| <p class=return>  | <p class=return>  | ||||||
| @@ -167,7 +171,7 @@ If  successful, the function returns 1. Otherwise, the function returns | |||||||
| </p> | </p> | ||||||
|  |  | ||||||
| <p class=note> | <p class=note> | ||||||
| Note: SMTP servers are can be very picky with the format of e-mail | Note: SMTP servers can be very picky with the format of e-mail | ||||||
| addresses. To be safe, use only addresses of the form | addresses. To be safe, use only addresses of the form | ||||||
| "<tt><fulano@example.com></tt>" in the <tt>from</tt> and | "<tt><fulano@example.com></tt>" in the <tt>from</tt> and | ||||||
| <tt>rcpt</tt> arguments to the <tt>send</tt> function. In headers, e-mail | <tt>rcpt</tt> arguments to the <tt>send</tt> function. In headers, e-mail | ||||||
|   | |||||||
| @@ -80,12 +80,12 @@ socket.<b>connect(</b>address, port [, locaddr, locport]<b>)</b> | |||||||
| This function is a shortcut that creates and returns a TCP client object | This function is a shortcut that creates and returns a TCP client object | ||||||
| connected to a remote <tt>host</tt> at a given <tt>port</tt>. Optionally, | connected to a remote <tt>host</tt> at a given <tt>port</tt>. Optionally, | ||||||
| the user can also specify the local address and port to bind | the user can also specify the local address and port to bind | ||||||
| (<tt>locaddr</tt> and </tt>locport</tt>). | (<tt>locaddr</tt> and <tt>locport</tt>). | ||||||
| </p> | </p> | ||||||
|  |  | ||||||
| <!-- debug ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> | <!-- debug ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> | ||||||
|  |  | ||||||
| <p class=name id=_debug>  | <p class=name id=debug>  | ||||||
| socket.<b>_DEBUG</b> | socket.<b>_DEBUG</b> | ||||||
| </p> | </p> | ||||||
|  |  | ||||||
| @@ -372,7 +372,7 @@ c = socket.try(socket.connect("localhost", 80)) | |||||||
|  |  | ||||||
| <!-- version ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> | <!-- version ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> | ||||||
|  |  | ||||||
| <p class=name id=_version>  | <p class=name id=version>  | ||||||
| socket.<b>_VERSION</b> | socket.<b>_VERSION</b> | ||||||
| </p> | </p> | ||||||
|  |  | ||||||
|   | |||||||
							
								
								
									
										21
									
								
								doc/tcp.html
									
									
									
									
									
								
							
							
						
						
									
										21
									
								
								doc/tcp.html
									
									
									
									
									
								
							| @@ -79,7 +79,7 @@ reported by <b><tt>nil</tt></b> followed by a message describing the error. | |||||||
| <p class=note> | <p class=note> | ||||||
| Note: calling <a href=socket.html#select><tt>socket.select</tt></a> | Note: calling <a href=socket.html#select><tt>socket.select</tt></a> | ||||||
| with   a  server   object   in | with   a  server   object   in | ||||||
| the <tt>receive</tt>  parameter  before  a   call  to  <tt>accept</tt> does | the <tt>recvt</tt>  parameter  before  a   call  to  <tt>accept</tt> does | ||||||
| <em>not</em> guarantee  <tt>accept</tt> will  return immediately.  Use the <a | <em>not</em> guarantee  <tt>accept</tt> will  return immediately.  Use the <a | ||||||
| href=#settimeout><tt>settimeout</tt></a> method or <tt>accept</tt> | href=#settimeout><tt>settimeout</tt></a> method or <tt>accept</tt> | ||||||
| might block until <em>another</em> client shows up.  | might block until <em>another</em> client shows up.  | ||||||
| @@ -111,7 +111,7 @@ method returns <b><tt>nil</tt></b> followed by an error message. | |||||||
|  |  | ||||||
| <p class=note> | <p class=note> | ||||||
| Note: The function <a href=socket.html#bind><tt>socket.bind</tt></a>  | Note: The function <a href=socket.html#bind><tt>socket.bind</tt></a>  | ||||||
| is available and is a shortcut for the creation server sockets. | is available and is a shortcut for the creation of server sockets. | ||||||
| </p> | </p> | ||||||
|  |  | ||||||
| <!-- close ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> | <!-- close ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> | ||||||
| @@ -173,8 +173,11 @@ is available and is a shortcut for the creation of client sockets. | |||||||
| <p class=note> | <p class=note> | ||||||
| Note: Starting with LuaSocket 2.0,  | Note: Starting with LuaSocket 2.0,  | ||||||
| the <a href=#settimeout><tt>settimeout</tt></a> | the <a href=#settimeout><tt>settimeout</tt></a> | ||||||
| method affects the behavior of connect, causing it to return in case of | method affects the behavior of <tt>connect</tt>, causing it to return  | ||||||
| a timeout. | with an error in case of a timeout. If that happens, you can still call <a | ||||||
|  | href=socket.html#select><tt>socket.select</tt></a> with the socket in the | ||||||
|  | <tt>sendt</tt> table. The socket will be writable when the connection is | ||||||
|  | stablished. | ||||||
| </p> | </p> | ||||||
|  |  | ||||||
| <!-- getpeername ++++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> | <!-- getpeername ++++++++++++++++++++++++++++++++++++++++++++++++++++++++ --> | ||||||
| @@ -328,11 +331,11 @@ substring to be sent. | |||||||
| </p> | </p> | ||||||
|  |  | ||||||
| <p class=return> | <p class=return> | ||||||
| If successful, the method returns the number of bytes accepted by  | If successful, the method returns the number of bytes sent. | ||||||
| the transport layer. In case of error, the method returns  | In case of error, the method returns  | ||||||
| <b><tt>nil</tt></b>, followed by an error message, followed by the | <b><tt>nil</tt></b>, followed by an error message, followed by the | ||||||
| partial number of bytes accepted by the transport layer.   | index of the first character within <tt>[i, j]</tt> that has not been sent yet | ||||||
| The error message can be '<tt>closed</tt>' in case | (you might want to try again from then on). The error message can be '<tt>closed</tt>' in case | ||||||
| the connection was  closed before the transmission was  completed or the | the connection was  closed before the transmission was  completed or the | ||||||
| string  '<tt>timeout</tt>'  in  case  there was  a  timeout  during  the | string  '<tt>timeout</tt>'  in  case  there was  a  timeout  during  the | ||||||
| operation. | operation. | ||||||
| @@ -433,7 +436,7 @@ of bandwidth. | |||||||
| <p class=parameters> | <p class=parameters> | ||||||
| <tt>Received</tt> is a number with the new number of bytes received. | <tt>Received</tt> is a number with the new number of bytes received. | ||||||
| <tt>Sent</tt> is a number with the new number of bytes sent. | <tt>Sent</tt> is a number with the new number of bytes sent. | ||||||
| <tt>Age</tt> is the new age in seconds</tt> | <tt>Age</tt> is the new age in seconds. | ||||||
| </p> | </p> | ||||||
|  |  | ||||||
| <p class=return> | <p class=return> | ||||||
|   | |||||||
| @@ -84,17 +84,22 @@ function newcreate(thread) | |||||||
|                 first = (first or 1) - 1 |                 first = (first or 1) - 1 | ||||||
|                 local result, error |                 local result, error | ||||||
|                 while true do |                 while true do | ||||||
|  |                     -- tell dispatcher we want to keep sending before we | ||||||
|  |                     -- yield control | ||||||
|  |                     sending:insert(tcp)                    | ||||||
|  |                     -- return control to dispatcher | ||||||
|  |                     -- if upon return the dispatcher tells us we timed out, | ||||||
|  |                     -- return an error to whoever called us | ||||||
|  |                     if coroutine.yield() == "timeout" then  | ||||||
|  |                         return nil, "timeout"  | ||||||
|  |                     end | ||||||
|  |                     -- mark time we started waiting | ||||||
|  |                     context[tcp].last = socket.gettime() | ||||||
|  |                     -- try sending | ||||||
|                     result, error, first = tcp:send(data, first+1, last) |                     result, error, first = tcp:send(data, first+1, last) | ||||||
|                     if error == "timeout" then |                     -- if we are done, or there was an unexpected error,  | ||||||
|                         -- tell dispatcher we want to keep sending |                     -- break away from loop | ||||||
|                         sending:insert(tcp) |                     if error ~= "timeout" then return result, error, first end | ||||||
|                         -- mark time we started waiting |  | ||||||
|                         context[tcp].last = socket.gettime() |  | ||||||
|                         -- return control to dispatcher |  | ||||||
|                         if coroutine.yield() == "timeout" then  |  | ||||||
|                             return nil, "timeout"  |  | ||||||
|                         end |  | ||||||
|                     else return result, error, first end |  | ||||||
|                 end |                 end | ||||||
|             end, |             end, | ||||||
|             -- receive in non-blocking mode and yield on timeout |             -- receive in non-blocking mode and yield on timeout | ||||||
| @@ -102,28 +107,35 @@ function newcreate(thread) | |||||||
|                 local error, partial = "timeout", "" |                 local error, partial = "timeout", "" | ||||||
|                 local value |                 local value | ||||||
|                 while true do  |                 while true do  | ||||||
|  |                     -- tell dispatcher we want to keep receiving before we | ||||||
|  |                     -- yield control | ||||||
|  |                     receiving:insert(tcp) | ||||||
|  |                     -- return control to dispatcher | ||||||
|  |                     -- if upon return the dispatcher tells us we timed out, | ||||||
|  |                     -- return an error to whoever called us | ||||||
|  |                     if coroutine.yield() == "timeout" then  | ||||||
|  |                         return nil, "timeout"  | ||||||
|  |                     end | ||||||
|  |                     -- mark time we started waiting | ||||||
|  |                     context[tcp].last = socket.gettime() | ||||||
|  |                     -- try receiving | ||||||
|                     value, error, partial = tcp:receive(pattern, partial) |                     value, error, partial = tcp:receive(pattern, partial) | ||||||
|                     if error == "timeout" then  |                     -- if we are done, or there was an unexpected error,  | ||||||
|                         -- tell dispatcher we want to keep receiving |                     -- break away from loop | ||||||
|                         receiving:insert(tcp) |                     if error ~= "timeout" then return value, error, partial end | ||||||
|                         -- mark time we started waiting |  | ||||||
|                         context[tcp].last = socket.gettime() |  | ||||||
|                         -- return control to dispatcher |  | ||||||
|                         if coroutine.yield() == "timeout" then  |  | ||||||
|                             return nil, "timeout"  |  | ||||||
|                         end |  | ||||||
|                     else return value, error, partial end |  | ||||||
|                 end |                 end | ||||||
|             end, |             end, | ||||||
|             -- connect in non-blocking mode and yield on timeout |             -- connect in non-blocking mode and yield on timeout | ||||||
|             connect = function(self, host, port) |             connect = function(self, host, port) | ||||||
|                 local result, error = tcp:connect(host, port) |                 local result, error = tcp:connect(host, port) | ||||||
|  |                 -- mark time we started waiting | ||||||
|  |                 context[tcp].last = socket.gettime() | ||||||
|                 if error == "timeout" then |                 if error == "timeout" then | ||||||
|                     -- tell dispatcher we will be able to write uppon connection |                     -- tell dispatcher we will be able to write uppon connection | ||||||
|                     sending:insert(tcp) |                     sending:insert(tcp) | ||||||
|                     -- mark time we started waiting |  | ||||||
|                     context[tcp].last = socket.gettime() |  | ||||||
|                     -- return control to dispatcher |                     -- return control to dispatcher | ||||||
|  |                     -- if upon return the dispatcher tells us we have a | ||||||
|  |                     -- timeout, just abort | ||||||
|                     if coroutine.yield() == "timeout" then  |                     if coroutine.yield() == "timeout" then  | ||||||
|                         return nil, "timeout"  |                         return nil, "timeout"  | ||||||
|                     end |                     end | ||||||
| @@ -148,10 +160,10 @@ function newcreate(thread) | |||||||
| end | end | ||||||
|  |  | ||||||
| -- get the status of a URL, non-blocking | -- get the status of a URL, non-blocking | ||||||
| function getstatus(from, link) | function getstatus(link) | ||||||
|     local parsed = url.parse(link, {scheme = "file"}) |     local parsed = url.parse(link, {scheme = "file"}) | ||||||
|     if parsed.scheme == "http" then |     if parsed.scheme == "http" then | ||||||
|         local thread = coroutine.create(function(thread, from, link) |         local thread = coroutine.create(function(thread, link) | ||||||
|             local r, c, h, s = http.request{ |             local r, c, h, s = http.request{ | ||||||
|                 method = "HEAD", |                 method = "HEAD", | ||||||
|                 url = link,  |                 url = link,  | ||||||
| @@ -162,7 +174,7 @@ function getstatus(from, link) | |||||||
|             nthreads = nthreads - 1 |             nthreads = nthreads - 1 | ||||||
|         end) |         end) | ||||||
|         nthreads = nthreads + 1 |         nthreads = nthreads + 1 | ||||||
|         assert(coroutine.resume(thread, thread, from, link)) |         assert(coroutine.resume(thread, thread, link)) | ||||||
|     end |     end | ||||||
| end | end | ||||||
|  |  | ||||||
| @@ -190,6 +202,8 @@ function dispatch() | |||||||
|         local now = socket.gettime() |         local now = socket.gettime() | ||||||
|         for who, data in pairs(context) do |         for who, data in pairs(context) do | ||||||
|             if  data.last and now - data.last > TIMEOUT then |             if  data.last and now - data.last > TIMEOUT then | ||||||
|  |                 sending:remove(who) | ||||||
|  |                 receiving:remove(who) | ||||||
|                 assert(coroutine.resume(context[who].thread, "timeout")) |                 assert(coroutine.resume(context[who].thread, "timeout")) | ||||||
|             end |             end | ||||||
|         end |         end | ||||||
| @@ -206,14 +220,15 @@ function readfile(path) | |||||||
|     else return nil, error end |     else return nil, error end | ||||||
| end | end | ||||||
|  |  | ||||||
| function retrieve(u) | function load(u) | ||||||
|     local parsed = url.parse(u, { scheme = "file" }) |     local parsed = url.parse(u, { scheme = "file" }) | ||||||
|     local body, headers, code, error |     local body, headers, code, error | ||||||
|     local base = u |     local base = u | ||||||
|     if parsed.scheme == "http" then |     if parsed.scheme == "http" then | ||||||
|         body, code, headers = http.request(u) |         body, code, headers = http.request(u) | ||||||
|         if code == 200 then |         if code == 200 then | ||||||
|             base = base or headers.location |             -- if there was a redirect, update base to reflect it | ||||||
|  |             base = headers.location or base | ||||||
|         end |         end | ||||||
|         if not body then |         if not body then | ||||||
|             error = code |             error = code | ||||||
| @@ -241,12 +256,13 @@ function getlinks(body, base) | |||||||
|     return links |     return links | ||||||
| end | end | ||||||
|  |  | ||||||
| function checklinks(from) | function checklinks(address) | ||||||
|     local base, body, error = retrieve(from) |     local base, body, error = load(address) | ||||||
|     if not body then print(error) return end |     if not body then print(error) return end | ||||||
|  |     print("Checking ", base) | ||||||
|     local links = getlinks(body, base) |     local links = getlinks(body, base) | ||||||
|     for _, link in ipairs(links) do |     for _, link in ipairs(links) do | ||||||
|         getstatus(from, link) |         getstatus(link) | ||||||
|     end |     end | ||||||
| end | end | ||||||
|  |  | ||||||
| @@ -255,8 +271,7 @@ if table.getn(arg) < 1 then | |||||||
|     print("Usage:\n  luasocket check-links.lua {<url>}") |     print("Usage:\n  luasocket check-links.lua {<url>}") | ||||||
|     exit() |     exit() | ||||||
| end | end | ||||||
| for _, a in ipairs(arg) do | for _, address in ipairs(arg) do | ||||||
|     print("Checking ", a) |     checklinks(url.absolute("file:", address)) | ||||||
|     checklinks(url.absolute("file:", a)) |  | ||||||
| end | end | ||||||
| dispatch() | dispatch() | ||||||
|   | |||||||
| @@ -37,7 +37,7 @@ function retrieve(u) | |||||||
| 	if parsed.scheme == "http" then  | 	if parsed.scheme == "http" then  | ||||||
|         body, code, headers = http.request(u) |         body, code, headers = http.request(u) | ||||||
|         if code == 200 then  |         if code == 200 then  | ||||||
|             base = base or headers.location |             base = headers.location or base | ||||||
|         end |         end | ||||||
|         if not body then  |         if not body then  | ||||||
|             error = code |             error = code | ||||||
|   | |||||||
| @@ -16,6 +16,7 @@ local url = require("socket.url") | |||||||
| local tp = require("socket.tp") | local tp = require("socket.tp") | ||||||
|  |  | ||||||
| module("socket.dict") | module("socket.dict") | ||||||
|  | getmetatable(_M).__index = nil | ||||||
|  |  | ||||||
| ----------------------------------------------------------------------------- | ----------------------------------------------------------------------------- | ||||||
| -- Globals  | -- Globals  | ||||||
| @@ -151,4 +152,3 @@ get = socket.protect(function(gett) | |||||||
|     else return tget(gett) end |     else return tget(gett) end | ||||||
| end) | end) | ||||||
|  |  | ||||||
| --getmetatable(_M).__index = nil |  | ||||||
|   | |||||||
| @@ -15,6 +15,7 @@ local string = require("string") | |||||||
| local socket = require("socket") | local socket = require("socket") | ||||||
| local ltn12 = require("ltn12") | local ltn12 = require("ltn12") | ||||||
| module("socket.lp") | module("socket.lp") | ||||||
|  | getmetatable(_M).__index = nil | ||||||
|  |  | ||||||
| -- default port | -- default port | ||||||
| PORT = 515 | PORT = 515 | ||||||
| @@ -318,4 +319,3 @@ query = socket.protect(function(p) | |||||||
|   return data |   return data | ||||||
| end) | end) | ||||||
|  |  | ||||||
| --getmetatable(_M).__index = nil |  | ||||||
|   | |||||||
| @@ -16,6 +16,7 @@ local socket = require("socket") | |||||||
| local ltn12 = require("ltn12") | local ltn12 = require("ltn12") | ||||||
| local url = require("socket.url") | local url = require("socket.url") | ||||||
| module("socket.tftp") | module("socket.tftp") | ||||||
|  | getmetatable(_M).__index = nil | ||||||
|  |  | ||||||
| ----------------------------------------------------------------------------- | ----------------------------------------------------------------------------- | ||||||
| -- Program constants | -- Program constants | ||||||
| @@ -153,4 +154,3 @@ get = socket.protect(function(gett) | |||||||
|     else return tget(gett) end |     else return tget(gett) end | ||||||
| end) | end) | ||||||
|  |  | ||||||
| --getmetatable(_M).__index = nil |  | ||||||
|   | |||||||
							
								
								
									
										52
									
								
								makefile
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										52
									
								
								makefile
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,52 @@ | |||||||
|  | #------ | ||||||
|  | # Load configuration | ||||||
|  | # | ||||||
|  | include config | ||||||
|  |  | ||||||
|  | #------ | ||||||
|  | # Hopefully no need to change anything below this line | ||||||
|  | # | ||||||
|  | INSTALL_SOCKET=$(INSTALL_TOP)/socket | ||||||
|  | INSTALL_MIME=$(INSTALL_TOP)/mime | ||||||
|  |  | ||||||
|  | all clean: | ||||||
|  | 	cd src; $(MAKE) $@ | ||||||
|  |  | ||||||
|  | #------ | ||||||
|  | # Files to install | ||||||
|  | # | ||||||
|  | TO_SOCKET:= \ | ||||||
|  | 	socket.lua \ | ||||||
|  | 	http.lua \ | ||||||
|  | 	url.lua \ | ||||||
|  | 	tp.lua \ | ||||||
|  | 	ftp.lua \ | ||||||
|  | 	smtp.lua | ||||||
|  |  | ||||||
|  | TO_TOP:= \ | ||||||
|  | 	ltn12.lua | ||||||
|  |  | ||||||
|  | TO_MIME:= \ | ||||||
|  | 	$(MIME_SO) \ | ||||||
|  | 	mime.lua | ||||||
|  |  | ||||||
|  | #------ | ||||||
|  | # Install LuaSocket according to recommendation | ||||||
|  | # | ||||||
|  | install: all | ||||||
|  | 	cd src; mkdir -p $(INSTALL_TOP) | ||||||
|  | 	cd src; $(INSTALL_DATA) $(COMPAT)/compat-5.1.lua $(INSTALL_TOP) | ||||||
|  | 	cd src; $(INSTALL_DATA) ltn12.lua $(INSTALL_TOP) | ||||||
|  | 	cd src; mkdir -p $(INSTALL_SOCKET) | ||||||
|  | 	cd src; $(INSTALL_EXEC) $(SOCKET_SO) $(INSTALL_SOCKET) | ||||||
|  | 	cd src; $(INSTALL_DATA) $(TO_SOCKET) $(INSTALL_SOCKET) | ||||||
|  | 	cd src; cd $(INSTALL_SOCKET); $(INSTALL_LINK) -s $(SOCKET_SO) core.$(EXT) | ||||||
|  | 	cd src; cd $(INSTALL_SOCKET); $(INSTALL_LINK) -s socket.lua init.lua | ||||||
|  | 	cd src; mkdir -p $(INSTALL_MIME) | ||||||
|  | 	cd src; $(INSTALL_DATA) $(TO_MIME) $(INSTALL_MIME) | ||||||
|  | 	cd src; cd $(INSTALL_MIME); $(INSTALL_LINK) -s $(MIME_SO) core.$(EXT) | ||||||
|  | 	cd src; cd $(INSTALL_MIME); $(INSTALL_LINK) -s mime.lua init.lua | ||||||
|  |  | ||||||
|  | #------ | ||||||
|  | # End of makefile | ||||||
|  | # | ||||||
							
								
								
									
										12
									
								
								src/ftp.lua
									
									
									
									
									
								
							
							
						
						
									
										12
									
								
								src/ftp.lua
									
									
									
									
									
								
							| @@ -17,6 +17,7 @@ local url = require("socket.url") | |||||||
| local tp = require("socket.tp") | local tp = require("socket.tp") | ||||||
| local ltn12 = require("ltn12") | local ltn12 = require("ltn12") | ||||||
| module("socket.ftp") | module("socket.ftp") | ||||||
|  | getmetatable(_M).__index = nil | ||||||
|  |  | ||||||
| ----------------------------------------------------------------------------- | ----------------------------------------------------------------------------- | ||||||
| -- Program constants | -- Program constants | ||||||
| @@ -35,8 +36,8 @@ PASSWORD = "anonymous@anonymous.org" | |||||||
| ----------------------------------------------------------------------------- | ----------------------------------------------------------------------------- | ||||||
| local metat = { __index = {} } | local metat = { __index = {} } | ||||||
|  |  | ||||||
| function open(server, port) | function open(server, port, create) | ||||||
|     local tp = socket.try(tp.connect(server, port or PORT, TIMEOUT)) |     local tp = socket.try(tp.connect(server, port or PORT, create, TIMEOUT)) | ||||||
|     local f = base.setmetatable({ tp = tp }, metat) |     local f = base.setmetatable({ tp = tp }, metat) | ||||||
|     -- make sure everything gets closed in an exception |     -- make sure everything gets closed in an exception | ||||||
|     f.try = socket.newtry(function() f:close() end) |     f.try = socket.newtry(function() f:close() end) | ||||||
| @@ -199,7 +200,7 @@ end | |||||||
| local function tput(putt) | local function tput(putt) | ||||||
|     putt = override(putt) |     putt = override(putt) | ||||||
|     socket.try(putt.host, "missing hostname") |     socket.try(putt.host, "missing hostname") | ||||||
|     local f = open(putt.host, putt.port) |     local f = open(putt.host, putt.port, putt.create) | ||||||
|     f:greet() |     f:greet() | ||||||
|     f:login(putt.user, putt.password) |     f:login(putt.user, putt.password) | ||||||
|     if putt.type then f:type(putt.type) end |     if putt.type then f:type(putt.type) end | ||||||
| @@ -242,7 +243,7 @@ end) | |||||||
| local function tget(gett) | local function tget(gett) | ||||||
|     gett = override(gett) |     gett = override(gett) | ||||||
|     socket.try(gett.host, "missing hostname") |     socket.try(gett.host, "missing hostname") | ||||||
|     local f = open(gett.host, gett.port) |     local f = open(gett.host, gett.port, gett.create) | ||||||
|     f:greet() |     f:greet() | ||||||
|     f:login(gett.user, gett.password) |     f:login(gett.user, gett.password) | ||||||
|     if gett.type then f:type(gett.type) end |     if gett.type then f:type(gett.type) end | ||||||
| @@ -264,7 +265,7 @@ command = socket.protect(function(cmdt) | |||||||
|     cmdt = override(cmdt) |     cmdt = override(cmdt) | ||||||
|     socket.try(cmdt.host, "missing hostname") |     socket.try(cmdt.host, "missing hostname") | ||||||
|     socket.try(cmdt.command, "missing command") |     socket.try(cmdt.command, "missing command") | ||||||
|     local f = open(cmdt.host, cmdt.port) |     local f = open(cmdt.host, cmdt.port, cmdt.create) | ||||||
|     f:greet() |     f:greet() | ||||||
|     f:login(cmdt.user, cmdt.password) |     f:login(cmdt.user, cmdt.password) | ||||||
|     f.try(f.tp:command(cmdt.command, cmdt.argument)) |     f.try(f.tp:command(cmdt.command, cmdt.argument)) | ||||||
| @@ -278,4 +279,3 @@ get = socket.protect(function(gett) | |||||||
|     else return tget(gett) end |     else return tget(gett) end | ||||||
| end) | end) | ||||||
|  |  | ||||||
| --getmetatable(_M).__index = nil |  | ||||||
|   | |||||||
							
								
								
									
										45
									
								
								src/http.lua
									
									
									
									
									
								
							
							
						
						
									
										45
									
								
								src/http.lua
									
									
									
									
									
								
							| @@ -16,6 +16,7 @@ local string = require("string") | |||||||
| local base = _G | local base = _G | ||||||
| local table = require("table") | local table = require("table") | ||||||
| module("socket.http") | module("socket.http") | ||||||
|  | getmetatable(_M).__index = nil | ||||||
|  |  | ||||||
| ----------------------------------------------------------------------------- | ----------------------------------------------------------------------------- | ||||||
| -- Program constants | -- Program constants | ||||||
| @@ -105,26 +106,16 @@ end | |||||||
| ----------------------------------------------------------------------------- | ----------------------------------------------------------------------------- | ||||||
| local metat = { __index = {} } | local metat = { __index = {} } | ||||||
|  |  | ||||||
| -- default connect function, respecting the timeout |  | ||||||
| local function connect(host, port, create) |  | ||||||
|     local c, e = (create or socket.tcp)() |  | ||||||
|     if not c then return nil, e end |  | ||||||
|     c:settimeout(TIMEOUT) |  | ||||||
|     local r, e = c:connect(host, port or PORT) |  | ||||||
|     if not r then  |  | ||||||
|         c:close() |  | ||||||
|         return nil, e  |  | ||||||
|     end |  | ||||||
|     return c |  | ||||||
| end |  | ||||||
|  |  | ||||||
| function open(host, port, create) | function open(host, port, create) | ||||||
|     -- create socket with user connect function, or with default |     -- create socket with user connect function, or with default | ||||||
|     local c = socket.try(connect(host, port, create)) |     local c = socket.try(create or socket.tcp)() | ||||||
|     -- create our http request object, pointing to the socket |  | ||||||
|     local h = base.setmetatable({ c = c }, metat) |     local h = base.setmetatable({ c = c }, metat) | ||||||
|     -- make sure the object close gets called on exception |     -- create finalized try | ||||||
|     h.try = socket.newtry(function() h:close() end) |     h.try = socket.newtry(function() h:close() end) | ||||||
|  |     -- set timeout before connecting | ||||||
|  |     h.try(c:settimeout(TIMEOUT)) | ||||||
|  |     h.try(c:connect(host, port or PORT)) | ||||||
|  |     -- here everything worked | ||||||
|     return h  |     return h  | ||||||
| end | end | ||||||
|  |  | ||||||
| @@ -134,11 +125,11 @@ function metat.__index:sendrequestline(method, uri) | |||||||
| end | end | ||||||
|  |  | ||||||
| function metat.__index:sendheaders(headers) | function metat.__index:sendheaders(headers) | ||||||
|  |     local h = "\r\n" | ||||||
|     for i, v in base.pairs(headers) do |     for i, v in base.pairs(headers) do | ||||||
|         self.try(self.c:send(i .. ": " .. v .. "\r\n")) |         h = i .. ": " .. v .. "\r\n" .. h | ||||||
|     end |     end | ||||||
|     -- mark end of request headers |     self.try(self.c:send(h)) | ||||||
|     self.try(self.c:send("\r\n")) |  | ||||||
|     return 1 |     return 1 | ||||||
| end | end | ||||||
|  |  | ||||||
| @@ -213,7 +204,7 @@ local function adjustheaders(headers, host) | |||||||
|         ["te"] = "trailers" |         ["te"] = "trailers" | ||||||
|     } |     } | ||||||
|     -- override with user headers |     -- override with user headers | ||||||
|     for i,v in pairs(headers or lower) do |     for i,v in base.pairs(headers or lower) do | ||||||
|         lower[string.lower(i)] = v |         lower[string.lower(i)] = v | ||||||
|     end |     end | ||||||
|     return lower |     return lower | ||||||
| @@ -232,7 +223,7 @@ local function adjustrequest(reqt) | |||||||
|     local nreqt = reqt.url and url.parse(reqt.url, default) or {} |     local nreqt = reqt.url and url.parse(reqt.url, default) or {} | ||||||
|     local t = url.parse(reqt.url, default) |     local t = url.parse(reqt.url, default) | ||||||
|     -- explicit components override url |     -- explicit components override url | ||||||
|     for i,v in pairs(reqt) do nreqt[i] = v end |     for i,v in base.pairs(reqt) do nreqt[i] = v end | ||||||
|     socket.try(nreqt.host, "invalid host '" .. base.tostring(nreqt.host) .. "'") |     socket.try(nreqt.host, "invalid host '" .. base.tostring(nreqt.host) .. "'") | ||||||
|     -- compute uri if user hasn't overriden |     -- compute uri if user hasn't overriden | ||||||
|     nreqt.uri = reqt.uri or adjusturi(nreqt) |     nreqt.uri = reqt.uri or adjusturi(nreqt) | ||||||
| @@ -276,11 +267,11 @@ function tauthorize(reqt) | |||||||
|     return trequest(reqt) |     return trequest(reqt) | ||||||
| end | end | ||||||
|  |  | ||||||
| function tredirect(reqt, headers) | function tredirect(reqt, location) | ||||||
|     return trequest { |     local result, code, headers, status = trequest { | ||||||
|         -- the RFC says the redirect URL has to be absolute, but some |         -- the RFC says the redirect URL has to be absolute, but some | ||||||
|         -- servers do not respect that |         -- servers do not respect that | ||||||
|         url = url.absolute(reqt, headers["location"]), |         url = url.absolute(reqt, location), | ||||||
|         source = reqt.source, |         source = reqt.source, | ||||||
|         sink = reqt.sink, |         sink = reqt.sink, | ||||||
|         headers = reqt.headers, |         headers = reqt.headers, | ||||||
| @@ -288,6 +279,9 @@ function tredirect(reqt, headers) | |||||||
|         nredirects = (reqt.nredirects or 0) + 1, |         nredirects = (reqt.nredirects or 0) + 1, | ||||||
|         connect = reqt.connect |         connect = reqt.connect | ||||||
|     } |     } | ||||||
|  |     -- pass location header back as a hint we redirected | ||||||
|  |     headers.location = headers.location or location | ||||||
|  |     return result, code, headers, status | ||||||
| end | end | ||||||
|  |  | ||||||
| function trequest(reqt) | function trequest(reqt) | ||||||
| @@ -301,7 +295,7 @@ function trequest(reqt) | |||||||
|     headers = h:receiveheaders() |     headers = h:receiveheaders() | ||||||
|     if shouldredirect(reqt, code, headers) then  |     if shouldredirect(reqt, code, headers) then  | ||||||
|         h:close() |         h:close() | ||||||
|         return tredirect(reqt, headers) |         return tredirect(reqt, headers.location) | ||||||
|     elseif shouldauthorize(reqt, code) then  |     elseif shouldauthorize(reqt, code) then  | ||||||
|         h:close() |         h:close() | ||||||
|         return tauthorize(reqt) |         return tauthorize(reqt) | ||||||
| @@ -332,4 +326,3 @@ request = socket.protect(function(reqt, body) | |||||||
|     else return trequest(reqt) end |     else return trequest(reqt) end | ||||||
| end) | end) | ||||||
|  |  | ||||||
| --getmetatable(_M).__index = nil |  | ||||||
|   | |||||||
| @@ -12,6 +12,7 @@ local string = require("string") | |||||||
| local table = require("table") | local table = require("table") | ||||||
| local base = _G | local base = _G | ||||||
| module("ltn12") | module("ltn12") | ||||||
|  | getmetatable(_M).__index = nil | ||||||
|  |  | ||||||
| filter = {} | filter = {} | ||||||
| source = {} | source = {} | ||||||
| @@ -134,8 +135,6 @@ function source.rewind(src) | |||||||
|     end |     end | ||||||
| end | end | ||||||
|  |  | ||||||
| local print = print |  | ||||||
|  |  | ||||||
| -- chains a source with a filter | -- chains a source with a filter | ||||||
| function source.chain(src, f) | function source.chain(src, f) | ||||||
|     base.assert(src and f) |     base.assert(src and f) | ||||||
| @@ -258,7 +257,8 @@ end | |||||||
| function pump.step(src, snk) | function pump.step(src, snk) | ||||||
|     local chunk, src_err = src() |     local chunk, src_err = src() | ||||||
|     local ret, snk_err = snk(chunk, src_err) |     local ret, snk_err = snk(chunk, src_err) | ||||||
|     return chunk and ret and not src_err and not snk_err, src_err or snk_err |     if chunk and ret then return 1 | ||||||
|  |     else return nil, src_err or snk_err end | ||||||
| end | end | ||||||
|  |  | ||||||
| -- pumps all data from a source to a sink, using a step function | -- pumps all data from a source to a sink, using a step function | ||||||
| @@ -267,8 +267,10 @@ function pump.all(src, snk, step) | |||||||
|     step = step or pump.step |     step = step or pump.step | ||||||
|     while true do |     while true do | ||||||
|         local ret, err = step(src, snk) |         local ret, err = step(src, snk) | ||||||
|         if not ret then return not err, err end |         if not ret then  | ||||||
|  |             if err then return nil, err | ||||||
|  |             else return 1 end | ||||||
|  |         end | ||||||
|     end |     end | ||||||
| end | end | ||||||
|  |  | ||||||
| --getmetatable(_M).__index = nil |  | ||||||
|   | |||||||
| @@ -108,7 +108,7 @@ static int base_open(lua_State *L) { | |||||||
| /*-------------------------------------------------------------------------*\ | /*-------------------------------------------------------------------------*\ | ||||||
| * Initializes all library modules. | * Initializes all library modules. | ||||||
| \*-------------------------------------------------------------------------*/ | \*-------------------------------------------------------------------------*/ | ||||||
| LUASOCKET_API int luaopen_socketcore(lua_State *L) { | LUASOCKET_API int luaopen_socket_core(lua_State *L) { | ||||||
|     int i; |     int i; | ||||||
|     base_open(L); |     base_open(L); | ||||||
|     for (i = 0; mod[i].name; i++) mod[i].func(L); |     for (i = 0; mod[i].name; i++) mod[i].func(L); | ||||||
|   | |||||||
							
								
								
									
										87
									
								
								src/makefile
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										87
									
								
								src/makefile
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,87 @@ | |||||||
|  | #------ | ||||||
|  | # Load configuration | ||||||
|  | # | ||||||
|  | include ../config | ||||||
|  |  | ||||||
|  | #------ | ||||||
|  | # Hopefully no need to change anything below this line | ||||||
|  | # | ||||||
|  |  | ||||||
|  | #------ | ||||||
|  | # Modules belonging to socket-core | ||||||
|  | # | ||||||
|  | SOCKET_OBJS:= \ | ||||||
|  | 	luasocket.o \ | ||||||
|  | 	timeout.o \ | ||||||
|  | 	buffer.o \ | ||||||
|  | 	io.o \ | ||||||
|  | 	auxiliar.o \ | ||||||
|  | 	options.o \ | ||||||
|  | 	inet.o \ | ||||||
|  | 	tcp.o \ | ||||||
|  | 	udp.o \ | ||||||
|  | 	except.o \ | ||||||
|  | 	select.o \ | ||||||
|  | 	$(COMPAT)/compat-5.1.o \ | ||||||
|  | 	usocket.o  | ||||||
|  |  | ||||||
|  | #------ | ||||||
|  | # Modules belonging mime-core | ||||||
|  | # | ||||||
|  | MIME_OBJS:=\ | ||||||
|  | 	mime.o \ | ||||||
|  | 	$(COMPAT)/compat-5.1.o | ||||||
|  |  | ||||||
|  | #------ | ||||||
|  | # Modules belonging unix (local domain sockets) | ||||||
|  | # | ||||||
|  | UNIX_OBJS:=\ | ||||||
|  | 	buffer.o \ | ||||||
|  | 	auxiliar.o \ | ||||||
|  | 	options.o \ | ||||||
|  | 	timeout.o \ | ||||||
|  | 	io.o \ | ||||||
|  | 	usocket.o \ | ||||||
|  | 	unix.o | ||||||
|  |  | ||||||
|  | all: $(SOCKET_SO) $(MIME_SO)  | ||||||
|  |  | ||||||
|  | $(SOCKET_SO): $(SOCKET_OBJS) | ||||||
|  | 	$(LD) $(LDFLAGS) -o $@ $^ | ||||||
|  |  | ||||||
|  | $(MIME_SO): $(MIME_OBJS) | ||||||
|  | 	$(LD) $(LDFLAGS) -o $@ $^ | ||||||
|  |  | ||||||
|  | $(UNIX_SO): $(UNIX_OBJS) | ||||||
|  | 	$(LD) $(LDFLAGS) -o $@ $^ | ||||||
|  |  | ||||||
|  | #------ | ||||||
|  | # List of dependencies | ||||||
|  | # | ||||||
|  | auxiliar.o: auxiliar.c auxiliar.h | ||||||
|  | buffer.o: buffer.c buffer.h io.h timeout.h | ||||||
|  | except.o: except.c except.h | ||||||
|  | inet.o: inet.c inet.h socket.h io.h timeout.h usocket.h | ||||||
|  | io.o: io.c io.h timeout.h | ||||||
|  | luasocket.o: luasocket.c luasocket.h auxiliar.h except.h timeout.h \ | ||||||
|  |   buffer.h io.h inet.h socket.h usocket.h tcp.h udp.h select.h | ||||||
|  | mime.o: mime.c mime.h | ||||||
|  | options.o: options.c auxiliar.h options.h socket.h io.h timeout.h \ | ||||||
|  |   usocket.h inet.h | ||||||
|  | select.o: select.c socket.h io.h timeout.h usocket.h select.h | ||||||
|  | tcp.o: tcp.c auxiliar.h socket.h io.h timeout.h usocket.h inet.h \ | ||||||
|  |   options.h tcp.h buffer.h | ||||||
|  | timeout.o: timeout.c auxiliar.h timeout.h | ||||||
|  | udp.o: udp.c auxiliar.h socket.h io.h timeout.h usocket.h inet.h \ | ||||||
|  |   options.h udp.h | ||||||
|  | unix.o: unix.c auxiliar.h socket.h io.h timeout.h usocket.h options.h \ | ||||||
|  |   unix.h buffer.h | ||||||
|  | usocket.o: usocket.c socket.h io.h timeout.h usocket.h | ||||||
|  |  | ||||||
|  | clean: | ||||||
|  | 	rm -f $(SOCKET_SO) $(SOCKET_OBJS)  | ||||||
|  | 	rm -f $(MIME_SO) $(UNIX_SO) $(MIME_OBJS) $(UNIX_OBJS) | ||||||
|  |  | ||||||
|  | #------ | ||||||
|  | # End of makefile configuration | ||||||
|  | # | ||||||
| @@ -14,6 +14,7 @@ local mime = require("mime.core") | |||||||
| local io = require("io") | local io = require("io") | ||||||
| local string = require("string") | local string = require("string") | ||||||
| module("mime") | module("mime") | ||||||
|  | getmetatable(_M).__index = nil | ||||||
|  |  | ||||||
| -- encode, decode and wrap algorithm tables | -- encode, decode and wrap algorithm tables | ||||||
| encodet = {} | encodet = {} | ||||||
| @@ -84,5 +85,3 @@ end | |||||||
| function stuff() | function stuff() | ||||||
|     return ltn12.filter.cycle(dot, 2) |     return ltn12.filter.cycle(dot, 2) | ||||||
| end | end | ||||||
|  |  | ||||||
| --getmetatable(_M).__index = nil |  | ||||||
|   | |||||||
							
								
								
									
										29
									
								
								src/smtp.lua
									
									
									
									
									
								
							
							
						
						
									
										29
									
								
								src/smtp.lua
									
									
									
									
									
								
							| @@ -18,6 +18,7 @@ local tp = require("socket.tp") | |||||||
| local ltn12 = require("ltn12") | local ltn12 = require("ltn12") | ||||||
| local mime = require("mime") | local mime = require("mime") | ||||||
| module("socket.smtp") | module("socket.smtp") | ||||||
|  | getmetatable(_M).__index = nil | ||||||
|  |  | ||||||
| ----------------------------------------------------------------------------- | ----------------------------------------------------------------------------- | ||||||
| -- Program constants | -- Program constants | ||||||
| @@ -111,12 +112,12 @@ function metat.__index:send(mailt) | |||||||
|     self:data(ltn12.source.chain(mailt.source, mime.stuff()), mailt.step) |     self:data(ltn12.source.chain(mailt.source, mime.stuff()), mailt.step) | ||||||
| end | end | ||||||
|  |  | ||||||
| function open(server, port) | function open(server, port, create) | ||||||
|     local tp = socket.try(tp.connect(server or SERVER, port or PORT, TIMEOUT)) |     local tp = socket.try(tp.connect(server or SERVER, port or PORT,  | ||||||
|  |         create, TIMEOUT)) | ||||||
|     local s = base.setmetatable({tp = tp}, metat) |     local s = base.setmetatable({tp = tp}, metat) | ||||||
|     -- make sure tp is closed if we get an exception |     -- make sure tp is closed if we get an exception | ||||||
|     s.try = socket.newtry(function()  |     s.try = socket.newtry(function()  | ||||||
|         if s.tp:command("QUIT") then s.tp:check("2..") end |  | ||||||
|         s:close() |         s:close() | ||||||
|     end) |     end) | ||||||
|     return s  |     return s  | ||||||
| @@ -165,10 +166,9 @@ end | |||||||
| local function send_source(mesgt) | local function send_source(mesgt) | ||||||
|     -- set content-type if user didn't override |     -- set content-type if user didn't override | ||||||
|     if not mesgt.headers or not mesgt.headers["content-type"] then |     if not mesgt.headers or not mesgt.headers["content-type"] then | ||||||
|         coroutine.yield('content-type: text/plain; charset="iso-8859-1"\r\n') |         coroutine.yield('content-type: text/plain; charset="iso-8859-1"\r\n\r\n') | ||||||
|     end |     else coroutine.yield("\r\n") end | ||||||
|     -- finish headers |     -- finish headers | ||||||
|     coroutine.yield("\r\n") |  | ||||||
|     -- send body from source |     -- send body from source | ||||||
|     while true do  |     while true do  | ||||||
|         local chunk, err = mesgt.body() |         local chunk, err = mesgt.body() | ||||||
| @@ -182,21 +182,20 @@ end | |||||||
| local function send_string(mesgt) | local function send_string(mesgt) | ||||||
|     -- set content-type if user didn't override |     -- set content-type if user didn't override | ||||||
|     if not mesgt.headers or not mesgt.headers["content-type"] then |     if not mesgt.headers or not mesgt.headers["content-type"] then | ||||||
|         coroutine.yield('content-type: text/plain; charset="iso-8859-1"\r\n') |       coroutine.yield('content-type: text/plain; charset="iso-8859-1"\r\n\r\n') | ||||||
|     end |     else coroutine.yield("\r\n") end | ||||||
|     -- finish headers |  | ||||||
|     coroutine.yield("\r\n") |  | ||||||
|     -- send body from string |     -- send body from string | ||||||
|     coroutine.yield(mesgt.body) |     coroutine.yield(mesgt.body) | ||||||
|  |  | ||||||
| end | end | ||||||
|  |  | ||||||
| -- yield the headers one by one | -- yield the headers all at once  | ||||||
| local function send_headers(mesgt) | local function send_headers(mesgt) | ||||||
|     if mesgt.headers then |     if mesgt.headers then | ||||||
|  |         local h = "" | ||||||
|         for i,v in base.pairs(mesgt.headers) do |         for i,v in base.pairs(mesgt.headers) do | ||||||
|             coroutine.yield(i .. ':' .. v .. "\r\n") |             h = i .. ': ' .. v .. "\r\n" .. h | ||||||
|         end |         end | ||||||
|  |         coroutine.yield(h) | ||||||
|     end |     end | ||||||
| end | end | ||||||
|  |  | ||||||
| @@ -237,12 +236,10 @@ end | |||||||
| -- High level SMTP API | -- High level SMTP API | ||||||
| ----------------------------------------------------------------------------- | ----------------------------------------------------------------------------- | ||||||
| send = socket.protect(function(mailt) | send = socket.protect(function(mailt) | ||||||
|     local s = open(mailt.server, mailt.port) |     local s = open(mailt.server, mailt.port, mailt.create) | ||||||
|     local ext = s:greet(mailt.domain) |     local ext = s:greet(mailt.domain) | ||||||
|     s:auth(mailt.user, mailt.password, ext) |     s:auth(mailt.user, mailt.password, ext) | ||||||
|     s:send(mailt) |     s:send(mailt) | ||||||
|     s:quit() |     s:quit() | ||||||
|     return s:close() |     return s:close() | ||||||
| end) | end) | ||||||
|  |  | ||||||
| --getmetatable(_M).__index = nil |  | ||||||
|   | |||||||
| @@ -12,6 +12,7 @@ local string = require("string") | |||||||
| local math = require("math") | local math = require("math") | ||||||
| local socket = require("socket.core") | local socket = require("socket.core") | ||||||
| module("socket") | module("socket") | ||||||
|  | getmetatable(_M).__index = nil | ||||||
|  |  | ||||||
| ----------------------------------------------------------------------------- | ----------------------------------------------------------------------------- | ||||||
| -- Exported auxiliar functions | -- Exported auxiliar functions | ||||||
| @@ -131,5 +132,3 @@ sourcet["default"] = sourcet["until-closed"] | |||||||
|  |  | ||||||
| source = choose(sourcet) | source = choose(sourcet) | ||||||
|  |  | ||||||
| -- clear globals from namespace |  | ||||||
| getmetatable(_M).__index = nil |  | ||||||
|   | |||||||
							
								
								
									
										70
									
								
								src/ssl.c
									
									
									
									
									
								
							
							
						
						
									
										70
									
								
								src/ssl.c
									
									
									
									
									
								
							| @@ -1,70 +0,0 @@ | |||||||
| /*=========================================================================*\ |  | ||||||
| * Simple client SSL support |  | ||||||
| * LuaSocket toolkit |  | ||||||
| * |  | ||||||
| * RCS ID: $Id$ |  | ||||||
| \*=========================================================================*/ |  | ||||||
| #include <lua.h> |  | ||||||
| #include <lauxlib.h> |  | ||||||
|  |  | ||||||
| #include "ssl.h" |  | ||||||
|  |  | ||||||
| /*=========================================================================*\ |  | ||||||
| * Internal function prototypes |  | ||||||
| \*=========================================================================*/ |  | ||||||
| static int global_wrap(lua_State *L); |  | ||||||
|  |  | ||||||
| /* functions in library namespace */ |  | ||||||
| static luaL_reg func[] = { |  | ||||||
|     {"wrap", global_create}, |  | ||||||
|     {NULL, NULL} |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| static luaL_reg wrap[] = { |  | ||||||
|     {"__tostring",  aux_tostring}, |  | ||||||
|     {"__gc",        meth_close}, |  | ||||||
|     {"close",       meth_close}, |  | ||||||
|     {"receive",     meth_receive}, |  | ||||||
|     {"send",        meth_send}, |  | ||||||
|     {NULL,          NULL} |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| static luaL_reg owned[] = { |  | ||||||
|     {"__tostring",  aux_tostring}, |  | ||||||
|     {NULL,          NULL} |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| /*-------------------------------------------------------------------------*\ |  | ||||||
| * Initializes module |  | ||||||
| \*-------------------------------------------------------------------------*/ |  | ||||||
| int ssl_open(lua_State *L) |  | ||||||
| { |  | ||||||
|     aux_newclass(L, "ssl{wraper}", wrap); |  | ||||||
|     aux_newclass(L, "ssl{owned}",  owned); |  | ||||||
|     lua_pushstring(L, "ssl") |  | ||||||
|     lua_newtable(L); |  | ||||||
|     luaL_openlib(L, NULL, func, 0); |  | ||||||
|     lua_settable(L, -3); |  | ||||||
|     return 0; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| /*=========================================================================*\ |  | ||||||
| * Library functions |  | ||||||
| \*=========================================================================*/ |  | ||||||
| /*-------------------------------------------------------------------------*\ |  | ||||||
| * Wraps a tcp object into an SSL object |  | ||||||
| \*-------------------------------------------------------------------------*/ |  | ||||||
| static int global_wrap(lua_State *L) { |  | ||||||
|     p_tcp tcp = (p_tcp) aux_checkclass(L, "tcp{client}", 1); |  | ||||||
|     /* change class of tcp object */ |  | ||||||
|     aux_setclass(L, "ssl{owned}", 1); |  | ||||||
|     /* create wrapper */ |  | ||||||
|     p_wrap wrap = (p_wrap) lua_newuserdata(L, sizeof(t_wrap)); |  | ||||||
|     /* lock reference */ |  | ||||||
|     lua_pushvalue(L, 1); |  | ||||||
|     wrap->ref = lua_ref(L, 1); |  | ||||||
|     /* initialize wrapper */ |  | ||||||
|     wrap->tcp = tcp; |  | ||||||
|     io_init(&tcp->io, wrap_send, wrap_recv, wrap); |  | ||||||
|     return 1; |  | ||||||
| } |  | ||||||
							
								
								
									
										29
									
								
								src/ssl.h
									
									
									
									
									
								
							
							
						
						
									
										29
									
								
								src/ssl.h
									
									
									
									
									
								
							| @@ -1,29 +0,0 @@ | |||||||
| #ifndef SSL_H |  | ||||||
| #define SSL_H |  | ||||||
| /*=========================================================================*\ |  | ||||||
| * Simple client SSL support |  | ||||||
| * LuaSocket toolkit |  | ||||||
| * |  | ||||||
| * This is just a simple example to show how to extend LuaSocket |  | ||||||
| * |  | ||||||
| * RCS ID: $Id$ |  | ||||||
| \*=========================================================================*/ |  | ||||||
| #include <lua.h> |  | ||||||
| #include <openssl/ssl.h> |  | ||||||
|  |  | ||||||
| #include "buffer.h" |  | ||||||
| #include "timeout.h" |  | ||||||
| #include "socket.h" |  | ||||||
| #include "tcp.h" |  | ||||||
|  |  | ||||||
| typedef struct t_wrap_ { |  | ||||||
|     p_tcp tcp; |  | ||||||
|     SSL* ssl; |  | ||||||
|     int ref; |  | ||||||
| } t_wrap; |  | ||||||
|  |  | ||||||
| typedef t_wrap *p_wrap; |  | ||||||
|  |  | ||||||
| int ssl_open(lua_State *L); |  | ||||||
|  |  | ||||||
| #endif /* SSL_H */ |  | ||||||
| @@ -13,6 +13,7 @@ local string = require("string") | |||||||
| local socket = require("socket") | local socket = require("socket") | ||||||
| local ltn12 = require("ltn12") | local ltn12 = require("ltn12") | ||||||
| module("socket.tp") | module("socket.tp") | ||||||
|  | getmetatable(_M).__index = nil | ||||||
|  |  | ||||||
| ----------------------------------------------------------------------------- | ----------------------------------------------------------------------------- | ||||||
| -- Program constants | -- Program constants | ||||||
| @@ -98,7 +99,8 @@ end | |||||||
|  |  | ||||||
| function metat.__index:source(source, step) | function metat.__index:source(source, step) | ||||||
|     local sink = socket.sink("keep-open", self.c) |     local sink = socket.sink("keep-open", self.c) | ||||||
|     return ltn12.pump.all(source, sink, step or ltn12.pump.step) |     local ret, err = ltn12.pump.all(source, sink, step or ltn12.pump.step) | ||||||
|  |     return ret, err | ||||||
| end | end | ||||||
|  |  | ||||||
| -- closes the underlying c | -- closes the underlying c | ||||||
| @@ -108,8 +110,8 @@ function metat.__index:close() | |||||||
| end | end | ||||||
|  |  | ||||||
| -- connect with server and return c object | -- connect with server and return c object | ||||||
| function connect(host, port, timeout) | function connect(host, port, create, timeout) | ||||||
|     local c, e = socket.tcp() |     local c, e = (create or socket.tcp()) | ||||||
|     if not c then return nil, e end |     if not c then return nil, e end | ||||||
|     c:settimeout(timeout or TIMEOUT) |     c:settimeout(timeout or TIMEOUT) | ||||||
|     local r, e = c:connect(host, port) |     local r, e = c:connect(host, port) | ||||||
| @@ -120,4 +122,3 @@ function connect(host, port, timeout) | |||||||
|     return base.setmetatable({c = c}, metat) |     return base.setmetatable({c = c}, metat) | ||||||
| end | end | ||||||
|  |  | ||||||
| --getmetatable(_M).__index = nil |  | ||||||
|   | |||||||
| @@ -12,6 +12,7 @@ local string = require("string") | |||||||
| local base = _G | local base = _G | ||||||
| local table = require("table") | local table = require("table") | ||||||
| module("socket.url") | module("socket.url") | ||||||
|  | getmetatable(_M).__index = nil | ||||||
|  |  | ||||||
| ----------------------------------------------------------------------------- | ----------------------------------------------------------------------------- | ||||||
| -- Encodes a string into its escaped hexadecimal representation | -- Encodes a string into its escaped hexadecimal representation | ||||||
| @@ -279,4 +280,3 @@ function build_path(parsed, unsafe) | |||||||
| 	return path | 	return path | ||||||
| end | end | ||||||
|  |  | ||||||
| --getmetatable(_M).__index = nil |  | ||||||
|   | |||||||
| @@ -74,7 +74,10 @@ int sock_select(int n, fd_set *rfds, fd_set *wfds, fd_set *efds, p_tm tm) { | |||||||
|     double t = tm_get(tm); |     double t = tm_get(tm); | ||||||
|     tv.tv_sec = (int) t; |     tv.tv_sec = (int) t; | ||||||
|     tv.tv_usec = (int) ((t - tv.tv_sec) * 1.0e6); |     tv.tv_usec = (int) ((t - tv.tv_sec) * 1.0e6); | ||||||
|     return select(0, rfds, wfds, efds, t >= 0.0? &tv: NULL); |     if (n <= 0) { | ||||||
|  |         Sleep(1000*t); | ||||||
|  |         return 0; | ||||||
|  |     } else return select(0, rfds, wfds, efds, t >= 0.0? &tv: NULL); | ||||||
| } | } | ||||||
|  |  | ||||||
| /*-------------------------------------------------------------------------*\ | /*-------------------------------------------------------------------------*\ | ||||||
|   | |||||||
| @@ -48,18 +48,19 @@ source = smtp.message{ | |||||||
|   } |   } | ||||||
| } | } | ||||||
|  |  | ||||||
| --[[ | function filter(s) | ||||||
| sink = ltn12.sink.file(io.stdout) |     if s then io.write(s) end | ||||||
| ltn12.pump.all(source, sink) |     return s | ||||||
| ]] | end | ||||||
|  |  | ||||||
| -- finally send it |  | ||||||
| r, e = smtp.send{ | r, e = smtp.send{ | ||||||
|     rcpt = {"<diego@tecgraf.puc-rio.br>", |     rcpt = {"<diego@tecgraf.puc-rio.br>", | ||||||
|             "<diego@princeton.edu>" }, |             "<diego@princeton.edu>" }, | ||||||
|     from = "<diego@princeton.edu>", |     from = "<diego@princeton.edu>", | ||||||
|     source = source, |     source = ltn12.source.chain(source, filter), | ||||||
|     server = "mail.cs.princeton.edu" |     --server = "mail.cs.princeton.edu" | ||||||
|  |     server = "localhost", | ||||||
|  |     port = 2525 | ||||||
| } | } | ||||||
|  |  | ||||||
| print(r, e) | print(r, e) | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user