|
|
|
@ -6,7 +6,6 @@ package main
|
|
|
|
|
|
|
|
|
|
import (
|
|
|
|
|
"encoding/base64"
|
|
|
|
|
"errors"
|
|
|
|
|
"fmt"
|
|
|
|
|
"log"
|
|
|
|
|
"os"
|
|
|
|
@ -39,11 +38,11 @@ func oxDeleteNodes(jid string, client *xmpp.Client, iqc chan xmpp.IQ) error {
|
|
|
|
|
}
|
|
|
|
|
query = nodeListReply.SelectElement("query")
|
|
|
|
|
if query == nil {
|
|
|
|
|
return errors.New("error parsing iq reply")
|
|
|
|
|
return fmt.Errorf("error parsing iq reply")
|
|
|
|
|
}
|
|
|
|
|
items := query.SelectElements("item")
|
|
|
|
|
if items == nil {
|
|
|
|
|
return errors.New("error parsing iq reply")
|
|
|
|
|
return fmt.Errorf("error parsing iq reply")
|
|
|
|
|
}
|
|
|
|
|
for _, item := range items {
|
|
|
|
|
node := item.SelectAttr("node")
|
|
|
|
@ -106,26 +105,26 @@ func oxDecrypt(m xmpp.Chat, client *xmpp.Client, iqc chan xmpp.IQ, user string,
|
|
|
|
|
}
|
|
|
|
|
signcrypt := doc.SelectElement("signcrypt")
|
|
|
|
|
if signcrypt == nil {
|
|
|
|
|
return strError, time.Now(), errors.New("ox: no signcrypt element")
|
|
|
|
|
return strError, time.Now(), fmt.Errorf("ox: no signcrypt element")
|
|
|
|
|
}
|
|
|
|
|
to := signcrypt.SelectElement("to")
|
|
|
|
|
if to == nil {
|
|
|
|
|
return strError, time.Now(), errors.New("ox: no to element")
|
|
|
|
|
return strError, time.Now(), fmt.Errorf("ox: no to element")
|
|
|
|
|
}
|
|
|
|
|
jid := to.SelectAttr("jid")
|
|
|
|
|
if jid == nil {
|
|
|
|
|
return strError, time.Now(), errors.New("ox: no jid attribute")
|
|
|
|
|
return strError, time.Now(), fmt.Errorf("ox: no jid attribute")
|
|
|
|
|
}
|
|
|
|
|
if strings.Split(jid.Value, "/")[0] != user {
|
|
|
|
|
return strError, time.Now(), errors.New("ox: encrypted for wrong user")
|
|
|
|
|
return strError, time.Now(), fmt.Errorf("ox: encrypted for wrong user")
|
|
|
|
|
}
|
|
|
|
|
timestamp := signcrypt.SelectElement("time")
|
|
|
|
|
if timestamp == nil {
|
|
|
|
|
return strError, time.Now(), errors.New("ox: no time element")
|
|
|
|
|
return strError, time.Now(), fmt.Errorf("ox: no time element")
|
|
|
|
|
}
|
|
|
|
|
stamp := timestamp.SelectAttr("stamp")
|
|
|
|
|
if stamp == nil {
|
|
|
|
|
return strError, time.Now(), errors.New("ox: no stamp attribute")
|
|
|
|
|
return strError, time.Now(), fmt.Errorf("ox: no stamp attribute")
|
|
|
|
|
}
|
|
|
|
|
msgStamp, err := time.Parse("2006-01-02T15:04:05Z0700", stamp.Value)
|
|
|
|
|
if err != nil {
|
|
|
|
@ -133,7 +132,7 @@ func oxDecrypt(m xmpp.Chat, client *xmpp.Client, iqc chan xmpp.IQ, user string,
|
|
|
|
|
}
|
|
|
|
|
payload := signcrypt.SelectElement("payload")
|
|
|
|
|
if payload == nil {
|
|
|
|
|
return strError, time.Now(), errors.New("ox: no payload element")
|
|
|
|
|
return strError, time.Now(), fmt.Errorf("ox: no payload element")
|
|
|
|
|
}
|
|
|
|
|
body := payload.SelectElement("body")
|
|
|
|
|
if body == nil {
|
|
|
|
@ -173,7 +172,7 @@ func oxImportPrivKey(jid string, privKeyLocation string, client *xmpp.Client, iq
|
|
|
|
|
}
|
|
|
|
|
entity := key.GetEntity()
|
|
|
|
|
if entity.Identities[xmppURI] == nil {
|
|
|
|
|
return errors.New("Key identity is not " + xmppURI)
|
|
|
|
|
return fmt.Errorf("Key identity is not %s", xmppURI)
|
|
|
|
|
}
|
|
|
|
|
pk, err := key.GetPublicKey()
|
|
|
|
|
if err != nil {
|
|
|
|
@ -262,19 +261,19 @@ func oxPublishPubKey(jid string, client *xmpp.Client, iqc chan xmpp.IQ, pubKey *
|
|
|
|
|
return fmt.Errorf("oxPublishPubKey: iq failure publishing public key: %w", err)
|
|
|
|
|
}
|
|
|
|
|
if iqReply.Type != strResult {
|
|
|
|
|
return errors.New("error while publishing public key")
|
|
|
|
|
return fmt.Errorf("error while publishing public key")
|
|
|
|
|
}
|
|
|
|
|
ownPubKeyRingFromPubsub, err := oxRecvPublicKeys(client, iqc, jid, fingerprint)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return errors.New("couldn't successfully verify public key upload")
|
|
|
|
|
return fmt.Errorf("couldn't successfully verify public key upload")
|
|
|
|
|
}
|
|
|
|
|
ownPubKeyFromPubsub := ownPubKeyRingFromPubsub.GetKeys()[0]
|
|
|
|
|
ownPubKeyFromPubsubSerialized, err := ownPubKeyFromPubsub.Serialize()
|
|
|
|
|
if err != nil {
|
|
|
|
|
return errors.New("couldn't successfully verify public key upload")
|
|
|
|
|
return fmt.Errorf("couldn't successfully verify public key upload")
|
|
|
|
|
}
|
|
|
|
|
if pubKeyBase64 != base64.StdEncoding.EncodeToString(ownPubKeyFromPubsubSerialized) {
|
|
|
|
|
return errors.New("couldn't successfully verify public key upload")
|
|
|
|
|
return fmt.Errorf("couldn't successfully verify public key upload")
|
|
|
|
|
}
|
|
|
|
|
root = etree.NewDocument()
|
|
|
|
|
root.WriteSettings.AttrSingleQuote = true
|
|
|
|
@ -310,7 +309,7 @@ func oxPublishPubKey(jid string, client *xmpp.Client, iqc chan xmpp.IQ, pubKey *
|
|
|
|
|
return fmt.Errorf("oxPublishPubKey: iq failure publishing public key list: %w", err)
|
|
|
|
|
}
|
|
|
|
|
if iqReply.Type != strResult {
|
|
|
|
|
return errors.New("couldn't publish public key list")
|
|
|
|
|
return fmt.Errorf("couldn't publish public key list")
|
|
|
|
|
}
|
|
|
|
|
return nil
|
|
|
|
|
}
|
|
|
|
@ -392,7 +391,7 @@ func oxGetPrivKey(jid string, passphrase string) (*crypto.Key, error) {
|
|
|
|
|
log.Fatal("Ox: private key is locked.")
|
|
|
|
|
}
|
|
|
|
|
if key.IsExpired() {
|
|
|
|
|
return nil, errors.New("Ox: private key is expired: " + key.GetFingerprint())
|
|
|
|
|
return nil, fmt.Errorf("Ox: private key is expired: %s", key.GetFingerprint())
|
|
|
|
|
}
|
|
|
|
|
return key, nil
|
|
|
|
|
}
|
|
|
|
@ -478,7 +477,7 @@ func oxRecvPublicKeys(client *xmpp.Client, iqc chan xmpp.IQ, recipient string, f
|
|
|
|
|
return nil, fmt.Errorf("oxRecvPublicKeys: iq error requesting public keys: %w", err)
|
|
|
|
|
}
|
|
|
|
|
if oxPublicKey.Type != strResult {
|
|
|
|
|
return nil, errors.New("error while requesting public key for " +
|
|
|
|
|
return nil, fmt.Errorf("error while requesting public key for %s",
|
|
|
|
|
recipient)
|
|
|
|
|
}
|
|
|
|
|
oxPublicKeyXML := etree.NewDocument()
|
|
|
|
@ -492,18 +491,15 @@ func oxRecvPublicKeys(client *xmpp.Client, iqc chan xmpp.IQ, recipient string, f
|
|
|
|
|
}
|
|
|
|
|
oxPublicKeyXMLPubsub := oxPublicKeyXML.SelectElement("pubsub")
|
|
|
|
|
if oxPublicKeyXMLPubsub == nil {
|
|
|
|
|
return nil, errors.New("ox: no pubsub element in reply to public " +
|
|
|
|
|
"key request")
|
|
|
|
|
return nil, fmt.Errorf("ox: no pubsub element in reply to public key request")
|
|
|
|
|
}
|
|
|
|
|
oxPublicKeyXMLItems := oxPublicKeyXMLPubsub.SelectElement("items")
|
|
|
|
|
if oxPublicKeyXMLItems == nil {
|
|
|
|
|
return nil, errors.New("ox: no items element in reply to public " +
|
|
|
|
|
"key request")
|
|
|
|
|
return nil, fmt.Errorf("ox: no items element in reply to public key request")
|
|
|
|
|
}
|
|
|
|
|
oxPublicKeyXMLItem := oxPublicKeyXMLItems.SelectElement("item")
|
|
|
|
|
if oxPublicKeyXMLItem == nil {
|
|
|
|
|
return nil, errors.New("ox: no item element in reply to public " +
|
|
|
|
|
"key request")
|
|
|
|
|
return nil, fmt.Errorf("ox: no item element in reply to public key request")
|
|
|
|
|
}
|
|
|
|
|
oxPublicKeyXMLPubkeys := oxPublicKeyXMLItem.SelectElements("pubkey")
|
|
|
|
|
for _, r := range oxPublicKeyXMLPubkeys {
|
|
|
|
@ -520,7 +516,7 @@ func oxRecvPublicKeys(client *xmpp.Client, iqc chan xmpp.IQ, recipient string, f
|
|
|
|
|
return nil, fmt.Errorf("oxRecvPublicKeys: failed to decode public key: %w", err)
|
|
|
|
|
}
|
|
|
|
|
if key.IsExpired() {
|
|
|
|
|
return nil, errors.New("Key is expired: " + fingerprint)
|
|
|
|
|
return nil, fmt.Errorf("Key is expired: %s", fingerprint)
|
|
|
|
|
}
|
|
|
|
|
err = keyring.AddKey(key)
|
|
|
|
|
if err != nil {
|
|
|
|
@ -552,7 +548,7 @@ func oxGetPublicKeyRing(client *xmpp.Client, iqc chan xmpp.IQ, recipient string)
|
|
|
|
|
log.Fatal(err)
|
|
|
|
|
}
|
|
|
|
|
if oxPublicKeyList.Type != strResult {
|
|
|
|
|
return nil, errors.New("error while requesting public openpgp keys for " +
|
|
|
|
|
return nil, fmt.Errorf("error while requesting public openpgp keys for %s",
|
|
|
|
|
recipient)
|
|
|
|
|
}
|
|
|
|
|
oxPubKeyListXML := etree.NewDocument()
|
|
|
|
@ -569,19 +565,19 @@ func oxGetPublicKeyRing(client *xmpp.Client, iqc chan xmpp.IQ, recipient string)
|
|
|
|
|
|
|
|
|
|
oxPubKeyListXMLPubsub := oxPubKeyListXML.SelectElement("pubsub")
|
|
|
|
|
if oxPubKeyListXMLPubsub == nil {
|
|
|
|
|
return nil, errors.New("ox: no pubsub element in public key list")
|
|
|
|
|
return nil, fmt.Errorf("ox: no pubsub element in public key list")
|
|
|
|
|
}
|
|
|
|
|
oxPubKeyListXMLPubsubItems := oxPubKeyListXMLPubsub.SelectElement("items")
|
|
|
|
|
if oxPubKeyListXMLPubsubItems == nil {
|
|
|
|
|
return nil, errors.New("ox: no items element in public key list")
|
|
|
|
|
return nil, fmt.Errorf("ox: no items element in public key list")
|
|
|
|
|
}
|
|
|
|
|
oxPubKeyListXMLPubsubItemsItem := oxPubKeyListXMLPubsubItems.SelectElement("item")
|
|
|
|
|
if oxPubKeyListXMLPubsubItemsItem == nil {
|
|
|
|
|
return nil, errors.New("ox: no item element in public key list")
|
|
|
|
|
return nil, fmt.Errorf("ox: no item element in public key list")
|
|
|
|
|
}
|
|
|
|
|
oxPubKeyListXMLPubsubItemsItemPkl := oxPubKeyListXMLPubsubItemsItem.SelectElement("public-keys-list")
|
|
|
|
|
if oxPubKeyListXMLPubsubItemsItemPkl == nil {
|
|
|
|
|
return nil, errors.New("ox: no public-keys-list element")
|
|
|
|
|
return nil, fmt.Errorf("ox: no public-keys-list element")
|
|
|
|
|
}
|
|
|
|
|
oxPubKeyListXMLPubsubItemsItemPklPm := oxPubKeyListXMLPubsubItemsItemPkl.SelectElements("pubkey-metadata")
|
|
|
|
|
for _, r := range oxPubKeyListXMLPubsubItemsItemPklPm {
|
|
|
|
@ -603,7 +599,7 @@ func oxGetPublicKeyRing(client *xmpp.Client, iqc chan xmpp.IQ, recipient string)
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
if pubKeyRingID == "none" {
|
|
|
|
|
return nil, errors.New("server didn't provide public key fingerprints for " + recipient)
|
|
|
|
|
return nil, fmt.Errorf("server didn't provide public key fingerprints for %s", recipient)
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
pubKeyRingLocation, err := oxGetPubKeyLoc(pubKeyRingID)
|
|
|
|
@ -623,7 +619,7 @@ func oxGetPublicKeyRing(client *xmpp.Client, iqc chan xmpp.IQ, recipient string)
|
|
|
|
|
if !savedKeysDate.Before(newestKey) {
|
|
|
|
|
pubKeys := pubKeyReadXML.SelectElements("pubkey")
|
|
|
|
|
if pubKeys == nil {
|
|
|
|
|
return nil, errors.New("couldn't read public keys from cache")
|
|
|
|
|
return nil, fmt.Errorf("couldn't read public keys from cache")
|
|
|
|
|
}
|
|
|
|
|
for _, r := range pubKeys {
|
|
|
|
|
keyByte, err := base64.StdEncoding.DecodeString(r.Text())
|
|
|
|
|