func GoRpcServerOpts(env jutil.Env, obj jutil.Object) ([]rpc.ServerOpt, error) { var opts []rpc.ServerOpt if opt, err := jutil.JBoolField(env, obj, "servesMountTable"); err != nil { return nil, err } else { opts = append(opts, options.ServesMountTable(opt)) } if opt, err := getDuration(env, obj, "lameDuckTimeout"); err != nil { return nil, err } else if opt != nil { opts = append(opts, options.LameDuckTimeout(*opt)) } if opt, err := jutil.JBoolField(env, obj, "isLeaf"); err != nil { return nil, err } else { opts = append(opts, options.IsLeaf(opt)) } if opt, err := getDuration(env, obj, "channelTimeout"); err != nil { return nil, err } else if opt != nil { opts = append(opts, options.ChannelTimeout(*opt)) } return opts, nil }
func GoRpcOpts(env jutil.Env, obj jutil.Object) ([]rpc.CallOpt, error) { var opts []rpc.CallOpt if opt, err := getAuthorizer(env, obj, "nameResolutionAuthorizer"); err != nil { return nil, err } else if opt != nil { opts = append(opts, options.NameResolutionAuthorizer{opt}) } if opt, err := getAuthorizer(env, obj, "serverAuthorizer"); err != nil { return nil, err } else if opt != nil { opts = append(opts, options.ServerAuthorizer{opt}) } if opt, err := getPreresolved(env, obj); err != nil { return nil, err } else if opt != nil { opts = append(opts, options.Preresolved{opt}) } if opt, err := jutil.JBoolField(env, obj, "noRetry"); err != nil { return nil, err } else if opt { opts = append(opts, options.NoRetry{}) } if opt, err := getDuration(env, obj, "connectionTimeout"); err != nil { return nil, err } else if opt != nil { opts = append(opts, options.ConnectionTimeout(*opt)) } if opt, err := getDuration(env, obj, "channelTimeout"); err != nil { return nil, err } else if opt != nil { opts = append(opts, options.ChannelTimeout(*opt)) } return opts, nil }
//export Java_io_v_impl_google_services_syncbase_SyncbaseServer_nativeWithNewServer func Java_io_v_impl_google_services_syncbase_SyncbaseServer_nativeWithNewServer(jenv *C.JNIEnv, jSyncbaseServerClass C.jclass, jContext C.jobject, jSyncbaseServerParams C.jobject) C.jobject { env := jutil.Env(uintptr(unsafe.Pointer(jenv))) jCtx := jutil.Object(uintptr(unsafe.Pointer(jContext))) jParams := jutil.Object(uintptr(unsafe.Pointer(jSyncbaseServerParams))) // Read and translate all of the server params. jPerms, err := jutil.CallObjectMethod(env, jParams, "getPermissions", nil, permissionsSign) if err != nil { jutil.JThrowV(env, err) return nil } perms, err := jaccess.GoPermissions(env, jPerms) if err != nil { jutil.JThrowV(env, err) return nil } name, err := jutil.CallStringMethod(env, jParams, "getName", nil) if err != nil { jutil.JThrowV(env, err) return nil } rootDir, err := jutil.CallStringMethod(env, jParams, "getStorageRootDir", nil) if err != nil { jutil.JThrowV(env, err) return nil } if rootDir == "" { rootDir = filepath.Join(os.TempDir(), "syncbaseserver") if err := os.Mkdir(rootDir, 0755); err != nil && !os.IsExist(err) { jutil.JThrowV(env, err) return nil } } jEngine, err := jutil.CallObjectMethod(env, jParams, "getStorageEngine", nil, storageEngineSign) if err != nil { jutil.JThrowV(env, err) return nil } engine, err := GoStorageEngine(env, jEngine) if err != nil { jutil.JThrowV(env, err) return nil } ctx, cancel, err := jcontext.GoContext(env, jCtx) if err != nil { jutil.JThrowV(env, err) return nil } // Create the rpc server before the service so that connections are shared between // clients in the service and the rpc server. (i.e. connections are shared if the // context returned from WithNewDispatchingServer is used for client calls). d := dispatcher.NewDispatcherWrapper() ctx, s, err := v23.WithNewDispatchingServer(ctx, name, d, options.ChannelTimeout(vsync.NeighborConnectionTimeout)) if err != nil { cancel() jutil.JThrowV(env, err) return nil } service, err := server.NewService(ctx, server.ServiceOptions{ Perms: perms, RootDir: rootDir, Engine: engine, }) if err != nil { cancel() jutil.JThrowV(env, err) return nil } // Set the dispatcher in the dispatcher wrapper for the server to start responding // to incoming rpcs. d.SetDispatcher(server.NewDispatcher(service)) if err := service.AddNames(ctx, s); err != nil { cancel() jutil.JThrowV(env, err) return nil } jNewCtx, err := jcontext.JavaContext(env, ctx, cancel) if err != nil { jutil.JThrowV(env, err) return nil } jServer, err := jrpc.JavaServer(env, s) if err != nil { jutil.JThrowV(env, err) return nil } // Attach a server to the new context. jServerAttCtx, err := jutil.CallStaticObjectMethod(env, jVRuntimeImplClass, "withServer", []jutil.Sign{contextSign, serverSign}, contextSign, jNewCtx, jServer) if err != nil { jutil.JThrowV(env, err) return nil } return C.jobject(unsafe.Pointer(jServerAttCtx)) }
func btAndDiscoveryFunc(ctx *context.T, w io.Writer) error { bothf := func(ctx *context.T, w io.Writer, format string, args ...interface{}) { fmt.Fprintf(w, format, args...) ctx.Infof(format, args...) } defer bothf(ctx, w, "finishing!") dis, err := v23.NewDiscovery(ctx) if err != nil { bothf(ctx, w, "Can't create discovery %v", err) return err } ctx = v23.WithListenSpec(ctx, rpc.ListenSpec{Addrs: rpc.ListenAddrs{{Protocol: "bt", Address: "/0"}}}) _, server, err := v23.WithNewServer(ctx, "", &echoServer{}, security.AllowEveryone()) if err != nil { bothf(ctx, w, "Can't create server %v", err) return err } ctx.Infof("Server listening on %v", server.Status().Endpoints) ctx.Infof("Server listen errors: %v", server.Status().ListenErrors) interfaces := []string{ "v.io/x/jni/impl/google/services/vango/Echo", "v.io/x/jni/impl/google/services/vango/Echo2", "v.io/x/jni/impl/google/services/vango/Echo3", "v.io/x/jni/impl/google/services/vango/Echo4", } type adstate struct { ad *discovery.Advertisement stop func() } ads := []adstate{} for _, name := range interfaces { ad := &discovery.Advertisement{ InterfaceName: name, Attributes: discovery.Attributes{ "one": "A value of some kind", "two": "Yet another value", "three": "More and more", "four": "This is insane", }, } nctx, ncancel := context.WithCancel(ctx) ch, err := libdiscovery.AdvertiseServer(nctx, dis, server, "", ad, nil) if err != nil { bothf(nctx, w, "Can't advertise server %v", err) return err } stop := func() { ncancel() <-ch } ads = append(ads, adstate{ad, stop}) } type updateState struct { ch <-chan discovery.Update stop func() } var updates []updateState for _, name := range interfaces { nctx, ncancel := context.WithCancel(ctx) u, err := dis.Scan(nctx, `v.InterfaceName="`+name+`"`) if err != nil { bothf(nctx, w, "Can't scan %v", err) return err } stop := func() { ncancel() } updates = append(updates, updateState{u, stop}) } for _, u := range updates[1:] { go func(up updateState) { for _ = range up.ch { } }(u) } makeopt := func(ad discovery.Advertisement) options.Preresolved { me := &naming.MountEntry{ IsLeaf: true, } for _, a := range ad.Addresses { addr, _ := naming.SplitAddressName(a) me.Servers = append(me.Servers, naming.MountedServer{ Server: addr, }) } return options.Preresolved{Resolution: me} } alive := map[discovery.AdId]options.Preresolved{} ticker := time.NewTicker(time.Second) for { select { case <-ticker.C: if len(alive) == 0 { bothf(ctx, w, "No live connections to dial.") } for _, opt := range alive { dialtime := options.ConnectionTimeout(5 * time.Second) channeltime := options.ChannelTimeout(2 * time.Second) data := make([]byte, 1024) summary, err := runTimedCall(ctx, "A timed call.", string(data), opt, dialtime, channeltime) if err != nil { bothf(ctx, w, "failed call %s, %v, %v", summary, err, opt.Resolution.Servers) } else { bothf(ctx, w, "succeeded call: %s, %v", summary, opt.Resolution.Servers) } } case u := <-updates[0].ch: if u.IsLost() { bothf(ctx, w, "lost %v", u.Addresses()) delete(alive, u.Id()) } else { bothf(ctx, w, "found %v", u.Addresses()) alive[u.Id()] = makeopt(u.Advertisement()) } } } }
func main() { ctx, shutdown := v23.Init() defer shutdown() // Run server if *to == "" { // We are not the caller, so make the RPC available for the // caller to call in on. bsrv := ifc.BridgeServer(makeImpl()) _, server, err := v23.WithNewServer(ctx, *serviceName, bsrv, security.DefaultAuthorizer()) if err != nil { ctx.Error("Error serving service: ", err) return } endpoint := server.Status().Endpoints[0] fmt.Printf("Listening at: %v\n", endpoint) // Wait forever. <-signals.ShutdownOnSignals(ctx) } else if *to != "" && *from != "" { // pipe mode ifct := ifcTopics(*topics) tmout := options.ChannelTimeout(*timeout) leftc := ifc.BridgeClient(*to) rightc := ifc.BridgeClient(*from) leftcc, err := leftc.Link(ctx, ifct, tmout) if err != nil { ctx.Error(err) return } rightcc, err := rightc.Link(ctx, ifct, tmout) if err != nil { ctx.Error(err) return } errCh := make(chan error, 2) wg := &sync.WaitGroup{} wg.Add(2) go linkToLink(leftcc.RecvStream(), rightcc.SendStream(), errCh, wg) go linkToLink(rightcc.RecvStream(), leftcc.SendStream(), errCh, wg) wg.Wait() select { case err := <-errCh: log.Print("pipe error: ", err) default: // don't block on channel read } } else { cc, mu, err := mqttConnect() if err != nil { ctx.Error("mqtt connect: ", err) return } bc := ifc.BridgeClient(*to) ifct := ifcTopics(*topics) bcc, err := bc.Link(ctx, ifct, options.ChannelTimeout(*timeout)) if err != nil { ctx.Error(err) return } done := make(chan error, 2) go func() { done <- transmitter(ifct, bcc.SendStream(), cc, mu) println("send done") }() go func() { done <- receiver(bcc.RecvStream(), cc, mu) println("recv done") }() err = <-done log.Print("Stopped with error ", err) // Stop sender by closing cc.Incoming cc.Disconnect() } }