github.com/linapex/ethereum-go-chinese@v0.0.0-20190316121929-f8b7a73c3fa1/whisper/whisperv5/filter_test.go (about)

     1  
     2  //<developer>
     3  //    <name>linapex 曹一峰</name>
     4  //    <email>linapex@163.com</email>
     5  //    <wx>superexc</wx>
     6  //    <qqgroup>128148617</qqgroup>
     7  //    <url>https://jsq.ink</url>
     8  //    <role>pku engineer</role>
     9  //    <date>2019-03-16 19:16:46</date>
    10  //</624450124440932352>
    11  
    12  
    13  package whisperv5
    14  
    15  import (
    16  	"math/big"
    17  	mrand "math/rand"
    18  	"testing"
    19  	"time"
    20  
    21  	"github.com/ethereum/go-ethereum/common"
    22  	"github.com/ethereum/go-ethereum/crypto"
    23  )
    24  
    25  var seed int64
    26  
    27  //应在每个
    28  //使用RNG进行测试
    29  //与序列无关的再现性。
    30  func InitSingleTest() {
    31  	seed = time.Now().Unix()
    32  	mrand.Seed(seed)
    33  }
    34  
    35  func InitDebugTest(i int64) {
    36  	seed = i
    37  	mrand.Seed(seed)
    38  }
    39  
    40  type FilterTestCase struct {
    41  	f      *Filter
    42  	id     string
    43  	alive  bool
    44  	msgCnt int
    45  }
    46  
    47  func generateFilter(t *testing.T, symmetric bool) (*Filter, error) {
    48  	var f Filter
    49  	f.Messages = make(map[common.Hash]*ReceivedMessage)
    50  
    51  	const topicNum = 8
    52  	f.Topics = make([][]byte, topicNum)
    53  	for i := 0; i < topicNum; i++ {
    54  		f.Topics[i] = make([]byte, 4)
    55  		mrand.Read(f.Topics[i])
    56  		f.Topics[i][0] = 0x01
    57  	}
    58  
    59  	key, err := crypto.GenerateKey()
    60  	if err != nil {
    61  		t.Fatalf("generateFilter 1 failed with seed %d.", seed)
    62  		return nil, err
    63  	}
    64  	f.Src = &key.PublicKey
    65  
    66  	if symmetric {
    67  		f.KeySym = make([]byte, aesKeyLength)
    68  		mrand.Read(f.KeySym)
    69  		f.SymKeyHash = crypto.Keccak256Hash(f.KeySym)
    70  	} else {
    71  		f.KeyAsym, err = crypto.GenerateKey()
    72  		if err != nil {
    73  			t.Fatalf("generateFilter 2 failed with seed %d.", seed)
    74  			return nil, err
    75  		}
    76  	}
    77  
    78  //未设置acceptp2p&pow
    79  	return &f, nil
    80  }
    81  
    82  func generateTestCases(t *testing.T, SizeTestFilters int) []FilterTestCase {
    83  	cases := make([]FilterTestCase, SizeTestFilters)
    84  	for i := 0; i < SizeTestFilters; i++ {
    85  		f, _ := generateFilter(t, true)
    86  		cases[i].f = f
    87  		cases[i].alive = mrand.Int()&int(1) == 0
    88  	}
    89  	return cases
    90  }
    91  
    92  func TestInstallFilters(t *testing.T) {
    93  	InitSingleTest()
    94  
    95  	const SizeTestFilters = 256
    96  	w := New(&Config{})
    97  	filters := NewFilters(w)
    98  	tst := generateTestCases(t, SizeTestFilters)
    99  
   100  	var err error
   101  	var j string
   102  	for i := 0; i < SizeTestFilters; i++ {
   103  		j, err = filters.Install(tst[i].f)
   104  		if err != nil {
   105  			t.Fatalf("seed %d: failed to install filter: %s", seed, err)
   106  		}
   107  		tst[i].id = j
   108  		if len(j) != keyIdSize*2 {
   109  			t.Fatalf("seed %d: wrong filter id size [%d]", seed, len(j))
   110  		}
   111  	}
   112  
   113  	for _, testCase := range tst {
   114  		if !testCase.alive {
   115  			filters.Uninstall(testCase.id)
   116  		}
   117  	}
   118  
   119  	for i, testCase := range tst {
   120  		fil := filters.Get(testCase.id)
   121  		exist := fil != nil
   122  		if exist != testCase.alive {
   123  			t.Fatalf("seed %d: failed alive: %d, %v, %v", seed, i, exist, testCase.alive)
   124  		}
   125  		if exist && fil.PoW != testCase.f.PoW {
   126  			t.Fatalf("seed %d: failed Get: %d, %v, %v", seed, i, exist, testCase.alive)
   127  		}
   128  	}
   129  }
   130  
   131  func TestInstallSymKeyGeneratesHash(t *testing.T) {
   132  	InitSingleTest()
   133  
   134  	w := New(&Config{})
   135  	filters := NewFilters(w)
   136  	filter, _ := generateFilter(t, true)
   137  
   138  //保存当前symkeyhash进行比较
   139  	initialSymKeyHash := filter.SymKeyHash
   140  
   141  //确保symkeyhash无效,以便安装重新创建它
   142  	var invalid common.Hash
   143  	filter.SymKeyHash = invalid
   144  
   145  	_, err := filters.Install(filter)
   146  
   147  	if err != nil {
   148  		t.Fatalf("Error installing the filter: %s", err)
   149  	}
   150  
   151  	for i, b := range filter.SymKeyHash {
   152  		if b != initialSymKeyHash[i] {
   153  			t.Fatalf("The filter's symmetric key hash was not properly generated by Install")
   154  		}
   155  	}
   156  }
   157  
   158  func TestInstallIdenticalFilters(t *testing.T) {
   159  	InitSingleTest()
   160  
   161  	w := New(&Config{})
   162  	filters := NewFilters(w)
   163  	filter1, _ := generateFilter(t, true)
   164  
   165  //复制第一个筛选器,因为它的某些字段
   166  //随机磁化。
   167  	filter2 := &Filter{
   168  		KeySym:   filter1.KeySym,
   169  		Topics:   filter1.Topics,
   170  		PoW:      filter1.PoW,
   171  		AllowP2P: filter1.AllowP2P,
   172  		Messages: make(map[common.Hash]*ReceivedMessage),
   173  	}
   174  
   175  	_, err := filters.Install(filter1)
   176  
   177  	if err != nil {
   178  		t.Fatalf("Error installing the first filter with seed %d: %s", seed, err)
   179  	}
   180  
   181  	_, err = filters.Install(filter2)
   182  
   183  	if err != nil {
   184  		t.Fatalf("Error installing the second filter with seed %d: %s", seed, err)
   185  	}
   186  
   187  	params, err := generateMessageParams()
   188  	if err != nil {
   189  		t.Fatalf("Error generating message parameters with seed %d: %s", seed, err)
   190  	}
   191  
   192  	params.KeySym = filter1.KeySym
   193  	params.Topic = BytesToTopic(filter1.Topics[0])
   194  
   195  	filter1.Src = &params.Src.PublicKey
   196  	filter2.Src = &params.Src.PublicKey
   197  
   198  	sentMessage, err := NewSentMessage(params)
   199  	if err != nil {
   200  		t.Fatalf("failed to create new message with seed %d: %s.", seed, err)
   201  	}
   202  	env, err := sentMessage.Wrap(params)
   203  	if err != nil {
   204  		t.Fatalf("failed Wrap with seed %d: %s.", seed, err)
   205  	}
   206  	msg := env.Open(filter1)
   207  	if msg == nil {
   208  		t.Fatalf("failed to Open with filter1")
   209  	}
   210  
   211  	if !filter1.MatchEnvelope(env) {
   212  		t.Fatalf("failed matching with the first filter")
   213  	}
   214  
   215  	if !filter2.MatchEnvelope(env) {
   216  		t.Fatalf("failed matching with the first filter")
   217  	}
   218  
   219  	if !filter1.MatchMessage(msg) {
   220  		t.Fatalf("failed matching with the second filter")
   221  	}
   222  
   223  	if !filter2.MatchMessage(msg) {
   224  		t.Fatalf("failed matching with the second filter")
   225  	}
   226  }
   227  
   228  func TestComparePubKey(t *testing.T) {
   229  	InitSingleTest()
   230  
   231  	key1, err := crypto.GenerateKey()
   232  	if err != nil {
   233  		t.Fatalf("failed to generate first key with seed %d: %s.", seed, err)
   234  	}
   235  	key2, err := crypto.GenerateKey()
   236  	if err != nil {
   237  		t.Fatalf("failed to generate second key with seed %d: %s.", seed, err)
   238  	}
   239  	if IsPubKeyEqual(&key1.PublicKey, &key2.PublicKey) {
   240  		t.Fatalf("public keys are equal, seed %d.", seed)
   241  	}
   242  
   243  //生成key3==key1
   244  	mrand.Seed(seed)
   245  	key3, err := crypto.GenerateKey()
   246  	if err != nil {
   247  		t.Fatalf("failed to generate third key with seed %d: %s.", seed, err)
   248  	}
   249  	if IsPubKeyEqual(&key1.PublicKey, &key3.PublicKey) {
   250  		t.Fatalf("key1 == key3, seed %d.", seed)
   251  	}
   252  }
   253  
   254  func TestMatchEnvelope(t *testing.T) {
   255  	InitSingleTest()
   256  
   257  	fsym, err := generateFilter(t, true)
   258  	if err != nil {
   259  		t.Fatalf("failed generateFilter with seed %d: %s.", seed, err)
   260  	}
   261  
   262  	fasym, err := generateFilter(t, false)
   263  	if err != nil {
   264  		t.Fatalf("failed generateFilter() with seed %d: %s.", seed, err)
   265  	}
   266  
   267  	params, err := generateMessageParams()
   268  	if err != nil {
   269  		t.Fatalf("failed generateMessageParams with seed %d: %s.", seed, err)
   270  	}
   271  
   272  params.Topic[0] = 0xFF //确保不匹配
   273  
   274  //与伪随机数据不匹配
   275  	msg, err := NewSentMessage(params)
   276  	if err != nil {
   277  		t.Fatalf("failed to create new message with seed %d: %s.", seed, err)
   278  	}
   279  	env, err := msg.Wrap(params)
   280  	if err != nil {
   281  		t.Fatalf("failed Wrap with seed %d: %s.", seed, err)
   282  	}
   283  	match := fsym.MatchEnvelope(env)
   284  	if match {
   285  		t.Fatalf("failed MatchEnvelope symmetric with seed %d.", seed)
   286  	}
   287  	match = fasym.MatchEnvelope(env)
   288  	if match {
   289  		t.Fatalf("failed MatchEnvelope asymmetric with seed %d.", seed)
   290  	}
   291  
   292  //对称加密
   293  	i := mrand.Int() % 4
   294  	fsym.Topics[i] = params.Topic[:]
   295  	fasym.Topics[i] = params.Topic[:]
   296  	msg, err = NewSentMessage(params)
   297  	if err != nil {
   298  		t.Fatalf("failed to create new message with seed %d: %s.", seed, err)
   299  	}
   300  	env, err = msg.Wrap(params)
   301  	if err != nil {
   302  		t.Fatalf("failed Wrap() with seed %d: %s.", seed, err)
   303  	}
   304  
   305  //对称+匹配主题:匹配
   306  	match = fsym.MatchEnvelope(env)
   307  	if !match {
   308  		t.Fatalf("failed MatchEnvelope() symmetric with seed %d.", seed)
   309  	}
   310  
   311  //不对称+匹配主题:不匹配
   312  	match = fasym.MatchEnvelope(env)
   313  	if match {
   314  		t.Fatalf("failed MatchEnvelope() asymmetric with seed %d.", seed)
   315  	}
   316  
   317  //对称+匹配主题+功率不足:不匹配
   318  	fsym.PoW = env.PoW() + 1.0
   319  	match = fsym.MatchEnvelope(env)
   320  	if match {
   321  		t.Fatalf("failed MatchEnvelope(symmetric + matching topic + insufficient PoW) asymmetric with seed %d.", seed)
   322  	}
   323  
   324  //对称+匹配主题+充分功率:匹配
   325  	fsym.PoW = env.PoW() / 2
   326  	match = fsym.MatchEnvelope(env)
   327  	if !match {
   328  		t.Fatalf("failed MatchEnvelope(symmetric + matching topic + sufficient PoW) with seed %d.", seed)
   329  	}
   330  
   331  //对称+主题为零(通配符):匹配
   332  	prevTopics := fsym.Topics
   333  	fsym.Topics = nil
   334  	match = fsym.MatchEnvelope(env)
   335  	if !match {
   336  		t.Fatalf("failed MatchEnvelope(symmetric + topics are nil) with seed %d.", seed)
   337  	}
   338  	fsym.Topics = prevTopics
   339  
   340  //不对称加密
   341  	key, err := crypto.GenerateKey()
   342  	if err != nil {
   343  		t.Fatalf("failed GenerateKey with seed %d: %s.", seed, err)
   344  	}
   345  	params.KeySym = nil
   346  	params.Dst = &key.PublicKey
   347  	msg, err = NewSentMessage(params)
   348  	if err != nil {
   349  		t.Fatalf("failed to create new message with seed %d: %s.", seed, err)
   350  	}
   351  	env, err = msg.Wrap(params)
   352  	if err != nil {
   353  		t.Fatalf("failed Wrap() with seed %d: %s.", seed, err)
   354  	}
   355  
   356  //加密方法不匹配
   357  	match = fsym.MatchEnvelope(env)
   358  	if match {
   359  		t.Fatalf("failed MatchEnvelope(encryption method mismatch) with seed %d.", seed)
   360  	}
   361  
   362  //不对称+不匹配主题:不匹配
   363  	match = fasym.MatchEnvelope(env)
   364  	if !match {
   365  		t.Fatalf("failed MatchEnvelope(asymmetric + mismatching topic) with seed %d.", seed)
   366  	}
   367  
   368  //不对称+匹配主题:匹配
   369  	fasym.Topics[i] = fasym.Topics[i+1]
   370  	match = fasym.MatchEnvelope(env)
   371  	if match {
   372  		t.Fatalf("failed MatchEnvelope(asymmetric + matching topic) with seed %d.", seed)
   373  	}
   374  
   375  //不带主题的非对称+筛选器(通配符):匹配
   376  	fasym.Topics = nil
   377  	match = fasym.MatchEnvelope(env)
   378  	if !match {
   379  		t.Fatalf("failed MatchEnvelope(asymmetric + filter without topic) with seed %d.", seed)
   380  	}
   381  
   382  //不对称+功率不足:不匹配
   383  	fasym.PoW = env.PoW() + 1.0
   384  	match = fasym.MatchEnvelope(env)
   385  	if match {
   386  		t.Fatalf("failed MatchEnvelope(asymmetric + insufficient PoW) with seed %d.", seed)
   387  	}
   388  
   389  //不对称+充足功率:匹配
   390  	fasym.PoW = env.PoW() / 2
   391  	match = fasym.MatchEnvelope(env)
   392  	if !match {
   393  		t.Fatalf("failed MatchEnvelope(asymmetric + sufficient PoW) with seed %d.", seed)
   394  	}
   395  
   396  //不带主题的筛选器+不带主题的信封:匹配
   397  	env.Topic = TopicType{}
   398  	match = fasym.MatchEnvelope(env)
   399  	if !match {
   400  		t.Fatalf("failed MatchEnvelope(filter without topic + envelope without topic) with seed %d.", seed)
   401  	}
   402  
   403  //带主题+不带主题的信封的筛选器:不匹配
   404  	fasym.Topics = fsym.Topics
   405  	match = fasym.MatchEnvelope(env)
   406  	if match {
   407  		t.Fatalf("failed MatchEnvelope(filter without topic + envelope without topic) with seed %d.", seed)
   408  	}
   409  }
   410  
   411  func TestMatchMessageSym(t *testing.T) {
   412  	InitSingleTest()
   413  
   414  	params, err := generateMessageParams()
   415  	if err != nil {
   416  		t.Fatalf("failed generateMessageParams with seed %d: %s.", seed, err)
   417  	}
   418  
   419  	f, err := generateFilter(t, true)
   420  	if err != nil {
   421  		t.Fatalf("failed generateFilter with seed %d: %s.", seed, err)
   422  	}
   423  
   424  	const index = 1
   425  	params.KeySym = f.KeySym
   426  	params.Topic = BytesToTopic(f.Topics[index])
   427  
   428  	sentMessage, err := NewSentMessage(params)
   429  	if err != nil {
   430  		t.Fatalf("failed to create new message with seed %d: %s.", seed, err)
   431  	}
   432  	env, err := sentMessage.Wrap(params)
   433  	if err != nil {
   434  		t.Fatalf("failed Wrap with seed %d: %s.", seed, err)
   435  	}
   436  	msg := env.Open(f)
   437  	if msg == nil {
   438  		t.Fatalf("failed Open with seed %d.", seed)
   439  	}
   440  
   441  //SRC:匹配
   442  	*f.Src.X = *params.Src.PublicKey.X
   443  	*f.Src.Y = *params.Src.PublicKey.Y
   444  	if !f.MatchMessage(msg) {
   445  		t.Fatalf("failed MatchEnvelope(src match) with seed %d.", seed)
   446  	}
   447  
   448  //功率不足:不匹配
   449  	f.PoW = msg.PoW + 1.0
   450  	if f.MatchMessage(msg) {
   451  		t.Fatalf("failed MatchEnvelope(insufficient PoW) with seed %d.", seed)
   452  	}
   453  
   454  //足够的力量:匹配
   455  	f.PoW = msg.PoW / 2
   456  	if !f.MatchMessage(msg) {
   457  		t.Fatalf("failed MatchEnvelope(sufficient PoW) with seed %d.", seed)
   458  	}
   459  
   460  //主题失配
   461  	f.Topics[index][0]++
   462  	if f.MatchMessage(msg) {
   463  		t.Fatalf("failed MatchEnvelope(topic mismatch) with seed %d.", seed)
   464  	}
   465  	f.Topics[index][0]--
   466  
   467  //密钥失配
   468  	f.SymKeyHash[0]++
   469  	if f.MatchMessage(msg) {
   470  		t.Fatalf("failed MatchEnvelope(key mismatch) with seed %d.", seed)
   471  	}
   472  	f.SymKeyHash[0]--
   473  
   474  //SRC缺少:匹配
   475  	f.Src = nil
   476  	if !f.MatchMessage(msg) {
   477  		t.Fatalf("failed MatchEnvelope(src absent) with seed %d.", seed)
   478  	}
   479  
   480  //键哈希不匹配
   481  	h := f.SymKeyHash
   482  	f.SymKeyHash = common.Hash{}
   483  	if f.MatchMessage(msg) {
   484  		t.Fatalf("failed MatchEnvelope(key hash mismatch) with seed %d.", seed)
   485  	}
   486  	f.SymKeyHash = h
   487  	if !f.MatchMessage(msg) {
   488  		t.Fatalf("failed MatchEnvelope(key hash match) with seed %d.", seed)
   489  	}
   490  
   491  //加密方法不匹配
   492  	f.KeySym = nil
   493  	f.KeyAsym, err = crypto.GenerateKey()
   494  	if err != nil {
   495  		t.Fatalf("failed GenerateKey with seed %d: %s.", seed, err)
   496  	}
   497  	if f.MatchMessage(msg) {
   498  		t.Fatalf("failed MatchEnvelope(encryption method mismatch) with seed %d.", seed)
   499  	}
   500  }
   501  
   502  func TestMatchMessageAsym(t *testing.T) {
   503  	InitSingleTest()
   504  
   505  	f, err := generateFilter(t, false)
   506  	if err != nil {
   507  		t.Fatalf("failed generateFilter with seed %d: %s.", seed, err)
   508  	}
   509  
   510  	params, err := generateMessageParams()
   511  	if err != nil {
   512  		t.Fatalf("failed generateMessageParams with seed %d: %s.", seed, err)
   513  	}
   514  
   515  	const index = 1
   516  	params.Topic = BytesToTopic(f.Topics[index])
   517  	params.Dst = &f.KeyAsym.PublicKey
   518  	keySymOrig := params.KeySym
   519  	params.KeySym = nil
   520  
   521  	sentMessage, err := NewSentMessage(params)
   522  	if err != nil {
   523  		t.Fatalf("failed to create new message with seed %d: %s.", seed, err)
   524  	}
   525  	env, err := sentMessage.Wrap(params)
   526  	if err != nil {
   527  		t.Fatalf("failed Wrap with seed %d: %s.", seed, err)
   528  	}
   529  	msg := env.Open(f)
   530  	if msg == nil {
   531  		t.Fatalf("failed to open with seed %d.", seed)
   532  	}
   533  
   534  //SRC:匹配
   535  	*f.Src.X = *params.Src.PublicKey.X
   536  	*f.Src.Y = *params.Src.PublicKey.Y
   537  	if !f.MatchMessage(msg) {
   538  		t.Fatalf("failed MatchMessage(src match) with seed %d.", seed)
   539  	}
   540  
   541  //功率不足:不匹配
   542  	f.PoW = msg.PoW + 1.0
   543  	if f.MatchMessage(msg) {
   544  		t.Fatalf("failed MatchEnvelope(insufficient PoW) with seed %d.", seed)
   545  	}
   546  
   547  //足够的力量:匹配
   548  	f.PoW = msg.PoW / 2
   549  	if !f.MatchMessage(msg) {
   550  		t.Fatalf("failed MatchEnvelope(sufficient PoW) with seed %d.", seed)
   551  	}
   552  
   553  //主题失配
   554  	f.Topics[index][0]++
   555  	if f.MatchMessage(msg) {
   556  		t.Fatalf("failed MatchEnvelope(topic mismatch) with seed %d.", seed)
   557  	}
   558  	f.Topics[index][0]--
   559  
   560  //密钥失配
   561  	prev := *f.KeyAsym.PublicKey.X
   562  	zero := *big.NewInt(0)
   563  	*f.KeyAsym.PublicKey.X = zero
   564  	if f.MatchMessage(msg) {
   565  		t.Fatalf("failed MatchEnvelope(key mismatch) with seed %d.", seed)
   566  	}
   567  	*f.KeyAsym.PublicKey.X = prev
   568  
   569  //SRC缺少:匹配
   570  	f.Src = nil
   571  	if !f.MatchMessage(msg) {
   572  		t.Fatalf("failed MatchEnvelope(src absent) with seed %d.", seed)
   573  	}
   574  
   575  //加密方法不匹配
   576  	f.KeySym = keySymOrig
   577  	f.KeyAsym = nil
   578  	if f.MatchMessage(msg) {
   579  		t.Fatalf("failed MatchEnvelope(encryption method mismatch) with seed %d.", seed)
   580  	}
   581  }
   582  
   583  func cloneFilter(orig *Filter) *Filter {
   584  	var clone Filter
   585  	clone.Messages = make(map[common.Hash]*ReceivedMessage)
   586  	clone.Src = orig.Src
   587  	clone.KeyAsym = orig.KeyAsym
   588  	clone.KeySym = orig.KeySym
   589  	clone.Topics = orig.Topics
   590  	clone.PoW = orig.PoW
   591  	clone.AllowP2P = orig.AllowP2P
   592  	clone.SymKeyHash = orig.SymKeyHash
   593  	return &clone
   594  }
   595  
   596  func generateCompatibeEnvelope(t *testing.T, f *Filter) *Envelope {
   597  	params, err := generateMessageParams()
   598  	if err != nil {
   599  		t.Fatalf("failed generateMessageParams with seed %d: %s.", seed, err)
   600  		return nil
   601  	}
   602  
   603  	params.KeySym = f.KeySym
   604  	params.Topic = BytesToTopic(f.Topics[2])
   605  	sentMessage, err := NewSentMessage(params)
   606  	if err != nil {
   607  		t.Fatalf("failed to create new message with seed %d: %s.", seed, err)
   608  	}
   609  	env, err := sentMessage.Wrap(params)
   610  	if err != nil {
   611  		t.Fatalf("failed Wrap with seed %d: %s.", seed, err)
   612  		return nil
   613  	}
   614  	return env
   615  }
   616  
   617  func TestWatchers(t *testing.T) {
   618  	InitSingleTest()
   619  
   620  	const NumFilters = 16
   621  	const NumMessages = 256
   622  	var i int
   623  	var j uint32
   624  	var e *Envelope
   625  	var x, firstID string
   626  	var err error
   627  
   628  	w := New(&Config{})
   629  	filters := NewFilters(w)
   630  	tst := generateTestCases(t, NumFilters)
   631  	for i = 0; i < NumFilters; i++ {
   632  		tst[i].f.Src = nil
   633  		x, err = filters.Install(tst[i].f)
   634  		if err != nil {
   635  			t.Fatalf("failed to install filter with seed %d: %s.", seed, err)
   636  		}
   637  		tst[i].id = x
   638  		if len(firstID) == 0 {
   639  			firstID = x
   640  		}
   641  	}
   642  
   643  	lastID := x
   644  
   645  	var envelopes [NumMessages]*Envelope
   646  	for i = 0; i < NumMessages; i++ {
   647  		j = mrand.Uint32() % NumFilters
   648  		e = generateCompatibeEnvelope(t, tst[j].f)
   649  		envelopes[i] = e
   650  		tst[j].msgCnt++
   651  	}
   652  
   653  	for i = 0; i < NumMessages; i++ {
   654  		filters.NotifyWatchers(envelopes[i], false)
   655  	}
   656  
   657  	var total int
   658  	var mail []*ReceivedMessage
   659  	var count [NumFilters]int
   660  
   661  	for i = 0; i < NumFilters; i++ {
   662  		mail = tst[i].f.Retrieve()
   663  		count[i] = len(mail)
   664  		total += len(mail)
   665  	}
   666  
   667  	if total != NumMessages {
   668  		t.Fatalf("failed with seed %d: total = %d, want: %d.", seed, total, NumMessages)
   669  	}
   670  
   671  	for i = 0; i < NumFilters; i++ {
   672  		mail = tst[i].f.Retrieve()
   673  		if len(mail) != 0 {
   674  			t.Fatalf("failed with seed %d: i = %d.", seed, i)
   675  		}
   676  
   677  		if tst[i].msgCnt != count[i] {
   678  			t.Fatalf("failed with seed %d: count[%d]: get %d, want %d.", seed, i, tst[i].msgCnt, count[i])
   679  		}
   680  	}
   681  
   682  //另一轮使用克隆过滤器
   683  
   684  	clone := cloneFilter(tst[0].f)
   685  	filters.Uninstall(lastID)
   686  	total = 0
   687  	last := NumFilters - 1
   688  	tst[last].f = clone
   689  	filters.Install(clone)
   690  	for i = 0; i < NumFilters; i++ {
   691  		tst[i].msgCnt = 0
   692  		count[i] = 0
   693  	}
   694  
   695  //确保第一个观察者至少收到一条消息
   696  	e = generateCompatibeEnvelope(t, tst[0].f)
   697  	envelopes[0] = e
   698  	tst[0].msgCnt++
   699  	for i = 1; i < NumMessages; i++ {
   700  		j = mrand.Uint32() % NumFilters
   701  		e = generateCompatibeEnvelope(t, tst[j].f)
   702  		envelopes[i] = e
   703  		tst[j].msgCnt++
   704  	}
   705  
   706  	for i = 0; i < NumMessages; i++ {
   707  		filters.NotifyWatchers(envelopes[i], false)
   708  	}
   709  
   710  	for i = 0; i < NumFilters; i++ {
   711  		mail = tst[i].f.Retrieve()
   712  		count[i] = len(mail)
   713  		total += len(mail)
   714  	}
   715  
   716  	combined := tst[0].msgCnt + tst[last].msgCnt
   717  	if total != NumMessages+count[0] {
   718  		t.Fatalf("failed with seed %d: total = %d, count[0] = %d.", seed, total, count[0])
   719  	}
   720  
   721  	if combined != count[0] {
   722  		t.Fatalf("failed with seed %d: combined = %d, count[0] = %d.", seed, combined, count[0])
   723  	}
   724  
   725  	if combined != count[last] {
   726  		t.Fatalf("failed with seed %d: combined = %d, count[last] = %d.", seed, combined, count[last])
   727  	}
   728  
   729  	for i = 1; i < NumFilters-1; i++ {
   730  		mail = tst[i].f.Retrieve()
   731  		if len(mail) != 0 {
   732  			t.Fatalf("failed with seed %d: i = %d.", seed, i)
   733  		}
   734  
   735  		if tst[i].msgCnt != count[i] {
   736  			t.Fatalf("failed with seed %d: i = %d, get %d, want %d.", seed, i, tst[i].msgCnt, count[i])
   737  		}
   738  	}
   739  
   740  //测试接受P2P
   741  
   742  	total = 0
   743  	filters.NotifyWatchers(envelopes[0], true)
   744  
   745  	for i = 0; i < NumFilters; i++ {
   746  		mail = tst[i].f.Retrieve()
   747  		total += len(mail)
   748  	}
   749  
   750  	if total != 0 {
   751  		t.Fatalf("failed with seed %d: total: got %d, want 0.", seed, total)
   752  	}
   753  
   754  	f := filters.Get(firstID)
   755  	if f == nil {
   756  		t.Fatalf("failed to get the filter with seed %d.", seed)
   757  	}
   758  	f.AllowP2P = true
   759  	total = 0
   760  	filters.NotifyWatchers(envelopes[0], true)
   761  
   762  	for i = 0; i < NumFilters; i++ {
   763  		mail = tst[i].f.Retrieve()
   764  		total += len(mail)
   765  	}
   766  
   767  	if total != 1 {
   768  		t.Fatalf("failed with seed %d: total: got %d, want 1.", seed, total)
   769  	}
   770  }
   771  
   772  func TestVariableTopics(t *testing.T) {
   773  	InitSingleTest()
   774  
   775  	const lastTopicByte = 3
   776  	var match bool
   777  	params, err := generateMessageParams()
   778  	if err != nil {
   779  		t.Fatalf("failed generateMessageParams with seed %d: %s.", seed, err)
   780  	}
   781  	msg, err := NewSentMessage(params)
   782  	if err != nil {
   783  		t.Fatalf("failed to create new message with seed %d: %s.", seed, err)
   784  	}
   785  	env, err := msg.Wrap(params)
   786  	if err != nil {
   787  		t.Fatalf("failed Wrap with seed %d: %s.", seed, err)
   788  	}
   789  
   790  	f, err := generateFilter(t, true)
   791  	if err != nil {
   792  		t.Fatalf("failed generateFilter with seed %d: %s.", seed, err)
   793  	}
   794  
   795  	for i := 0; i < 4; i++ {
   796  		env.Topic = BytesToTopic(f.Topics[i])
   797  		match = f.MatchEnvelope(env)
   798  		if !match {
   799  			t.Fatalf("failed MatchEnvelope symmetric with seed %d, step %d.", seed, i)
   800  		}
   801  
   802  		f.Topics[i][lastTopicByte]++
   803  		match = f.MatchEnvelope(env)
   804  		if match {
   805  			t.Fatalf("MatchEnvelope symmetric with seed %d, step %d: false positive.", seed, i)
   806  		}
   807  	}
   808  }
   809  
   810  func TestMatchSingleTopic_ReturnTrue(t *testing.T) {
   811  	bt := []byte("test")
   812  	topic := BytesToTopic(bt)
   813  
   814  	if !matchSingleTopic(topic, bt) {
   815  		t.FailNow()
   816  	}
   817  }
   818  
   819  func TestMatchSingleTopic_WithTail_ReturnTrue(t *testing.T) {
   820  	bt := []byte("test with tail")
   821  	topic := BytesToTopic([]byte("test"))
   822  
   823  	if !matchSingleTopic(topic, bt) {
   824  		t.FailNow()
   825  	}
   826  }
   827  
   828  func TestMatchSingleTopic_PartialTopic_ReturnTrue(t *testing.T) {
   829  	bt := []byte("tes")
   830  	topic := BytesToTopic([]byte("test"))
   831  
   832  	if !matchSingleTopic(topic, bt) {
   833  		t.FailNow()
   834  	}
   835  }
   836  
   837  func TestMatchSingleTopic_NotEquals_ReturnFalse(t *testing.T) {
   838  	bt := []byte("test")
   839  	topic := BytesToTopic([]byte("not_equal"))
   840  
   841  	if matchSingleTopic(topic, bt) {
   842  		t.FailNow()
   843  	}
   844  }
   845