diff --git a/proxy/vmess/encoding/commands.go b/proxy/vmess/encoding/commands.go index f1f228f06..ff3ef2f03 100644 --- a/proxy/vmess/encoding/commands.go +++ b/proxy/vmess/encoding/commands.go @@ -139,7 +139,7 @@ func (f *CommandSwitchAccountFactory) Unmarshal(data []byte) (interface{}, error } cmd.Level = uint32(data[levelStart]) timeStart := levelStart + 1 - if len(data) < timeStart { + if len(data) < timeStart+1 { return nil, newError("insufficient length.") } cmd.ValidMin = data[timeStart] diff --git a/proxy/vmess/encoding/commands_test.go b/proxy/vmess/encoding/commands_test.go index f22a24777..4c85bfcb5 100644 --- a/proxy/vmess/encoding/commands_test.go +++ b/proxy/vmess/encoding/commands_test.go @@ -1,6 +1,7 @@ package encoding_test import ( + "github.com/stretchr/testify/assert" "testing" "github.com/google/go-cmp/cmp" @@ -35,3 +36,23 @@ func TestSwitchAccount(t *testing.T) { t.Error(r) } } + +func TestSwitchAccountBugOffByOne(t *testing.T) { + sa := &protocol.CommandSwitchAccount{ + Port: 1234, + ID: uuid.New(), + AlterIds: 1024, + Level: 128, + ValidMin: 16, + } + + buffer := buf.New() + csaf := CommandSwitchAccountFactory{} + common.Must(csaf.Marshal(sa, buffer)) + + Payload := buffer.Bytes() + + cmd, err := csaf.Unmarshal(Payload[:len(Payload)-1]) + assert.Error(t, err) + assert.Nil(t, cmd) +}