util-soc-imp-socket.lua /size: 4905 b    last modification: 2020-07-01 14:35
1
-- original file : socket.lua
2
-- for more into : see util-soc.lua
3 4
local
type
,
tostring
,
setmetatable
=
type
,
tostring
,
setmetatable
5
local
min
=
math
.
min
6
local
format
=
string
.
format
7 8
local
socket
=
socket
or
package
.
loaded
.
socket
or
require
(
"
socket.core
"
)
9 10
local
connect
=
socket
.
connect
11
local
tcp4
=
socket
.
tcp4
12
local
tcp6
=
socket
.
tcp6
13
local
getaddrinfo
=
socket
.
dns
.
getaddrinfo
14 15
local
defaulthost
=
"
0.0.0.0
"
16 17
local
function
report
(
fmt
,
first
,
...
)
18
if
logs
then
19
report
=
logs
and
logs
.
reporter
(
"
socket
"
)
20
report
(
fmt
,
first
,
...
)
21
elseif
fmt
then
22
fmt
=
"
socket:
"
.
.
fmt
23
if
first
then
24
print
(
format
(
fmt
,
first
,
...
)
)
25
else
26
print
(
fmt
)
27
end
28
end
29
end
30 31
socket
.
report
=
report
32 33
function
socket
.
connect4
(
address
,
port
,
laddress
,
lport
)
34
return
connect
(
address
,
port
,
laddress
,
lport
,
"
inet
"
)
35
end
36 37
function
socket
.
connect6
(
address
,
port
,
laddress
,
lport
)
38
return
connect
(
address
,
port
,
laddress
,
lport
,
"
inet6
"
)
39
end
40 41
function
socket
.
bind
(
host
,
port
,
backlog
)
42
if
host
=
=
"
*
"
or
host
=
=
"
"
then
43
host
=
defaulthost
44
end
45
local
addrinfo
,
err
=
getaddrinfo
(
host
)
46
if
not
addrinfo
then
47
return
nil
,
err
48
end
49
for
i
=
1
,
#
addrinfo
do
50
local
alt
=
addrinfo
[
i
]
51
local
sock
,
err
=
(
alt
.
family
=
=
"
inet
"
and
tcp4
or
tcp6
)
(
)
52
if
not
sock
then
53
return
nil
,
err
or
"
unknown error
"
54
end
55
sock
:
setoption
(
"
reuseaddr
"
,
true
)
56
local
res
,
err
=
sock
:
bind
(
alt
.
addr
,
port
)
57
if
res
then
58
res
,
err
=
sock
:
listen
(
backlog
)
59
if
res
then
60
return
sock
61
else
62
sock
:
close
(
)
63
end
64
else
65
sock
:
close
(
)
66
end
67
end
68
return
nil
,
"
invalid address
"
69
end
70 71
socket
.
try
=
socket
.
newtry
(
)
72 73
function
socket
.
choose
(
list
)
74
return
function
(
name
,
opt1
,
opt2
)
75
if
type
(
name
)
~
=
"
string
"
then
76
name
,
opt1
,
opt2
=
"
default
"
,
name
,
opt1
77
end
78
local
f
=
list
[
name
or
"
nil
"
]
79
if
f
then
80
return
f
(
opt1
,
opt2
)
81
else
82
report
(
"
error: unknown key '%s'
"
,
tostring
(
name
)
)
83
end
84
end
85
end
86 87
local
sourcet
=
{
}
88
local
sinkt
=
{
}
89 90
socket
.
sourcet
=
sourcet
91
socket
.
sinkt
=
sinkt
92 93
socket
.
BLOCKSIZE
=
2048
94 95
sinkt
[
"
close-when-done
"
]
=
function
(
sock
)
96
return
setmetatable
(
97
{
98
getfd
=
function
(
)
return
sock
:
getfd
(
)
end
,
99
dirty
=
function
(
)
return
sock
:
dirty
(
)
end
,
100
}
,
101
{
102
__call
=
function
(
self
,
chunk
,
err
)
103
if
chunk
then
104
return
sock
:
send
(
chunk
)
105
else
106
sock
:
close
(
)
107
return
1
-- why 1
108
end
109
end
110
}
111
)
112
end
113 114
sinkt
[
"
keep-open
"
]
=
function
(
sock
)
115
return
setmetatable
(
116
{
117
getfd
=
function
(
)
return
sock
:
getfd
(
)
end
,
118
dirty
=
function
(
)
return
sock
:
dirty
(
)
end
,
119
}
,
{
120
__call
=
function
(
self
,
chunk
,
err
)
121
if
chunk
then
122
return
sock
:
send
(
chunk
)
123
else
124
return
1
-- why 1
125
end
126
end
127
}
128
)
129
end
130 131
sinkt
[
"
default
"
]
=
sinkt
[
"
keep-open
"
]
132 133
socket
.
sink
=
socket
.
choose
(
sinkt
)
134 135
sourcet
[
"
by-length
"
]
=
function
(
sock
,
length
)
136
local
blocksize
=
socket
.
BLOCKSIZE
137
return
setmetatable
(
138
{
139
getfd
=
function
(
)
return
sock
:
getfd
(
)
end
,
140
dirty
=
function
(
)
return
sock
:
dirty
(
)
end
,
141
}
,
142
{
143
__call
=
function
(
)
144
if
length
<
=
0
then
145
return
nil
146
end
147
local
chunk
,
err
=
sock
:
receive
(
min
(
blocksize
,
length
)
)
148
if
err
then
149
return
nil
,
err
150
end
151
length
=
length
-
#
chunk
152
return
chunk
153
end
154
}
155
)
156
end
157 158
sourcet
[
"
until-closed
"
]
=
function
(
sock
)
159
local
blocksize
=
socket
.
BLOCKSIZE
160
local
done
=
false
161
return
setmetatable
(
162
{
163
getfd
=
function
(
)
return
sock
:
getfd
(
)
end
,
164
dirty
=
function
(
)
return
sock
:
dirty
(
)
end
,
165
}
,
{
166
__call
=
function
(
)
167
if
done
then
168
return
nil
169
end
170
local
chunk
,
status
,
partial
=
sock
:
receive
(
blocksize
)
171
if
not
status
then
172
return
chunk
173
elseif
status
=
=
"
closed
"
then
174
sock
:
close
(
)
175
done
=
true
176
return
partial
177
else
178
return
nil
,
status
179
end
180
end
181
}
182
)
183
end
184 185
sourcet
[
"
default
"
]
=
sourcet
[
"
until-closed
"
]
186 187
socket
.
source
=
socket
.
choose
(
sourcet
)
188 189
_G
.
socket
=
socket
-- for now global
190 191
package
.
loaded
[
"
socket
"
]
=
socket
192 193
return
socket
194