p2p/proto/identify: use observed listen addrs
This commit finally makes use of the sent observed addrs. If the connection's local address is from one of our listen addrs, then the remote's observed addr is its natted mapping, which is useful to us. For now, we add it directly to our address book. (a future commit should make addressbook addresses expire)
Juan Batiz-Benet committed
Jan 19, 2015 at 03:58 UTC
e59b88dace1d4fe182144fca7ea9b59a304e51af
1 file changed
+43
p2p/protocol/identify/id.go
+43
@@ -163,7 +163,9 @@ func (ids *IDService) consumeMessage(mes *pb.Identify, c inet.Conn) {
163
p := c.RemotePeer()
164
165
// mes.Protocols
166
+
167
// mes.ObservedAddr
168
+ ids.consumeObservedAddress(mes.GetObservedAddr(), c)
169
170
// mes.ListenAddrs
171
laddrs := mes.GetListenAddrs()
@@ -208,3 +210,44 @@ func (ids *IDService) IdentifyWait(c inet.Conn) <-chan struct{} {
210
close(ch)
211
return ch
212
}
213
+
214
+func (ids *IDService) consumeObservedAddress(observed []byte, c inet.Conn) {
215
+ if observed == nil {
216
+ return
217
+ }
218
+
219
+ maddr, err := ma.NewMultiaddrBytes(observed)
220
+ if err != nil {
221
+ log.Debugf("error parsing received observed addr for %s: %s", c, err)
222
+ return
223
+ }
224
+
225
+ // we should only use ObservedAddr when our connection's LocalAddr is one
226
+ // of our ListenAddrs. If we Dial out using an ephemeral addr, knowing that
227
+ // address's external mapping is not very useful because the port will not be
228
+ // the same as the listen addr.
229
+ ifaceaddrs, err := ids.Host.Network().InterfaceListenAddresses()
230
+ if err != nil {
231
+ log.Infof("failed to get interface listen addrs", err)
232
+ return
233
+ }
234
+
235
+ log.Debugf("identify identifying observed multiaddr: %s %s", c.LocalMultiaddr(), ifaceaddrs)
236
+ if !addrInAddrs(c.LocalMultiaddr(), ifaceaddrs) {
237
+ // not in our list
238
+ return
239
+ }
240
+
241
+ // ok! we have the observed version of one of our ListenAddresses!
242
+ log.Debugf("added own observed listen addr: %s --> %s", c.LocalMultiaddr(), maddr)
243
+ ids.Host.Peerstore().AddAddress(ids.Host.ID(), maddr)
244
+}
245
+
246
+func addrInAddrs(a ma.Multiaddr, as []ma.Multiaddr) bool {
247
+ for _, b := range as {
248
+ if a.Equal(b) {
249
+ return true
250
+ }
251
+ }
252
+ return false
253
+}