diff --git a/doc/idea/idea-set-up.md b/doc/idea/idea-set-up.md index 713477f1..94878700 100644 --- a/doc/idea/idea-set-up.md +++ b/doc/idea/idea-set-up.md @@ -141,7 +141,7 @@ Line separator,Unix and MacOs (\n) */ ``` -- 版权信息设置:Editor->Copyright->Copyright Profiles +- 版权信息设置:Editor->Copyright->Copyright Profiles,注意下面的版权信息不要有多余的换行 ``` Copyright (C) 2020 The zfoo Authors diff --git a/protocol/src/test/go/buffer/ByteBuffer.go b/protocol/src/test/go/buffer/ByteBuffer.go new file mode 100644 index 00000000..d9e3517c --- /dev/null +++ b/protocol/src/test/go/buffer/ByteBuffer.go @@ -0,0 +1,418 @@ +package protocol + +import ( + "bytes" + "encoding/binary" + "fmt" + "math" +) + +const initSize int = 128 +const maxSize int = 655537 + +var initArray []byte = make([]byte, initSize, initSize) + +type ByteBuffer struct { + buffer []byte + writeIndex int + readIndex int +} + +// -------------------------------------------------get/set------------------------------------------------- +func (byteBuffer *ByteBuffer) WriteOffset() int { + return byteBuffer.writeIndex +} + +func (byteBuffer *ByteBuffer) SetWriteOffset(writeIndex int) { + if writeIndex > len(byteBuffer.buffer) { + var error = fmt.Sprintf("writeIndex:[{%d}] out of bounds exception: readerIndex:[{%d}] , writerIndex:[{%d}] (expected: 0 <= readerIndex <= writerIndex <= capacity:[{%d}])", writeIndex, byteBuffer.readIndex, byteBuffer.writeIndex, len(byteBuffer.buffer)) + panic(error) + } + byteBuffer.writeIndex = writeIndex +} + +func (byteBuffer *ByteBuffer) SetReadOffset(readIndex int) { + if readIndex > byteBuffer.writeIndex { + var error = fmt.Sprintf("readIndex:[{%d}] out of bounds exception: readerIndex:[{%d}] , writerIndex:[{%d}] (expected: 0 <= readerIndex <= writerIndex <= capacity:[{%d}])", readIndex, byteBuffer.readIndex, byteBuffer.writeIndex, len(byteBuffer.buffer)) + panic(error) + } + byteBuffer.readIndex = readIndex +} + +func (byteBuffer *ByteBuffer) ToBytes() []byte { + return byteBuffer.buffer[0:byteBuffer.writeIndex] +} + +func (byteBuffer *ByteBuffer) ToString() string { + return fmt.Sprintf("writeIndex:[{%d}], readIndex:[{%d}], len:[{%d}], cap:[{%d}]", byteBuffer.writeIndex, byteBuffer.readIndex, len(byteBuffer.buffer), cap(byteBuffer.buffer)) +} + +func (byteBuffer *ByteBuffer) GetCapacity() int { + return len(byteBuffer.buffer) - byteBuffer.writeIndex +} + +func (byteBuffer *ByteBuffer) EnsureCapacity(capacity int) { + for { + if byteBuffer.GetCapacity() > capacity { + break + } + + byteBuffer.buffer = append(byteBuffer.buffer, initArray...) + + if len(byteBuffer.buffer) > maxSize { + panic("Bytebuf max size is [655537], out of memory error") + } + } +} + +// -------------------------------------------------write/read------------------------------------------------- + +// 整形转换成字节 +func IntToBytes(n int) []byte { + var x = int32(n) + bytesBuffer := bytes.NewBuffer([]byte{}) + binary.Write(bytesBuffer, binary.BigEndian, x) + return bytesBuffer.Bytes() +} + +// 字节转换成整形 +func BytesToInt(b []byte) int { + bytesBuffer := bytes.NewBuffer(b) + var x int32 + binary.Read(bytesBuffer, binary.BigEndian, &x) + return int(x) +} + +func (byteBuffer *ByteBuffer) WriteBool(value bool) { + byteBuffer.EnsureCapacity(1) + if value { + byteBuffer.buffer[byteBuffer.writeIndex] = 1 + } else { + byteBuffer.buffer[byteBuffer.writeIndex] = 0 + } + byteBuffer.writeIndex++ +} + +func (byteBuffer *ByteBuffer) ReadBool() bool { + var byteValue = byteBuffer.buffer[byteBuffer.readIndex] + byteBuffer.readIndex++ + return byteValue == 1 +} + +func (byteBuffer *ByteBuffer) WriteByte(value int8) { + byteBuffer.EnsureCapacity(1) + byteBuffer.buffer[byteBuffer.writeIndex] = byte(value) + byteBuffer.writeIndex++ +} + +func (byteBuffer *ByteBuffer) ReadByte() int8 { + var byteValue = byteBuffer.buffer[byteBuffer.readIndex] + byteBuffer.readIndex++ + return int8(byteValue) +} + +func (byteBuffer *ByteBuffer) WriteUByte(value byte) { + byteBuffer.EnsureCapacity(1) + byteBuffer.buffer[byteBuffer.writeIndex] = value + byteBuffer.writeIndex++ +} + +func (byteBuffer *ByteBuffer) ReadUByte() byte { + var byteValue = byteBuffer.buffer[byteBuffer.readIndex] + byteBuffer.readIndex++ + return byteValue +} + +func (byteBuffer *ByteBuffer) WriteUBytes(bytes []byte) { + var length = len(bytes) + byteBuffer.EnsureCapacity(length) + copy(byteBuffer.buffer[byteBuffer.writeIndex:], bytes) + byteBuffer.writeIndex += length +} + +func (byteBuffer *ByteBuffer) ReadUBytes(length int) []byte { + var readOffset = byteBuffer.readIndex + var endOffset = byteBuffer.readIndex + length + var bytes = byteBuffer.buffer[readOffset:endOffset] + byteBuffer.readIndex += length + return bytes +} + +func (byteBuffer *ByteBuffer) WriteShort(value int16) { + byteBuffer.EnsureCapacity(2) + var bytesBuffer = bytes.NewBuffer([]byte{}) + binary.Write(bytesBuffer, binary.BigEndian, value) + var byteArray = bytesBuffer.Bytes() + byteBuffer.WriteUBytes(byteArray) +} + +func (byteBuffer *ByteBuffer) ReadShort() int16 { + var byteArray = byteBuffer.ReadUBytes(2) + bytesBuffer := bytes.NewBuffer(byteArray) + var value int16 + binary.Read(bytesBuffer, binary.BigEndian, &value) + return value +} + +func (byteBuffer *ByteBuffer) WriteRawInt32(intValue int32) { + byteBuffer.WriteUByte(byte(intValue >> 24)) + byteBuffer.WriteUByte(byte(intValue >> 16)) + byteBuffer.WriteUByte(byte(intValue >> 8)) + byteBuffer.WriteUByte(byte(intValue)) +} + +func (byteBuffer *ByteBuffer) ReadRawInt32() int32 { + return int32(uint32(byteBuffer.ReadUByte())<<24 | uint32(byteBuffer.ReadUByte())<<16 | uint32(byteBuffer.ReadUByte())<<8 | uint32(byteBuffer.ReadUByte())) +} + +func (byteBuffer *ByteBuffer) WriteInt(intValue int) { + if intValue < math.MinInt32 || intValue > math.MaxInt32 { + panic("intValue must range between math.MinInt32:-2147483648 and math.MaxInt32:2147483647") + } + byteBuffer.WriteInt32(int32(intValue)) +} + +func (byteBuffer *ByteBuffer) ReadInt() int { + return int(byteBuffer.ReadInt32()) +} + +func (byteBuffer *ByteBuffer) WriteInt32(intValue int32) { + var value uint32 = uint32(((intValue << 1) ^ (intValue >> 31))) + // 右移操作>>是带符号右移 + if value>>7 == 0 { + byteBuffer.WriteUByte(byte(value)) + return + } + + if value>>14 == 0 { + byteBuffer.WriteUByte(byte(value | 0x80)) + byteBuffer.WriteUByte(byte(value >> 7)) + return + } + + if value>>21 == 0 { + byteBuffer.WriteUByte(byte(value | 0x80)) + byteBuffer.WriteUByte(byte((value >> 7) | 0x80)) + byteBuffer.WriteUByte(byte(value >> 14)) + return + } + + if value>>28 == 0 { + byteBuffer.WriteUByte(byte(value | 0x80)) + byteBuffer.WriteUByte(byte((value >> 7) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 14) | 0x80)) + byteBuffer.WriteUByte(byte(value >> 21)) + return + } + + byteBuffer.WriteUByte(byte(value | 0x80)) + byteBuffer.WriteUByte(byte((value >> 7) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 14) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 21) | 0x80)) + byteBuffer.WriteUByte(byte(value >> 28)) +} + +func (byteBuffer *ByteBuffer) ReadInt32() int32 { + var b byte = byteBuffer.ReadUByte() + var value uint32 = uint32(b & 0x7F) + if (b & 0x80) != 0 { + b = byteBuffer.ReadUByte() + value |= uint32(b&0x7F) << 7 + if (b & 0x80) != 0 { + b = byteBuffer.ReadUByte() + value |= uint32(b&0x7F) << 14 + if (b & 0x80) != 0 { + b = byteBuffer.ReadUByte() + value |= uint32(b&0x7F) << 21 + if (b & 0x80) != 0 { + b = byteBuffer.ReadUByte() + value |= uint32(b&0x7F) << 28 + } + } + } + } + + return int32(value>>1) ^ -(int32(value & 1)) +} + +func (byteBuffer *ByteBuffer) WriteLong(longValue int64) { + var value uint64 = uint64(((longValue << 1) ^ (longValue >> 63))) + + if value>>7 == 0 { + byteBuffer.WriteUByte(byte(value)) + return + } + + if value>>14 == 0 { + byteBuffer.WriteUByte(byte(value | 0x80)) + byteBuffer.WriteUByte(byte(value >> 7)) + return + } + + if value>>21 == 0 { + byteBuffer.WriteUByte(byte(value | 0x80)) + byteBuffer.WriteUByte(byte((value >> 7) | 0x80)) + byteBuffer.WriteUByte(byte(value >> 14)) + return + } + + if value>>28 == 0 { + byteBuffer.WriteUByte(byte(value | 0x80)) + byteBuffer.WriteUByte(byte((value >> 7) | 0x80)) + byteBuffer.WriteUByte(byte(value>>14) | 0x80) + byteBuffer.WriteUByte(byte(value >> 21)) + return + } + + if value>>35 == 0 { + byteBuffer.WriteUByte(byte(value | 0x80)) + byteBuffer.WriteUByte(byte((value >> 7) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 14) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 21) | 0x80)) + byteBuffer.WriteUByte(byte(value >> 28)) + return + } + + if value>>42 == 0 { + byteBuffer.WriteUByte(byte(value | 0x80)) + byteBuffer.WriteUByte(byte(value>>7) | 0x80) + byteBuffer.WriteUByte(byte((value >> 14) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 21) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 28) | 0x80)) + byteBuffer.WriteUByte(byte(value >> 35)) + return + } + + if value>>49 == 0 { + byteBuffer.WriteUByte(byte(value | 0x80)) + byteBuffer.WriteUByte(byte((value >> 7) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 14) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 21) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 28) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 35) | 0x80)) + byteBuffer.WriteUByte(byte(value >> 42)) + return + } + + if (value >> 56) == 0 { + byteBuffer.WriteUByte(byte(value | 0x80)) + byteBuffer.WriteUByte(byte((value >> 7) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 14) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 21) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 28) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 35) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 42) | 0x80)) + byteBuffer.WriteUByte(byte(value >> 49)) + return + } + + byteBuffer.WriteUByte(byte(value | 0x80)) + byteBuffer.WriteUByte(byte((value >> 7) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 14) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 21) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 28) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 35) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 42) | 0x80)) + byteBuffer.WriteUByte(byte((value >> 49) | 0x80)) + byteBuffer.WriteUByte(byte(value >> 56)) +} + +func (byteBuffer *ByteBuffer) ReadLong() int64 { + var b byte = byteBuffer.ReadUByte() + var value uint64 = uint64(b & 0x7F) + if (b & 0x80) != 0 { + b = byteBuffer.ReadUByte() + value |= uint64(b&0x7F) << 7 + if (b & 0x80) != 0 { + b = byteBuffer.ReadUByte() + value |= uint64(b&0x7F) << 14 + if (b & 0x80) != 0 { + b = byteBuffer.ReadUByte() + value |= uint64(b&0x7F) << 21 + if (b & 0x80) != 0 { + b = byteBuffer.ReadUByte() + value |= uint64(b&0x7F) << 28 + if (b & 0x80) != 0 { + b = byteBuffer.ReadUByte() + value |= uint64(b&0x7F) << 35 + if (b & 0x80) != 0 { + b = byteBuffer.ReadUByte() + value |= uint64(b&0x7F) << 42 + if (b & 0x80) != 0 { + b = byteBuffer.ReadUByte() + value |= uint64(b&0x7F) << 49 + if (b & 0x80) != 0 { + b = byteBuffer.ReadUByte() + value |= uint64(b) << 56 + } + } + } + } + } + } + } + } + + return int64(value>>1) ^ -(int64(value & 1)) +} + +func (byteBuffer *ByteBuffer) WriteFloat(value float32) { + byteBuffer.EnsureCapacity(4) + var bytesBuffer = bytes.NewBuffer([]byte{}) + binary.Write(bytesBuffer, binary.BigEndian, value) + var byteArray = bytesBuffer.Bytes() + byteBuffer.WriteUBytes(byteArray) +} + +func (byteBuffer *ByteBuffer) ReadFloat() float32 { + var byteArray = byteBuffer.ReadUBytes(4) + bytesBuffer := bytes.NewBuffer(byteArray) + var value float32 + binary.Read(bytesBuffer, binary.BigEndian, &value) + return value +} + +func (byteBuffer *ByteBuffer) WriteDouble(value float64) { + byteBuffer.EnsureCapacity(8) + var bytesBuffer = bytes.NewBuffer([]byte{}) + binary.Write(bytesBuffer, binary.BigEndian, value) + var byteArray = bytesBuffer.Bytes() + byteBuffer.WriteUBytes(byteArray) +} + +func (byteBuffer *ByteBuffer) ReadDouble() float64 { + var byteArray = byteBuffer.ReadUBytes(8) + bytesBuffer := bytes.NewBuffer(byteArray) + var value float64 + binary.Read(bytesBuffer, binary.BigEndian, &value) + return value +} + +func (byteBuffer *ByteBuffer) WriteString(value string) { + var bytes []byte = []byte(value) + var length = len(bytes) + byteBuffer.EnsureCapacity(length) + byteBuffer.WriteInt(length) + byteBuffer.WriteUBytes(bytes) +} + +func (byteBuffer *ByteBuffer) ReadString() string { + var length = byteBuffer.ReadInt() + var bytes = byteBuffer.ReadUBytes(length) + return string(bytes[:]) +} + +func (byteBuffer *ByteBuffer) WriteChar(value string) { + // 如果为空则写入一个默认的字符0 + if len(value) == 0 { + byteBuffer.WriteInt(0) + byteBuffer.WriteUByte(0) + return + } + var char = value[0:1] + byteBuffer.WriteString(char) +} + +func (byteBuffer *ByteBuffer) ReadChar() string { + return byteBuffer.ReadString() +} diff --git a/protocol/src/test/go/buffer/buffer_test.go b/protocol/src/test/go/buffer/buffer_test.go new file mode 100644 index 00000000..ca07fcf9 --- /dev/null +++ b/protocol/src/test/go/buffer/buffer_test.go @@ -0,0 +1,120 @@ +/* + * Copyright (C) 2020 The zfoo Authors + * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except + * in compliance with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed + * on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and limitations under the License. + */ + +package protocol + +import ( + "math" + "testing" +) + +func assert(flag bool) { + if !flag { + panic("exception happen") + } +} + +func TestByteBuffer(t *testing.T) { + var buffer = new(ByteBuffer) + boolTest(buffer) + byteTest(buffer) + bytesTest(buffer) + shortTest(buffer) + intTest(buffer) + longTest(buffer) + floatTest(buffer) + doubleTest(buffer) + stringTest(buffer) +} + +func boolTest(buffer *ByteBuffer) { + var value = true + buffer.WriteBool(value) + assert(buffer.ReadBool() == value) + value = false + buffer.WriteBool(value) + assert(buffer.ReadBool() == value) +} + +func byteTest(buffer *ByteBuffer) { + var byteValues = []byte{127, 0, 255} + for _, value := range byteValues { + buffer.WriteUByte(value) + assert(buffer.ReadUByte() == value) + } + + var int8Values = []int8{127, 0, -128} + for _, value := range int8Values { + buffer.WriteByte(value) + assert(buffer.ReadByte() == value) + } +} + +func bytesTest(buffer *ByteBuffer) { + var bytes = []byte{127, 0, 255} + buffer.WriteUBytes(bytes) + var readBytes = buffer.ReadUBytes(len(bytes)) + for i, value := range bytes { + assert(readBytes[i] == value) + } +} + +func shortTest(buffer *ByteBuffer) { + var shortValues = []int16{-32768, -100, -2, -1, 0, 1, 2, 100, 32767} + for _, value := range shortValues { + buffer.WriteShort(value) + var readValue = buffer.ReadShort() + assert(readValue == value) + } +} + +func intTest(buffer *ByteBuffer) { + var intValues = []int{math.MinInt32, -99999999, -32768, -100, -2, -1, 0, 1, 2, 100, 32767, 99999999, math.MaxInt32} + for _, value := range intValues { + buffer.WriteInt(value) + var readValue = buffer.ReadInt() + assert(readValue == value) + } +} + +func longTest(buffer *ByteBuffer) { + var longValues = []int64{math.MinInt64, -99999999, -32768, -100, -2, -1, 0, 1, 2, 100, 32767, 99999999, math.MaxInt64} + for _, value := range longValues { + buffer.WriteLong(value) + var readValue = buffer.ReadLong() + assert(readValue == value) + } +} + +func floatTest(buffer *ByteBuffer) { + var floatValues = []float32{-12345678.12345678, -1234.5678, -100, -2, -1, 0, 1, 2, 100, 1234.5678, math.MaxFloat32} + for _, value := range floatValues { + buffer.WriteFloat(value) + var readValue = buffer.ReadFloat() + assert(math.Abs(float64(readValue-value)) < 0.01) + } +} + +func doubleTest(buffer *ByteBuffer) { + var doubleValues = []float64{-12345678.12345678, -1234.5678, -100, -2, -1, 0, 1, 2, 100, 1234.5678, math.MaxFloat64} + for _, value := range doubleValues { + buffer.WriteDouble(value) + var readValue = buffer.ReadDouble() + assert(math.Abs(float64(readValue-value)) < 0.01) + } +} + +func stringTest(buffer *ByteBuffer) { + var value = "hello world!" + buffer.WriteString(value) + assert(buffer.ReadString() == value) +} diff --git a/protocol/src/test/go/go.mod b/protocol/src/test/go/go.mod new file mode 100644 index 00000000..076e39c5 --- /dev/null +++ b/protocol/src/test/go/go.mod @@ -0,0 +1,3 @@ +module protocol + +go 1.19