From 38fe1f21dc8d356157845bf7b930291d54879def Mon Sep 17 00:00:00 2001 From: adnano Date: Sun, 27 Sep 2020 20:20:59 -0400 Subject: [PATCH] Change package name to gmi --- README.md | 4 +-- cert.go | 2 +- client.go | 2 +- examples/auth/auth.go | 62 ++++++++++++++++++--------------------- examples/client/client.go | 30 +++++++++---------- examples/server/server.go | 6 ++-- gemini.go | 2 +- gemini_test.go | 2 +- server.go | 2 +- tofu.go | 2 +- verify.go | 18 ++++++------ 11 files changed, 64 insertions(+), 68 deletions(-) diff --git a/README.md b/README.md index 4847217..daa3ffb 100644 --- a/README.md +++ b/README.md @@ -59,7 +59,7 @@ gemini.Send(req) Clients can also load their own list of known hosts: ```go -client := &Client{} +client := &gmi.Client{} if err := client.KnownHosts.LoadFrom("path/to/my/known_hosts"); err != nil { log.Fatal(err) } @@ -69,7 +69,7 @@ Clients can then specify how to trust certificates in the `TrustCertificate` field: ```go -client.TrustCertificate = func(hostname string, cert *x509.Certificate, knownHosts *gemini.KnownHosts) error { +client.TrustCertificate = func(hostname string, cert *x509.Certificate, knownHosts *gmi.KnownHosts) error { // If the certificate is in the known hosts list, allow the connection return knownHosts.Lookup(hostname, cert) } diff --git a/cert.go b/cert.go index e9c4863..8c82aa4 100644 --- a/cert.go +++ b/cert.go @@ -1,4 +1,4 @@ -package gemini +package gmi import ( "bytes" diff --git a/client.go b/client.go index c067dc2..960b7b1 100644 --- a/client.go +++ b/client.go @@ -1,5 +1,5 @@ // Package gemini implements the Gemini protocol. -package gemini +package gmi import ( "bufio" diff --git a/examples/auth/auth.go b/examples/auth/auth.go index 0c99535..6abd0c8 100644 --- a/examples/auth/auth.go +++ b/examples/auth/auth.go @@ -39,12 +39,12 @@ func main() { // // go run -tags=example ../cert // - cert, err := tls.LoadX509KeyPair("examples/client/localhost.crt", "examples/client/localhost.key") + cert, err := tls.LoadX509KeyPair("examples/server/localhost.crt", "examples/server/localhost.key") if err != nil { log.Fatal(err) } - handler := &gemini.ServeMux{} + handler := &gmi.ServeMux{} handler.HandleFunc("", welcome) handler.HandleFunc("/login", login) handler.HandleFunc("/login/password", loginPassword) @@ -52,7 +52,7 @@ func main() { handler.HandleFunc("/admin", admin) handler.HandleFunc("/logout", logout) - server := &gemini.Server{ + server := &gmi.Server{ Certificate: cert, Handler: handler, } @@ -63,102 +63,98 @@ func main() { } func getSession(crt *x509.Certificate) (*session, bool) { - fingerprint := gemini.Fingerprint(crt) + fingerprint := gmi.Fingerprint(crt) session, ok := sessions[fingerprint] return session, ok } -func welcome(rw *gemini.ResponseWriter, req *gemini.Request) { - rw.WriteHeader(gemini.StatusSuccess, "text/gemini") +func welcome(rw *gmi.ResponseWriter, req *gmi.Request) { + rw.WriteHeader(gmi.StatusSuccess, "text/gemini") rw.Write([]byte("Welcome to this example.\n=> /login Login\n")) } -func login(rw *gemini.ResponseWriter, req *gemini.Request) { +func login(rw *gmi.ResponseWriter, req *gmi.Request) { if len(req.TLS.PeerCertificates) > 0 { if username := req.URL.RawQuery; username == "" { - rw.WriteHeader(gemini.StatusInput, "Username") + rw.WriteHeader(gmi.StatusInput, "Username") } else { - fingerprint := gemini.Fingerprint(req.TLS.PeerCertificates[0]) + fingerprint := gmi.Fingerprint(req.TLS.PeerCertificates[0]) sessions[fingerprint] = &session{ username: username, } // TODO: Remove scheme and host once example client can handle relative redirects - rw.WriteHeader(gemini.StatusRedirectTemporary, "gemini://localhost/login/password") + rw.WriteHeader(gmi.StatusRedirect, "gemini://localhost/login/password") } } else { - rw.WriteHeader(gemini.StatusClientCertificateRequired, "Certificate required") + rw.WriteHeader(gmi.StatusClientCertificateRequired, "Certificate required") } } -func loginPassword(rw *gemini.ResponseWriter, req *gemini.Request) { +func loginPassword(rw *gmi.ResponseWriter, req *gmi.Request) { if len(req.TLS.PeerCertificates) > 0 { session, ok := getSession(req.TLS.PeerCertificates[0]) if !ok { - rw.WriteHeader(gemini.StatusCertificateNotAuthorised, "Not authorized") + rw.WriteHeader(gmi.StatusCertificateNotAuthorised, "Not authorized") return } if password := req.URL.RawQuery; password == "" { - rw.WriteHeader(gemini.StatusInput, "Password") + rw.WriteHeader(gmi.StatusInput, "Password") } else { expected := logins[session.username].password if password == expected { // TODO: Remove scheme and host once example client can handle relative redirects session.authorized = true - rw.WriteHeader(gemini.StatusRedirectTemporary, "gemini://localhost/profile") + rw.WriteHeader(gmi.StatusRedirect, "gemini://localhost/profile") } else { - rw.WriteHeader(gemini.StatusInput, "Wrong password. Please try again") + rw.WriteHeader(gmi.StatusInput, "Wrong password. Please try again") } } } else { - rw.WriteHeader(gemini.StatusClientCertificateRequired, "Certificate required") + rw.WriteHeader(gmi.StatusClientCertificateRequired, "Certificate required") } } -func logout(rw *gemini.ResponseWriter, req *gemini.Request) { +func logout(rw *gmi.ResponseWriter, req *gmi.Request) { if len(req.TLS.PeerCertificates) > 0 { - fingerprint := gemini.Fingerprint(req.TLS.PeerCertificates[0]) + fingerprint := gmi.Fingerprint(req.TLS.PeerCertificates[0]) delete(sessions, fingerprint) } - rw.WriteHeader(gemini.StatusSuccess, "text/gemini") + rw.WriteHeader(gmi.StatusSuccess, "text/gemini") rw.Write([]byte("Successfully logged out.\n")) } -func badLogin(rw *gemini.ResponseWriter, req *gemini.Request) { - -} - -func profile(rw *gemini.ResponseWriter, req *gemini.Request) { +func profile(rw *gmi.ResponseWriter, req *gmi.Request) { if len(req.TLS.PeerCertificates) > 0 { session, ok := getSession(req.TLS.PeerCertificates[0]) if !ok { - rw.WriteHeader(gemini.StatusCertificateNotAuthorised, "Certificate not authorized") + rw.WriteHeader(gmi.StatusCertificateNotAuthorised, "Certificate not authorized") return } user := logins[session.username] profile := fmt.Sprintf("Username: %s\nAdmin: %t\n=> /logout Logout", session.username, user.admin) - rw.WriteHeader(gemini.StatusSuccess, "text/gemini") + rw.WriteHeader(gmi.StatusSuccess, "text/gemini") rw.Write([]byte(profile)) } else { - rw.WriteHeader(gemini.StatusClientCertificateRequired, "Certificate required") + rw.WriteHeader(gmi.StatusClientCertificateRequired, "Certificate required") } } -func admin(rw *gemini.ResponseWriter, req *gemini.Request) { +func admin(rw *gmi.ResponseWriter, req *gmi.Request) { if len(req.TLS.PeerCertificates) > 0 { session, ok := getSession(req.TLS.PeerCertificates[0]) if !ok { - rw.WriteHeader(gemini.StatusCertificateNotAuthorised, "Certificate not authorized") + rw.WriteHeader(gmi.StatusCertificateNotAuthorised, "Certificate not authorized") return } user := logins[session.username] if !user.admin { - rw.WriteHeader(gemini.StatusCertificateNotAuthorised, "Admins only!") + rw.WriteHeader(gmi.StatusCertificateNotAuthorised, "Admins only!") return } - rw.WriteHeader(gemini.StatusSuccess, "text/gemini") + rw.WriteHeader(gmi.StatusSuccess, "text/gemini") rw.Write([]byte("Welcome to the admin portal.\n")) } else { - rw.WriteHeader(gemini.StatusClientCertificateRequired, "Certificate required") + rw.WriteHeader(gmi.StatusClientCertificateRequired, "Certificate required") } } diff --git a/examples/client/client.go b/examples/client/client.go index 4c924a6..b209d0e 100644 --- a/examples/client/client.go +++ b/examples/client/client.go @@ -13,22 +13,22 @@ import ( var ( scanner = bufio.NewScanner(os.Stdin) - client *gemini.Client + client *gmi.Client ) func init() { // Initialize the client - client = &gemini.Client{} + client = &gmi.Client{} client.KnownHosts.Load() // Load known hosts - client.TrustCertificate = func(hostname string, cert *x509.Certificate, knownHosts *gemini.KnownHosts) error { + client.TrustCertificate = func(hostname string, cert *x509.Certificate, knownHosts *gmi.KnownHosts) error { err := knownHosts.Lookup(hostname, cert) if err != nil { switch err { - case gemini.ErrCertificateNotTrusted: + case gmi.ErrCertificateNotTrusted: // Alert the user that the certificate is not trusted fmt.Printf("Warning: Certificate for %s is not trusted!\n", hostname) fmt.Println("This could indicate a Man-in-the-Middle attack.") - case gemini.ErrUnknownCertificate: + case gmi.ErrUnknownCertificate: // Prompt the user to trust the certificate trust := trustCertificate(cert) switch trust { @@ -48,33 +48,33 @@ func init() { } // sendRequest sends a request to the given url. -func sendRequest(req *gemini.Request) error { +func sendRequest(req *gmi.Request) error { resp, err := client.Send(req) if err != nil { return err } switch resp.Status / 10 { - case gemini.StatusClassInput: + case gmi.StatusClassInput: fmt.Printf("%s: ", resp.Meta) scanner.Scan() req.URL.RawQuery = scanner.Text() return sendRequest(req) - case gemini.StatusClassSuccess: + case gmi.StatusClassSuccess: fmt.Print(string(resp.Body)) return nil - case gemini.StatusClassRedirect: + case gmi.StatusClassRedirect: fmt.Println("Redirecting to ", resp.Meta) - req, err := gemini.NewRequest(resp.Meta) + req, err := gmi.NewRequest(resp.Meta) if err != nil { return err } return sendRequest(req) - case gemini.StatusClassTemporaryFailure: + case gmi.StatusClassTemporaryFailure: return fmt.Errorf("Temporary failure: %s", resp.Meta) - case gemini.StatusClassPermanentFailure: + case gmi.StatusClassPermanentFailure: return fmt.Errorf("Permanent failure: %s", resp.Meta) - case gemini.StatusClassClientCertificateRequired: + case gmi.StatusClassClientCertificateRequired: fmt.Println("Generating client certificate for", req.Hostname()) return nil // TODO: Generate and store client certificate } @@ -99,7 +99,7 @@ Otherwise, this should be safe to trust. => ` func trustCertificate(cert *x509.Certificate) trust { - fmt.Printf(trustPrompt, gemini.Fingerprint(cert)) + fmt.Printf(trustPrompt, gmi.Fingerprint(cert)) scanner.Scan() switch scanner.Text() { case "t": @@ -118,7 +118,7 @@ func main() { } url := os.Args[1] - req, err := gemini.NewRequest(url) + req, err := gmi.NewRequest(url) if err != nil { fmt.Println(err) os.Exit(1) diff --git a/examples/server/server.go b/examples/server/server.go index e761cd0..09abf50 100644 --- a/examples/server/server.go +++ b/examples/server/server.go @@ -20,10 +20,10 @@ func main() { log.Fatal(err) } - mux := &gemini.ServeMux{} - mux.Handle("/", gemini.FileServer(gemini.Dir("/var/www"))) + mux := &gmi.ServeMux{} + mux.Handle("/", gmi.FileServer(gmi.Dir("/var/www"))) - server := gemini.Server{ + server := gmi.Server{ Handler: mux, Certificate: cert, } diff --git a/gemini.go b/gemini.go index bef4c68..957dd43 100644 --- a/gemini.go +++ b/gemini.go @@ -1,4 +1,4 @@ -package gemini +package gmi import ( "crypto/x509" diff --git a/gemini_test.go b/gemini_test.go index b118640..b92792b 100644 --- a/gemini_test.go +++ b/gemini_test.go @@ -1,4 +1,4 @@ -package gemini +package gmi import ( "math/rand" diff --git a/server.go b/server.go index 7eb3aaf..5a5db48 100644 --- a/server.go +++ b/server.go @@ -1,4 +1,4 @@ -package gemini +package gmi import ( "bufio" diff --git a/tofu.go b/tofu.go index 21384ab..81502d6 100644 --- a/tofu.go +++ b/tofu.go @@ -1,4 +1,4 @@ -package gemini +package gmi import ( "bufio" diff --git a/verify.go b/verify.go index 7abef8f..8a0fd5a 100644 --- a/verify.go +++ b/verify.go @@ -1,4 +1,12 @@ -package gemini +// Hostname verification code from the crypto/x509 package. +// Modified to allow Common Names in the short term, until new certificates +// can be issued with SANs. + +// Copyright 2011 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +package gmi import ( "crypto/x509" @@ -9,14 +17,6 @@ import ( "unicode/utf8" ) -// Hostname verification code from the crypto/x509 package. -// Modified to allow Common Names in the short term, until new certificates -// can be issued with SANs. - -// Copyright 2011 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - var ( oidExtensionSubjectAltName = []int{2, 5, 29, 17} )