adds fernet key decryption analogous to python

- first fragment currently auto-starts process
  to decrypt static message
- token parsed from message correctly
- token validation not yet sucessfull
This commit is contained in:
Raphael Maenle 2021-12-13 23:41:08 +01:00
parent 9e12972677
commit 941cc2dc3f
3 changed files with 88 additions and 0 deletions

View File

@ -48,6 +48,7 @@ dependencies {
implementation "androidx.camera:camera-lifecycle:$camerax_version" implementation "androidx.camera:camera-lifecycle:$camerax_version"
implementation 'com.google.zxing:core:3.3.0' implementation 'com.google.zxing:core:3.3.0'
implementation "androidx.camera:camera-view:1.0.0-alpha31" implementation "androidx.camera:camera-view:1.0.0-alpha31"
implementation 'com.macasaet.fernet:fernet-java8:1.4.2'
testImplementation 'junit:junit:4.+' testImplementation 'junit:junit:4.+'
androidTestImplementation 'androidx.test.ext:junit:1.1.2' androidTestImplementation 'androidx.test.ext:junit:1.1.2'
androidTestImplementation 'androidx.test.espresso:espresso-core:3.3.0' androidTestImplementation 'androidx.test.espresso:espresso-core:3.3.0'

View File

@ -6,6 +6,7 @@ import android.view.LayoutInflater
import android.view.View import android.view.View
import android.view.ViewGroup import android.view.ViewGroup
import androidx.navigation.fragment.findNavController import androidx.navigation.fragment.findNavController
import com.example.bump.MessageProcessor
import com.maenle.bump.databinding.FragmentFirstBinding import com.maenle.bump.databinding.FragmentFirstBinding
/** /**
@ -35,6 +36,19 @@ class FirstFragment : Fragment() {
binding.buttonFirst.setOnClickListener { binding.buttonFirst.setOnClickListener {
findNavController().navigate(R.id.action_FirstFragment_to_SecondFragment) findNavController().navigate(R.id.action_FirstFragment_to_SecondFragment)
} }
testDecryption()
}
fun testDecryption() {
val code = "dydoes-unknowledgeable-indiscretion-househusbands-pot-walloper-indiscretion-discophorous-transcriptions-dydoes-poodle-faker-transcriptions-budlike"
var mp = MessageProcessor()
if(mp.codeValid(code)) {
mp.codeSave(code)
}
mp.decrypt("M1dEAxKZ5HUHCJoRkgGOvAABhqCAAAAAAGG2eKTSlKXWLDQx5B_wssZsNwsanzQID2UyUm4KKuKYKgfwH5MG2N-qzt6K4mg3pfZmWPaiDB9PiqlX236k6zo9Yvvq")
} }
override fun onDestroyView() { override fun onDestroyView() {

View File

@ -0,0 +1,73 @@
package com.example.bump
import android.util.Log
import com.google.zxing.common.StringUtils
import java.security.SecureRandom
import java.util.Base64
import javax.crypto.spec.PBEKeySpec
import javax.crypto.SecretKeyFactory
import com.macasaet.fernet.Key
import com.macasaet.fernet.Token
import com.macasaet.fernet.StringValidator
import com.macasaet.fernet.Validator
import com.maenle.bump.MainActivity
import java.time.Duration
import java.time.temporal.TemporalAmount
class MessageProcessor {
lateinit var sender:String
lateinit var key: String
fun codeValid(code: String): Boolean {
return code.split("-").size >= KEY_LENGTH + SENDER_LENGTH
}
fun codeSave(new_code: String) {
var code: List<String> = new_code.split("-")
sender = code.subList(0, SENDER_LENGTH).joinToString("-")
key = code.subList(SENDER_LENGTH, code.size).joinToString("-")
Log.d(TAG, sender)
Log.d(TAG, key)
}
fun decrypt(message : String) {
// Data from encryption
val decoded : ByteArray = Base64.getUrlDecoder().decode(message)
val salt = decoded.copyOfRange(0, 16)
val iter = decoded.copyOfRange(16, 20)
val str_token = String(Base64.getUrlEncoder().encode(decoded.copyOfRange(20, decoded.size)))
// Derive Fernet key
val saltedKey = deriveKey(key, salt, 100_000)
val fernetKey = Key(saltedKey)
val token =
Token.fromString(str_token);
// Decrypt
val validator: Validator<String> = object : StringValidator {
override fun getTimeToLive(): TemporalAmount {
return Duration.ofHours(24)
}
}
val data = token.validateAndDecrypt(fernetKey, validator)
Log.d(TAG, data )
}
fun deriveKey(password: String, salt: ByteArray, iterations : Int): String {
val derivedKeyLength = 256
val spec = PBEKeySpec(password.toCharArray(), salt, iterations, derivedKeyLength)
val secretKeyFactory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA256")
val key = secretKeyFactory.generateSecret(spec).encoded
return Base64.getUrlEncoder().encodeToString(key)
}
companion object {
private val TAG = MainActivity::class.java.simpleName
val KEY_LENGTH = 8
val SENDER_LENGTH = 4
}
}