func (sr *StampSignature) UnmarshalJSON(dataJSON []byte) error { type Alias StampSignature suite := app.GetSuite(sr.SuiteStr) aux := &struct { BinaryBlob []byte Response abstract.Secret Challenge abstract.Secret AggCommit abstract.Point AggPublic abstract.Point *Alias }{ Response: suite.Secret(), Challenge: suite.Secret(), AggCommit: suite.Point(), AggPublic: suite.Point(), Alias: (*Alias)(sr), } if err := json.Unmarshal(dataJSON, &aux); err != nil { return err } if err := suite.Read(bytes.NewReader(aux.BinaryBlob), &sr.Response, &sr.Challenge, &sr.AggCommit, &sr.AggPublic); err != nil { dbg.Fatal("decoding signature Response / Challenge / AggCommit:", err) return err } return nil }
func readConfig() *app.ConfigConode { conf := &app.ConfigConode{} if err := app.ReadTomlConfig(conf, "testdata/config.toml"); err != nil { dbg.Fatal("Could not read toml config... : ", err) } dbg.Lvl2("Configuration file read") suite = app.GetSuite(conf.Suite) return conf }
// NewStamp initializes a new stamp-client by reading all // configuration from a "config.toml"-file. // If an error occurs, it is returned by the second argument. // It also initializes X0 and Suite for later use. func NewStamp(file string) (*Stamp, error) { s := &Stamp{} err := app.ReadTomlConfig(&s.Config, file) if err != nil { return nil, err } s.Suite = app.GetSuite(s.Config.Suite) pub, _ := base64.StdEncoding.DecodeString(s.Config.AggPubKey) s.Suite.Read(bytes.NewReader(pub), &s.X0) return s, nil }
// NewPeer returns a peer that can be used to set up // connections. func NewPeer(address string, conf *app.ConfigConode) *Peer { suite := app.GetSuite(conf.Suite) var err error // make sure address has a port or insert default one address, err = cliutils.VerifyPort(address, DefaultPort) if err != nil { dbg.Fatal(err) } // For retro compatibility issues, convert the base64 encoded key into hex // encoded keys.... convertTree(suite, conf.Tree) // Add our private key to the tree (compatibility issues again with graphs/ // lib) addPrivateKey(suite, address, conf) // load the configuration dbg.Lvl3("loading configuration") var hc *graphs.HostConfig opts := graphs.ConfigOptions{ConnType: "tcp", Host: address, Suite: suite} hc, err = graphs.LoadConfig(conf.Hosts, conf.Tree, suite, opts) if err != nil { dbg.Fatal(err) } // Listen to stamp-requests on port 2001 node := hc.Hosts[address] peer := &Peer{ conf: conf, Node: node, RLock: sync.Mutex{}, CloseChan: make(chan bool, 5), Hostname: address, } // Start the cothority-listener on port 2000 err = hc.Run(true, sign.MerkleTree, address) if err != nil { dbg.Fatal(err) } go func() { err := peer.Node.Listen() dbg.Lvl3("Node.listen quits with status", err) peer.CloseChan <- true peer.Close() }() return peer }
func wait_for_blocks() { server := "localhost:2011" suite = app.GetSuite("25519") dbg.Lvl2("Connecting to", server) conn := coconet.NewTCPConn(server) err := conn.Connect() if err != nil { dbg.Fatal("Error when getting the connection to the host:", err) } dbg.Lvl1("Connected to ", server) for i := 0; i < 1000; i++ { time.Sleep(1 * time.Second) msg := &BitCoSi.BitCoSiMessage{ Type: BitCoSi.BlockRequestType, ReqNo: 0, } err = conn.PutData(msg) if err != nil { dbg.Fatal("Couldn't send hash-message to server: ", err) } dbg.Lvl1("Sent signature request") // Wait for the signed message tsm := new(BitCoSi.BitCoSiMessage) tsm.Brep = &BitCoSi.BlockReply{} tsm.Brep.SuiteStr = suite.String() err = conn.GetData(tsm) if err != nil { dbg.Fatal("Error while receiving signature:", err) } //dbg.Lvlf1("Got signature response %+v", tsm.Brep) T := new(BitCoSi.TrBlock) T.Block = tsm.Brep.Block T.Print() dbg.Lvlf1("Response %v ", tsm.Brep.Response) } // Asking to close the connection err = conn.PutData(&BitCoSi.BitCoSiMessage{ ReqNo: 1, Type: BitCoSi.BitCoSiClose, }) conn.Close() }
func (sr *StampSignature) MarshalJSON() ([]byte, error) { type Alias StampSignature var b bytes.Buffer suite := app.GetSuite(sr.SuiteStr) if err := suite.Write(&b, sr.Response, sr.Challenge, sr.AggCommit, sr.AggPublic); err != nil { dbg.Lvl1("encoding stampreply response/challenge/AggCommit:", err) return nil, err } return json.Marshal(&struct { BinaryBlob []byte *Alias }{ BinaryBlob: b.Bytes(), Alias: (*Alias)(sr), }) }
// Write will write the struct in a human readable format into this writer // The format is TOML and most fields are written in base64 func (sr *StampSignature) Save(file string) error { var p []string for _, pr := range sr.Prf { p = append(p, base64.StdEncoding.EncodeToString(pr)) } suite := app.GetSuite(sr.SuiteStr) // Write challenge and response + commitment part var bufChall bytes.Buffer var bufResp bytes.Buffer var bufCommit bytes.Buffer var bufPublic bytes.Buffer if err := cliutils.WriteSecret64(suite, &bufChall, sr.Challenge); err != nil { return fmt.Errorf("Could not write secret challenge:", err) } if err := cliutils.WriteSecret64(suite, &bufResp, sr.Response); err != nil { return fmt.Errorf("Could not write secret response:", err) } if err := cliutils.WritePub64(suite, &bufCommit, sr.AggCommit); err != nil { return fmt.Errorf("Could not write aggregated commitment:", err) } if err := cliutils.WritePub64(suite, &bufPublic, sr.AggPublic); err != nil { return fmt.Errorf("Could not write aggregated public key:", err) } // Signature file struct containing everything needed sigStr := &sigFile{ Name: file, SuiteStr: suite.String(), Timestamp: sr.Timestamp, Proof: p, MerkleRoot: base64.StdEncoding.EncodeToString(sr.MerkleRoot), Challenge: bufChall.String(), Response: bufResp.String(), AggCommitment: bufCommit.String(), AggPublic: bufPublic.String(), } // Print to the screen, and write to file dbg.Lvl2("Signature-file will be:\n%+v", sigStr) app.WriteTomlConfig(sigStr, file) return nil }
func (sr *StampSignature) Open(file string) error { // Read in the toml-file sigStr := &sigFile{} err := app.ReadTomlConfig(sigStr, file) if err != nil { return err } suite := app.GetSuite(sigStr.SuiteStr) sr.Timestamp = sigStr.Timestamp for _, pr := range sigStr.Proof { pro, err := base64.StdEncoding.DecodeString(pr) if err != nil { dbg.Lvl1("Couldn't decode proof:", pr) return err } sr.Prf = append(sr.Prf, pro) } // Read the root, the challenge and response sr.MerkleRoot, err = base64.StdEncoding.DecodeString(sigStr.MerkleRoot) if err != nil { fmt.Errorf("Could not decode Merkle Root from sig file:", err) } sr.Response, err = cliutils.ReadSecret64(suite, strings.NewReader(sigStr.Response)) if err != nil { fmt.Errorf("Could not read secret challenge:", err) } if sr.Challenge, err = cliutils.ReadSecret64(suite, strings.NewReader(sigStr.Challenge)); err != nil { fmt.Errorf("Could not read the aggregate commitment:", err) } if sr.AggCommit, err = cliutils.ReadPub64(suite, strings.NewReader(sigStr.AggCommitment)); err != nil { return err } if sr.AggPublic, err = cliutils.ReadPub64(suite, strings.NewReader(sigStr.AggPublic)); err != nil { return err } return nil }
func setupTestSig() { var sig = test_sig{ Suite: "Ed25519", Name: "stamp.sig", Timestamp: 1448637057, Proof: []string{"fN1GPbpXUqLGh20Ls1JmiFncbWcnvai4pt2ufJnUcIo=", "ehvna7oGGqwZsCgLVP1GvEHxCbYl2Bv8fS0EgGEvmB4=", "AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=", "cFol1fkwjOXyXLNM8Bhu3Bafs1L8GnrWWswE19YDh/E=", "cFol1fkwjOXyXLNM8Bhu3Bafs1L8GnrWWswE19YDh/E="}, Root: "vu2wvZDMc5ZlCNspMRWKZCI0ShYZ8zyLfy2cuZFf54A=", Challenge: "ClSG6pa3uklYndfBztJ9yAD8aY2g/GzTq0rs8nQC12w=", Response: "AJXkEEiyvWdoidjjUMUi5nryHRzJSywXoFY/fIT/8FM=", Commitment: "LbMi53pBXpHN1IYa7pRaC953KAox+NvzQSzAOsK1CEQ=", AggPubKey: "dkp32QL4viiR0EiMtnLIVYLgk6PXTcSQlNXFNwpnLiI=", Hash: "RnZyRnItjXQBSMYLfY/f8WDgiYJI9Yh4lQXa6+VwWxc=", } suite = app.GetSuite(sig.Suite) suite.Read(get64R(sig.AggPubKey), &X0) reply.SuiteStr = sig.Suite reply.Timestamp = int64(sig.Timestamp) reply.MerkleRoot = get64(sig.Root) var proof []hashid.HashId for _, p := range sig.Proof { proof = append(proof, get64(p)) } reply.Prf = proof suite.Read(get64R(sig.Challenge), &reply.Challenge) suite.Read(get64R(sig.Response), &reply.Response) suite.Read(get64R(sig.Commitment), &reply.AggCommit) suite.Read(get64R(sig.AggPubKey), &reply.AggPublic) hash = get64(sig.Hash) dbg.Lvl3("Challenge", reply.Challenge) dbg.Lvl3("Response", reply.Response) dbg.Lvl3("Commitment", reply.AggCommit) dbg.Lvl3("AggPubKey", reply.AggPublic) }
// If the server is only given with it's hostname, it supposes that the stamp // server is run on port 2001. Else you will have to add the port yourself. func main() { stamp := cli.NewApp() stamp.Name = "collective" stamp.Usage = "Used to sign files to a cothority tree and to verify issued signatures" stamp.Version = "0.0.1" stamp.Authors = []cli.Author{ { Name: "Linus Gasser", Email: "*****@*****.**", }, { Name: "nikkolasg", Email: "", }, } stamp.Commands = []cli.Command{ { Name: "sign", Aliases: []string{"s"}, Usage: "Request a signed time-stamp on a file. Provide with FILE.", Action: func(c *cli.Context) { dbg.Lvl1("Requesting a timestamp on a cothority tree") server := c.String("server") StampFile(c.Args().First(), server) }, Flags: []cli.Flag{ cli.StringFlag{ Name: "server, s", Value: "", Usage: "Server in the cothority tree we wish to contact. If not given, it will select a random one.", }, }, }, { Name: "check", Aliases: []string{"c"}, Usage: "Verify a given signature against a file", ArgsUsage: "FILE is the name of the file. Signature file should be file.sig otherwise use the sig option", Flags: []cli.Flag{ cli.StringFlag{ Name: "sig", Value: "", Usage: "signature file to verify", }, }, Action: func(c *cli.Context) { sigFile := c.String("sig") if sigFile == "" { sigFile = c.Args().First() + sigExtension } if VerifyFileSignature(c.Args().First(), sigFile) { dbg.Lvl1("Verification OK") } else { dbg.Lvl1("Verification of file failed") } }, }, } stamp.Flags = []cli.Flag{ cli.StringFlag{ Name: "config, c", Value: defaultConfigFile, Usage: "Configuration file of the cothority tree we are using.", }, cli.IntFlag{ Name: "debug, d", Value: 1, Usage: "debug level from 1 (major operations) to 5 (very noisy text)", }, } // Read the config file before stamp.Before = func(c *cli.Context) error { var cf string = c.String("config") if c.String("config") == "" { cf = defaultConfigFile } conf = new(app.ConfigConode) err := app.ReadTomlConfig(conf, cf) suite = app.GetSuite(conf.Suite) pub, _ := base64.StdEncoding.DecodeString(conf.AggPubKey) suite.Read(bytes.NewReader(pub), &public_X0) // sets the right debug options dbg.DebugVisible = c.GlobalInt("debug") return err } stamp.Run(os.Args) }