在线时间:8:00-16:00
迪恩网络APP
随时随地掌握行业动态
扫描二维码
关注迪恩网络微信公众号
开源软件名称(OpenSource Name):Heerozh/LuaAsio开源软件地址(OpenSource Url):https://github.com/Heerozh/LuaAsio开源编程语言(OpenSource Language):Lua 52.9%开源软件介绍(OpenSource Introduction):LuaAsioSimple transparent non-blocking, high concurrency I/O for LuaJIT. Only 600+ lines. There are no callbacks, Asynchronous happens when you perform a non-blocking operation. Lightweight, low resource usage, available for embedded devices. Based on Tested on windows, ubuntu, openwrt. UsageServer side: local asio = require 'asio'
function connection_th(con)
-- Issues a synchronous, but non-blocking I/O operation.
local data = con:read(5)
-- Still non-blocking
con:write(data .. '-pong')
con:close()
end
local s = asio.server('127.0.0.1', 1234, function(con)
-- light threads running asynchronously at various I/O operation.
asio.spawn_light_thread(connection_th, con)
end)
-- This event loop is blocked during code execution
asio.run() Client side: local asio = require 'asio'
local ping_send = function(text)
local con = asio.connect('localhost', '1234')
con:write(text)
con:read(10)
con:close()
end
asio.spawn_light_thread(ping_send, 'ping1')
asio.spawn_light_thread(ping_send, 'ping2')
asio.run() Light Thread & non-blockingYour code needs to execute in Light Thread, actually Light Threads are Lua coroutine that all running in one thread, so you don't have to worry about context switching overhead and race conditions. When goes to a non-blocking operation, the current Light Thread will wait for completion (block), and then it switches to the other available Light Thread to continue execution, or handle new connection. If you want to use multithreading, Client side can be simply achieved by multiple Lua State (use like torch/threads); Server side not supported yet, but easy to implement by Lua State pool. Although because non-blocking, there is high concurrency even in a single thread. Example: Real CaseFull duplex Transparent Proxy for RouterBig effect, so simple! Client/Router: -- you should replace the following with aes_256_cfb8 by require "resty.aes"
local bit = require 'bit'
local function xor_str(str, key)
local rtn = table.new(#str, 0)
for i = 1, #str do
rtn[#rtn + 1] = string.char( bit.bxor(string.byte(str, i), key) )
end
return table.concat( rtn )
end
function forward(from_con, to_con)
while true do
local data, rerr, werr, _
data, rerr = from_con:read_some()
if data and #data > 0 then
_, werr = to_con:write(xor_str(data, 0x79))
end
if rerr or werr then break end
end
from_con:close()
to_con:close()
end
local asio = require 'asio'
function connection_th(upstream)
local dest_addr = upstream:get_original_dst()
local proxy = asio.connect(remote_host, remote_port)
if not proxy then return end
local ok = proxy:write(xor_str(dest_addr, 0x79))
if not ok then return end
asio.spawn_light_thread(forward, proxy, upstream)
asio.spawn_light_thread(forward, upstream, proxy)
end
local s = asio.server('0.0.0.0', local_port, function(upstream)
asio.spawn_light_thread(connection_th, upstream)
end)
asio.run() Server: local asio = require 'asio'
function connection_th(upstream)
local dest_addr = upstream:read(128)
if not dest_addr then return end
local downstream = asio.connect(xor_str(dest_addr, 0x79))
if not downstream then return end
asio.spawn_light_thread(forward, downstream, upstream)
asio.spawn_light_thread(forward, upstream, downstream)
end
local s = asio.server(listen_host, listen_port, function(upstream)
asio.spawn_light_thread(connection_th, upstream)
end)
asio.run() Finally, you need to use BuildingWindows
Linux
ARM Cross Compile
Unit Test
Referenceholder = asio.server(ip, point, accept_handler) Listening port starts accepting connections.
Server are automatically closed when the return value conn, err_msg = asio.connect(host, port, resolve_v6=false) Connect to the host port. This is a non-blocking operation. Resolve host name is not a non-blocking operation yet, So use IP address. If there are no errors, return conn, err_msg = asio.connect(sockaddr_storage) Same as asio.sleep(sec) Suspends the execution of the current light thread until the duration have elapse. This is a non-blocking operation. data, err_msg = conn:read(size) Read binary data of a specified size. This is a non-blocking operation. If there are no errors, return data, err_msg = conn:read_some() Read binary data until one or more bytes. This is a non-blocking operation. If there are no errors, return ok, err_msg = conn:write(data) Write the data(lua str) to connection. This is a non-blocking operation. If there are no errors, return nil = conn:close() Close a connection. No returns. asio.spawn_light_thread(function, arg1, arg2, ...) Create and run a light thread. LicenseLuaAsio is available under the MIT license. Copyright (C) 2018, by Jianhao Zhang (Heerozh) ([email protected]), All rights reserved. |
2023-10-27
2022-08-15
2022-08-17
2022-09-23
2022-08-13
请发表评论