whisper: FilterID fixed

This commit is contained in:
Vlad 2016-11-25 17:20:10 +01:00
parent aa925b6384
commit cd70abb5c5
8 changed files with 68 additions and 104 deletions

View file

@ -149,9 +149,9 @@ func (api *PublicWhisperAPI) DeleteSymKey(name string) error {
// NewWhisperFilter creates and registers a new message filter to watch for inbound whisper messages.
// Returns the ID of the newly created Filter.
func (api *PublicWhisperAPI) NewFilter(args WhisperFilterArgs) (*rpc.HexNumber, error) {
func (api *PublicWhisperAPI) NewFilter(args WhisperFilterArgs) (uint32, error) {
if api.whisper == nil {
return nil, whisperOffLineErr
return 0, whisperOffLineErr
}
filter := whisperv5.Filter{
@ -173,25 +173,25 @@ func (api *PublicWhisperAPI) NewFilter(args WhisperFilterArgs) (*rpc.HexNumber,
if len(args.Topics) == 0 {
info := "NewFilter: at least one topic must be specified"
glog.V(logger.Error).Infof(info)
return nil, errors.New(info)
return 0, errors.New(info)
}
if len(args.KeyName) != 0 && len(filter.KeySym) == 0 {
info := "NewFilter: key was not found by name: " + args.KeyName
glog.V(logger.Error).Infof(info)
return nil, errors.New(info)
return 0, errors.New(info)
}
if len(args.To) == 0 && len(filter.KeySym) == 0 {
info := "NewFilter: filter must contain either symmetric or asymmetric key"
glog.V(logger.Error).Infof(info)
return nil, errors.New(info)
return 0, errors.New(info)
}
if len(args.To) != 0 && len(filter.KeySym) != 0 {
info := "NewFilter: filter must not contain both symmetric and asymmetric key"
glog.V(logger.Error).Infof(info)
return nil, errors.New(info)
return 0, errors.New(info)
}
if len(args.To) > 0 {
@ -199,13 +199,13 @@ func (api *PublicWhisperAPI) NewFilter(args WhisperFilterArgs) (*rpc.HexNumber,
if !whisperv5.ValidatePublicKey(dst) {
info := "NewFilter: Invalid 'To' address"
glog.V(logger.Error).Infof(info)
return nil, errors.New(info)
return 0, errors.New(info)
}
filter.KeyAsym = api.whisper.GetIdentity(string(args.To))
if filter.KeyAsym == nil {
info := "NewFilter: non-existent identity provided"
glog.V(logger.Error).Infof(info)
return nil, errors.New(info)
return 0, errors.New(info)
}
}
@ -213,22 +213,22 @@ func (api *PublicWhisperAPI) NewFilter(args WhisperFilterArgs) (*rpc.HexNumber,
if !whisperv5.ValidatePublicKey(filter.Src) {
info := "NewFilter: Invalid 'From' address"
glog.V(logger.Error).Infof(info)
return nil, errors.New(info)
return 0, errors.New(info)
}
}
id := api.whisper.Watch(&filter)
return rpc.NewHexNumber(id), nil
return id, nil
}
// UninstallFilter disables and removes an existing filter.
func (api *PublicWhisperAPI) UninstallFilter(filterId rpc.HexNumber) {
api.whisper.Unwatch(filterId.Int())
func (api *PublicWhisperAPI) UninstallFilter(filterId uint32) {
api.whisper.Unwatch(filterId)
}
// GetFilterChanges retrieves all the new messages matched by a filter since the last retrieval.
func (api *PublicWhisperAPI) GetFilterChanges(filterId rpc.HexNumber) []WhisperMessage {
f := api.whisper.GetFilter(filterId.Int())
func (api *PublicWhisperAPI) GetFilterChanges(filterId uint32) []WhisperMessage {
f := api.whisper.GetFilter(filterId)
if f != nil {
newMail := f.Retrieve()
return toWhisperMessages(newMail)
@ -237,8 +237,8 @@ func (api *PublicWhisperAPI) GetFilterChanges(filterId rpc.HexNumber) []WhisperM
}
// GetMessages retrieves all the known messages that match a specific filter.
func (api *PublicWhisperAPI) GetMessages(filterId rpc.HexNumber) []WhisperMessage {
all := api.whisper.Messages(filterId.Int())
func (api *PublicWhisperAPI) GetMessages(filterId uint32) []WhisperMessage {
all := api.whisper.Messages(filterId)
return toWhisperMessages(all)
}
@ -284,7 +284,7 @@ func (api *PublicWhisperAPI) Post(args PostArgs) error {
}
filter := api.whisper.GetFilter(args.FilterID)
if filter == nil && args.FilterID > -1 {
if filter == nil && args.FilterID > 0 {
info := fmt.Sprintf("Post: wrong filter id %d", args.FilterID)
glog.V(logger.Error).Infof(info)
return errors.New(info)
@ -367,58 +367,19 @@ func (api *PublicWhisperAPI) Post(args PostArgs) error {
}
type PostArgs struct {
TTL uint32
From string
To string
KeyName string
Topic whisperv5.TopicType
Padding rpc.HexBytes
Payload rpc.HexBytes
WorkTime uint32
PoW float64
FilterID int
PeerID rpc.HexBytes
}
func (args *PostArgs) UnmarshalJSON(data []byte) (err error) {
var obj struct {
TTL uint32 `json:"ttl"`
From string `json:"from"`
To string `json:"to"`
KeyName string `json:"keyname"`
Topic whisperv5.TopicType `json:"topic"`
Payload rpc.HexBytes `json:"payload"`
Padding rpc.HexBytes `json:"padding"`
Payload rpc.HexBytes `json:"payload"`
WorkTime uint32 `json:"worktime"`
PoW float64 `json:"pow"`
FilterID rpc.HexBytes `json:"filterID"`
FilterID uint32 `json:"filterID"`
PeerID rpc.HexBytes `json:"peerID"`
}
if err := json.Unmarshal(data, &obj); err != nil {
return err
}
args.TTL = obj.TTL
args.From = obj.From
args.To = obj.To
args.KeyName = obj.KeyName
args.Topic = obj.Topic
args.Payload = obj.Payload
args.Padding = obj.Padding
args.WorkTime = obj.WorkTime
args.PoW = obj.PoW
args.FilterID = -1
args.PeerID = obj.PeerID
if obj.FilterID != nil {
x := whisperv5.BytesToIntBigEndian(obj.FilterID)
args.FilterID = int(x)
}
return nil
}
type WhisperFilterArgs struct {
To string
From string

View file

@ -21,8 +21,9 @@ import (
"testing"
"time"
"encoding/json"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/rpc"
"github.com/ethereum/go-ethereum/whisper/whisperv5"
)
@ -42,10 +43,9 @@ func TestBasic(x *testing.T) {
x.Fatalf("wrong version: %d.", ver.Uint64())
}
var hexnum rpc.HexNumber
mail := api.GetFilterChanges(hexnum)
mail := api.GetFilterChanges(1)
if len(mail) != 0 {
x.Fatalf("failed GetFilterChanges")
x.Fatalf("failed GetFilterChanges: premature result")
}
exist, err := api.HasIdentity(id)
@ -213,12 +213,12 @@ func TestUnmarshalPostArgs(x *testing.T) {
"payload":"0x7061796C6F61642073686F756C642062652070736575646F72616E646F6D",
"worktime":777,
"pow":3.1416,
"filterID":"0x40",
"filterID":64,
"peerID":"0xf26e7779"
}`)
var a PostArgs
err := a.UnmarshalJSON(s)
err := json.Unmarshal(s, &a)
if err != nil {
x.Fatalf("failed UnmarshalJSON: %s.", err)
}
@ -258,9 +258,9 @@ func TestUnmarshalPostArgs(x *testing.T) {
}
}
func waitForMessage(api *PublicWhisperAPI, id *rpc.HexNumber, target int) bool {
func waitForMessage(api *PublicWhisperAPI, id uint32, target int) bool {
for i := 0; i < 64; i++ {
all := api.GetMessages(*id)
all := api.GetMessages(id)
if len(all) >= target {
return true
}
@ -336,7 +336,7 @@ func TestIntegrationAsym(x *testing.T) {
x.Fatalf("failed to receive first message: timeout.")
}
mail := api.GetFilterChanges(*id)
mail := api.GetFilterChanges(id)
if len(mail) != 1 {
x.Fatalf("failed to GetFilterChanges: got %d messages.", len(mail))
}
@ -358,7 +358,7 @@ func TestIntegrationAsym(x *testing.T) {
x.Fatalf("failed to receive second message: timeout.")
}
mail = api.GetFilterChanges(*id)
mail = api.GetFilterChanges(id)
if len(mail) != 1 {
x.Fatalf("failed to GetFilterChanges: got %d messages.", len(mail))
}
@ -432,7 +432,7 @@ func TestIntegrationSym(x *testing.T) {
x.Fatalf("failed test case 33 (receive first message: timeout).")
}
mail := api.GetFilterChanges(*id)
mail := api.GetFilterChanges(id)
if len(mail) != 1 {
x.Fatalf("failed test case 34 (GetFilterChanges: got %d messages).", len(mail))
}
@ -454,7 +454,7 @@ func TestIntegrationSym(x *testing.T) {
x.Fatalf("failed test case 43 (receive second message: timeout).")
}
mail = api.GetFilterChanges(*id)
mail = api.GetFilterChanges(id)
if len(mail) != 1 {
x.Fatalf("failed test case 44 (GetFilterChanges: got %d messages).", len(mail))
}
@ -510,7 +510,7 @@ func TestIntegrationSymWithFilter(x *testing.T) {
var p PostArgs
p.TTL = 1
p.FilterID = id.Int()
p.FilterID = id
p.From = sig
p.Padding = []byte("test string")
p.Payload = []byte("extended test string")
@ -528,7 +528,7 @@ func TestIntegrationSymWithFilter(x *testing.T) {
x.Fatalf("failed to receive first message: timeout.")
}
mail := api.GetFilterChanges(*id)
mail := api.GetFilterChanges(id)
if len(mail) != 1 {
x.Fatalf("failed to GetFilterChanges: got %d messages.", len(mail))
}
@ -550,7 +550,7 @@ func TestIntegrationSymWithFilter(x *testing.T) {
x.Fatalf("failed to receive second message: timeout.")
}
mail = api.GetFilterChanges(*id)
mail = api.GetFilterChanges(id)
if len(mail) != 1 {
x.Fatalf("failed to GetFilterChanges: got %d messages.", len(mail))
}

View file

@ -46,7 +46,7 @@ const (
messagesCode = 1
p2pCode = 2
mailRequestCode = 3
NumberOfMessageCodes = 10
NumberOfMessageCodes = 32
paddingMask = byte(3)
signatureFlag = byte(4)

View file

@ -131,7 +131,7 @@ func (e *Envelope) calculatePoW(diff uint32) {
h = crypto.Keccak256(buf)
firstBit := common.FirstBitSet(common.BigD(h))
x := math.Pow(2, float64(firstBit))
x /= float64(len(e.Data))
x /= float64(len(e.Data) + len(e.Salt) + len(e.AESNonce))
x /= float64(e.TTL + diff)
e.pow = x
}

View file

@ -37,20 +37,20 @@ type Filter struct {
}
type Filters struct {
id int
watchers map[int]*Filter
id uint32 // can contain any value except zero
watchers map[uint32]*Filter
whisper *Whisper
mutex sync.RWMutex
}
func NewFilters(w *Whisper) *Filters {
return &Filters{
watchers: make(map[int]*Filter),
watchers: make(map[uint32]*Filter),
whisper: w,
}
}
func (fs *Filters) Install(watcher *Filter) int {
func (fs *Filters) Install(watcher *Filter) uint32 {
if watcher.Messages == nil {
watcher.Messages = make(map[common.Hash]*ReceivedMessage)
}
@ -58,19 +58,18 @@ func (fs *Filters) Install(watcher *Filter) int {
fs.mutex.Lock()
defer fs.mutex.Unlock()
fs.watchers[fs.id] = watcher
ret := fs.id
fs.id++
return ret
fs.watchers[fs.id] = watcher
return fs.id
}
func (fs *Filters) Uninstall(id int) {
func (fs *Filters) Uninstall(id uint32) {
fs.mutex.Lock()
defer fs.mutex.Unlock()
delete(fs.watchers, id)
}
func (fs *Filters) Get(i int) *Filter {
func (fs *Filters) Get(i uint32) *Filter {
fs.mutex.RLock()
defer fs.mutex.RUnlock()
return fs.watchers[i]

View file

@ -43,7 +43,7 @@ func InitDebugTest(i int64) {
type FilterTestCase struct {
f *Filter
id int
id uint32
alive bool
msgCnt int
}
@ -100,7 +100,7 @@ func TestInstallFilters(x *testing.T) {
filters := NewFilters(w)
tst := generateTestCases(x, SizeTestFilters)
var j int
var j uint32
for i := 0; i < SizeTestFilters; i++ {
j = filters.Install(tst[i].f)
tst[i].id = j
@ -516,7 +516,8 @@ func TestWatchers(x *testing.T) {
const NumFilters = 16
const NumMessages = 256
var i, j int
var i int
var j uint32
var e *Envelope
w := NewWhisper(nil)
@ -532,7 +533,7 @@ func TestWatchers(x *testing.T) {
var envelopes [NumMessages]*Envelope
for i = 0; i < NumMessages; i++ {
j = rand.Int() % NumFilters
j = rand.Uint32() % NumFilters
e = generateCompatibeEnvelope(x, tst[j].f)
envelopes[i] = e
tst[j].msgCnt++
@ -585,7 +586,7 @@ func TestWatchers(x *testing.T) {
envelopes[0] = e
tst[0].msgCnt++
for i = 1; i < NumMessages; i++ {
j = rand.Int() % NumFilters
j = rand.Uint32() % NumFilters
e = generateCompatibeEnvelope(x, tst[j].f)
envelopes[i] = e
tst[j].msgCnt++
@ -639,7 +640,10 @@ func TestWatchers(x *testing.T) {
x.Fatalf("failed test case 9 with seed %d.", seed)
}
f := filters.Get(0)
f := filters.Get(1)
if f == nil {
x.Fatalf("failed to get the filter with seed %d.", seed)
}
f.AcceptP2P = true
total = 0
filters.NotifyWatchers(envelopes[0], p2pCode)

View file

@ -79,7 +79,7 @@ type TestNode struct {
shh *Whisper
id *ecdsa.PrivateKey
server *p2p.Server
filerId int
filerId uint32
}
var result TestData

View file

@ -245,16 +245,16 @@ func (w *Whisper) GetSymKey(name string) []byte {
// Watch installs a new message handler to run in case a matching packet arrives
// from the whisper network.
func (w *Whisper) Watch(f *Filter) int {
func (w *Whisper) Watch(f *Filter) uint32 {
return w.filters.Install(f)
}
func (w *Whisper) GetFilter(id int) *Filter {
func (w *Whisper) GetFilter(id uint32) *Filter {
return w.filters.Get(id)
}
// Unwatch removes an installed message handler.
func (w *Whisper) Unwatch(id int) {
func (w *Whisper) Unwatch(id uint32) {
w.filters.Uninstall(id)
}
@ -507,7 +507,7 @@ func (w *Whisper) Envelopes() []*Envelope {
}
// Messages retrieves all the decrypted messages matching a filter id.
func (w *Whisper) Messages(id int) []*ReceivedMessage {
func (w *Whisper) Messages(id uint32) []*ReceivedMessage {
result := make([]*ReceivedMessage, 0)
w.poolMu.RLock()
defer w.poolMu.RUnlock()