Beispiel #1
0
func (dt *DbTask) handleCmd(cmd string) bool {
	cont := true
	svcname := ""
	idx := strings.Index(cmd, ":")
	if idx > 0 {
		svcname = cmd[idx+1:]
		cmd = cmd[0:idx]
	}
	switch cmd {
	case "Start":
		dt.numTrans = 0
		dt.role = Active
	case "Stop":
		dt.role = Standby
	case "Shutdown":
		cont = false
	case "AddService":
		if len(svcname) > 0 {
			ch := make(chan string)
			dt.dbRespChans[svcname] = ch
			dt.rot.AttachSendChan(router.StrID("/App/"+svcname+"/DB/Response"), ch)
		}
	case "DelService":
		if len(svcname) > 0 {
			ch, ok := dt.dbRespChans[svcname]
			if ok {
				dt.dbRespChans[svcname] = nil, false
				dt.rot.DetachChan(router.StrID("/App/"+svcname+"/DB/Response"), ch)
			}
		}
	default:
	}
	return cont
}
Beispiel #2
0
func (ft *FaultMgrTask) handleCmd(cmd string) bool {
	cont := true
	svcname := ""
	idx := strings.Index(cmd, ":")
	if idx > 0 {
		svcname = cmd[idx+1:]
		cmd = cmd[0:idx]
	}
	switch cmd {
	case "Start":
		ft.role = Active
	case "Stop":
		ft.role = Standby
	case "Shutdown":
		cont = false
	case "AddService":
		if len(svcname) > 0 {
			ch := make(chan string)
			ft.svcCmdChans[svcname] = ch
			ft.rot.AttachSendChan(router.StrID("/App/"+svcname+"/Command"), ch)
		}
	case "DelService":
		if len(svcname) > 0 {
			ch, ok := ft.svcCmdChans[svcname]
			if ok {
				ft.svcCmdChans[svcname] = nil, false
				ft.rot.DetachChan(router.StrID("/App/"+svcname+"/Command"), ch)
			}
		}
	default:
	}
	return cont
}
Beispiel #3
0
func (ft *FaultMgrTask) shutdown() {
	for k, v := range ft.svcCmdChans {
		ft.rot.DetachChan(router.StrID("/App/"+k+"/Command"), v)
	}
	ft.rot.DetachChan(router.StrID("/Sys/OutOfService"), ft.sysOOSChan)
	ft.rot.DetachChan(router.StrID("/Fault/DB/Exception"), ft.faultReportChan)
	ft.rot.DetachChan(router.StrID("/Fault/AppService/Exception"), ft.faultReportChan)
	ft.rot.DetachChan(router.StrID("/Sys/Command"), ft.sysCmdChan)
}
Beispiel #4
0
func (dt *DbTask) shutdown() {
	//output_intf or send chans
	dt.FaultRaiser.Close()
	for k, v := range dt.dbRespChans {
		dt.rot.DetachChan(router.StrID("/App/"+k+"/DB/Response"), v)
	}
	//input_intf or recv chans
	dt.rot.DetachChan(router.StrID("/Sys/Command"), dt.sysCmdChan)
	dt.rot.DetachChan(router.StrID("/DB/Request"), dt.dbReqChan)
}
Beispiel #5
0
func newPinger(rot router.Router, done chan<- bool, numRuns int) {
	//attach chans to router
	pingChan := make(chan *Msg)
	pongChan := make(chan *Msg)
	rot.AttachSendChan(router.StrID("ping"), pingChan)
	rot.AttachRecvChan(router.StrID("pong"), pongChan)
	//start pinger
	ping := &Pinger{pingChan, pongChan, done, numRuns}
	go ping.Run()
}
Beispiel #6
0
func newPonger(rot router.Router, done chan<- bool) {
	//attach chans to router
	pingChan := make(chan Msg)
	pongChan := make(chan Msg)
	rot.AttachSendChan(router.StrID("pong"), pongChan)
	rot.AttachRecvChan(router.StrID("ping"), pingChan)
	//start ponger
	pong := &Ponger{pongChan, pingChan, done}
	go pong.Run()
}
Beispiel #7
0
func (ft *FaultMgrTask) init(r router.Router, sn string, role ServantRole) {
	ft.rot = r
	ft.role = role
	ft.servName = sn
	ft.svcCmdChans = make(map[string](chan string))
	ft.sysOOSChan = make(chan string)
	ft.faultReportChan = make(chan *router.FaultRecord)
	ft.sysCmdChan = make(chan string)
	ft.rot.AttachSendChan(router.StrID("/Sys/OutOfService"), ft.sysOOSChan)
	ft.rot.AttachRecvChan(router.StrID("/Sys/Command"), ft.sysCmdChan)
	//use a bindChan to keep faultReportChan open when all clients exit
	bc := make(chan *router.BindEvent, 1)
	ft.rot.AttachRecvChan(router.StrID("/Fault/DB/Exception"), ft.faultReportChan, bc)
	ft.rot.AttachRecvChan(router.StrID("/Fault/AppService/Exception"), ft.faultReportChan, bc)
}
Beispiel #8
0
func (dt *DbTask) init(r router.Router, sn string, role ServantRole) {
	dt.rot = r
	dt.role = role
	dt.servName = sn
	dt.random = rand.New(rand.NewSource(time.Seconds()))
	dt.dbRespChans = make(map[string](chan string))
	dt.dbReqChan = make(chan *DbReq)
	dt.sysCmdChan = make(chan string)
	//output_intf or send chans
	dt.FaultRaiser = router.NewFaultRaiser(router.StrID("/Fault/DB/Exception"), r, "DbTask")
	//input_intf or recv chans
	r.AttachRecvChan(router.StrID("/Sys/Command"), dt.sysCmdChan)
	//use a bindChan to keep dbReqChan open when all clients detach & exit
	bc := make(chan *router.BindEvent, 1)
	r.AttachRecvChan(router.StrID("/DB/Request"), dt.dbReqChan, bc)
}
Beispiel #9
0
func main() {
	flag.Parse()
	if flag.NArg() < 1 {
		fmt.Println("Usage: pingpong5 num_runs hideTrace")
		return
	} else if flag.NArg() > 1 {
		showPingPong = false
	}
	numRuns, _ := strconv.Atoi(flag.Arg(0))
	done := make(chan bool)
	connNow := make(chan bool)
	//start two goroutines to setup a unix sock connection
	//connect two routers thru unix sock
	//and then hook up Pinger and Ponger to the routers
	go func() { //setup Pinger sock conn
		//wait for ponger up
		<-connNow
		//set up an io conn to ponger thru tcp sock
		conn, _ := net.Dial("tcp", "", "[::]:9099")
		fmt.Println("ping conn up")

		//create router and connect it to io conn
		rot := router.New(router.StrID(), 32, router.BroadcastPolicy)
		rot.ConnectRemote(conn, router.GobMarshaling)

		//hook up Pinger and Ponger
		newPinger(rot, done, numRuns)
	}()
	go func() { //setup Ponger sock conn
		//wait to set up an io conn thru tcp sock
		l, _ := net.Listen("tcp", ":9099")
		connNow <- true //notify pinger that ponger's ready to accept
		conn, _ := l.Accept()
		fmt.Println("pong conn up")

		//create router and connect it to io conn
		rot := router.New(router.StrID(), 32, router.BroadcastPolicy)
		rot.ConnectRemote(conn, router.GobMarshaling)

		//hook up Ponger
		newPonger(rot, done)
	}()
	//wait for ping-pong to finish
	<-done
	<-done
}
Beispiel #10
0
func newPonger(rot router.Router, done chan<- bool) {
	//attach chans to router
	pingChan := make(chan *Msg)
	pongChan := make(chan *Msg)
	//bindChan := make(chan *router.BindEvent, 1)
	rot.AttachSendChan(router.StrID("pong"), pongChan /*, bindChan*/)
	rot.AttachRecvChan(router.StrID("ping"), pingChan)
	//wait for pinger connecting
	/*
		for {
			if (<-bindChan).Count > 0 {
				break
			}
		}
	*/
	//start ponger
	pong := &Ponger{pongChan, pingChan, done}
	go pong.Run()
}
Beispiel #11
0
func main() {
	flag.Parse()
	if flag.NArg() < 1 {
		fmt.Println("Usage: pingpong3 num_runs hideTrace")
		return
	} else if flag.NArg() > 1 {
		showPingPong = false
	}
	numRuns, _ := strconv.Atoi(flag.Arg(0))
	//alloc two routers to connect them
	rot1 := router.New(router.StrID(), 32, router.BroadcastPolicy)
	rot2 := router.New(router.StrID(), 32, router.BroadcastPolicy)
	rot1.Connect(rot2)
	done := make(chan bool)
	//hook up Pinger and Ponger
	newPinger(rot1, done, numRuns)
	newPonger(rot2, done)
	//wait for ping-pong to finish
	<-done
	<-done
}
Beispiel #12
0
func NewServant(n string, role ServantRole, done chan bool) *Servant {
	s := new(Servant)
	s.Rot = router.New(router.StrID(), 32, router.BroadcastPolicy /*, n, router.ScopeLocal*/)
	s.role = role
	s.name = n
	//start system tasks, ServiceTask will be created when clients connect
	NewSysMgrTask(s.Rot, n, role)
	NewDbTask(s.Rot, n, role)
	NewFaultMgrTask(s.Rot, n, role)
	//run Servant mainloop to wait for client connection
	go s.Run(done)
	return s
}
Beispiel #13
0
func (at *ServiceTask) shutdown() {
	svcname := "/App/" + at.name
	//output_intf or send chans
	at.FaultRaiser.Close()
	at.rot.DetachChan(router.StrID(svcname+"/Response"), at.svcRespChan)
	at.rot.DetachChan(router.StrID("/DB/Request"), at.dbReqChan)
	//input_intf or recv chans
	at.rot.DetachChan(router.StrID(svcname+"/Request"), at.svcReqChan)
	at.rot.DetachChan(router.StrID("/Sys/Command"), at.sysCmdChan)
	at.rot.DetachChan(router.StrID(svcname+"/Command"), at.svcCmdChan)
	at.rot.DetachChan(router.StrID(svcname+"/DB/Response"), at.dbRespChan)
}
Beispiel #14
0
func (at *ServiceTask) init(r router.Router, sn string, n string, role ServantRole) {
	at.rot = r
	at.name = n
	at.servantName = sn
	at.role = role
	at.random = rand.New(rand.NewSource(time.Seconds()))
	at.svcRespChan = make(chan string)
	at.dbReqChan = make(chan *DbReq)
	at.svcReqChan = make(chan string, router.DefDataChanBufSize)
	at.sysCmdChan = make(chan string)
	at.svcCmdChan = make(chan string)
	at.dbRespChan = make(chan string)
	at.bindChan = make(chan *router.BindEvent, 1)
	svcname := "/App/" + at.name
	//output_intf or send chans
	at.FaultRaiser = router.NewFaultRaiser(router.StrID("/Fault/AppService/Exception"), at.rot, at.name)
	at.rot.AttachSendChan(router.StrID("/DB/Request"), at.dbReqChan)
	at.rot.AttachSendChan(router.StrID(svcname+"/Response"), at.svcRespChan)
	//input_intf or recv chans
	at.rot.AttachRecvChan(router.StrID("/Sys/Command"), at.sysCmdChan)
	at.rot.AttachRecvChan(router.StrID(svcname+"/Command"), at.svcCmdChan)
	at.rot.AttachRecvChan(router.StrID(svcname+"/DB/Response"), at.dbRespChan)
	at.rot.AttachRecvChan(router.StrID(svcname+"/Request"), at.svcReqChan, at.bindChan)
}
Beispiel #15
0
func main() {
	l, err := net.Listen("tcp", ":0")
	if err != nil {
		fmt.Println(err)
		return
	}
	fmt.Println(l.Addr().String())

	subjMap := make(map[string]*Subject)

	rot := router.New(router.StrID(), 32, router.BroadcastPolicy /*, "chatsrv", router.ScopeLocal*/)

	//start server mainloop in a separate goroutine, and recv client conn in main goroutine
	go func() {
		//subscribe to remote publications, so learn what subjects are created
		pubChan := make(chan *router.IdChanInfoMsg)
		//attach a recv chan with a "chan BindEvent"
		//this recv chan will not be closed when all senders detach
		bindChan := make(chan *router.BindEvent, 1)
		rot.AttachRecvChan(rot.NewSysID(router.PubId, router.ScopeRemote), pubChan, bindChan)
		//stopChan to notify when all people leave a subject
		stopChan := make(chan string, 36)

		for {
			select {
			case idstr := <-stopChan:
				subjMap[idstr] = nil, false
			case pub := <-pubChan:
				//process recved client publication of subjects
				for _, v := range pub.Info {
					id := v.Id.(*router.StrId) //get the real id type
					subj, ok := subjMap[id.Val]
					if ok {
						continue
					}
					fmt.Printf("add subject: %v\n", id.Val)
					//add a new subject with ScopeRemote, so that msgs are forwarded
					//to peers in connected routers
					id.ScopeVal = router.ScopeRemote
					id.MemberVal = router.MemberLocal
					subj = newSubject()
					subjMap[id.Val] = subj
					//subscribe to new subjects, forward recved msgs to other
					rot.AttachSendChan(id, subj.sendChan)
					rot.AttachRecvChan(id, subj.recvChan)
					//start forwarding
					go func(subjname string) {
						for val := range subj.recvChan {
							fmt.Printf("chatsrv forward: subject[%v], msg[%s]\n", subjname, val)
							subj.sendChan <- val
						}
						stopChan <- subjname
						fmt.Printf("chatsrv stop forwarding for : %v\n", subjname)
					}(id.Val)
				}
			}
		}
	}()

	//keep accepting client conn and connect local router to it
	for {
		conn, err := l.Accept()
		if err != nil {
			fmt.Println(err)
			return
		}
		fmt.Println("one client connect")

		_, err = rot.ConnectRemote(conn, router.JsonMarshaling)
		if err != nil {
			fmt.Println(err)
			return
		}
	}

	//in fact never reach here
	rot.Close()
	l.Close()
}