Cosmos Nicolaou | c9c41fb | 2014-10-16 23:53:10 -0700 | [diff] [blame^] | 1 | // Package static provides a network-aware Profile that provides appropriate |
| 2 | // options and configuration for a variety of network configurations, including |
| 3 | // being behind 1-1 NATs, but without the ability to respond to dhcp changes. |
| 4 | package profiles |
| 5 | |
| 6 | import ( |
| 7 | "flag" |
| 8 | |
| 9 | "veyron.io/veyron/veyron2" |
| 10 | "veyron.io/veyron/veyron2/config" |
| 11 | "veyron.io/veyron/veyron2/ipc" |
| 12 | "veyron.io/veyron/veyron2/rt" |
| 13 | |
| 14 | "veyron.io/veyron/veyron/lib/flags" |
| 15 | "veyron.io/veyron/veyron/lib/netstate" |
| 16 | "veyron.io/veyron/veyron/profiles" |
| 17 | "veyron.io/veyron/veyron/profiles/internal" |
| 18 | ) |
| 19 | |
| 20 | var ( |
| 21 | listenProtocolFlag = flags.TCPProtocolFlag{"tcp"} |
| 22 | listenAddressFlag = flags.IPHostPortFlag{Port: "0"} |
| 23 | listenProxyFlag string |
| 24 | |
| 25 | // ListenSpec is an initialized instance of ipc.ListenSpec that can |
| 26 | // be used with ipc.Listen. |
| 27 | ListenSpec *ipc.ListenSpec |
| 28 | ) |
| 29 | |
| 30 | func init() { |
| 31 | flag.Var(&listenProtocolFlag, "veyron.tcp.protocol", "protocol to listen with") |
| 32 | flag.Var(&listenAddressFlag, "veyron.tcp.address", "address to listen on") |
| 33 | flag.StringVar(&listenProxyFlag, "veyron.proxy", "", "object name of proxy service to use to export services across network boundaries") |
| 34 | rt.RegisterProfile(New()) |
| 35 | } |
| 36 | |
| 37 | type static struct { |
| 38 | gce string |
| 39 | } |
| 40 | |
| 41 | // New returns a new instance of a very static Profile. It can be used |
| 42 | // as a default by Runtime implementations, in unit tests etc. |
| 43 | func New() veyron2.Profile { |
| 44 | return &static{} |
| 45 | } |
| 46 | |
| 47 | func (p *static) Name() string { |
| 48 | return "static" + p.gce |
| 49 | } |
| 50 | |
| 51 | func (p *static) Runtime() string { |
| 52 | return "" |
| 53 | } |
| 54 | |
| 55 | func (*static) Platform() *veyron2.Platform { |
| 56 | p, _ := profiles.Platform() |
| 57 | return p |
| 58 | } |
| 59 | |
| 60 | func (p *static) Init(rt veyron2.Runtime, _ *config.Publisher) error { |
| 61 | log := rt.Logger() |
| 62 | |
| 63 | ListenSpec = &ipc.ListenSpec{ |
| 64 | Protocol: listenProtocolFlag.Protocol, |
| 65 | Address: listenAddressFlag.String(), |
| 66 | Proxy: listenProxyFlag, |
| 67 | } |
| 68 | |
| 69 | // Our address is private, so we test for running on GCE and for its |
| 70 | // 1:1 NAT configuration. GCEPublicAddress returns a non-nil addr |
| 71 | // if we are indeed running on GCE. |
| 72 | if !internal.HasPublicIP(log) { |
| 73 | if addr := internal.GCEPublicAddress(log); addr != nil { |
| 74 | ListenSpec.AddressChooser = func(string, []ipc.Address) ([]ipc.Address, error) { |
| 75 | return []ipc.Address{&netstate.AddrIfc{addr, "nat", nil}}, nil |
| 76 | } |
| 77 | p.gce = "+gce" |
| 78 | return nil |
| 79 | } |
| 80 | } |
| 81 | ListenSpec.AddressChooser = internal.IPAddressChooser |
| 82 | return nil |
| 83 | } |
| 84 | |
| 85 | func (p *static) String() string { |
| 86 | return "static profile on " + p.Platform().String() |
| 87 | } |