func runTreeSmallConfig(signType sign.Type, RoundsPerView int, suite abstract.Suite, failureRate int, faultyNodes ...int) error { var hc *config.HostConfig var err error opts := config.ConfigOptions{Suite: suite} if len(faultyNodes) > 0 { opts.Faulty = true } hc, err = config.LoadConfig("testdata/exconf.json", opts) if err != nil { return err } for _, fh := range faultyNodes { fmt.Println("Setting", hc.SNodes[fh].Name(), "as faulty") if failureRate == 100 { hc.SNodes[fh].Host.(*coconet.FaultyHost).SetDeadFor("commit", true) } // hc.SNodes[fh].Host.(*coconet.FaultyHost).Die() } if len(faultyNodes) > 0 { for i := range hc.SNodes { hc.SNodes[i].FailureRate = failureRate } } for _, sn := range hc.SNodes { sn.RoundsPerView = RoundsPerView } err = hc.Run(false, signType) if err != nil { return err } for _, sn := range hc.SNodes { defer sn.Close() } // Have root node initiate the signing protocol via a simple annoucement hc.SNodes[0].LogTest = []byte("Hello World") hc.SNodes[0].StartAnnouncement(&sign.AnnouncementMessage{LogTest: hc.SNodes[0].LogTest, Round: 1}) return nil }
// # Messages per round, # rounds, failure rate[0..100], list of faulty nodes func runTSSIntegration(RoundsPerView, nMessages, nRounds, failureRate, failAsRootEvery, failAsFollowerEvery int, faultyNodes ...int) error { //coll_stamp.ROUND_TIME = 1 * time.Second var hostConfig *config.HostConfig var err error // load config with faulty or healthy hosts opts := config.ConfigOptions{} if len(faultyNodes) > 0 { opts.Faulty = true } hostConfig, err = config.LoadConfig("testdata/exconf.json", opts) if err != nil { return err } log.Printf("load config returned dir: %p", hostConfig.Dir) // set FailureRates as pure percentages if len(faultyNodes) > 0 { for i := range hostConfig.SNodes { hostConfig.SNodes[i].FailureRate = failureRate } } // set root failures if failAsRootEvery > 0 { for i := range hostConfig.SNodes { hostConfig.SNodes[i].FailAsRootEvery = failAsRootEvery } } // set followerfailures for _, f := range faultyNodes { hostConfig.SNodes[f].FailAsFollowerEvery = failAsFollowerEvery } for _, n := range hostConfig.SNodes { n.RoundsPerView = RoundsPerView } err = hostConfig.Run(true, sign.MerkleTree) if err != nil { return err } // Connect all TSServers to their clients, except for root TSServer ncps := 3 // # clients per TSServer stampers := make([]*stamp.Server, len(hostConfig.SNodes)) for i := range stampers { stampers[i] = stamp.NewServer(hostConfig.SNodes[i]) defer func() { hostConfig.SNodes[i].Close() time.Sleep(1 * time.Second) }() } clientsLists := make([][]*stamp.Client, len(hostConfig.SNodes[1:])) for i, s := range stampers[1:] { clientsLists[i] = createClientsForTSServer(ncps, s, hostConfig.Dir, 0+i+ncps) } for i, s := range stampers[1:] { go s.Run("regular", nRounds) go s.ListenToClients() go func(clients []*stamp.Client, nRounds int, nMessages int, s *stamp.Server) { log.Println("clients Talk") time.Sleep(1 * time.Second) clientsTalk(clients, nRounds, nMessages, s) log.Println("Clients done Talking") }(clientsLists[i], nRounds, nMessages, s) } log.Println("RUNNING ROOT") stampers[0].ListenToClients() stampers[0].Run("root", nRounds) log.Println("Done running root") // After clients receive messages back we need a better way // of waiting to make sure servers check ElGamal sigs // time.Sleep(1 * time.Second) log.Println("DONE with test") return nil }
// Dispatch-function for running either client or server (mode-parameter) func Run(app *config.AppConfig, conf *deploy.Config) { // Do some common setup if app.Mode == "client" { app.Hostname = app.Name } dbg.Lvl3(app.Hostname, "Starting to run") if conf.Debug > 1 { sign.DEBUG = true } if app.Hostname == "" { log.Fatal("no hostname given", app.Hostname) } // load the configuration dbg.Lvl3("loading configuration for", app.Hostname) var hc *config.HostConfig var err error s := GetSuite(conf.Suite) opts := config.ConfigOptions{ConnType: "tcp", Host: app.Hostname, Suite: s} if conf.Failures > 0 || conf.FFail > 0 { opts.Faulty = true } hc, err = config.LoadConfig("tree.json", opts) if err != nil { fmt.Println(err) log.Fatal(err) } // Wait for everybody to be ready before going on ioutil.WriteFile("coll_stamp_up/up"+app.Hostname, []byte("started"), 0666) for { _, err := os.Stat("coll_stamp_up") if err == nil { files, _ := ioutil.ReadDir("coll_stamp_up") dbg.Lvl4(app.Hostname, "waiting for others to finish", len(files)) time.Sleep(time.Second) } else { break } } dbg.Lvl2(app.Hostname, "thinks everybody's here") // set FailureRates if conf.Failures > 0 { for i := range hc.SNodes { hc.SNodes[i].FailureRate = conf.Failures } } // set root failures if conf.RFail > 0 { for i := range hc.SNodes { hc.SNodes[i].FailAsRootEvery = conf.RFail } } // set follower failures // a follower fails on %ffail round with failureRate probability for i := range hc.SNodes { hc.SNodes[i].FailAsFollowerEvery = conf.FFail } defer func() { dbg.Lvl1("Collective Signing", app.Hostname, "has terminated in mode", app.Mode) }() switch app.Mode { case "client": log.Panic("No client mode") case "server": RunServer(app, conf, hc) } }
func RunServer(hostname, app string, rounds int, rootwait int, debug int, testConnect bool, failureRate, rFail, fFail int, logger, suite string) { dbg.Lvl3(hostname, "Starting to run") if debug > 1 { sign.DEBUG = true } // fmt.Println("EXEC TIMESTAMPER: " + hostname) if hostname == "" { log.Fatal("no hostname given") } // load the configuration //dbg.Lvl3("loading configuration") var hc *config.HostConfig var err error s := GetSuite(suite) opts := config.ConfigOptions{ConnType: "tcp", Host: hostname, Suite: s} if failureRate > 0 || fFail > 0 { opts.Faulty = true } configTime := time.Now() hc, err = config.LoadConfig("tree.json", opts) if err != nil { fmt.Println(err) log.Fatal(err) } dbg.Lvl3(hostname, "finished loading config after", time.Since(configTime)) for i := range hc.SNodes { // set FailureRates if failureRate > 0 { hc.SNodes[i].FailureRate = failureRate } // set root failures if rFail > 0 { hc.SNodes[i].FailAsRootEvery = rFail } // set follower failures // a follower fails on %ffail round with failureRate probability hc.SNodes[i].FailAsFollowerEvery = fFail } // Wait for everybody to be ready before going on ioutil.WriteFile("coll_stamp_up/up"+hostname, []byte("started"), 0666) for { _, err := os.Stat("coll_stamp_up") if err == nil { dbg.Lvl4(hostname, "waiting for others to finish") time.Sleep(time.Second) } else { break } } dbg.Lvl3(hostname, "thinks everybody's here") err = hc.Run(app != "coll_sign", sign.MerkleTree, hostname) if err != nil { log.Fatal(err) } defer func(sn *sign.Node) { //log.Panicln("program has terminated:", hostname) dbg.Lvl1("Program timestamper has terminated:", hostname) sn.Close() }(hc.SNodes[0]) stampers, _, err := RunTimestamper(hc, 0, hostname) // get rid of the hc information so it can be GC'ed hc = nil if err != nil { log.Fatal(err) } for _, s := range stampers { // only listen if this is the hostname specified if s.Name() == hostname { s.Logger = logger s.Hostname = hostname s.App = app if s.IsRoot(0) { dbg.Lvl1("Root timestamper at:", hostname, rounds, "Waiting: ", rootwait) // wait for the other nodes to get set up time.Sleep(time.Duration(rootwait) * time.Second) dbg.Lvl1("Starting root-round") s.Run("root", rounds) // dbg.Lvl3("\n\nROOT DONE\n\n") } else if !testConnect { dbg.Lvl2("Running regular timestamper on:", hostname) s.Run("regular", rounds) // dbg.Lvl1("\n\nREGULAR DONE\n\n") } else { // testing connection dbg.Lvl1("Running connection-test on:", hostname) s.Run("test_connect", rounds) } } } }