Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Is there anybody out there that have used capillary on server and decrypted messages on iOS? #13

Open
einarnot opened this issue Apr 15, 2019 · 2 comments

Comments

@einarnot
Copy link

einarnot commented Apr 15, 2019

We want to use capillary to support E2E encryption for push messages, on both android and iOS, on iOS we need to generate an RSA keypair, and provide the public key to the server. The problem is that we don't know what format Capillary expects the public key in.

We have tried to find out, and think that its an RSA 2048 in X.509 format and base64encoded. But our early attempts at this fails when Capillary tries to parse the public-key generated by our iOS app. We have used Heimdall to generate the keypair, and experimented with CryptoExportImportManager to convert the keys into DER format, but still no luck...

Anybody who can help, or at least say if this is feasible. (that is, using Capillary on server and E2E encrypt for iOS Clients.)

(Please excuse me if any of this doesn't make sense, as crypto is something Im not very familiar with. Im trying to learn, but all these key-types, formats, sizes, curves and encodings is still a jungle for me.)

@SlaveMast3r
Copy link

@einarnot it's almost one year since you asked. Did you solved it somehow? Have similar use case.

@einarnot
Copy link
Author

einarnot commented Jan 15, 2020

Capillary expects the RSA key wrapped in Protobuf objects. So we had to use SwiftProtobuf (Swift version of Googles Protobuf).

-Use SwiftProtobuf to generate Swift file from the capillary_internal.proto.

  1. Using AsymmetricCryptoException to create a secure keypair.

  2. Use exportRSAPublicKeyToDER in CryptoExportImportManager to export RSA key to DER format.

  3. Wrap the result of exportRSAPublicKeyToDER in the structs from capillary_internal.pb.swift (see swift function below).

  4. Provide the capillaryPublicKeyString to your backend that run capillary, it will now be able to encrypt using it.

  5. When you receive the push, handle it using Notification Service Extension (look for tutorials on how to do this. One major thing is that the push message must have mutableContent set to true.)

  6. To decrypt the encrypted string inside Notification Service Extension you need to put the encrypted string in an Capillary_Internal_CapillaryCiphertext object, split out the signature and payload data from that object.ciphertext. Length of the signature is then found in the first 4 bytes of the ciphertext. Then you need to put the payload in Capillary_Internal_HybridRsaCiphertext object, and symmetricKeyCiphertext is now the Data object to use for further decryption.

  7. We used TINK to decrypt the symmetricKeyCiphertext.

Function to wrap keydata in capillary protobuf structs (step 3):

func capillaryPublicKeyProtobufString(keyData: Data?) -> String? {
		guard let keyData = keyData else {
			return nil
		}

		var capillaryPublicKeyString = ""

		var wrappedRsaEcdsaPublicKey = Capillary_Internal_WrappedRsaEcdsaPublicKey.init()
		wrappedRsaEcdsaPublicKey.keyBytes = keyData
		wrappedRsaEcdsaPublicKey.padding = kPadding

		var capillaryPublicKey = Capillary_Internal_CapillaryPublicKey.init()
		do {
			capillaryPublicKey.keyBytes = try wrappedRsaEcdsaPublicKey.serializedData()
			capillaryPublicKeyString = try capillaryPublicKey.serializedData().base64EncodedString()
		} catch {
			Debugger.print("Failed to generate capillaryPublic Key: \(error.localizedDescription)")
		}

		return capillaryPublicKeyString
	}

I know this might be confusing, and there is alot of steps. But we made it work this way, so its possible, and this might help you figure things out.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants