mirror of
https://gitlab.com/pulsechaincom/erigon-pulse.git
synced 2024-12-27 05:57:28 +00:00
68 lines
1.2 KiB
Go
68 lines
1.2 KiB
Go
package nat
|
|
|
|
import (
|
|
"fmt"
|
|
"net"
|
|
"time"
|
|
|
|
"github.com/pion/stun"
|
|
)
|
|
|
|
const STUNDefaultServerAddr = "stun.l.google.com:19302"
|
|
|
|
type STUN struct {
|
|
serverAddr string
|
|
}
|
|
|
|
func NewSTUN(serverAddr string) STUN {
|
|
if serverAddr == "" {
|
|
serverAddr = STUNDefaultServerAddr
|
|
}
|
|
return STUN{serverAddr: serverAddr}
|
|
}
|
|
|
|
func (s STUN) String() string {
|
|
return fmt.Sprintf("STUN(%s)", s.serverAddr)
|
|
}
|
|
|
|
func (STUN) SupportsMapping() bool {
|
|
return false
|
|
}
|
|
|
|
func (STUN) AddMapping(string, int, int, string, time.Duration) error {
|
|
return nil
|
|
}
|
|
|
|
func (STUN) DeleteMapping(string, int, int) error {
|
|
return nil
|
|
}
|
|
|
|
func (s STUN) ExternalIP() (net.IP, error) {
|
|
conn, err := stun.Dial("udp4", s.serverAddr)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
defer func() {
|
|
_ = conn.Close()
|
|
}()
|
|
|
|
message := stun.MustBuild(stun.TransactionID, stun.BindingRequest)
|
|
var response *stun.Event
|
|
err = conn.Do(message, func(event stun.Event) {
|
|
response = &event
|
|
})
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
if response.Error != nil {
|
|
return nil, response.Error
|
|
}
|
|
|
|
var mappedAddr stun.XORMappedAddress
|
|
if err := mappedAddr.GetFrom(response.Message); err != nil {
|
|
return nil, err
|
|
}
|
|
|
|
return mappedAddr.IP, nil
|
|
}
|