mirror of
https://github.com/e1732a364fed/v2ray_simple.git
synced 2025-09-27 13:12:07 +08:00

在标准 toml 配置中 配置 logfile 配置文件路径。 如 `logfile = "/var/log/verysimple/vs_log"` 将 -sp 的行为 改为 打印完毕后立即退出。
385 lines
6.5 KiB
Go
385 lines
6.5 KiB
Go
package netLayer
|
||
|
||
import (
|
||
"bytes"
|
||
"crypto/rand"
|
||
"io"
|
||
"net"
|
||
"strings"
|
||
"testing"
|
||
|
||
"github.com/e1732a364fed/v2ray_simple/utils"
|
||
)
|
||
|
||
/*
|
||
我们本地benchmark,实际benchmark readv 是比 经典拷贝慢的
|
||
|
||
BenchmarkReadVCopy-8 426525 2934 ns/op
|
||
BenchmarkClassicCopy-8 531406 2185 ns/op
|
||
BenchmarkClassicCopy_SimulateRealWorld-8 60873 19631 ns/op
|
||
BenchmarkClassicCopy_SimulateRealWorld_ReadV-8 66138 17907 ns/op
|
||
|
||
|
||
我们添加一种情况 SimulateRealWorld, 分10次写入, 每次写入长度均小于MTU,此时即可发现readv更快
|
||
|
||
总之这种本地benchmark 对于 readv来说意义不大,因为本地回环太快了, readv只能徒增各种附加操作.
|
||
|
||
理论上来说,在非本地测试环境下,只要每次传输的包超过了MTU,那么readv就应该是有优势的,包长度越大越有优势,因为越大越容易被割包,那么readv就越好用
|
||
*/
|
||
|
||
//我们不断向一个net.Conn 发送大数据
|
||
func TestReadVCopy(t *testing.T) {
|
||
|
||
utils.InitLog("")
|
||
|
||
listenAddr := GetRandLocalAddr(true, false)
|
||
listener, err := net.Listen("tcp", listenAddr)
|
||
if err != nil {
|
||
t.Log(err)
|
||
t.FailNow()
|
||
}
|
||
|
||
bigBytes := make([]byte, 10240) //10k
|
||
|
||
n, err := rand.Reader.Read(bigBytes)
|
||
if err != nil || n != 10240 {
|
||
t.Log(err)
|
||
t.FailNow()
|
||
}
|
||
|
||
transmitCount := 10
|
||
|
||
go func() {
|
||
conn, err := listener.Accept()
|
||
if err != nil {
|
||
//t.Log(err)
|
||
t.Fail()
|
||
return
|
||
}
|
||
|
||
for i := 0; i < transmitCount; i++ {
|
||
buf := &bytes.Buffer{}
|
||
_, err := TryCopyOnce(buf, conn)
|
||
|
||
if err != nil {
|
||
if strings.Contains(err.Error(), "close") {
|
||
t.Fail()
|
||
|
||
}
|
||
//t.Log(err)
|
||
return
|
||
}
|
||
|
||
}
|
||
|
||
}()
|
||
|
||
tcpConn, err := net.Dial("tcp", listenAddr)
|
||
if err != nil {
|
||
t.Log(err)
|
||
t.FailNow()
|
||
}
|
||
|
||
for i := 0; i < transmitCount; i++ {
|
||
_, e := tcpConn.Write(bigBytes)
|
||
if e != nil {
|
||
t.Log(err)
|
||
t.FailNow()
|
||
}
|
||
}
|
||
tcpConn.Close()
|
||
}
|
||
|
||
func BenchmarkReadVCopy(b *testing.B) {
|
||
transmitCount := b.N
|
||
|
||
listenAddr := GetRandLocalAddr(true, false)
|
||
listener, err := net.Listen("tcp", listenAddr)
|
||
if err != nil {
|
||
b.Log(err)
|
||
b.FailNow()
|
||
}
|
||
|
||
bigBytes := make([]byte, 10240) //10k
|
||
|
||
n, err := rand.Reader.Read(bigBytes)
|
||
if err != nil || n != 10240 {
|
||
b.Log(n, err)
|
||
b.FailNow()
|
||
}
|
||
|
||
go func() {
|
||
conn, err := listener.Accept()
|
||
if err != nil {
|
||
//b.Log(err)
|
||
b.Fail()
|
||
}
|
||
//buf := &bytes.Buffer{}
|
||
|
||
for i := 0; i < transmitCount; i++ {
|
||
buf := utils.GetBuf()
|
||
_, err := TryCopyOnce(buf, conn)
|
||
|
||
if err != nil {
|
||
if strings.Contains(err.Error(), "close") {
|
||
b.Fail()
|
||
|
||
}
|
||
}
|
||
utils.PutBuf(buf)
|
||
//buf.Reset()
|
||
|
||
}
|
||
|
||
}()
|
||
|
||
tcpConn, err := net.Dial("tcp", listenAddr)
|
||
if err != nil {
|
||
b.Log(err)
|
||
b.FailNow()
|
||
}
|
||
|
||
for i := 0; i < transmitCount; i++ {
|
||
_, e := tcpConn.Write(bigBytes)
|
||
if e != nil {
|
||
b.Log(err)
|
||
b.FailNow()
|
||
}
|
||
}
|
||
tcpConn.Close()
|
||
}
|
||
|
||
func BenchmarkClassicCopy(b *testing.B) {
|
||
|
||
b.StopTimer()
|
||
b.ResetTimer()
|
||
|
||
transmitCount := b.N
|
||
|
||
listenAddr := GetRandLocalAddr(true, false)
|
||
listener, err := net.Listen("tcp", listenAddr)
|
||
if err != nil {
|
||
b.Log(err)
|
||
b.FailNow()
|
||
}
|
||
|
||
const bigBytesLen = 10240
|
||
|
||
bigBytes := make([]byte, bigBytesLen) //10k
|
||
|
||
n, err := rand.Reader.Read(bigBytes)
|
||
if err != nil || n != bigBytesLen {
|
||
b.Log(n, err)
|
||
b.FailNow()
|
||
}
|
||
|
||
go func() {
|
||
conn, err := listener.Accept()
|
||
if err != nil {
|
||
//b.Log(err)
|
||
b.Fail()
|
||
}
|
||
|
||
//bs := make([]byte, bigBytesLen)
|
||
//buf := &bytes.Buffer{}
|
||
// 不能直接使用单一buf,否则对readv来说不公平,必须同样从pool中存取
|
||
|
||
for {
|
||
|
||
buf := utils.GetBuf()
|
||
//bs := utils.GetMTU()
|
||
bs := utils.GetPacket()
|
||
|
||
n, err := conn.Read(bs)
|
||
|
||
if err != nil {
|
||
if err != io.EOF && !strings.Contains(err.Error(), "close") {
|
||
b.Fail()
|
||
}
|
||
return
|
||
}
|
||
buf.Write(bs[:n])
|
||
utils.PutBuf(buf)
|
||
|
||
utils.PutPacket(bs)
|
||
//utils.PutBytes(bs)
|
||
|
||
//buf.Reset()
|
||
|
||
}
|
||
|
||
}()
|
||
|
||
tcpConn, err := net.Dial("tcp", listenAddr)
|
||
if err != nil {
|
||
b.Log(err)
|
||
b.FailNow()
|
||
}
|
||
b.StartTimer()
|
||
|
||
for i := 0; i < transmitCount; i++ {
|
||
_, e := tcpConn.Write(bigBytes)
|
||
if e != nil {
|
||
b.Log(err)
|
||
b.FailNow()
|
||
}
|
||
}
|
||
tcpConn.Close()
|
||
}
|
||
|
||
func BenchmarkClassicCopy_SimulateRealWorld(b *testing.B) {
|
||
b.StopTimer()
|
||
b.ResetTimer()
|
||
|
||
transmitCount := b.N
|
||
|
||
listenAddr := GetRandLocalAddr(true, false)
|
||
listener, err := net.Listen("tcp", listenAddr)
|
||
if err != nil {
|
||
b.Log(err)
|
||
b.FailNow()
|
||
}
|
||
|
||
const bigBytesLen = 10240
|
||
|
||
bigBytes := make([]byte, bigBytesLen) //10k
|
||
|
||
n, err := rand.Reader.Read(bigBytes)
|
||
if err != nil || n != bigBytesLen {
|
||
b.Log(err)
|
||
b.FailNow()
|
||
}
|
||
|
||
go func() {
|
||
conn, err := listener.Accept()
|
||
if err != nil {
|
||
b.Log(err)
|
||
b.Fail()
|
||
return
|
||
}
|
||
|
||
//bs := make([]byte, bigBytesLen)
|
||
|
||
for {
|
||
//bs := utils.GetMTU()
|
||
bs := utils.GetPacket()
|
||
|
||
n, err := conn.Read(bs)
|
||
|
||
if err != nil {
|
||
if err != io.EOF && !strings.Contains(err.Error(), "close") {
|
||
b.Log(err)
|
||
b.Fail()
|
||
|
||
}
|
||
return
|
||
}
|
||
buf := utils.GetBuf()
|
||
buf.Write(bs[:n])
|
||
|
||
utils.PutBuf(buf)
|
||
|
||
utils.PutPacket(bs)
|
||
|
||
//utils.PutBytes(bs)
|
||
|
||
}
|
||
|
||
}()
|
||
|
||
tcpConn, err := net.Dial("tcp", listenAddr)
|
||
if err != nil {
|
||
b.Log(err)
|
||
b.FailNow()
|
||
}
|
||
|
||
b.StartTimer()
|
||
|
||
for i := 0; i < transmitCount; i++ {
|
||
unit := bigBytesLen / 10
|
||
|
||
for cursor := 0; cursor < bigBytesLen; cursor += unit {
|
||
_, e := tcpConn.Write(bigBytes[cursor : cursor+unit])
|
||
if e != nil {
|
||
b.Log(err)
|
||
b.FailNow()
|
||
}
|
||
}
|
||
|
||
}
|
||
tcpConn.Close()
|
||
}
|
||
|
||
func BenchmarkClassicCopy_SimulateRealWorld_ReadV(b *testing.B) {
|
||
b.StopTimer()
|
||
b.ResetTimer()
|
||
|
||
transmitCount := b.N
|
||
|
||
listenAddr := GetRandLocalAddr(true, false)
|
||
listener, err := net.Listen("tcp", listenAddr)
|
||
if err != nil {
|
||
b.Log(err)
|
||
b.FailNow()
|
||
}
|
||
|
||
const bigBytesLen = 10240
|
||
|
||
bigBytes := make([]byte, bigBytesLen) //10k
|
||
|
||
n, err := rand.Reader.Read(bigBytes)
|
||
if err != nil || n != bigBytesLen {
|
||
b.Log(err)
|
||
b.FailNow()
|
||
}
|
||
|
||
go func() {
|
||
conn, err := listener.Accept()
|
||
if err != nil {
|
||
b.Log(err)
|
||
b.Fail()
|
||
return
|
||
}
|
||
|
||
for {
|
||
|
||
//buf := &bytes.Buffer{}
|
||
buf := utils.GetBuf()
|
||
_, err := TryCopyOnce(buf, conn)
|
||
|
||
if err != nil {
|
||
if err != io.EOF && strings.Contains(err.Error(), "close") {
|
||
b.Fail()
|
||
|
||
}
|
||
return
|
||
}
|
||
utils.PutBuf(buf)
|
||
|
||
}
|
||
|
||
}()
|
||
|
||
tcpConn, err := net.Dial("tcp", listenAddr)
|
||
if err != nil {
|
||
b.Log(err)
|
||
b.FailNow()
|
||
}
|
||
unit := bigBytesLen / 10
|
||
|
||
b.StartTimer()
|
||
|
||
for i := 0; i < transmitCount; i++ {
|
||
|
||
for cursor := 0; cursor < bigBytesLen; cursor += unit {
|
||
_, e := tcpConn.Write(bigBytes[cursor : cursor+unit])
|
||
if e != nil {
|
||
b.Log(err)
|
||
b.FailNow()
|
||
}
|
||
}
|
||
|
||
}
|
||
tcpConn.Close()
|
||
}
|