|
发表于 2018-4-16 17:07:05
|
显示全部楼层
本帖最后由 dr2001 于 2018-4-16 17:10 编辑
端口转发数据本身非常简单,代码没几行。问题是配对之类的。
如果你会nim,端口转发的非常简单的代码:
- # buffer size for data forward.
- const buf_size = 2048
- import os, ospaths, strutils, parsecfg
- import asyncdispatch, asyncnet
- type
- Args_t = ref object
- port_local : uint16
- Serv_t = ref object
- serv : AsyncSocket # for server listen proxy.
- proc async_data_forward(src: AsyncSocket, dst: AsyncSocket, dir: string) {.async.} =
- ## forward data, return when socket closed.
- ## - socket closed -> src.recvInto return length 0 :OR: recv/send raise an exception.
- var buf : array[1 .. buf_size, uint8]
- while true:
- try:
- let rx_len = await src.recvInto(buf.addr, buf_size)
- if rx_len == 0:
- break
- await dst.send(buf.addr, rx_len)
- except:
- break
- proc async_server(s: Serv_t) {.async.} =
- while true:
- # wait connections.
- let proxy = await s.serv.accept()
- let debug = await s.serv.accept()
- # forward data, await completes if any forward thread completes.
- var x = async_data_forward(proxy, debug, "server: proxy -> debug: ")
- var y = async_data_forward(debug, proxy, "server: debug -> proxy: ")
- await x or y
- # close connection.
- proxy.close()
- debug.close()
- proc role_server(a: Args_t) =
- var s = new(Serv_t)
- s.serv = newAsyncSocket(buffered=false)
- # server: bind and listen
- try:
- s.serv.setSockOpt(OptReuseAddr, true)
- s.serv.bindAddr(Port(a.port_local))
- s.serv.listen()
- except:
- s.serv.close()
- return
- # poll dispatcher until completed.
- waitFor async_server(s)
- proc main() =
- # extract argument/settings
- var arg = new(Args_t)
- arg.port_local = 2189
- role_server(arg)
- when isMainModule:
- main()
复制代码
用C之类的写这种东西略麻烦,因为两个socket要poll。
带有比较好的多线程/异步库的高级语言就会省事儿的多,而且Linux/Windows通吃,比如Go,Rust,Nim,Python,etc。 |
|