Skip to content

Commit

Permalink
start JS/WASM wrapper functions
Browse files Browse the repository at this point in the history
  • Loading branch information
cryptix committed Jun 9, 2024
1 parent ed1e27c commit 2265bc5
Show file tree
Hide file tree
Showing 7 changed files with 261 additions and 132 deletions.
13 changes: 6 additions & 7 deletions golang/cmd/sig0namectl/request_key.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,23 +12,22 @@ import (

var requestKeyCmd = &cli.Command{
Name: "requestKey",
Usage: "requestKey <subZone> <zone>",
Usage: "requestKey <my.new.name>",
Aliases: []string{"rk"},
Action: requestKeyAction,
}

func requestKeyAction(cCtx *cli.Context) error {
newSubZone := cCtx.Args().Get(0)
zone := cCtx.Args().Get(1)
if newSubZone == "" || zone == "" {
return cli.Exit("subZone and zone are required", 1)
newName := cCtx.Args().Get(0)
if newName == "" {
return cli.Exit("newName required", 1)
}

reqMsg, dohServer, err := sig0.CreateRequestKeyMsg(newSubZone, zone)
reqMsg, dohServer, err := sig0.CreateRequestKeyMsg(newName)
if err != nil {
return fmt.Errorf("Failed to create request key message: %w", err)
}
log.Println("Requesting key for", newSubZone, "under", zone, "from", dohServer)
log.Println("Requesting key for", newName, "from", dohServer)
spew.Dump(reqMsg)

answer, err := sig0.SendDOHQuery(dohServer, reqMsg)
Expand Down
27 changes: 19 additions & 8 deletions golang/sig0/answers.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package sig0

import (
"encoding/base64"
"errors"
"fmt"

"github.com/miekg/dns"
Expand All @@ -20,26 +21,36 @@ func ParseBase64Answer(answer string) (*dns.Msg, error) {
return resp, nil
}

func ExpectSOA(answer *dns.Msg) (string, error) {
func ExpectSOA(answer *dns.Msg) (*dns.SOA, error) {
if len(answer.Answer) < 1 {
return "", fmt.Errorf("expected at least one authority section.")
return nil, fmt.Errorf("expected at least one answer section.")
}
firstNS := answer.Answer[0]
soa, ok := firstNS.(*dns.SOA)
if !ok {
return "", fmt.Errorf("expected SOA but got type of RR: %T: %+v", firstNS, firstNS)
return nil, fmt.Errorf("expected SOA but got type of RR: %T: %+v", firstNS, firstNS)
}
return soa.Ns, nil
return soa, nil
}

func ExpectAdditonalSOA(answer *dns.Msg) (string, error) {
func ExpectAdditonalSOA(answer *dns.Msg) (*dns.SOA, error) {
if len(answer.Ns) < 1 {
return "", fmt.Errorf("expected at least one authority section.")
return nil, fmt.Errorf("expected at least one authority section.")
}
firstNS := answer.Ns[0]
soa, ok := firstNS.(*dns.SOA)
if !ok {
return "", fmt.Errorf("expected SOA but got type of RR: %T: %+v", firstNS, firstNS)
return nil, fmt.Errorf("expected SOA but got type of RR: %T: %+v", firstNS, firstNS)
}
return soa.Ns, nil
return soa, nil
}

func AnySOA(answer *dns.Msg) (*dns.SOA, error) {
if soa, err := ExpectSOA(answer); err == nil {
return soa, nil
}
if soa, err := ExpectAdditonalSOA(answer); err == nil {
return soa, nil
}
return nil, errors.New("no SOA in either answer or additional")
}
4 changes: 2 additions & 2 deletions golang/sig0/query_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -35,12 +35,12 @@ func TestQuerySOA(t *testing.T) {

soa, err := ExpectSOA(answer)
r.NoError(err, testdata)
a.Equal(testdata.soa, soa)
a.Equal(testdata.soa, soa.Ns)

verifyication, err := QueryWithType(testdata.zone, dns.TypeSOA)
r.NoError(err, testdata)

verifyAnswer, err := SendUDPQuery(soa, verifyication)
verifyAnswer, err := SendUDPQuery(soa.Ns, verifyication)
r.NoError(err, testdata)
r.True(verifyAnswer.Authoritative, verifyAnswer)
}
Expand Down
63 changes: 47 additions & 16 deletions golang/sig0/request_key.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ package sig0
import (
"errors"
"fmt"
"log"
"strings"

"github.com/miekg/dns"
Expand All @@ -14,10 +15,37 @@ var (
DefaultDOHResolver = "dns.quad9.net"
)

func CreateRequestKeyMsg(subZone, zone string) (*dns.Msg, string, error) {
func CreateRequestKeyMsg(newName string) (*dns.Msg, string, error) {
querySOAForNewZone, err := QuerySOA(newName)
if err != nil {
return nil, "", fmt.Errorf("Error: ZONE %s SOA record does not resolve: %w", newName, err)
}

newZoneSOAAnswer, err := SendDOHQuery(DefaultDOHResolver, querySOAForNewZone)
if err != nil {
return nil, "", fmt.Errorf("Error: DOH query failed for %s: %w", DefaultDOHResolver, err)
}

soaForZone, err := AnySOA(newZoneSOAAnswer)
if err != nil {
return nil, "", fmt.Errorf("Error: SOA record not found in response for %s: %w", newName, err)
}

zoneOfName := soaForZone.Hdr.Name
log.Printf("[requestKey] Found zone for new name: %s", zoneOfName)

newNameFQDN := newName
if !strings.HasSuffix(newNameFQDN, ".") {
newNameFQDN += "."
}

if !strings.HasSuffix(newNameFQDN, zoneOfName) {
return nil, "", fmt.Errorf("Error: expected new zone to be under it's SOA. Instead got SOA %q for %q", zoneOfName, newNameFQDN)
}
subDomain := strings.TrimSuffix(newNameFQDN, zoneOfName)

// Determine the zone master using the provided sub zone and base zone
signalZone := fmt.Sprintf("%s.%s", SignalSubzonePrefix, zone)
signalZone := fmt.Sprintf("%s.%s", SignalSubzonePrefix, zoneOfName)
querySOAForSignal, err := QuerySOA(signalZone)
if err != nil {
return nil, "", fmt.Errorf("Error: ZONE %s SOA record does not resolve: %w", signalZone, err)
Expand All @@ -28,38 +56,41 @@ func CreateRequestKeyMsg(subZone, zone string) (*dns.Msg, string, error) {
return nil, "", fmt.Errorf("Error: DOH query failed for %s: %w", DefaultDOHResolver, err)
}

zoneSoa, err := ExpectSOA(soaAnswer)
signalZoneSoa, err := ExpectSOA(soaAnswer)
if err != nil {
return nil, "", fmt.Errorf("Error: SOA record not found in response for %s: %w", signalZone, err)
}

if zoneSoa != "ns1.free2air.org." {
return nil, "", fmt.Errorf("Unexpected SOA: %s - TODO: Query SVCB to get the zone master's DOH endpoint", zoneSoa)
if !strings.HasSuffix(signalZoneSoa.Hdr.Name, soaForZone.Hdr.Name) {
return nil, "", fmt.Errorf("Expected signal zone to be under requested zonet got %q and %q", signalZoneSoa.Hdr.Name, soaForZone.Hdr.Name)
}

if signalZoneSoa.Ns != "ns1.free2air.org." {
return nil, "", fmt.Errorf("Unexpected SOA: %s - TODO: Query SVCB to get the zone master's DOH endpoint", zoneOfName)
}
var dohUpdateHost = "doh.zenr.io"

// Check if zone already exists
newSubZone := fmt.Sprintf("%s.%s", subZone, zone)
err = checkZoneDoesntExist(dohUpdateHost, newSubZone)
err = checkZoneDoesntExist(dohUpdateHost, newName)
if err != nil {
return nil, "", err
return nil, "", fmt.Errorf("exists check for new name %q failed: %w", newName, err)
}

zoneRequest := fmt.Sprintf("%s.%s.%s", subZone, SignalSubzonePrefix, zone)
zoneRequest := fmt.Sprintf("%s%s.%s", subDomain, SignalSubzonePrefix, zoneOfName)
err = checkZoneDoesntExist(dohUpdateHost, zoneRequest)
if err != nil {
return nil, "", err
return nil, "", fmt.Errorf("exists check for zoneRequest %q failed: %w", zoneRequest, err)
}

// craft RRs and create signed update
subZoneSigner, err := LoadOrGenerateKey(newSubZone)
subZoneSigner, err := LoadOrGenerateKey(newName)
if err != nil {
return nil, "", err
}

err = subZoneSigner.StartUpdate(zone)
err = subZoneSigner.StartUpdate(zoneOfName)
if err != nil {
return nil, "", err
return nil, "", fmt.Errorf("unable to start update for zone: %q: %w", zoneOfName, err)
}

// Here we split the key details
Expand All @@ -75,18 +106,18 @@ func CreateRequestKeyMsg(subZone, zone string) (*dns.Msg, string, error) {
nsupdateItemSig0Key := fmt.Sprintf("%s %d %s", zoneRequest, DefaultTTL, keyData)
err = subZoneSigner.UpdateParsedRR(nsupdateItemSig0Key)
if err != nil {
return nil, "", err
return nil, "", fmt.Errorf("failed to add KEY RR: %w", err)
}

nsupdateItemPtr := fmt.Sprintf("%s %d IN PTR %s", signalZone, DefaultTTL, zoneRequest)
err = subZoneSigner.UpdateParsedRR(nsupdateItemPtr)
if err != nil {
return nil, "", err
return nil, "", fmt.Errorf("failed to add PTR RR: %w", err)
}

updateMsg, err := subZoneSigner.UnsignedUpdate(signalZone)
if err != nil {
return nil, "", err
return nil, "", fmt.Errorf("unable to create update message")
}

return updateMsg, dohUpdateHost, nil
Expand Down
4 changes: 2 additions & 2 deletions golang/sig0/request_key_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -13,9 +13,9 @@ func TestRequestKey(t *testing.T) {

buf := make([]byte, 5)
rand.Read(buf)
testSubZone := fmt.Sprintf("sig0namectl-test-%x", buf)
testName := fmt.Sprintf("sig0namectl-test-%x.zenr.io", buf)

zoneRequestMsg, dohServer, err := CreateRequestKeyMsg(testSubZone, "zenr.io")
zoneRequestMsg, dohServer, err := CreateRequestKeyMsg(testName)
r.NoError(err)
r.Equal("doh.zenr.io", dohServer)
t.Log(zoneRequestMsg)
Expand Down
97 changes: 0 additions & 97 deletions golang/wasm/q_js.go

This file was deleted.

Loading

0 comments on commit 2265bc5

Please sign in to comment.