Browse Source

added apps installed on split tunnel, etc, home screen ui update...

Khubaib 1 year ago
parent
commit
db784a3a13
100 changed files with 23514 additions and 45 deletions
  1. 3 0
      app/build.gradle.kts
  2. 10 7
      app/src/main/java/com/vpn/fastestvpnservice/beans/SelectApplicationEntry.kt
  3. 2 1
      app/src/main/java/com/vpn/fastestvpnservice/beans/SplitTunnelList.kt
  4. 3 3
      app/src/main/java/com/vpn/fastestvpnservice/beans/SubscriptionDataList.kt
  5. 27 13
      app/src/main/java/com/vpn/fastestvpnservice/customItems/SplitTunnelingItem.kt
  6. 21 0
      app/src/main/java/com/vpn/fastestvpnservice/customItems/SubscriptionPackageItem.kt
  7. 6 1
      app/src/main/java/com/vpn/fastestvpnservice/fragments/BlankFragment.kt
  8. 23 4
      app/src/main/java/com/vpn/fastestvpnservice/screens/accountScreensAll/SubscriptionScreen.kt
  9. 22 11
      app/src/main/java/com/vpn/fastestvpnservice/screens/bottomNavBarScreens/HomeScreen.kt
  10. 73 4
      app/src/main/java/com/vpn/fastestvpnservice/screens/settingsScreenAll/SplitTunneling.kt
  11. 0 1
      app/src/main/java/com/vpn/fastestvpnservice/viewmodels/BillingViewModel.kt
  12. 4 0
      app/src/main/java/com/vpn/fastestvpnservice/viewmodels/SubscriptionViewModel.kt
  13. 64 0
      app/src/main/jni/libandroidbridge/Android.mk
  14. 176 0
      app/src/main/jni/libandroidbridge/android_jni.c
  15. 175 0
      app/src/main/jni/libandroidbridge/android_jni.h
  16. 139 0
      app/src/main/jni/libandroidbridge/backend/android_attr.c
  17. 52 0
      app/src/main/jni/libandroidbridge/backend/android_attr.h
  18. 376 0
      app/src/main/jni/libandroidbridge/backend/android_creds.c
  19. 76 0
      app/src/main/jni/libandroidbridge/backend/android_creds.h
  20. 418 0
      app/src/main/jni/libandroidbridge/backend/android_dns_proxy.c
  21. 86 0
      app/src/main/jni/libandroidbridge/backend/android_dns_proxy.h
  22. 169 0
      app/src/main/jni/libandroidbridge/backend/android_fetcher.c
  23. 33 0
      app/src/main/jni/libandroidbridge/backend/android_fetcher.h
  24. 496 0
      app/src/main/jni/libandroidbridge/backend/android_private_key.c
  25. 38 0
      app/src/main/jni/libandroidbridge/backend/android_private_key.h
  26. 955 0
      app/src/main/jni/libandroidbridge/backend/android_service.c
  27. 60 0
      app/src/main/jni/libandroidbridge/backend/android_service.h
  28. 722 0
      app/src/main/jni/libandroidbridge/byod/imc_android.c
  29. 30 0
      app/src/main/jni/libandroidbridge/byod/imc_android.h
  30. 191 0
      app/src/main/jni/libandroidbridge/byod/imc_android_state.c
  31. 52 0
      app/src/main/jni/libandroidbridge/byod/imc_android_state.h
  32. 791 0
      app/src/main/jni/libandroidbridge/charonservice.c
  33. 168 0
      app/src/main/jni/libandroidbridge/charonservice.h
  34. 192 0
      app/src/main/jni/libandroidbridge/kernel/android_ipsec.c
  35. 48 0
      app/src/main/jni/libandroidbridge/kernel/android_ipsec.h
  36. 323 0
      app/src/main/jni/libandroidbridge/kernel/android_net.c
  37. 35 0
      app/src/main/jni/libandroidbridge/kernel/android_net.h
  38. 240 0
      app/src/main/jni/libandroidbridge/kernel/network_manager.c
  39. 89 0
      app/src/main/jni/libandroidbridge/kernel/network_manager.h
  40. 279 0
      app/src/main/jni/libandroidbridge/vpnservice_builder.c
  41. 102 0
      app/src/main/jni/libandroidbridge/vpnservice_builder.h
  42. 25 0
      app/src/main/jni/openssl/Android.mk
  43. 127 0
      app/src/main/jni/openssl/NOTICE
  44. 12 0
      app/src/main/jni/openssl/README.ndk
  45. 9 0
      app/src/main/jni/openssl/UPDATING
  46. 4 0
      app/src/main/jni/openssl/flavor.mk
  47. 346 0
      app/src/main/jni/openssl/include/openssl/aead.h
  48. 158 0
      app/src/main/jni/openssl/include/openssl/aes.h
  49. 127 0
      app/src/main/jni/openssl/include/openssl/arm_arch.h
  50. 1167 0
      app/src/main/jni/openssl/include/openssl/asn1.h
  51. 75 0
      app/src/main/jni/openssl/include/openssl/asn1_mac.h
  52. 906 0
      app/src/main/jni/openssl/include/openssl/asn1t.h
  53. 261 0
      app/src/main/jni/openssl/include/openssl/base.h
  54. 184 0
      app/src/main/jni/openssl/include/openssl/base64.h
  55. 902 0
      app/src/main/jni/openssl/include/openssl/bio.h
  56. 93 0
      app/src/main/jni/openssl/include/openssl/blowfish.h
  57. 888 0
      app/src/main/jni/openssl/include/openssl/bn.h
  58. 118 0
      app/src/main/jni/openssl/include/openssl/buf.h
  59. 18 0
      app/src/main/jni/openssl/include/openssl/buffer.h
  60. 378 0
      app/src/main/jni/openssl/include/openssl/bytestring.h
  61. 96 0
      app/src/main/jni/openssl/include/openssl/cast.h
  62. 37 0
      app/src/main/jni/openssl/include/openssl/chacha.h
  63. 571 0
      app/src/main/jni/openssl/include/openssl/cipher.h
  64. 76 0
      app/src/main/jni/openssl/include/openssl/cmac.h
  65. 145 0
      app/src/main/jni/openssl/include/openssl/conf.h
  66. 184 0
      app/src/main/jni/openssl/include/openssl/cpu.h
  67. 68 0
      app/src/main/jni/openssl/include/openssl/crypto.h
  68. 92 0
      app/src/main/jni/openssl/include/openssl/curve25519.h
  69. 177 0
      app/src/main/jni/openssl/include/openssl/des.h
  70. 238 0
      app/src/main/jni/openssl/include/openssl/dh.h
  71. 258 0
      app/src/main/jni/openssl/include/openssl/digest.h
  72. 343 0
      app/src/main/jni/openssl/include/openssl/dsa.h
  73. 16 0
      app/src/main/jni/openssl/include/openssl/dtls1.h
  74. 355 0
      app/src/main/jni/openssl/include/openssl/ec.h
  75. 280 0
      app/src/main/jni/openssl/include/openssl/ec_key.h
  76. 102 0
      app/src/main/jni/openssl/include/openssl/ecdh.h
  77. 206 0
      app/src/main/jni/openssl/include/openssl/ecdsa.h
  78. 98 0
      app/src/main/jni/openssl/include/openssl/engine.h
  79. 487 0
      app/src/main/jni/openssl/include/openssl/err.h
  80. 750 0
      app/src/main/jni/openssl/include/openssl/evp.h
  81. 213 0
      app/src/main/jni/openssl/include/openssl/ex_data.h
  82. 44 0
      app/src/main/jni/openssl/include/openssl/hkdf.h
  83. 160 0
      app/src/main/jni/openssl/include/openssl/hmac.h
  84. 192 0
      app/src/main/jni/openssl/include/openssl/lhash.h
  85. 132 0
      app/src/main/jni/openssl/include/openssl/lhash_macros.h
  86. 102 0
      app/src/main/jni/openssl/include/openssl/md4.h
  87. 107 0
      app/src/main/jni/openssl/include/openssl/md5.h
  88. 140 0
      app/src/main/jni/openssl/include/openssl/mem.h
  89. 198 0
      app/src/main/jni/openssl/include/openssl/obj.h
  90. 4144 0
      app/src/main/jni/openssl/include/openssl/obj_mac.h
  91. 18 0
      app/src/main/jni/openssl/include/openssl/objects.h
  92. 60 0
      app/src/main/jni/openssl/include/openssl/opensslconf.h
  93. 18 0
      app/src/main/jni/openssl/include/openssl/opensslv.h
  94. 18 0
      app/src/main/jni/openssl/include/openssl/ossl_typ.h
  95. 517 0
      app/src/main/jni/openssl/include/openssl/pem.h
  96. 18 0
      app/src/main/jni/openssl/include/openssl/pkcs12.h
  97. 16 0
      app/src/main/jni/openssl/include/openssl/pkcs7.h
  98. 220 0
      app/src/main/jni/openssl/include/openssl/pkcs8.h
  99. 51 0
      app/src/main/jni/openssl/include/openssl/poly1305.h
  100. 0 0
      app/src/main/jni/openssl/include/openssl/pqueue.h

+ 3 - 0
app/build.gradle.kts

@@ -91,6 +91,9 @@ dependencies {
     implementation("com.android.billingclient:billing:6.1.0")
 
 
+    implementation("io.coil-kt:coil-compose:1.3.1")
+    implementation("com.google.accompanist:accompanist-drawablepainter:0.34.0")
+
     testImplementation("junit:junit:4.13.2")
     androidTestImplementation("androidx.test.ext:junit:1.1.5")
     androidTestImplementation("androidx.test.espresso:espresso-core:3.5.1")

+ 10 - 7
app/src/main/java/com/vpn/fastestvpnservice/beans/SelectApplicationEntry.kt

@@ -3,27 +3,30 @@ package com.vpn.fastestvpnservice.beans
 import android.content.pm.ApplicationInfo
 import android.content.pm.PackageManager
 import android.graphics.drawable.Drawable
+import androidx.compose.runtime.MutableState
+import androidx.compose.runtime.mutableStateOf
 import java.text.Collator
 
 class SelectApplicationEntry : Comparable<SelectApplicationEntry> {
 
+    private var mInfo: ApplicationInfo? = null
+    private var mIcon: Drawable? = null
+    private var mName: String? = null
+    var mSelected: MutableState<Boolean> = mutableStateOf(false)
+
     constructor(packageManager: PackageManager?, info: ApplicationInfo) {
         mInfo = info
         val name = info.loadLabel(packageManager!!)
         mName = name.toString()
         mIcon = info.loadIcon(packageManager)
+        mSelected.value = false
     }
 
-    private var mInfo: ApplicationInfo? = null
-    private var mIcon: Drawable? = null
-    private var mName: String? = null
-    private var mSelected = false
-
-    fun setSelected(selected: Boolean) {
+    fun setSelected(selected: MutableState<Boolean>) {
         mSelected = selected
     }
 
-    fun isSelected(): Boolean {
+    fun isSelected(): MutableState<Boolean> {
         return mSelected
     }
 

+ 2 - 1
app/src/main/java/com/vpn/fastestvpnservice/beans/SplitTunnelList.kt

@@ -10,7 +10,8 @@ data class SplitTunnelData(
     var isSelected: MutableState<Boolean>
 )
 
-val splitTunnelList = listOf(
+
+val splitTunnelList1 = listOf(
     SplitTunnelData(R.drawable.adaptive3x, "Adaptive Connectivity Services", mutableStateOf(false)),
     SplitTunnelData(R.drawable.accessibility3x, "Android Accessibility Suite", mutableStateOf(false)),
     SplitTunnelData(R.drawable.calculator3x, "Calculator", mutableStateOf(false))

+ 3 - 3
app/src/main/java/com/vpn/fastestvpnservice/beans/SubscriptionDataList.kt

@@ -31,7 +31,7 @@ val subscriptionPackageList = listOf(
     SubscriptionPackageList(
         "Pro Monthly", "Auto-Renewable",
         "Unlimited Access For A Month", "Rs 550", mutableStateOf(false)),
-    SubscriptionPackageList(
-            "Lifetime", "Auto-Renewable",
-    "Unlimited Access For Lifetime", "Rs 12,000", mutableStateOf(false))
+//    SubscriptionPackageList(
+//            "Lifetime", "Auto-Renewable",
+//    "Unlimited Access For Lifetime", "Rs 12,000", mutableStateOf(false))
 )

+ 27 - 13
app/src/main/java/com/vpn/fastestvpnservice/customItems/SplitTunnelingItem.kt

@@ -1,6 +1,11 @@
 package com.vpn.fastestvpnservice.customItems
 
+import android.content.pm.PackageManager
+import android.graphics.Bitmap
+import android.graphics.drawable.BitmapDrawable
+import android.graphics.drawable.Drawable
 import android.widget.Toast
+import androidx.compose.foundation.Image
 import androidx.compose.foundation.background
 import androidx.compose.foundation.clickable
 import androidx.compose.foundation.interaction.MutableInteractionSource
@@ -19,6 +24,7 @@ import androidx.compose.material.Surface
 import androidx.compose.material.Text
 import androidx.compose.material3.Icon
 import androidx.compose.material3.MaterialTheme
+import androidx.compose.material3.rememberDrawerState
 import androidx.compose.runtime.Composable
 import androidx.compose.runtime.getValue
 import androidx.compose.runtime.mutableStateOf
@@ -29,6 +35,8 @@ import androidx.compose.ui.Alignment
 import androidx.compose.ui.Modifier
 import androidx.compose.ui.draw.alpha
 import androidx.compose.ui.graphics.Color
+import androidx.compose.ui.graphics.ImageBitmap
+import androidx.compose.ui.graphics.asImageBitmap
 import androidx.compose.ui.platform.LocalContext
 import androidx.compose.ui.res.colorResource
 import androidx.compose.ui.res.painterResource
@@ -36,12 +44,16 @@ import androidx.compose.ui.text.TextStyle
 import androidx.compose.ui.tooling.preview.Preview
 import androidx.compose.ui.unit.dp
 import androidx.compose.ui.unit.sp
+import androidx.core.graphics.drawable.DrawableCompat
+import androidx.core.graphics.drawable.toBitmap
 import com.vpn.fastestvpnservice.R
+import com.vpn.fastestvpnservice.beans.SelectApplicationEntry
 import com.vpn.fastestvpnservice.beans.SplitTunnelData
-import com.vpn.fastestvpnservice.beans.splitTunnelList
+import androidx.compose.ui.graphics.painter.BitmapPainter
+import com.google.accompanist.drawablepainter.rememberDrawablePainter
 
 @Composable
-fun SplitTunnelingItem(app: SplitTunnelData) {
+fun SplitTunnelingItem(app: SelectApplicationEntry) {
     Surface(
         modifier = Modifier
             .fillMaxWidth()
@@ -49,7 +61,7 @@ fun SplitTunnelingItem(app: SplitTunnelData) {
                 color = MaterialTheme.colorScheme.background
             )
             .padding(bottom = 1.dp),
-        color = if (app.isSelected.value) colorResource(id = R.color.split_background)
+        color = if (app.mSelected.value) colorResource(id = R.color.split_background)
                 else MaterialTheme.colorScheme.background
 
     ) {
@@ -67,21 +79,24 @@ fun SplitTunnelingItem(app: SplitTunnelData) {
                         MutableInteractionSource()
                     },
                 ) {
-                    app.isSelected.value = !app.isSelected.value
+                    app.mSelected = mutableStateOf(!app.mSelected.value)
+                    Toast.makeText(
+                        context, "${app.toString()} ${app.mSelected.value}", Toast.LENGTH_SHORT
+                    ).show()
                 }
         ) {
-            Icon(
-                painter = painterResource(id = app.icon),
+            Image(
+                painter = rememberDrawablePainter(drawable = app.getIcon()),
                 contentDescription = "Server Logo",
-                tint = Color.Unspecified,
+//                tint = Color.Unspecified,
                 modifier = Modifier
                     .padding(bottom = 16.dp)
                     .size(40.dp)
             )
-            Text(text = app.appName,
+            Text(text = app.toString(),
                 style = TextStyle(
                     fontSize = 14.sp,
-                    color = if (app.isSelected.value) colorResource(id = R.color.dark_blue_gray_text)
+                    color = if (app.mSelected.value) colorResource(id = R.color.dark_blue_gray_text)
                             else MaterialTheme.colorScheme.primary
                 ),
                 modifier = Modifier
@@ -93,9 +108,9 @@ fun SplitTunnelingItem(app: SplitTunnelData) {
             var isSelected by rememberSaveable { mutableStateOf(false) }
 
             Checkbox(
-                checked = app.isSelected.value,
+                checked = app.mSelected.value,
                 onCheckedChange = {
-                    app.isSelected.value = it
+                    app.mSelected = mutableStateOf(it)
                 },
                 colors = CheckboxDefaults.colors(
                     uncheckedColor = colorResource(id = R.color.switch_gray),
@@ -106,7 +121,7 @@ fun SplitTunnelingItem(app: SplitTunnelData) {
                     .padding(bottom = 18.dp, end = 8.dp)
                     .align(Alignment.CenterVertically)
                     .background(
-                        color = if (app.isSelected.value) colorResource(id = R.color.blue_text)
+                        color = if (app.mSelected.value) colorResource(id = R.color.blue_text)
                         else colorResource(id = R.color.switch_gray),
                         shape = RoundedCornerShape(5.dp)
                     )
@@ -119,5 +134,4 @@ fun SplitTunnelingItem(app: SplitTunnelData) {
 @Preview
 @Composable
 fun SplitTunnelingItemPreview() {
-    SplitTunnelingItem(splitTunnelList[0])
 }

+ 21 - 0
app/src/main/java/com/vpn/fastestvpnservice/customItems/SubscriptionPackageItem.kt

@@ -19,6 +19,7 @@ import androidx.compose.foundation.shape.RoundedCornerShape
 import androidx.compose.material3.Text
 import androidx.compose.runtime.Composable
 import androidx.compose.runtime.getValue
+import androidx.compose.runtime.livedata.observeAsState
 import androidx.compose.runtime.mutableIntStateOf
 import androidx.compose.runtime.mutableStateOf
 import androidx.compose.runtime.remember
@@ -37,10 +38,12 @@ import androidx.compose.ui.text.style.TextAlign
 import androidx.compose.ui.tooling.preview.Preview
 import androidx.compose.ui.unit.dp
 import androidx.compose.ui.unit.sp
+import androidx.lifecycle.viewmodel.compose.viewModel
 import androidx.navigation.compose.rememberNavController
 import com.vpn.fastestvpnservice.R
 import com.vpn.fastestvpnservice.beans.SubscriptionPackageList
 import com.vpn.fastestvpnservice.beans.subscriptionPackageList
+import com.vpn.fastestvpnservice.viewmodels.SubscriptionViewModel
 import java.util.Random
 
 var getPosition: Int = 0
@@ -53,6 +56,9 @@ fun SubscriptionPackageItem(item: SubscriptionPackageList, position: Int) {
     var items by remember { mutableStateOf(item) }
     var isSelected by remember { mutableStateOf(true) }
     val random = kotlin.random.Random.nextInt(1, 999)
+    val subscriptionViewModel: SubscriptionViewModel = viewModel{
+        SubscriptionViewModel(context = context)
+    }
 
     Box(
         modifier = Modifier
@@ -98,6 +104,20 @@ fun SubscriptionPackageItem(item: SubscriptionPackageList, position: Int) {
                     if (!item.isSelected.value) {
 //                        Log.d("test_plan", "False : selectedPosition = $selectedPosition position = $position" )
                         selectedPosition = position
+
+                        subscriptionViewModel.mutableLiveDataProducts.value?.let { it1 ->
+                            subscriptionViewModel.setProductsData(
+                                it1
+                            )
+                        }
+
+                        val featuresSize = subscriptionViewModel.liveDataProducts.value
+                        Log.d(
+                            "test_api_response_p",
+                            "Products selectedPosition = $selectedPosition ," +
+                                    "features size = ${featuresSize?.data?.get(selectedPosition)?.features?.size}"
+                        )
+
                         subscriptionPackageList.forEachIndexed { index, subscriptionPackageList ->
 //                            if (selectedPosition == index) {
 //                                Log.d("test_plan", "True Inside : selectedPosition = $selectedPosition index = $index" )
@@ -110,6 +130,7 @@ fun SubscriptionPackageItem(item: SubscriptionPackageList, position: Int) {
 //                            Log.d("test_plan", "Update ${subscriptionPackageList.packageDuration} $index $position" )
 
                             subscriptionPackageList.isSelected.value = index == position
+
                             getPosition = position
 //                            Log.d("test_plan", "Update ${subscriptionPackageList.packageDuration} ${subscriptionPackageList.isSelected.value}" )
 

+ 6 - 1
app/src/main/java/com/vpn/fastestvpnservice/fragments/BlankFragment.kt

@@ -5,6 +5,7 @@ import androidx.fragment.app.Fragment
 import android.view.LayoutInflater
 import android.view.View
 import android.view.ViewGroup
+import androidx.compose.ui.platform.ComposeView
 import com.vpn.fastestvpnservice.R
 
 // TODO: Rename parameter arguments, choose names that match
@@ -35,7 +36,11 @@ class BlankFragment : Fragment() {
         savedInstanceState: Bundle?
     ): View? {
         // Inflate the layout for this fragment
-        return inflater.inflate(R.layout.fragment_blank, container, false)
+        return ComposeView(requireContext()).apply {
+            setContent {
+
+            }
+        }
     }
 
     companion object {

+ 23 - 4
app/src/main/java/com/vpn/fastestvpnservice/screens/accountScreensAll/SubscriptionScreen.kt

@@ -38,8 +38,12 @@ import androidx.compose.runtime.Composable
 import androidx.compose.runtime.CompositionLocalProvider
 import androidx.compose.runtime.DisposableEffect
 import androidx.compose.runtime.LaunchedEffect
+import androidx.compose.runtime.getValue
 import androidx.compose.runtime.livedata.observeAsState
+import androidx.compose.runtime.mutableStateOf
+import androidx.compose.runtime.remember
 import androidx.compose.runtime.rememberUpdatedState
+import androidx.compose.runtime.setValue
 import androidx.compose.ui.Alignment
 import androidx.compose.ui.Modifier
 import androidx.compose.ui.graphics.Color
@@ -128,7 +132,9 @@ fun SubscriptionScreen(navHostController: NavHostController)
     val subscriptionViewModel: SubscriptionViewModel = viewModel{
         SubscriptionViewModel(context = context)
     }
-    var selectedPosition: Int = 0
+    var selectedPosition by remember {
+        mutableStateOf(0)
+    }
     var skuDetailsList: List<SkuDetails>? = null
 
 
@@ -172,17 +178,29 @@ fun SubscriptionScreen(navHostController: NavHostController)
                 CompositionLocalProvider(
                     LocalOverscrollConfiguration provides null
                 ) {
+
                     val productsData = subscriptionViewModel.liveDataProducts.observeAsState().value
 
                     LazyColumn() {
 
+                        selectedPosition = getSelectedPosition()
+
                         productsData?.let {
-                            Log.d("test_api_response p", "Products screen = ${it.message}")
 
-                            items(items = it.data?.get(0)?.features!!) {item ->
-                                SubscriptionDataItem(item = item)
+                            it.data?.let {
+                                Log.d("test_api_response_p",
+                                    "Products screen = ${it.size}, selectedPosition = $selectedPosition")
+
+                                val features = it.get(selectedPosition).features
+                                features?.let {
+                                    items(items = it) {item ->
+                                        SubscriptionDataItem(item = item)
+                                    }
+                                }
                             }
 
+
+
                         }
 
 
@@ -205,6 +223,7 @@ fun SubscriptionScreen(navHostController: NavHostController)
                         context, subscriptionPackageList[selectedPosition].packageDuration, Toast.LENGTH_SHORT
                     )
                     .show()
+
             },
             modifier = Modifier
                 .padding(

+ 22 - 11
app/src/main/java/com/vpn/fastestvpnservice/screens/bottomNavBarScreens/HomeScreen.kt

@@ -168,23 +168,34 @@ fun Home(navHostController: NavHostController) {
     Box(
         modifier = Modifier
             .background(MaterialTheme.colorScheme.background)
-            .paint(
-                if (isConnect) blueBackground() else pinkBackground(),
-                alignment = Alignment.TopStart,
-                contentScale = ContentScale.FillWidth,
-//                colorFilter = ColorFilter.tint(
-//                    color = colorResource(id = R.color.pink_color)),
-            )
+//            .paint(
+//                if (isConnect) blueBackground() else pinkBackground(),
+//                alignment = Alignment.TopStart,
+//                contentScale = ContentScale.FillWidth,
+////                colorFilter = ColorFilter.tint(
+////                    color = colorResource(id = R.color.pink_color)),
+//            )
             .fillMaxSize(),
 //        contentAlignment = Alignment.TopCenter
     ) {
 
+        Image(
+            modifier = Modifier
+                .fillMaxWidth()
+                .align(Alignment.TopStart)
+                .height(320.dp)
+                .padding(top = 0.dp),
+            painter = if (isConnect) blueBackground() else pinkBackground(),
+            contentDescription = "Home Map",
+            contentScale = ContentScale.FillBounds,
+        )
+
         if (!isDarkTheme.value) {
             Image(
                 modifier = Modifier
                     .fillMaxWidth()
                     .align(Alignment.TopStart)
-                    .padding(top = 75.dp),
+                    .padding(top = 50.dp),
                 painter = painterResource(id = R.drawable.map_home3x),
                 contentDescription = "Home Map",
                 contentScale = ContentScale.FillWidth,
@@ -207,7 +218,7 @@ fun Home(navHostController: NavHostController) {
             },
             modifier = Modifier
                 .align(Alignment.TopCenter)
-                .padding(top = 230.dp)
+                .padding(top = 200.dp)
                 .size(234.dp),
         )
         {
@@ -233,7 +244,7 @@ fun Home(navHostController: NavHostController) {
                 .fillMaxWidth()
                 .background(Color.Transparent)
                 .align(Alignment.TopStart)
-                .padding(top = 75.dp)
+                .padding(top = 40.dp)
                 .height(125.dp),
         ) {
 
@@ -293,7 +304,7 @@ fun Home(navHostController: NavHostController) {
             Column(
                 modifier = Modifier
                     .align(Alignment.TopCenter)
-                    .padding(top = 490.dp, bottom = 20.dp)
+                    .padding(top = 450.dp, bottom = 20.dp)
                     .verticalScroll(rememberScrollState())
                     .fillMaxSize()
             ) {

+ 73 - 4
app/src/main/java/com/vpn/fastestvpnservice/screens/settingsScreenAll/SplitTunneling.kt

@@ -1,5 +1,9 @@
 package com.vpn.fastestvpnservice.screens.settingsScreenAll
 
+import android.Manifest
+import android.content.pm.ApplicationInfo
+import android.content.pm.PackageManager
+import android.util.Log
 import androidx.compose.animation.core.animateFloatAsState
 import androidx.compose.foundation.background
 import androidx.compose.foundation.layout.Arrangement
@@ -36,6 +40,7 @@ import androidx.compose.ui.Modifier
 import androidx.compose.ui.draw.alpha
 import androidx.compose.ui.draw.rotate
 import androidx.compose.ui.graphics.Color
+import androidx.compose.ui.platform.LocalContext
 import androidx.compose.ui.res.colorResource
 import androidx.compose.ui.res.painterResource
 import androidx.compose.ui.text.TextStyle
@@ -46,11 +51,16 @@ import androidx.compose.ui.unit.dp
 import androidx.compose.ui.unit.sp
 import androidx.navigation.NavHostController
 import androidx.navigation.compose.rememberNavController
+import com.google.gson.Gson
+import com.google.gson.reflect.TypeToken
 import com.vpn.fastestvpnservice.R
+import com.vpn.fastestvpnservice.beans.SelectApplicationEntry
 import com.vpn.fastestvpnservice.beans.SplitTunnelData
-import com.vpn.fastestvpnservice.beans.splitTunnelList
 import com.vpn.fastestvpnservice.beans.splitTunnelList2
 import com.vpn.fastestvpnservice.customItems.SplitTunnelingItem
+import java.util.ArrayList
+import java.util.SortedSet
+import java.util.TreeSet
 
 @Composable
 fun SplitTunneling(navHostController: NavHostController) {
@@ -177,16 +187,75 @@ fun ColumnScope.ShowRadioButtons() {
         color = colorResource(id = R.color.gray_icon)
     ) {}
 
+    val context = LocalContext.current
+    val apps: ArrayList<SelectApplicationEntry> = ArrayList()
+    val apps2: ArrayList<SelectApplicationEntry> = ArrayList()
+    val seen: SortedSet<String> = TreeSet()
+    var selectedAppsList = ArrayList<String>()
+    var selectedAppsListNoVpn = ArrayList<String>()
+
+    val mPackageManager: PackageManager = context.packageManager
+
+    for (info in mPackageManager.getInstalledApplications(PackageManager.GET_META_DATA)) { /* skip apps that can't access the network anyway */
+
+        if (info.flags and ApplicationInfo.FLAG_UPDATED_SYSTEM_APP != 0) {
+            Log.d("--package names !0", "" + info.packageName)
+            if (mPackageManager.checkPermission(
+                    Manifest.permission.INTERNET, info.packageName
+                ) == PackageManager.PERMISSION_GRANTED
+            ) {
+                if (info.packageName == context.packageName) continue
+                val entry = SelectApplicationEntry(mPackageManager, info)
+
+                Log.d("entry split", entry.toString())
+
+                apps.add(entry)
+                apps2.add(entry)
+                seen.add(info.packageName)
+
+            }
+        }
+        if (info.flags and ApplicationInfo.FLAG_SYSTEM == 0) {
+            Log.d("--package names 0 ", "" + info.packageName)
+            if (mPackageManager.checkPermission(
+                    Manifest.permission.INTERNET, info.packageName
+                ) == PackageManager.PERMISSION_GRANTED
+            ) {
+                if (info.packageName == context.packageName) continue
+                val entry = SelectApplicationEntry(mPackageManager, info)
+
+                apps.add(entry)
+                apps2.add(entry)
+                seen.add(info.packageName)
+            }
+
+        }
+    }
+
+    apps.sort()
+    apps2.sort()
+
+    apps.forEach {
+        Log.d("test_split_apps", "$it ${it.getIcon()}")
+    }
+    apps2.forEach {
+        Log.d("test_split_apps 2", "$$it ${it.getIcon()}")
+    }
+
+
     if (selectedList == splitList[1]) {
-        ShowSplitTunnelList(splitTunnelList)
+        ShowSplitTunnelList(apps)
     }
     else if (selectedList == splitList[2]) {
-        ShowSplitTunnelList(splitTunnelList2)
+        ShowSplitTunnelList(apps2)
     }
 }
 
 @Composable
-fun ColumnScope.ShowSplitTunnelList(list: List<SplitTunnelData>) {
+fun ColumnScope.ShowSplitTunnelList(list: List<SelectApplicationEntry>) {
+
+
+
     Box(modifier = Modifier
         .padding(top = 5.dp)
         .fillMaxSize()

+ 0 - 1
app/src/main/java/com/vpn/fastestvpnservice/viewmodels/BillingViewModel.kt

@@ -181,7 +181,6 @@ class BillingViewModel(application: App): AndroidViewModel(application),
 
 
     override fun onPurchasesUpdated(p0: BillingResult, p1: MutableList<Purchase>?) {
-        TODO("Not yet implemented")
     }
 
 

+ 4 - 0
app/src/main/java/com/vpn/fastestvpnservice/viewmodels/SubscriptionViewModel.kt

@@ -26,6 +26,10 @@ class SubscriptionViewModel constructor(context: Context): ViewModel() {
     init {
         preferenceHelper = BasePreferenceHelper(context)
     }
+
+    fun setProductsData(products: DataResponse<ArrayList<ProductFeatures>>) {
+        mutableLiveDataProducts.value = products
+    }
     fun getProducts(){
         WebServiceFactory.getInstance().getProducts().enqueue(
             RetrofitNetworkHandling<Any>(object :

+ 64 - 0
app/src/main/jni/libandroidbridge/Android.mk

@@ -0,0 +1,64 @@
+LOCAL_PATH := $(call my-dir)
+include $(CLEAR_VARS)
+
+# copy-n-paste from Makefile.am
+LOCAL_SRC_FILES := \
+android_jni.c \
+backend/android_attr.c \
+backend/android_creds.c \
+backend/android_fetcher.c \
+backend/android_dns_proxy.c \
+backend/android_private_key.c \
+backend/android_service.c \
+charonservice.c \
+kernel/android_ipsec.c \
+kernel/android_net.c \
+kernel/network_manager.c \
+vpnservice_builder.c
+
+ifneq ($(strongswan_USE_BYOD),)
+LOCAL_SRC_FILES += \
+byod/imc_android_state.c \
+byod/imc_android.c
+endif
+
+# build libandroidbridge -------------------------------------------------------
+
+LOCAL_C_INCLUDES += \
+	$(strongswan_PATH)/src/libipsec \
+	$(strongswan_PATH)/src/libcharon \
+	$(strongswan_PATH)/src/libstrongswan
+
+ifneq ($(strongswan_USE_BYOD),)
+LOCAL_C_INCLUDES += \
+	$(strongswan_PATH)/src/libimcv \
+	$(strongswan_PATH)/src/libtncif \
+	$(strongswan_PATH)/src/libtnccs \
+	$(strongswan_PATH)/src/libtpmtss \
+	$(strongswan_PATH)/src/libtls
+endif
+
+LOCAL_CFLAGS := $(strongswan_CFLAGS) \
+	-DPLUGINS='"$(strongswan_CHARON_PLUGINS)"'
+
+ifneq ($(strongswan_USE_BYOD),)
+LOCAL_CFLAGS += -DPLUGINS_BYOD='"$(strongswan_BYOD_PLUGINS)"'
+endif
+
+LOCAL_MODULE := libandroidbridge
+
+LOCAL_MODULE_TAGS := optional
+
+LOCAL_ARM_MODE := arm
+
+LOCAL_PRELINK_MODULE := false
+
+LOCAL_LDLIBS := -llog
+
+LOCAL_SHARED_LIBRARIES := libstrongswan libipsec libcharon
+
+ifneq ($(strongswan_USE_BYOD),)
+LOCAL_SHARED_LIBRARIES += libimcv libtncif libtnccs libtpmtss
+endif
+
+include $(BUILD_SHARED_LIBRARY)

+ 176 - 0
app/src/main/jni/libandroidbridge/android_jni.c

@@ -0,0 +1,176 @@
+/*
+ * Copyright (C) 2012-2017 Tobias Brunner
+ * Copyright (C) 2012 Giuliano Grassi
+ * Copyright (C) 2012 Ralf Sager
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+#include <dlfcn.h>
+
+#include "android_jni.h"
+
+#include <library.h>
+#include <threading/thread_value.h>
+
+/**
+ * JVM
+ */
+static JavaVM *android_jvm;
+
+static struct {
+	char name[32];
+	void *handle;
+} libs[] = {
+	{ "libstrongswan.so", NULL },
+#ifdef USE_BYOD
+	{ "libtpmtss.so", NULL },
+	{ "libtncif.so", NULL },
+	{ "libtnccs.so", NULL },
+	{ "libimcv.so", NULL },
+#endif
+	{ "libcharon.so", NULL },
+	{ "libipsec.so", NULL },
+};
+
+jclass *android_charonvpnservice_class;
+jclass *android_charonvpnservice_builder_class;
+jclass *android_simple_fetcher_class;
+android_sdk_version_t android_sdk_version;
+char *android_version_string;
+char *android_device_string;
+
+/**
+ * Thread-local variable. Only used because of the destructor
+ */
+static thread_value_t *androidjni_threadlocal;
+
+/**
+ * Thread-local destructor to ensure that a native thread is detached
+ * from the JVM even if androidjni_detach_thread() is not called.
+ */
+static void attached_thread_cleanup(void *arg)
+{
+	(*android_jvm)->DetachCurrentThread(android_jvm);
+}
+
+/*
+ * Described in header
+ */
+void androidjni_attach_thread(JNIEnv **env)
+{
+	if ((*android_jvm)->GetEnv(android_jvm, (void**)env,
+							   JNI_VERSION_1_6) == JNI_OK)
+	{	/* already attached or even a Java thread */
+		return;
+	}
+	(*android_jvm)->AttachCurrentThread(android_jvm, env, NULL);
+	/* use a thread-local value with a destructor that automatically detaches
+	 * the thread from the JVM before it terminates, if not done manually */
+	androidjni_threadlocal->set(androidjni_threadlocal, (void*)*env);
+}
+
+/*
+ * Described in header
+ */
+void androidjni_detach_thread()
+{
+	if (androidjni_threadlocal->get(androidjni_threadlocal))
+	{	/* only do this if we actually attached this thread */
+		androidjni_threadlocal->set(androidjni_threadlocal, NULL);
+		(*android_jvm)->DetachCurrentThread(android_jvm);
+	}
+}
+
+/**
+ * Called when this library is loaded by the JVM
+ */
+jint JNI_OnLoad(JavaVM *vm, void *reserved)
+{
+	JNIEnv *env;
+	jclass jversion;
+	jfieldID jsdk_int;
+	jmethodID method_id;
+	jstring jstr;
+	int i;
+
+	android_jvm = vm;
+
+	if ((*vm)->GetEnv(vm, (void**)&env, JNI_VERSION_1_6) != JNI_OK)
+	{
+		return -1;
+	}
+
+	for (i = 0; i < countof(libs); i++)
+	{
+		libs[i].handle = dlopen(libs[i].name, RTLD_GLOBAL);
+		if (!libs[i].handle)
+		{
+			return -1;
+		}
+	}
+
+	androidjni_threadlocal = thread_value_create(attached_thread_cleanup);
+
+	android_charonvpnservice_class =
+				(*env)->NewGlobalRef(env, (*env)->FindClass(env,
+						JNI_PACKAGE_STRING "/CharonVpnService"));
+	android_charonvpnservice_builder_class =
+				(*env)->NewGlobalRef(env, (*env)->FindClass(env,
+						JNI_PACKAGE_STRING "/CharonVpnService$BuilderAdapter"));
+	android_simple_fetcher_class =
+				(*env)->NewGlobalRef(env, (*env)->FindClass(env,
+						JNI_PACKAGE_STRING "/SimpleFetcher"));
+
+	jversion = (*env)->FindClass(env, "android/os/Build$VERSION");
+	jsdk_int = (*env)->GetStaticFieldID(env, jversion, "SDK_INT", "I");
+	android_sdk_version = (*env)->GetStaticIntField(env, jversion, jsdk_int);
+
+	method_id = (*env)->GetStaticMethodID(env, android_charonvpnservice_class,
+									"getAndroidVersion", "()Ljava/lang/String;");
+	jstr = (*env)->CallStaticObjectMethod(env,
+									android_charonvpnservice_class, method_id);
+	if (jstr)
+	{
+		android_version_string = androidjni_convert_jstring(env, jstr);
+	}
+	method_id = (*env)->GetStaticMethodID(env, android_charonvpnservice_class,
+									"getDeviceString", "()Ljava/lang/String;");
+	jstr = (*env)->CallStaticObjectMethod(env,
+									android_charonvpnservice_class, method_id);
+	if (jstr)
+	{
+		android_device_string = androidjni_convert_jstring(env, jstr);
+	}
+	return JNI_VERSION_1_6;
+}
+
+/**
+ * Called when this library is unloaded by the JVM (which never happens on
+ * Android)
+ */
+void JNI_OnUnload(JavaVM *vm, void *reserved)
+{
+	int i;
+
+	androidjni_threadlocal->destroy(androidjni_threadlocal);
+
+	for (i = countof(libs) - 1; i >= 0; i--)
+	{
+		if (libs[i].handle)
+		{
+			dlclose(libs[i].handle);
+		}
+	}
+	free(android_version_string);
+	free(android_device_string);
+}

+ 175 - 0
app/src/main/jni/libandroidbridge/android_jni.h

@@ -0,0 +1,175 @@
+/*
+ * Copyright (C) 2012-2017 Tobias Brunner
+ * Copyright (C) 2012 Giuliano Grassi
+ * Copyright (C) 2012 Ralf Sager
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+/**
+ * @defgroup android_jni android_jni
+ * @{ @ingroup libandroidbridge
+ */
+
+#ifndef ANDROID_JNI_H_
+#define ANDROID_JNI_H_
+
+#include <jni.h>
+#include <library.h>
+
+#define JNI_PACKAGE org_strongswan_android_logic
+#define JNI_PACKAGE_STRING "org/strongswan/android/logic"
+
+#define JNI_METHOD_PP(pack, klass, name, ret, ...) \
+	ret Java_##pack##_##klass##_##name(JNIEnv *env, jobject this, ##__VA_ARGS__)
+
+#define JNI_METHOD_P(pack, klass, name, ret, ...) \
+	JNI_METHOD_PP(pack, klass, name, ret, ##__VA_ARGS__)
+
+#define JNI_METHOD(klass, name, ret, ...) \
+	JNI_METHOD_P(JNI_PACKAGE, klass, name, ret, ##__VA_ARGS__)
+
+/**
+ * Java classes
+ * Initialized in JNI_OnLoad()
+ */
+extern jclass *android_charonvpnservice_class;
+extern jclass *android_charonvpnservice_builder_class;
+extern jclass *android_simple_fetcher_class;
+
+/**
+ * Currently known (supported) SDK versions
+ *
+ * see android.os.Build.VERSION_CODES for definitions
+ */
+typedef enum {
+	ANDROID_ICE_CREAM_SANDWICH = 14,
+	ANDROID_ICE_CREAM_SANDWICH_MR1 = 15,
+	ANDROID_JELLY_BEAN = 16,
+	ANDROID_JELLY_BEAN_MR1 = 17,
+	ANDROID_JELLY_BEAN_MR2 = 18,
+	ANDROID_LOLLIPOP = 21,
+} android_sdk_version_t;
+
+/**
+ * The current SDK version of the Android framework
+ *
+ * see android.os.Build.VERSION.SDK_INT
+ */
+extern android_sdk_version_t android_sdk_version;
+
+/**
+ * A description of the current Android release
+ *
+ * see android.os.Build
+ */
+extern char *android_version_string;
+
+/**
+ * A description of the current device
+ *
+ * see android.os.Build
+ */
+extern char *android_device_string;
+
+/**
+ * Attach the current thread to the JVM
+ *
+ * As local JNI references are not freed until the thread detaches
+ * androidjni_detach_thread() should be called as soon as possible.
+ * If it is not called a thread-local destructor ensures that the
+ * thread is at least detached as soon as it terminates.
+ *
+ * @param env		JNIEnv
+ */
+void androidjni_attach_thread(JNIEnv **env);
+
+/**
+ * Detach the current thread from the JVM
+ *
+ * Call this as soon as possible to ensure that local JNI references are freed.
+ */
+void androidjni_detach_thread();
+
+/**
+ * Handle exceptions thrown by a JNI call
+ *
+ * @param env		JNIEnv
+ * @return			TRUE if an exception was thrown
+ */
+static inline bool androidjni_exception_occurred(JNIEnv *env)
+{
+	if ((*env)->ExceptionOccurred(env))
+	{	/* clear any exception, otherwise the VM is terminated */
+		(*env)->ExceptionDescribe(env);
+		(*env)->ExceptionClear(env);
+		return TRUE;
+	}
+	return FALSE;
+}
+
+/**
+ * Convert a Java string to a C string.  Memory is allocated.
+ *
+ * @param env		JNIEnv
+ * @param jstr		Java string
+ * @return			native C string (allocated)
+ */
+static inline char *androidjni_convert_jstring(JNIEnv *env, jstring jstr)
+{
+	char *str = NULL;
+	jsize bytes, chars;
+
+	if (jstr)
+	{
+		chars = (*env)->GetStringLength(env, jstr);
+		bytes = (*env)->GetStringUTFLength(env, jstr);
+		str = malloc(bytes + 1);
+		(*env)->GetStringUTFRegion(env, jstr, 0, chars, str);
+		str[bytes] = '\0';
+	}
+	return str;
+}
+
+/**
+ * Converts the given Java byte array to a chunk
+ *
+ * @param env			JNIEnv
+ * @param jbytearray	Java byte array
+ * @return				allocated chunk
+ */
+static inline chunk_t chunk_from_byte_array(JNIEnv *env, jbyteArray jbytearray)
+{
+	chunk_t chunk;
+
+	chunk = chunk_alloc((*env)->GetArrayLength(env, jbytearray));
+	(*env)->GetByteArrayRegion(env, jbytearray, 0, chunk.len, chunk.ptr);
+	return chunk;
+}
+
+/**
+ * Converts the given chunk to a Java byte array
+ *
+ * @param env			JNIEnv
+ * @param chunk			native chunk
+ * @return				allocated Java byte array
+ */
+static inline jbyteArray byte_array_from_chunk(JNIEnv *env, chunk_t chunk)
+{
+	jbyteArray jbytearray;
+
+	jbytearray = (*env)->NewByteArray(env, chunk.len);
+	(*env)->SetByteArrayRegion(env, jbytearray, 0, chunk.len, chunk.ptr);
+	return jbytearray;
+}
+
+#endif /** ANDROID_JNI_H_ @}*/

+ 139 - 0
app/src/main/jni/libandroidbridge/backend/android_attr.c

@@ -0,0 +1,139 @@
+/*
+ * Copyright (C) 2012-2013 Tobias Brunner
+ * Copyright (C) 2012 Giuliano Grassi
+ * Copyright (C) 2012 Ralf Sager
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+#include "android_attr.h"
+#include "../charonservice.h"
+
+#include <utils/debug.h>
+#include <library.h>
+
+typedef struct private_android_attr_t private_android_attr_t;
+
+/**
+ * Private data of an android_attr_t object.
+ */
+struct private_android_attr_t {
+
+	/**
+	 * Public interface.
+	 */
+	android_attr_t public;
+};
+
+METHOD(attribute_handler_t, handle, bool,
+	private_android_attr_t *this, ike_sa_t *ike_sa,
+	configuration_attribute_type_t type, chunk_t data)
+{
+	vpnservice_builder_t *builder;
+	host_t *dns;
+
+	switch (type)
+	{
+		case INTERNAL_IP4_DNS:
+			dns = host_create_from_chunk(AF_INET, data, 0);
+			break;
+		case INTERNAL_IP6_DNS:
+			dns = host_create_from_chunk(AF_INET6, data, 0);
+			break;
+		default:
+			return FALSE;
+	}
+
+	if (!dns || dns->is_anyaddr(dns))
+	{
+		DESTROY_IF(dns);
+		return FALSE;
+	}
+	DBG1(DBG_IKE, "installing DNS server %H", dns);
+	builder = charonservice->get_vpnservice_builder(charonservice);
+	builder->add_dns(builder, dns);
+	dns->destroy(dns);
+	return TRUE;
+}
+
+METHOD(attribute_handler_t, release, void,
+	private_android_attr_t *this, ike_sa_t *ike_sa,
+	configuration_attribute_type_t type, chunk_t data)
+{
+	/* DNS servers cannot be removed from an existing TUN device */
+}
+
+METHOD(enumerator_t, enumerate_dns6, bool,
+	enumerator_t *this, va_list args)
+{
+	configuration_attribute_type_t *type;
+	chunk_t *data;
+
+	VA_ARGS_VGET(args, type, data);
+	*type = INTERNAL_IP6_DNS;
+	*data = chunk_empty;
+	this->venumerate = (void*)return_false;
+	return TRUE;
+}
+
+METHOD(enumerator_t, enumerate_dns4, bool,
+	enumerator_t *this, va_list args)
+{
+	configuration_attribute_type_t *type;
+	chunk_t *data;
+
+	VA_ARGS_VGET(args, type, data);
+	*type = INTERNAL_IP4_DNS;
+	*data = chunk_empty;
+	this->venumerate = _enumerate_dns6;
+	return TRUE;
+}
+
+METHOD(attribute_handler_t, create_attribute_enumerator, enumerator_t*,
+	private_android_attr_t *this, ike_sa_t *ike_sa, linked_list_t *vips)
+{
+	enumerator_t *enumerator;
+
+	INIT(enumerator,
+			.enumerate = enumerator_enumerate_default,
+			.venumerate = _enumerate_dns4,
+			.destroy = (void*)free,
+	);
+	return enumerator;
+}
+
+METHOD(android_attr_t, destroy, void,
+	private_android_attr_t *this)
+{
+	free(this);
+}
+
+/**
+ * Described in header
+ */
+android_attr_t *android_attr_create()
+{
+	private_android_attr_t *this;
+
+	INIT(this,
+		.public = {
+			.handler = {
+				.handle = _handle,
+				.release = _release,
+				.create_attribute_enumerator = _create_attribute_enumerator,
+			},
+			.destroy = _destroy,
+		},
+	);
+
+	return &this->public;
+}

+ 52 - 0
app/src/main/jni/libandroidbridge/backend/android_attr.h

@@ -0,0 +1,52 @@
+/*
+ * Copyright (C) 2012 Giuliano Grassi
+ * Copyright (C) 2012 Ralf Sager
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+/**
+ * @defgroup android_attr android_attr
+ * @{ @ingroup android_backend
+ */
+
+#ifndef ANDROID_ATTR_H_
+#define ANDROID_ATTR_H_
+
+#include <library.h>
+#include <attributes/attribute_handler.h>
+
+typedef struct android_attr_t android_attr_t;
+
+/**
+ * Handler for DNS configuration
+ */
+struct android_attr_t {
+
+	/**
+	 * implements the attribute_handler_t interface
+	 */
+	attribute_handler_t handler;
+
+	/**
+	 * Destroy a android_attr_t
+	 */
+	void (*destroy)(android_attr_t *this);
+};
+
+/**
+ * Create a android_attr_t instance.
+ */
+android_attr_t *android_attr_create(void);
+
+#endif /** ANDROID_ATTR_H_ @}*/
+

+ 376 - 0
app/src/main/jni/libandroidbridge/backend/android_creds.c

@@ -0,0 +1,376 @@
+/*
+ * Copyright (C) 2012-2017 Tobias Brunner
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+#include <unistd.h>
+#include <sys/stat.h>
+#include <errno.h>
+#include <time.h>
+
+#include "android_creds.h"
+#include "../charonservice.h"
+
+#include <daemon.h>
+#include <library.h>
+#include <credentials/sets/mem_cred.h>
+#include <threading/rwlock.h>
+
+#define CRL_PREFIX "crl-"
+
+typedef struct private_android_creds_t private_android_creds_t;
+
+/**
+ * Private data of an android_creds_t object
+ */
+struct private_android_creds_t {
+
+	/**
+	 * Public interface
+	 */
+	android_creds_t public;
+
+	/**
+	 * Credential set storing trusted certificates and user credentials
+	 */
+	mem_cred_t *creds;
+
+	/**
+	 * read/write lock to make sure certificates are only loaded once
+	 */
+	rwlock_t *lock;
+
+	/**
+	 * TRUE if certificates have been loaded via JNI
+	 */
+	bool loaded;
+
+	/**
+	 * Directory for CRLs
+	 */
+	char *crldir;
+};
+
+/**
+ * Free allocated DER encoding
+ */
+static void free_encoding(chunk_t *chunk)
+{
+	chunk_free(chunk);
+	free(chunk);
+}
+
+/**
+ * Load trusted certificates via charonservice (JNI).
+ */
+static void load_trusted_certificates(private_android_creds_t *this)
+{
+	linked_list_t *certs;
+	certificate_t *cert;
+	chunk_t *current;
+
+	certs = charonservice->get_trusted_certificates(charonservice);
+	if (certs)
+	{
+		while (certs->remove_first(certs, (void**)&current) == SUCCESS)
+		{
+			cert = lib->creds->create(lib->creds, CRED_CERTIFICATE, CERT_X509,
+									  BUILD_BLOB_ASN1_DER, *current, BUILD_END);
+			if (cert)
+			{
+				DBG2(DBG_CFG, "loaded CA certificate '%Y'",
+					 cert->get_subject(cert));
+				this->creds->add_cert(this->creds, TRUE, cert);
+			}
+			free_encoding(current);
+		}
+		certs->destroy(certs);
+	}
+}
+
+/**
+ * Load a CRL from a file
+ */
+static void load_crl(private_android_creds_t *this, char *file)
+{
+	certificate_t *cert;
+	time_t now, notAfter;
+
+	cert = lib->creds->create(lib->creds, CRED_CERTIFICATE, CERT_X509_CRL,
+							  BUILD_FROM_FILE, file, BUILD_END);
+	if (cert)
+	{
+		now = time(NULL);
+		if (cert->get_validity(cert, &now, NULL, &notAfter))
+		{
+			DBG1(DBG_CFG, "loaded crl issued by '%Y'", cert->get_issuer(cert));
+			this->creds->add_crl(this->creds, (crl_t*)cert);
+		}
+		else
+		{
+			DBG1(DBG_CFG, "deleted crl issued by '%Y', expired (%V ago)",
+				 cert->get_issuer(cert), &now, &notAfter);
+			unlink(file);
+		}
+	}
+	else
+	{
+		DBG1(DBG_CFG, "loading crl failed");
+		unlink(file);
+	}
+}
+
+/**
+ * Load cached CRLs
+ */
+static void load_crls(private_android_creds_t *this)
+{
+	enumerator_t *enumerator;
+	struct stat st;
+	char *rel, *abs;
+
+	enumerator = enumerator_create_directory(this->crldir);
+	if (enumerator)
+	{
+		while (enumerator->enumerate(enumerator, &rel, &abs, &st))
+		{
+			if (S_ISREG(st.st_mode) && strpfx(rel, CRL_PREFIX))
+			{
+				load_crl(this, abs);
+			}
+		}
+		enumerator->destroy(enumerator);
+	}
+	else
+	{
+		DBG1(DBG_CFG, "  reading directory '%s' failed", this->crldir);
+	}
+}
+
+METHOD(credential_set_t, create_cert_enumerator, enumerator_t*,
+	private_android_creds_t *this, certificate_type_t cert, key_type_t key,
+	identification_t *id, bool trusted)
+{
+	enumerator_t *enumerator;
+
+	switch (cert)
+	{
+		case CERT_ANY:
+		case CERT_X509:
+		case CERT_X509_CRL:
+			break;
+		default:
+			return NULL;
+	}
+	this->lock->read_lock(this->lock);
+	if (!this->loaded)
+	{
+		this->lock->unlock(this->lock);
+		this->lock->write_lock(this->lock);
+		/* check again after acquiring the write lock */
+		if (!this->loaded)
+		{
+			load_crls(this);
+			load_trusted_certificates(this);
+			this->loaded = TRUE;
+		}
+		this->lock->unlock(this->lock);
+		this->lock->read_lock(this->lock);
+	}
+	enumerator = this->creds->set.create_cert_enumerator(&this->creds->set,
+													cert, key, id, trusted);
+	return enumerator_create_cleaner(enumerator, (void*)this->lock->unlock,
+									 this->lock);
+}
+
+METHOD(credential_set_t, cache_cert, void,
+	private_android_creds_t *this, certificate_t *cert)
+{
+	if (this->crldir && cert->get_type(cert) == CERT_X509_CRL)
+	{
+		/* CRLs get written to /<app>/<path>/crl-<authkeyId>[-delta] */
+		crl_t *crl = (crl_t*)cert;
+
+		cert->get_ref(cert);
+		if (this->creds->add_crl(this->creds, crl))
+		{
+			char buf[BUF_LEN];
+			chunk_t chunk, hex;
+			bool is_delta_crl;
+
+			is_delta_crl = crl->is_delta_crl(crl, NULL);
+			chunk = crl->get_authKeyIdentifier(crl);
+			hex = chunk_to_hex(chunk, NULL, FALSE);
+			snprintf(buf, sizeof(buf), "%s/%s%s%s", this->crldir, CRL_PREFIX,
+					 hex.ptr, is_delta_crl ? "-delta" : "");
+			free(hex.ptr);
+
+			if (cert->get_encoding(cert, CERT_ASN1_DER, &chunk))
+			{
+				if (chunk_write(chunk, buf, 022, TRUE))
+				{
+					DBG1(DBG_CFG, "  written crl to file (%d bytes)",
+						 chunk.len);
+				}
+				else
+				{
+					DBG1(DBG_CFG, "  writing crl to file failed: %s",
+						 strerror(errno));
+				}
+				free(chunk.ptr);
+			}
+		}
+	}
+}
+
+METHOD(android_creds_t, add_username_password, void,
+	private_android_creds_t *this, char *username, char *password)
+{
+	shared_key_t *shared_key;
+	identification_t *id;
+	chunk_t secret;
+
+	secret = chunk_create(password, strlen(password));
+	shared_key = shared_key_create(SHARED_EAP, chunk_clone(secret));
+	id = identification_create_from_string(username);
+
+	this->creds->add_shared(this->creds, shared_key, id, NULL);
+}
+
+METHOD(credential_set_t, create_shared_enumerator, enumerator_t*,
+	private_android_creds_t *this, shared_key_type_t type,
+	identification_t *me, identification_t *other)
+{
+	return this->creds->set.create_shared_enumerator(&this->creds->set,
+													 type, me, other);
+}
+
+METHOD(android_creds_t, load_user_certificate, certificate_t*,
+	private_android_creds_t *this)
+{
+	linked_list_t *encodings;
+	certificate_t *cert = NULL, *ca_cert;
+	chunk_t *current;
+
+	encodings = charonservice->get_user_certificate(charonservice);
+	if (!encodings)
+	{
+		DBG1(DBG_CFG, "failed to load user certificate and key");
+		return NULL;
+	}
+
+	while (encodings->remove_first(encodings, (void**)&current) == SUCCESS)
+	{
+		if (!cert)
+		{	/* the first element is the user certificate */
+			cert = lib->creds->create(lib->creds, CRED_CERTIFICATE, CERT_X509,
+									  BUILD_BLOB_ASN1_DER, *current, BUILD_END);
+			if (!cert)
+			{
+				DBG1(DBG_CFG, "failed to load user certificate");
+				free_encoding(current);
+				break;
+			}
+			DBG1(DBG_CFG, "loaded user certificate '%Y' and private key",
+				 cert->get_subject(cert));
+			cert = this->creds->add_cert_ref(this->creds, TRUE, cert);
+			free_encoding(current);
+			continue;
+		}
+		/* the rest are CA certificates, we ignore failures */
+		ca_cert = lib->creds->create(lib->creds, CRED_CERTIFICATE, CERT_X509,
+									 BUILD_BLOB_ASN1_DER, *current, BUILD_END);
+		if (ca_cert)
+		{
+			DBG1(DBG_CFG, "loaded CA certificate '%Y'",
+				 ca_cert->get_subject(ca_cert));
+			this->creds->add_cert(this->creds, TRUE, ca_cert);
+		}
+		free_encoding(current);
+	}
+	encodings->destroy_function(encodings, (void*)free_encoding);
+
+	if (cert)
+	{
+		private_key_t *key;
+
+		key = charonservice->get_user_key(charonservice,
+										  cert->get_public_key(cert));
+		if (key)
+		{
+			this->creds->add_key(this->creds, key);
+		}
+		else
+		{
+			DBG1(DBG_CFG, "failed to load private key");
+			cert->destroy(cert);
+			cert = NULL;
+		}
+	}
+	return cert;
+}
+
+METHOD(credential_set_t, create_private_enumerator, enumerator_t*,
+	private_android_creds_t *this, key_type_t type, identification_t *id)
+{
+	return this->creds->set.create_private_enumerator(&this->creds->set,
+													  type, id);
+}
+
+METHOD(android_creds_t, clear, void,
+	private_android_creds_t *this)
+{
+	this->lock->write_lock(this->lock);
+	this->creds->clear(this->creds);
+	this->loaded = FALSE;
+	this->lock->unlock(this->lock);
+}
+
+METHOD(android_creds_t, destroy, void,
+	private_android_creds_t *this)
+{
+	clear(this);
+	this->creds->destroy(this->creds);
+	this->lock->destroy(this->lock);
+	free(this->crldir);
+	free(this);
+}
+
+/**
+ * Described in header.
+ */
+android_creds_t *android_creds_create(char *crldir)
+{
+	private_android_creds_t *this;
+
+	INIT(this,
+		.public = {
+			.set = {
+				.create_cert_enumerator = _create_cert_enumerator,
+				.create_shared_enumerator = _create_shared_enumerator,
+				.create_private_enumerator = _create_private_enumerator,
+				.create_cdp_enumerator = (void*)return_null,
+				.cache_cert = _cache_cert,
+			},
+			.add_username_password = _add_username_password,
+			.load_user_certificate = _load_user_certificate,
+			.clear = _clear,
+			.destroy = _destroy,
+		},
+		.creds = mem_cred_create(),
+		.lock = rwlock_create(RWLOCK_TYPE_DEFAULT),
+		.crldir = strdupnull(crldir),
+	);
+
+	return &this->public;
+}

+ 76 - 0
app/src/main/jni/libandroidbridge/backend/android_creds.h

@@ -0,0 +1,76 @@
+/*
+ * Copyright (C) 2012-2017 Tobias Brunner
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+/**
+ * @defgroup android_creds android_creds
+ * @{ @ingroup android_backend
+ */
+
+#ifndef ANDROID_CREDS_H_
+#define ANDROID_CREDS_H_
+
+#include <library.h>
+#include <credentials/credential_set.h>
+
+typedef struct android_creds_t android_creds_t;
+
+/**
+ * Android credential set that provides CA certificates via JNI and supplied
+ * user credentials.
+ */
+struct android_creds_t {
+
+	/**
+	 * Implements credential_set_t
+	 */
+	credential_set_t set;
+
+	/**
+	 * Add user name and password for EAP authentication
+	 *
+	 * @param username			user name
+	 * @param password			password
+	 */
+	void (*add_username_password)(android_creds_t *this, char *username,
+								  char *password);
+
+	/**
+	 * Load the user certificate and private key
+	 *
+	 * @return					loaded client certificate, NULL on failure
+	 */
+	certificate_t *(*load_user_certificate)(android_creds_t *this);
+
+	/**
+	 * Clear the cached certificates and stored credentials.
+	 */
+	void (*clear)(android_creds_t *this);
+
+	/**
+	 * Destroy a android_creds instance.
+	 */
+	void (*destroy)(android_creds_t *this);
+
+};
+
+/**
+ * Create an android_creds instance.
+ *
+ * @param crldir				directory for cached CRLs
+ */
+android_creds_t *android_creds_create(char *crldir);
+
+#endif /** ANDROID_CREDS_H_ @}*/
+

+ 418 - 0
app/src/main/jni/libandroidbridge/backend/android_dns_proxy.c

@@ -0,0 +1,418 @@
+/*
+ * Copyright (C) 2014 Tobias Brunner
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+#include <sys/socket.h>
+#include <netinet/in.h>
+#include <netinet/udp.h>
+#include <unistd.h>
+#include <errno.h>
+#include <string.h>
+
+#include "android_dns_proxy.h"
+
+#include <daemon.h>
+#include <threading/rwlock.h>
+#include <collections/hashtable.h>
+#include <processing/jobs/callback_job.h>
+
+/**
+ * Timeout in seconds for sockets (i.e. not used for x seconds -> delete)
+ */
+#define SOCKET_TIMEOUT 30
+
+typedef struct private_android_dns_proxy_t private_android_dns_proxy_t;
+
+struct private_android_dns_proxy_t {
+
+	/**
+	 * Public interface
+	 */
+	android_dns_proxy_t public;
+
+	/**
+	 * Mapping from source address to sockets
+	 */
+	hashtable_t *sockets;
+
+	/**
+	 * Registered callback
+	 */
+	dns_proxy_response_cb_t cb;
+
+	/**
+	 * Data passed to callback
+	 */
+	void *data;
+
+	/**
+	 * Lock used to synchronize access to the private members
+	 */
+	rwlock_t *lock;
+
+	/**
+	 * Hostnames to filter queries by
+	 */
+	hashtable_t *hostnames;
+};
+
+/**
+ * Data for proxy sockets
+ */
+typedef struct {
+	private_android_dns_proxy_t *proxy;
+	time_t last_use;
+	host_t *src;
+	int fd;
+} proxy_socket_t;
+
+/**
+ * Destroy a socket
+ */
+static void socket_destroy(proxy_socket_t *this)
+{
+	this->src->destroy(this->src);
+	if (this->fd != -1)
+	{
+		close(this->fd);
+	}
+	free(this);
+}
+
+/**
+ * Hash a proxy socket by src address
+ */
+static u_int socket_hash(host_t *src)
+{
+	uint16_t port = src->get_port(src);
+	return chunk_hash_inc(src->get_address(src),
+						  chunk_hash(chunk_from_thing(port)));
+}
+
+/**
+ * Compare proxy sockets by src address
+ */
+static bool socket_equals(host_t *a, host_t *b)
+{
+	return a->equals(a, b);
+}
+
+/**
+ * Opens a UDP socket for the given address family
+ */
+static int open_socket(int family)
+{
+	int skt;
+
+	skt = socket(family, SOCK_DGRAM, IPPROTO_UDP);
+	if (skt < 0)
+	{
+		DBG1(DBG_NET, "could not open proxy socket: %s", strerror(errno));
+		return -1;
+	}
+	if (!charon->kernel->bypass_socket(charon->kernel, skt, family))
+	{
+		DBG1(DBG_NET, "installing bypass policy for proxy socket failed");
+		close(skt);
+		return -1;
+	}
+	return skt;
+}
+
+/**
+ * Create a proxy socket for the given source
+ */
+static proxy_socket_t *create_socket(private_android_dns_proxy_t *this,
+									 host_t *src)
+{
+	proxy_socket_t *skt;
+
+	INIT(skt,
+		.proxy = this,
+		.src = src->clone(src),
+		.fd = open_socket(src->get_family(src)),
+	);
+	if (skt->fd == -1)
+	{
+		socket_destroy(skt);
+		return NULL;
+	}
+	return skt;
+}
+
+CALLBACK(handle_response, bool,
+	proxy_socket_t *this, int fd, watcher_event_t event)
+{
+	struct sockaddr_storage addr;
+	socklen_t addr_len = sizeof(addr);
+	char buf[4096];
+	ssize_t len;
+	host_t *src;
+
+	len = recvfrom(fd, buf, sizeof(buf), MSG_DONTWAIT, (struct sockaddr*)&addr,
+				   &addr_len);
+	if (len > 0)
+	{
+		ip_packet_t *packet;
+
+		src = host_create_from_sockaddr((sockaddr_t*)&addr);
+		if (!src)
+		{
+			DBG1(DBG_NET, "failed to parse source address");
+			return TRUE;
+		}
+		packet = ip_packet_create_udp_from_data(src, this->src,
+												chunk_create(buf, len));
+		if (!packet)
+		{
+			DBG1(DBG_NET, "failed to parse DNS response");
+			return TRUE;
+		}
+		this->proxy->lock->read_lock(this->proxy->lock);
+		this->last_use = time_monotonic(NULL);
+		if (this->proxy->cb)
+		{
+			this->proxy->cb(this->proxy->data, packet);
+		}
+		else
+		{
+			packet->destroy(packet);
+		}
+		this->proxy->lock->unlock(this->proxy->lock);
+	}
+	else if (errno != EWOULDBLOCK)
+	{
+		DBG1(DBG_NET, "receiving DNS response failed: %s", strerror(errno));
+	}
+	return TRUE;
+}
+
+CALLBACK(handle_timeout, job_requeue_t,
+	proxy_socket_t *this)
+{
+	time_t now, diff;
+
+	now = time_monotonic(NULL);
+	this->proxy->lock->write_lock(this->proxy->lock);
+	diff = now - this->last_use;
+	if (diff >= SOCKET_TIMEOUT)
+	{
+		this->proxy->sockets->remove(this->proxy->sockets, this->src);
+		lib->watcher->remove(lib->watcher, this->fd);
+		this->proxy->lock->unlock(this->proxy->lock);
+		socket_destroy(this);
+		return JOB_REQUEUE_NONE;
+	}
+	this->proxy->lock->unlock(this->proxy->lock);
+	return JOB_RESCHEDULE(SOCKET_TIMEOUT - diff);
+}
+
+/**
+ * DNS header and masks to access flags
+ */
+typedef struct __attribute__((packed)) {
+	uint16_t id;
+	uint16_t flags;
+#define DNS_QR_MASK 0x8000
+#define DNS_OPCODE_MASK 0x7800
+	uint16_t qdcount;
+	uint16_t ancount;
+	uint16_t nscount;
+	uint16_t arcount;
+} dns_header_t;
+
+/**
+ * Extract the hostname in the question section data points to.
+ * Hostnames can be at most 255 characters (including dots separating labels),
+ * each label must be between 1 and 63 characters.
+ * The format is [len][label][len][label], followed by a null byte to indicate
+ * the null label of the root.
+ */
+static char *extract_hostname(chunk_t data)
+{
+	char *hostname, *pos, *end;
+	uint8_t label;
+
+	if (!data.len || data.len > 255)
+	{
+		return NULL;
+	}
+	label = *data.ptr;
+	data = chunk_skip(data, 1);
+	hostname = strndup(data.ptr, data.len);
+	/* replace all label lengths with dots */
+	pos = hostname + label;
+	end = hostname + strlen(hostname);
+	while (pos < end)
+	{
+		label = *pos;
+		*pos++ = '.';
+		pos += label;
+	}
+	return hostname;
+}
+
+/**
+ * Check if the DNS query is for one of the allowed hostnames
+ */
+static bool check_hostname(private_android_dns_proxy_t *this, chunk_t data)
+{
+	dns_header_t *dns;
+	char *hostname;
+	bool success = FALSE;
+
+	this->lock->read_lock(this->lock);
+	if (!this->hostnames->get_count(this->hostnames))
+	{
+		this->lock->unlock(this->lock);
+		return TRUE;
+	}
+	if (data.len < sizeof(dns_header_t))
+	{
+		this->lock->unlock(this->lock);
+		return FALSE;
+	}
+	dns = (dns_header_t*)data.ptr;
+	if ((ntohs(dns->flags) & DNS_QR_MASK) == 0 &&
+		(ntohs(dns->flags) & DNS_OPCODE_MASK) == 0 &&
+		 dns->qdcount)
+	{
+		data = chunk_skip(data, sizeof(dns_header_t));
+		hostname = extract_hostname(data);
+		if (hostname && this->hostnames->get(this->hostnames, hostname))
+		{
+			success = TRUE;
+		}
+		free(hostname);
+	}
+	this->lock->unlock(this->lock);
+	return success;
+}
+
+METHOD(android_dns_proxy_t, handle, bool,
+	private_android_dns_proxy_t *this, ip_packet_t *packet)
+{
+	proxy_socket_t *skt;
+	host_t *dst, *src;
+	chunk_t data;
+
+	if (packet->get_next_header(packet) != IPPROTO_UDP)
+	{
+		return FALSE;
+	}
+	dst = packet->get_destination(packet);
+	if (dst->get_port(dst) != 53)
+	{	/* no DNS packet */
+		return FALSE;
+	}
+	data = packet->get_payload(packet);
+	/* remove UDP header */
+	data = chunk_skip(data, 8);
+	if (!check_hostname(this, data))
+	{
+		return FALSE;
+	}
+	src = packet->get_source(packet);
+	this->lock->write_lock(this->lock);
+	skt = this->sockets->get(this->sockets, src);
+	if (!skt)
+	{
+		skt = create_socket(this, src);
+		if (!skt)
+		{
+			this->lock->unlock(this->lock);
+			return FALSE;
+		}
+		this->sockets->put(this->sockets, skt->src, skt);
+		lib->watcher->add(lib->watcher, skt->fd, WATCHER_READ, handle_response,
+						  skt);
+		lib->scheduler->schedule_job(lib->scheduler,
+			(job_t*)callback_job_create(handle_timeout, skt,
+					NULL, (callback_job_cancel_t)return_false), SOCKET_TIMEOUT);
+	}
+	skt->last_use = time_monotonic(NULL);
+	if (sendto(skt->fd, data.ptr, data.len, 0, dst->get_sockaddr(dst),
+			   *dst->get_sockaddr_len(dst)) != data.len)
+	{
+		DBG1(DBG_NET, "sending DNS request failed: %s", strerror(errno));
+	}
+	this->lock->unlock(this->lock);
+	return TRUE;
+}
+
+METHOD(android_dns_proxy_t, register_cb, void,
+	private_android_dns_proxy_t *this, dns_proxy_response_cb_t cb, void *data)
+{
+	this->lock->write_lock(this->lock);
+	this->cb = cb;
+	this->data = data;
+	this->lock->unlock(this->lock);
+}
+
+METHOD(android_dns_proxy_t, unregister_cb, void,
+	private_android_dns_proxy_t *this, dns_proxy_response_cb_t cb)
+{
+	this->lock->write_lock(this->lock);
+	if (this->cb == cb)
+	{
+		this->cb = NULL;
+	}
+	this->lock->unlock(this->lock);
+}
+
+METHOD(android_dns_proxy_t, add_hostname, void,
+	private_android_dns_proxy_t *this, char *hostname)
+{
+	char *existing;
+
+	hostname = strdup(hostname);
+	this->lock->write_lock(this->lock);
+	existing = this->hostnames->put(this->hostnames, hostname, hostname);
+	this->lock->unlock(this->lock);
+	free(existing);
+}
+
+METHOD(android_dns_proxy_t, destroy, void,
+	private_android_dns_proxy_t *this)
+{
+	this->hostnames->destroy_function(this->hostnames, (void*)free);
+	this->sockets->destroy_function(this->sockets, (void*)socket_destroy);
+	this->lock->destroy(this->lock);
+	free(this);
+}
+
+/**
+ * Described in header.
+ */
+android_dns_proxy_t *android_dns_proxy_create()
+{
+	private_android_dns_proxy_t *this;
+
+	INIT(this,
+		.public = {
+			.handle = _handle,
+			.register_cb = _register_cb,
+			.unregister_cb = _unregister_cb,
+			.add_hostname = _add_hostname,
+			.destroy = _destroy,
+		},
+		.sockets = hashtable_create((hashtable_hash_t)socket_hash,
+									(hashtable_equals_t)socket_equals, 4),
+		.hostnames = hashtable_create(hashtable_hash_str,
+									  hashtable_equals_str, 4),
+		.lock = rwlock_create(RWLOCK_TYPE_DEFAULT),
+	);
+
+	return &this->public;
+}

+ 86 - 0
app/src/main/jni/libandroidbridge/backend/android_dns_proxy.h

@@ -0,0 +1,86 @@
+/*
+ * Copyright (C) 2014 Tobias Brunner
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+/**
+ * @defgroup android_dns_proxy android_dns_proxy
+ * @{ @ingroup android_backend
+ */
+
+#ifndef ANDROID_DNS_PROXY_H_
+#define ANDROID_DNS_PROXY_H_
+
+#include <ip_packet.h>
+
+typedef struct android_dns_proxy_t android_dns_proxy_t;
+
+/**
+ * Callback called to deliver a DNS response packet.
+ *
+ * @param data			data supplied during registration of the callback
+ * @param packet		DNS response packet (has to be destroyed)
+ */
+typedef void (*dns_proxy_response_cb_t)(void *data, ip_packet_t *packet);
+
+/**
+ * DNS proxy class
+ */
+struct android_dns_proxy_t {
+
+	/**
+	 * Handle an outbound DNS packet (if the packet is one)
+	 *
+	 * @param packet		packet to handle
+	 * @return 				TRUE if handled, FALSE otherwise (no DNS)
+	 */
+	bool (*handle)(android_dns_proxy_t *this, ip_packet_t *packet);
+
+	/**
+	 * Register the callback used to deliver DNS response packets.
+	 *
+	 * @param cb			the callback function
+	 * @param data			optional data provided to callback
+	 */
+	void (*register_cb)(android_dns_proxy_t *this, dns_proxy_response_cb_t cb,
+						void *data);
+
+	/**
+	 * Unregister the callback used to deliver DNS response packets.
+	 *
+	 * @param cb			the callback function
+	 * @param data			optional data provided to callback
+	 */
+	void (*unregister_cb)(android_dns_proxy_t *this, dns_proxy_response_cb_t cb);
+
+	/**
+	 * Add a hostname for which queries are proxied.  If at least one hostname
+	 * is configured DNS queries for others will not be handled.
+	 *
+	 * @param hostname		hostname to add (gets cloned)
+	 */
+	void (*add_hostname)(android_dns_proxy_t *this, char *hostname);
+
+	/**
+	 * Destroy an instance.
+	 */
+	void (*destroy)(android_dns_proxy_t *this);
+};
+
+/**
+ * Create an instance.
+ */
+android_dns_proxy_t *android_dns_proxy_create();
+
+#endif /** ANDROID_DNS_PROXY_H_ @}*/
+

+ 169 - 0
app/src/main/jni/libandroidbridge/backend/android_fetcher.c

@@ -0,0 +1,169 @@
+/*
+ * Copyright (C) 2017 Tobias Brunner
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.  *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+#include "android_fetcher.h"
+
+#include "../android_jni.h"
+#include "../charonservice.h"
+#include <utils/debug.h>
+
+typedef struct android_fetcher_t android_fetcher_t;
+
+struct android_fetcher_t {
+
+	/**
+	 * Public interface
+	 */
+	fetcher_t public;
+
+	/**
+	 * Callback function
+	 */
+	fetcher_callback_t cb;
+
+	/**
+	 * Data to POST
+	 */
+	chunk_t data;
+
+	/**
+	 * Type of data to POST
+	 */
+	char *request_type;
+};
+
+METHOD(fetcher_t, fetch, status_t,
+	android_fetcher_t *this, char *uri, void *userdata)
+{
+	JNIEnv *env;
+	jmethodID method_id;
+	jobjectArray jdata = NULL;
+	jstring juri, jct = NULL;
+	chunk_t data;
+	status_t status = FAILED;
+
+	if (this->cb == fetcher_default_callback)
+	{
+		*(chunk_t*)userdata = chunk_empty;
+	}
+
+	androidjni_attach_thread(&env);
+	/* can't use FindClass here as this is not called by the main thread */
+	method_id = (*env)->GetStaticMethodID(env, android_simple_fetcher_class,
+						"fetch", "(Ljava/lang/String;[BLjava/lang/String;)[B");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	juri = (*env)->NewStringUTF(env, uri);
+	if (!juri)
+	{
+		goto failed;
+	}
+	if (this->request_type)
+	{
+		jct = (*env)->NewStringUTF(env, this->request_type);
+		if (!jct)
+		{
+			goto failed;
+		}
+	}
+	if (this->data.ptr)
+	{
+		jdata = byte_array_from_chunk(env, this->data);
+		if (!jdata)
+		{
+			goto failed;
+		}
+	}
+	jdata = (*env)->CallStaticObjectMethod(env, android_simple_fetcher_class,
+										   method_id, juri, jdata, jct);
+	if (!jdata || androidjni_exception_occurred(env))
+	{
+		goto failed;
+	}
+	data = chunk_from_byte_array(env, jdata);
+	if (this->cb(userdata, data))
+	{
+		status = SUCCESS;
+	}
+	chunk_free(&data);
+	androidjni_detach_thread();
+	return status;
+
+failed:
+	DBG1(DBG_LIB, "failed to fetch from '%s'", uri);
+	androidjni_exception_occurred(env);
+	androidjni_detach_thread();
+	return FAILED;
+}
+
+METHOD(fetcher_t, set_option, bool,
+	android_fetcher_t *this, fetcher_option_t option, ...)
+{
+	bool supported = TRUE;
+	va_list args;
+
+	va_start(args, option);
+	switch (option)
+	{
+		case FETCH_CALLBACK:
+		{
+			this->cb = va_arg(args, fetcher_callback_t);
+			break;
+		}
+		case FETCH_REQUEST_DATA:
+		{
+			this->data = chunk_clone(va_arg(args, chunk_t));
+			break;
+		}
+		case FETCH_REQUEST_TYPE:
+		{
+			this->request_type = strdup(va_arg(args, char*));
+			break;
+		}
+		default:
+			supported = FALSE;
+			break;
+	}
+	va_end(args);
+	return supported;
+}
+
+METHOD(fetcher_t, destroy, void,
+	android_fetcher_t *this)
+{
+	chunk_clear(&this->data);
+	free(this->request_type);
+	free(this);
+}
+
+/*
+ * Described in header.
+ */
+fetcher_t *android_fetcher_create()
+{
+	android_fetcher_t *this;
+
+	INIT(this,
+		.public = {
+			.fetch = _fetch,
+			.set_option = _set_option,
+			.destroy = _destroy,
+		},
+		.cb = fetcher_default_callback,
+	);
+
+	return &this->public;
+}

+ 33 - 0
app/src/main/jni/libandroidbridge/backend/android_fetcher.h

@@ -0,0 +1,33 @@
+/*
+ * Copyright (C) 2017 Tobias Brunner
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+/**
+ * @defgroup android_fetcher android_fetcher
+ * @{ @ingroup android_backend
+ */
+
+#ifndef ANDROID_FETCHER_H_
+#define ANDROID_FETCHER_H_
+
+#include <library.h>
+
+/**
+ * Create an Android-specific fetcher instance based on SimpleFetcher
+ *
+ * @return						fetcher_t instance
+ */
+fetcher_t *android_fetcher_create();
+
+#endif /** ANDROID_FETCHER_H_ @}*/

+ 496 - 0
app/src/main/jni/libandroidbridge/backend/android_private_key.c

@@ -0,0 +1,496 @@
+/*
+ * Copyright (C) 2012-2017 Tobias Brunner
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+#include "android_private_key.h"
+
+#include "../android_jni.h"
+#include <utils/debug.h>
+#include <asn1/asn1.h>
+#include <credentials/keys/signature_params.h>
+
+typedef struct private_private_key_t private_private_key_t;
+
+/**
+ * Private data of a android_private_key_t object.
+ */
+struct private_private_key_t {
+
+	/**
+	 * Public interface
+	 */
+	private_key_t public;
+
+	/**
+	 * reference to the Java PrivateKey object
+	 */
+	jobject key;
+
+	/**
+	 * Java class used to build signatures
+	 */
+	jclass signature_class;
+
+	/**
+	 * public key that belongs to this private key
+	 */
+	public_key_t *pubkey;
+
+	/**
+	 * reference count
+	 */
+	refcount_t ref;
+};
+
+/**
+ * Get the Java name for the given hash algorithm
+ */
+static jstring hash_name(JNIEnv *env, hash_algorithm_t alg)
+{
+	const char *hash = NULL;
+
+	switch (alg)
+	{
+		case HASH_SHA1:
+			hash = "SHA-1";
+			break;
+		case HASH_SHA224:
+			hash = "SHA-224";
+			break;
+		case HASH_SHA256:
+			hash = "SHA-256";
+			break;
+		case HASH_SHA384:
+			hash = "SHA-384";
+			break;
+		case HASH_SHA512:
+			hash = "SHA-512";
+			break;
+		default:
+			return NULL;
+	}
+	return (*env)->NewStringUTF(env, hash);
+}
+
+/**
+ * Set PSSParameterSpec on Signature object
+ */
+static bool set_pss_params(private_private_key_t *this, JNIEnv *env,
+						   jobject jsignature, rsa_pss_params_t *pss)
+{
+	jmethodID method_id;
+	jclass cls;
+	jstring jhash, jmgf1;
+	jobject obj;
+	int slen;
+
+	/* create MGF1ParameterSpec instance */
+	cls = (*env)->FindClass(env, "java/security/spec/MGF1ParameterSpec");
+	if (!cls)
+	{
+		return FALSE;
+	}
+	method_id = (*env)->GetMethodID(env, cls, "<init>", "(Ljava/lang/String;)V");
+	if (!method_id)
+	{
+		return FALSE;
+	}
+	jhash = hash_name(env, pss->mgf1_hash);
+	if (!jhash)
+	{
+		return FALSE;
+	}
+	obj = (*env)->NewObject(env, cls, method_id, jhash);
+	if (!obj)
+	{
+		return FALSE;
+	}
+	/* create PSSParameterSpec instance */
+	cls = (*env)->FindClass(env, "java/security/spec/PSSParameterSpec");
+	if (!cls)
+	{
+		return FALSE;
+	}
+	method_id = (*env)->GetMethodID(env, cls, "<init>",
+							"(Ljava/lang/String;Ljava/lang/String;"
+							 "Ljava/security/spec/AlgorithmParameterSpec;II)V");
+	if (!method_id)
+	{
+		return FALSE;
+	}
+	jhash = hash_name(env, pss->hash);
+	jmgf1 = (*env)->NewStringUTF(env, "MGF1");
+	if (!jhash || !jmgf1)
+	{
+		return FALSE;
+	}
+	slen = pss->salt_len;
+	obj = (*env)->NewObject(env, cls, method_id, jhash, jmgf1, obj, slen, 1);
+	if (!obj)
+	{
+		return FALSE;
+	}
+	/* update Signature instance */
+	method_id = (*env)->GetMethodID(env, this->signature_class, "setParameter",
+							"(Ljava/security/spec/AlgorithmParameterSpec;)V");
+	if (!method_id)
+	{
+		return FALSE;
+	}
+	(*env)->CallVoidMethod(env, jsignature, method_id, obj);
+	if (androidjni_exception_occurred(env))
+	{
+		return FALSE;
+	}
+	return TRUE;
+}
+
+METHOD(private_key_t, sign, bool,
+	private_private_key_t *this, signature_scheme_t scheme, void *params,
+	chunk_t data, chunk_t *signature)
+{
+	JNIEnv *env;
+	jmethodID method_id;
+	const char *method = NULL;
+	rsa_pss_params_t *pss = NULL;
+	jstring jmethod;
+	jobject jsignature;
+	jbyteArray jdata, jsigarray;
+
+	switch (this->pubkey->get_type(this->pubkey))
+	{
+		case KEY_RSA:
+			switch (scheme)
+			{
+				case SIGN_RSA_EMSA_PKCS1_NULL:
+					method = "NONEwithRSA";
+					break;
+				case SIGN_RSA_EMSA_PKCS1_MD5:
+					method = "MD5withRSA";
+					break;
+				case SIGN_RSA_EMSA_PKCS1_SHA1:
+					method = "SHA1withRSA";
+					break;
+				case SIGN_RSA_EMSA_PKCS1_SHA2_224:
+					method = "SHA224withRSA";
+					break;
+				case SIGN_RSA_EMSA_PKCS1_SHA2_256:
+					method = "SHA256withRSA";
+					break;
+				case SIGN_RSA_EMSA_PKCS1_SHA2_384:
+					method = "SHA384withRSA";
+					break;
+				case SIGN_RSA_EMSA_PKCS1_SHA2_512:
+					method = "SHA512withRSA";
+					break;
+				case SIGN_RSA_EMSA_PSS:
+					if (!params)
+					{
+						return FALSE;
+					}
+					pss = params;
+					switch (pss->hash)
+					{
+						case HASH_SHA1:
+							method = "SHA1withRSA/PSS";
+							break;
+						case HASH_SHA224:
+							method = "SHA224withRSA/PSS";
+							break;
+						case HASH_SHA256:
+							method = "SHA256withRSA/PSS";
+							break;
+						case HASH_SHA384:
+							method = "SHA384withRSA/PSS";
+							break;
+						case HASH_SHA512:
+							method = "SHA512withRSA/PSS";
+							break;
+						default:
+							break;
+					}
+					break;
+				default:
+					break;
+			}
+			break;
+		case KEY_ECDSA:
+			switch (scheme)
+			{
+				case SIGN_ECDSA_WITH_SHA1_DER:
+					method = "SHA1withECDSA";
+					break;
+				case SIGN_ECDSA_WITH_SHA256_DER:
+				case SIGN_ECDSA_256:
+					method = "SHA256withECDSA";
+					break;
+				case SIGN_ECDSA_WITH_SHA384_DER:
+				case SIGN_ECDSA_384:
+					method = "SHA384withECDSA";
+					break;
+				case SIGN_ECDSA_WITH_SHA512_DER:
+				case SIGN_ECDSA_521:
+					method = "SHA512withECDSA";
+					break;
+				default:
+					break;
+			}
+			break;
+		default:
+			break;
+	}
+	if (!method)
+	{
+		DBG1(DBG_LIB, "signature scheme %N not supported via JNI",
+			 signature_scheme_names, scheme);
+		return FALSE;
+	}
+
+	androidjni_attach_thread(&env);
+	/* we use java.security.Signature to create the signature without requiring
+	 * access to the actual private key */
+	method_id = (*env)->GetStaticMethodID(env, this->signature_class,
+				"getInstance", "(Ljava/lang/String;)Ljava/security/Signature;");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	jmethod = (*env)->NewStringUTF(env, method);
+	if (!jmethod)
+	{
+		goto failed;
+	}
+	jsignature = (*env)->CallStaticObjectMethod(env, this->signature_class,
+												method_id, jmethod);
+	if (!jsignature)
+	{
+		goto failed;
+	}
+	if (pss && !set_pss_params(this, env, jsignature, pss))
+	{
+		goto failed;
+	}
+	method_id = (*env)->GetMethodID(env, this->signature_class, "initSign",
+									"(Ljava/security/PrivateKey;)V");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	(*env)->CallVoidMethod(env, jsignature, method_id, this->key);
+	if (androidjni_exception_occurred(env))
+	{
+		goto failed;
+	}
+	method_id = (*env)->GetMethodID(env, this->signature_class, "update",
+									"([B)V");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	jdata = byte_array_from_chunk(env, data);
+	(*env)->CallVoidMethod(env, jsignature, method_id, jdata);
+	if (androidjni_exception_occurred(env))
+	{
+		goto failed;
+	}
+	method_id = (*env)->GetMethodID(env, this->signature_class, "sign",
+									"()[B");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	jsigarray = (*env)->CallObjectMethod(env, jsignature, method_id);
+	if (!jsigarray)
+	{
+		goto failed;
+	}
+	if (this->pubkey->get_type(this->pubkey) == KEY_ECDSA)
+	{
+		chunk_t encoded, parse, r, s;
+		size_t len = 0;
+
+		switch (scheme)
+		{
+			case SIGN_ECDSA_256:
+				len = 32;
+				break;
+			case SIGN_ECDSA_384:
+				len = 48;
+				break;
+			case SIGN_ECDSA_521:
+				len = 66;
+				break;
+			default:
+				break;
+		}
+		if (len)
+		{
+			/* we get an ASN.1 encoded sequence of integers r and s */
+			parse = encoded = chunk_from_byte_array(env, jsigarray);
+			if (asn1_unwrap(&parse, &parse) != ASN1_SEQUENCE ||
+				asn1_unwrap(&parse, &r) != ASN1_INTEGER ||
+				asn1_unwrap(&parse, &s) != ASN1_INTEGER)
+			{
+				chunk_free(&encoded);
+				goto failed;
+			}
+			r = chunk_skip_zero(r);
+			s = chunk_skip_zero(s);
+			if (r.len > len || s.len > len)
+			{
+				chunk_free(&encoded);
+				goto failed;
+			}
+
+			/* concatenate r and s (forced to the defined length) */
+			*signature = chunk_alloc(2*len);
+			memset(signature->ptr, 0, signature->len);
+			memcpy(signature->ptr + (len - r.len), r.ptr, r.len);
+			memcpy(signature->ptr + len + (len - s.len), s.ptr, s.len);
+			chunk_free(&encoded);
+		}
+		else
+		{
+			*signature = chunk_from_byte_array(env, jsigarray);
+		}
+	}
+	else
+	{
+		*signature = chunk_from_byte_array(env, jsigarray);
+	}
+	androidjni_detach_thread();
+	return TRUE;
+
+failed:
+	DBG1(DBG_LIB, "failed to build %N signature via JNI",
+		 signature_scheme_names, scheme);
+	androidjni_exception_occurred(env);
+	androidjni_detach_thread();
+	return FALSE;
+}
+
+METHOD(private_key_t, get_type, key_type_t,
+	private_private_key_t *this)
+{
+	return this->pubkey->get_type(this->pubkey);
+}
+
+METHOD(private_key_t, decrypt, bool,
+	private_private_key_t *this, encryption_scheme_t scheme,
+	chunk_t crypto, chunk_t *plain)
+{
+	DBG1(DBG_LIB, "private key decryption is currently not supported via JNI");
+	return FALSE;
+}
+
+METHOD(private_key_t, get_keysize, int,
+	private_private_key_t *this)
+{
+	return this->pubkey->get_keysize(this->pubkey);
+}
+
+METHOD(private_key_t, get_public_key, public_key_t*,
+	private_private_key_t *this)
+{
+	return this->pubkey->get_ref(this->pubkey);
+}
+
+METHOD(private_key_t, get_encoding, bool,
+	private_private_key_t *this, cred_encoding_type_t type,
+	chunk_t *encoding)
+{
+	return FALSE;
+}
+
+METHOD(private_key_t, get_fingerprint, bool,
+	private_private_key_t *this, cred_encoding_type_t type, chunk_t *fp)
+{
+	return this->pubkey->get_fingerprint(this->pubkey, type, fp);
+}
+
+METHOD(private_key_t, get_ref, private_key_t*,
+	private_private_key_t *this)
+{
+	ref_get(&this->ref);
+	return &this->public;
+}
+
+METHOD(private_key_t, destroy, void,
+	private_private_key_t *this)
+{
+	if (ref_put(&this->ref))
+	{
+		JNIEnv *env;
+
+		androidjni_attach_thread(&env);
+		if (android_sdk_version == ANDROID_JELLY_BEAN)
+		{	/* there is a bug in JB that causes a SIGSEGV if the key object is
+			 * garbage collected so we intentionally leak the reference to it */
+			DBG1(DBG_LIB, "intentionally leaking private key reference due to "
+				 "a bug in the framework");
+		}
+		else
+		{
+			(*env)->DeleteGlobalRef(env, this->key);
+		}
+		(*env)->DeleteGlobalRef(env, this->signature_class);
+		androidjni_detach_thread();
+		this->pubkey->destroy(this->pubkey);
+		free(this);
+	}
+}
+
+/*
+ * See header
+ */
+private_key_t *android_private_key_create(jobject key, public_key_t *pubkey)
+{
+	JNIEnv *env;
+	private_private_key_t *this;
+
+	INIT(this,
+		.public = {
+			.get_type = _get_type,
+			.sign = _sign,
+			.decrypt = _decrypt,
+			.get_keysize = _get_keysize,
+			.get_public_key = _get_public_key,
+			.belongs_to = private_key_belongs_to,
+			.equals = private_key_equals,
+			.get_fingerprint = _get_fingerprint,
+			.has_fingerprint = private_key_has_fingerprint,
+			.get_encoding = _get_encoding,
+			.get_ref = _get_ref,
+			.destroy = _destroy,
+		},
+		.ref = 1,
+		.pubkey = pubkey,
+	);
+
+	if (!pubkey)
+	{
+		free(this);
+		return NULL;
+	}
+
+	/* in ICS we could simply call getEncoded and use the PKCS#8/DER encoded
+	 * private key, since JB that's not possible as there is no direct access
+	 * to private keys anymore (as these could now be hardware backed) */
+	androidjni_attach_thread(&env);
+	this->key = (*env)->NewGlobalRef(env, key);
+	this->signature_class = (*env)->NewGlobalRef(env, (*env)->FindClass(env,
+													"java/security/Signature"));
+	androidjni_detach_thread();
+	return &this->public;
+}

+ 38 - 0
app/src/main/jni/libandroidbridge/backend/android_private_key.h

@@ -0,0 +1,38 @@
+/*
+ * Copyright (C) 2012 Tobias Brunner
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+/**
+ * @defgroup android_private_key android_private_key
+ * @{ @ingroup android_backend
+ */
+
+#ifndef ANDROID_PRIVATE_KEY_H_
+#define ANDROID_PRIVATE_KEY_H_
+
+#include <jni.h>
+
+#include <credentials/keys/private_key.h>
+
+/**
+ * Create a JNI backed key, stored in the Android KeyChain
+ *
+ * @param key		PrivateKey instance
+ * @param pubkey	public key as extracted from the certificate (gets adopted)
+ * @return 			private_key_t instance
+ */
+private_key_t *android_private_key_create(jobject key, public_key_t *pubkey);
+
+#endif /** ANDROID_PRIVATE_KEY_H_ @}*/
+

+ 955 - 0
app/src/main/jni/libandroidbridge/backend/android_service.c

@@ -0,0 +1,955 @@
+/*
+ * Copyright (C) 2010-2018 Tobias Brunner
+ * Copyright (C) 2012 Giuliano Grassi
+ * Copyright (C) 2012 Ralf Sager
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+#include <errno.h>
+#include <unistd.h>
+
+#include "android_jni.h"
+#include "android_service.h"
+#include "android_dns_proxy.h"
+#include "../charonservice.h"
+#include "../vpnservice_builder.h"
+
+#include <daemon.h>
+#include <library.h>
+#include <ipsec.h>
+#include <processing/jobs/callback_job.h>
+#include <threading/rwlock.h>
+#include <threading/thread.h>
+
+typedef struct private_android_service_t private_android_service_t;
+
+/**
+ * private data of Android service
+ */
+struct private_android_service_t {
+
+	/**
+	 * public interface
+	 */
+	android_service_t public;
+
+	/**
+	 * credential set
+	 */
+	android_creds_t *creds;
+
+	/**
+	 * current IKE_SA
+	 */
+	ike_sa_t *ike_sa;
+
+	/**
+	 * configuration settings
+	 */
+	settings_t *settings;
+
+	/**
+	 * lock to safely access the TUN device fd
+	 */
+	rwlock_t *lock;
+
+	/**
+	 * TUN device file descriptor
+	 */
+	int tunfd;
+
+	/**
+	 * MTU of TUN device
+	 */
+	int mtu;
+
+	/**
+	 * DNS proxy
+	 */
+	android_dns_proxy_t *dns_proxy;
+
+	/**
+	 * Whether to use the DNS proxy or not
+	 */
+	bool use_dns_proxy;
+};
+
+/**
+ * Outbound callback
+ */
+static void send_esp(void *data, esp_packet_t *packet)
+{
+	charon->sender->send_no_marker(charon->sender, (packet_t*)packet);
+}
+
+/**
+ * Inbound callback
+ */
+static void deliver_plain(private_android_service_t *this,
+						  ip_packet_t *packet)
+{
+	chunk_t encoding;
+	ssize_t len;
+
+	encoding = packet->get_encoding(packet);
+
+	this->lock->read_lock(this->lock);
+	if (this->tunfd < 0)
+	{	/* the TUN device is already closed */
+		this->lock->unlock(this->lock);
+		packet->destroy(packet);
+		return;
+	}
+	len = write(this->tunfd, encoding.ptr, encoding.len);
+	this->lock->unlock(this->lock);
+
+	if (len < 0 || len != encoding.len)
+	{
+		DBG1(DBG_DMN, "failed to write packet to TUN device: %s",
+			 strerror(errno));
+	}
+	packet->destroy(packet);
+}
+
+/**
+ * Receiver callback
+ */
+static void receiver_esp_cb(void *data, packet_t *packet)
+{
+	esp_packet_t *esp_packet;
+
+	esp_packet = esp_packet_create_from_packet(packet);
+	ipsec->processor->queue_inbound(ipsec->processor, esp_packet);
+}
+
+/**
+ * Job handling outbound plaintext packets
+ */
+static job_requeue_t handle_plain(private_android_service_t *this)
+{
+	ip_packet_t *packet;
+	chunk_t raw;
+	fd_set set;
+	ssize_t len;
+	int tunfd;
+	bool old, dns_proxy;
+	timeval_t tv = {
+		/* check every second if tunfd is still valid */
+		.tv_sec = 1,
+	};
+
+	FD_ZERO(&set);
+
+	this->lock->read_lock(this->lock);
+	if (this->tunfd < 0)
+	{	/* the TUN device is already closed */
+		this->lock->unlock(this->lock);
+		return JOB_REQUEUE_NONE;
+	}
+	tunfd = this->tunfd;
+	FD_SET(tunfd, &set);
+	/* cache this while we have the lock */
+	dns_proxy = this->use_dns_proxy;
+	this->lock->unlock(this->lock);
+
+	old = thread_cancelability(TRUE);
+	len = select(tunfd + 1, &set, NULL, NULL, &tv);
+	thread_cancelability(old);
+
+	if (len < 0)
+	{
+		if (errno == EBADF)
+		{	/* the TUN device got closed just before calling select(), retry */
+			return JOB_REQUEUE_FAIR;
+		}
+		DBG1(DBG_DMN, "select on TUN device failed: %s", strerror(errno));
+		return JOB_REQUEUE_NONE;
+	}
+	else if (len == 0)
+	{	/* timeout, check again right away */
+		return JOB_REQUEUE_DIRECT;
+	}
+
+	raw = chunk_alloc(this->mtu);
+	len = read(tunfd, raw.ptr, raw.len);
+	if (len < 0)
+	{
+		DBG1(DBG_DMN, "reading from TUN device failed: %s", strerror(errno));
+		chunk_free(&raw);
+		return JOB_REQUEUE_FAIR;
+	}
+	raw.len = len;
+
+	packet = ip_packet_create(raw);
+	if (packet)
+	{
+		if (!dns_proxy || !this->dns_proxy->handle(this->dns_proxy, packet))
+		{
+			ipsec->processor->queue_outbound(ipsec->processor, packet);
+		}
+	}
+	else
+	{
+		DBG1(DBG_DMN, "invalid IP packet read from TUN device");
+	}
+	return JOB_REQUEUE_DIRECT;
+}
+
+/**
+ * Add a route to the TUN device builder
+ */
+static bool add_route(vpnservice_builder_t *builder, host_t *net,
+					  uint8_t prefix)
+{
+	/* if route is 0.0.0.0/0, split it into two routes 0.0.0.0/1 and
+	 * 128.0.0.0/1 because otherwise it would conflict with the current default
+	 * route.  likewise for IPv6 with ::/0. */
+	if (net->is_anyaddr(net) && prefix == 0)
+	{
+		bool success;
+
+		success = add_route(builder, net, 1);
+		if (net->get_family(net) == AF_INET)
+		{
+			net = host_create_from_string("128.0.0.0", 0);
+		}
+		else
+		{
+			net = host_create_from_string("8000::", 0);
+		}
+		success = success && add_route(builder, net, 1);
+		net->destroy(net);
+		return success;
+	}
+	return builder->add_route(builder, net, prefix);
+}
+
+/**
+ * Generate and set routes from installed IPsec policies
+ */
+static bool add_routes(vpnservice_builder_t *builder, child_sa_t *child_sa)
+{
+	traffic_selector_t *src_ts, *dst_ts;
+	enumerator_t *enumerator;
+	bool success = TRUE;
+
+	enumerator = child_sa->create_policy_enumerator(child_sa);
+	while (success && enumerator->enumerate(enumerator, &src_ts, &dst_ts))
+	{
+		host_t *net;
+		uint8_t prefix;
+
+		dst_ts->to_subnet(dst_ts, &net, &prefix);
+		success = add_route(builder, net, prefix);
+		net->destroy(net);
+	}
+	enumerator->destroy(enumerator);
+	return success;
+}
+
+/**
+ * Setup a new TUN device for the supplied SAs, also queues a job that
+ * reads packets from this device.
+ * Additional information such as DNS servers are gathered in appropriate
+ * listeners asynchronously.  To be sure every required bit of information is
+ * available this should be called after the CHILD_SA has been established.
+ */
+static bool setup_tun_device(private_android_service_t *this,
+							 ike_sa_t *ike_sa, child_sa_t *child_sa)
+{
+	vpnservice_builder_t *builder;
+	enumerator_t *enumerator;
+	bool vip_found = FALSE, already_registered = FALSE;
+	host_t *vip;
+	int tunfd;
+
+	DBG1(DBG_DMN, "setting up TUN device for CHILD_SA %s{%u}",
+		 child_sa->get_name(child_sa), child_sa->get_unique_id(child_sa));
+
+	builder = charonservice->get_vpnservice_builder(charonservice);
+
+	enumerator = ike_sa->create_virtual_ip_enumerator(ike_sa, TRUE);
+	while (enumerator->enumerate(enumerator, &vip))
+	{
+		if (!vip->is_anyaddr(vip))
+		{
+			if (!builder->add_address(builder, vip))
+			{
+				break;
+			}
+			vip_found = TRUE;
+		}
+	}
+	enumerator->destroy(enumerator);
+
+	if (!vip_found)
+	{
+		DBG1(DBG_DMN, "setting up TUN device failed, no virtual IP found");
+		return FALSE;
+	}
+	if (!add_routes(builder, child_sa) ||
+		!builder->set_mtu(builder, this->mtu))
+	{
+		return FALSE;
+	}
+
+	tunfd = builder->establish(builder);
+	if (tunfd == -1)
+	{
+		return FALSE;
+	}
+
+	this->lock->write_lock(this->lock);
+	if (this->tunfd > 0)
+	{	/* close previously opened TUN device */
+		close(this->tunfd);
+		already_registered = true;
+	}
+	this->tunfd = tunfd;
+	this->lock->unlock(this->lock);
+
+	DBG1(DBG_DMN, "successfully created TUN device");
+
+	if (!already_registered)
+	{
+		charon->receiver->add_esp_cb(charon->receiver,
+								(receiver_esp_cb_t)receiver_esp_cb, NULL);
+		ipsec->processor->register_inbound(ipsec->processor,
+									  (ipsec_inbound_cb_t)deliver_plain, this);
+		ipsec->processor->register_outbound(ipsec->processor,
+									   (ipsec_outbound_cb_t)send_esp, NULL);
+		this->dns_proxy->register_cb(this->dns_proxy,
+								(dns_proxy_response_cb_t)deliver_plain, this);
+
+		lib->processor->queue_job(lib->processor,
+			(job_t*)callback_job_create((callback_job_cb_t)handle_plain, this,
+									NULL, (callback_job_cancel_t)return_false));
+	}
+	return TRUE;
+}
+
+/**
+ * Setup a new TUN device based on the existing one, but without DNS server.
+ */
+static bool setup_tun_device_without_dns(private_android_service_t *this)
+{
+	vpnservice_builder_t *builder;
+	int tunfd;
+
+	DBG1(DBG_DMN, "setting up TUN device without DNS");
+
+	builder = charonservice->get_vpnservice_builder(charonservice);
+
+	tunfd = builder->establish_no_dns(builder);
+	if (tunfd == -1)
+	{
+		return FALSE;
+	}
+
+	this->lock->write_lock(this->lock);
+	if (this->tunfd > 0)
+	{	/* close previously opened TUN device, this should always be the case */
+		close(this->tunfd);
+	}
+	this->tunfd = tunfd;
+	this->lock->unlock(this->lock);
+
+	DBG1(DBG_DMN, "successfully created TUN device without DNS");
+	return TRUE;
+}
+
+/**
+ * Close the current tun device
+ */
+static void close_tun_device(private_android_service_t *this)
+{
+	int tunfd;
+
+	this->lock->write_lock(this->lock);
+	if (this->tunfd < 0)
+	{	/* already closed (or never created) */
+		this->lock->unlock(this->lock);
+		return;
+	}
+	tunfd = this->tunfd;
+	this->tunfd = -1;
+	this->lock->unlock(this->lock);
+
+	this->dns_proxy->unregister_cb(this->dns_proxy,
+								(dns_proxy_response_cb_t)deliver_plain);
+	ipsec->processor->unregister_outbound(ipsec->processor,
+										 (ipsec_outbound_cb_t)send_esp);
+	ipsec->processor->unregister_inbound(ipsec->processor,
+										(ipsec_inbound_cb_t)deliver_plain);
+	charon->receiver->del_esp_cb(charon->receiver,
+								(receiver_esp_cb_t)receiver_esp_cb);
+	close(tunfd);
+}
+
+/**
+ * Terminate the IKE_SA with the given unique ID
+ */
+CALLBACK(terminate, job_requeue_t,
+	uint32_t *id)
+{
+	charon->controller->terminate_ike(charon->controller, *id, FALSE,
+									  controller_cb_empty, NULL, 0);
+	return JOB_REQUEUE_NONE;
+}
+
+/**
+ * Reestablish the IKE_SA with the given unique ID
+ */
+CALLBACK(reestablish, job_requeue_t,
+	uint32_t *id)
+{
+	ike_sa_t *ike_sa;
+
+	ike_sa = charon->ike_sa_manager->checkout_by_id(charon->ike_sa_manager, *id);
+	if (ike_sa)
+	{
+		if (ike_sa->reauth(ike_sa) == DESTROY_ME)
+		{
+			charon->ike_sa_manager->checkin_and_destroy(charon->ike_sa_manager,
+														ike_sa);
+		}
+		else
+		{
+			charon->ike_sa_manager->checkin(charon->ike_sa_manager, ike_sa);
+		}
+	}
+	return JOB_REQUEUE_NONE;
+}
+
+METHOD(listener_t, ike_updown, bool,
+	private_android_service_t *this, ike_sa_t *ike_sa, bool up)
+{
+	/* this callback is only registered during initiation, so if the IKE_SA
+	 * goes down we assume some kind of authentication error, more specific
+	 * errors are caught in the alert() handler */
+	if (this->ike_sa == ike_sa && !up)
+	{
+		charonservice->update_status(charonservice,
+									 CHARONSERVICE_AUTH_ERROR);
+		return FALSE;
+	}
+	return TRUE;
+}
+
+METHOD(listener_t, ike_rekey, bool,
+	private_android_service_t *this, ike_sa_t *old, ike_sa_t *new)
+{
+	if (this->ike_sa == old)
+	{
+		this->ike_sa = new;
+	}
+	return TRUE;
+}
+
+METHOD(listener_t, ike_reestablish_post_redirect, bool,
+	private_android_service_t *this, ike_sa_t *old, ike_sa_t *new,
+	bool initiated)
+{
+	if (this->ike_sa == old && initiated)
+	{	/* if we get redirected during IKE_AUTH we just migrate to the new SA,
+		 * we don't have a TUN device yet, so reinstalling it without DNS would
+		 * fail (and using the DNS proxy is not required anyway) */
+		this->ike_sa = new;
+	}
+	return TRUE;
+}
+
+METHOD(listener_t, ike_reestablish_pre, bool,
+	private_android_service_t *this, ike_sa_t *old, ike_sa_t *new)
+{
+	if (this->ike_sa == old)
+	{
+		/* enable DNS proxy so hosts are properly resolved while the TUN device
+		 * is still active */
+		this->lock->write_lock(this->lock);
+		this->use_dns_proxy = TRUE;
+		this->lock->unlock(this->lock);
+		/* if DNS servers are installed that are only reachable through the VPN
+		 * the DNS proxy doesn't help, so uninstall DNS servers */
+		if (!setup_tun_device_without_dns(this))
+		{
+			DBG1(DBG_DMN, "failed to setup TUN device without DNS");
+			charonservice->update_status(charonservice,
+										 CHARONSERVICE_GENERIC_ERROR);
+		}
+	}
+	return TRUE;
+}
+
+METHOD(listener_t, ike_reestablish_post, bool,
+	private_android_service_t *this, ike_sa_t *old, ike_sa_t *new,
+	bool initiated)
+{
+	if (this->ike_sa == old && initiated)
+	{
+		this->ike_sa = new;
+		/* re-register hook to detect initiation failures */
+		this->public.listener.ike_updown = _ike_updown;
+		/* if the IKE_SA got deleted by the responder we get the child_down()
+		 * event on the old IKE_SA after this hook has been called, so they
+		 * get ignored and thus we trigger the event here */
+		charonservice->update_status(charonservice,
+									 CHARONSERVICE_CHILD_STATE_DOWN);
+	}
+	return TRUE;
+}
+
+METHOD(listener_t, child_updown, bool,
+	private_android_service_t *this, ike_sa_t *ike_sa, child_sa_t *child_sa,
+	bool up)
+{
+	if (this->ike_sa == ike_sa)
+	{
+		if (up)
+		{
+			/* disable the hooks registered to catch initiation failures */
+			this->public.listener.ike_updown = NULL;
+			/* enable hooks to handle reauthentications */
+			this->public.listener.ike_reestablish_pre = _ike_reestablish_pre;
+			this->public.listener.ike_reestablish_post = _ike_reestablish_post;
+			/* CHILD_SA is up so we can disable the DNS proxy we enabled to
+			 * reestablish the SA */
+			this->lock->write_lock(this->lock);
+			this->use_dns_proxy = FALSE;
+			this->lock->unlock(this->lock);
+			if (!setup_tun_device(this, ike_sa, child_sa))
+			{
+				DBG1(DBG_DMN, "failed to setup TUN device");
+				charonservice->update_status(charonservice,
+											 CHARONSERVICE_GENERIC_ERROR);
+				return FALSE;
+
+			}
+			charonservice->update_status(charonservice,
+										 CHARONSERVICE_CHILD_STATE_UP);
+		}
+		else
+		{
+			charonservice->update_status(charonservice,
+										 CHARONSERVICE_CHILD_STATE_DOWN);
+		}
+	}
+	return TRUE;
+}
+
+METHOD(listener_t, alert, bool,
+	private_android_service_t *this, ike_sa_t *ike_sa, alert_t alert,
+	va_list args)
+{
+	bool stay_registered = TRUE;
+
+	if (this->ike_sa == ike_sa)
+	{
+		switch (alert)
+		{
+			case ALERT_PEER_ADDR_FAILED:
+				charonservice->update_status(charonservice,
+											 CHARONSERVICE_LOOKUP_ERROR);
+				return FALSE;
+
+			case ALERT_PEER_AUTH_FAILED:
+				charonservice->update_status(charonservice,
+											 CHARONSERVICE_PEER_AUTH_ERROR);
+				return FALSE;
+
+			case ALERT_KEEP_ON_CHILD_SA_FAILURE:
+			{
+				uint32_t *id = malloc_thing(uint32_t);
+
+				/* because close_ike_on_child_failure is set this is only
+				 * triggered when CHILD_SA rekeying failed. reestablish it in
+				 * the hope that the initial setup works again. */
+				*id = ike_sa->get_unique_id(ike_sa);
+				lib->processor->queue_job(lib->processor,
+					(job_t*)callback_job_create_with_prio(
+						(callback_job_cb_t)reestablish, id, free,
+						(callback_job_cancel_t)return_false, JOB_PRIO_HIGH));
+				break;
+			}
+			case ALERT_PEER_INIT_UNREACHABLE:
+				this->lock->read_lock(this->lock);
+				if (this->tunfd < 0)
+				{
+					uint32_t *id = malloc_thing(uint32_t);
+
+					/* always fail if we are not able to initiate the IKE_SA
+					 * initially */
+					charonservice->update_status(charonservice,
+											CHARONSERVICE_UNREACHABLE_ERROR);
+					/* terminate the IKE_SA so no further keying tries are
+					 * attempted */
+					*id = ike_sa->get_unique_id(ike_sa);
+					lib->processor->queue_job(lib->processor,
+						(job_t*)callback_job_create_with_prio(
+							(callback_job_cb_t)terminate, id, free,
+							(callback_job_cancel_t)return_false, JOB_PRIO_HIGH));
+					stay_registered = FALSE;
+				}
+				else
+				{
+					peer_cfg_t *peer_cfg;
+					uint32_t tries, try;
+
+					/* when reestablishing and if keyingtries is not %forever
+					 * the IKE_SA is destroyed after the set number of tries,
+					 * so notify the GUI */
+					peer_cfg = ike_sa->get_peer_cfg(ike_sa);
+					tries = peer_cfg->get_keyingtries(peer_cfg);
+					try = va_arg(args, uint32_t);
+					if (tries != 0 && try == tries-1)
+					{
+						charonservice->update_status(charonservice,
+											CHARONSERVICE_UNREACHABLE_ERROR);
+						stay_registered = FALSE;
+					}
+				}
+				this->lock->unlock(this->lock);
+				break;
+			default:
+				break;
+		}
+	}
+	return stay_registered;
+}
+
+static void add_auth_cfg_pw(private_android_service_t *this,
+							peer_cfg_t *peer_cfg, bool byod)
+{
+	identification_t *user, *id = NULL;
+	auth_cfg_t *auth;
+	char *username, *password, *local_id;
+
+	auth = auth_cfg_create();
+	auth->add(auth, AUTH_RULE_AUTH_CLASS, AUTH_CLASS_EAP);
+	if (byod)
+	{	/* use EAP-TTLS if BYOD is enabled */
+		auth->add(auth, AUTH_RULE_EAP_TYPE, EAP_TTLS);
+	}
+	/* in case EAP-PEAP or EAP-TTLS is used we currently accept any identity */
+	auth->add(auth, AUTH_RULE_AAA_IDENTITY,
+			  identification_create_from_string("%any"));
+
+	username = this->settings->get_str(this->settings, "connection.username",
+									   NULL);
+	password = this->settings->get_str(this->settings, "connection.password",
+									   NULL);
+	local_id = this->settings->get_str(this->settings, "connection.local_id",
+									   NULL);
+	user = identification_create_from_string(username);
+	auth->add(auth, AUTH_RULE_EAP_IDENTITY, user);
+	if (local_id)
+	{
+		id = identification_create_from_string(local_id);
+	}
+	if (!id)
+	{
+		id = user->clone(user);
+	}
+	auth->add(auth, AUTH_RULE_IDENTITY, id);
+
+	this->creds->add_username_password(this->creds, username, password);
+	peer_cfg->add_auth_cfg(peer_cfg, auth, TRUE);
+}
+
+static bool add_auth_cfg_cert(private_android_service_t *this,
+							  peer_cfg_t *peer_cfg)
+{
+	certificate_t *cert;
+	identification_t *id = NULL;
+	auth_cfg_t *auth;
+	char *type, *local_id;
+
+	cert = this->creds->load_user_certificate(this->creds);
+	if (!cert)
+	{
+		return FALSE;
+	}
+
+	type = this->settings->get_str(this->settings, "connection.type", NULL);
+	auth = auth_cfg_create();
+	if (strpfx("ikev2-eap-tls", type))
+	{
+		auth->add(auth, AUTH_RULE_AUTH_CLASS, AUTH_CLASS_EAP);
+		auth->add(auth, AUTH_RULE_EAP_TYPE, EAP_TLS);
+		auth->add(auth, AUTH_RULE_AAA_IDENTITY,
+				  identification_create_from_string("%any"));
+	}
+	else
+	{
+		auth->add(auth, AUTH_RULE_AUTH_CLASS, AUTH_CLASS_PUBKEY);
+	}
+	auth->add(auth, AUTH_RULE_SUBJECT_CERT, cert);
+
+	local_id = this->settings->get_str(this->settings, "connection.local_id",
+									   NULL);
+	if (local_id)
+	{
+		id = identification_create_from_string(local_id);
+	}
+	if (!id)
+	{
+		id = cert->get_subject(cert);
+		id = id->clone(id);
+	}
+	auth->add(auth, AUTH_RULE_IDENTITY, id);
+	peer_cfg->add_auth_cfg(peer_cfg, auth, TRUE);
+	return TRUE;
+}
+
+static proposal_t *parse_proposal(private_android_service_t *this,
+								  protocol_id_t proto, char *opt)
+{
+	proposal_t *proposal = NULL;
+	char *prop;
+
+	prop = this->settings->get_str(this->settings, opt, NULL);
+	if (!prop || !strlen(prop))
+	{
+		return NULL;
+	}
+
+	proposal = proposal_create_from_string(proto, prop);
+	if (!proposal)
+	{
+		DBG1(DBG_CFG, "invalid %N proposal '%s', falling back to defaults",
+			 protocol_id_names, proto, prop);
+	}
+	return proposal;
+}
+
+static job_requeue_t initiate(private_android_service_t *this)
+{
+	identification_t *gateway = NULL;
+	ike_cfg_t *ike_cfg;
+	peer_cfg_t *peer_cfg;
+	child_cfg_t *child_cfg;
+	traffic_selector_t *ts;
+	proposal_t *proposal;
+	ike_sa_t *ike_sa;
+	auth_cfg_t *auth;
+	ike_cfg_create_t ike = {
+		.version = IKEV2,
+		.local = "0.0.0.0",
+		.local_port = charon->socket->get_port(charon->socket, FALSE),
+		.force_encap = TRUE,
+		.fragmentation = FRAGMENTATION_YES,
+	};
+	peer_cfg_create_t peer = {
+		.cert_policy = CERT_ALWAYS_SEND,
+		.unique = UNIQUE_REPLACE,
+		.rekey_time = 36000, /* 10h */
+		.jitter_time = 600, /* 10min */
+		.over_time = 600, /* 10min */
+	};
+	child_cfg_create_t child = {
+		.lifetime = {
+			.time = {
+				.life = 3600, /* 1h */
+				.rekey = 3000, /* 50min */
+				.jitter = 300 /* 5min */
+			},
+		},
+		.mode = MODE_TUNNEL,
+		.dpd_action = ACTION_RESTART,
+		.close_action = ACTION_RESTART,
+	};
+	char *type, *remote_id;
+
+	if (android_sdk_version >= ANDROID_LOLLIPOP)
+	{   /* only try once and notify the GUI on Android 5+ where we have a blocking TUN device */
+		peer.keyingtries = 1;
+	}
+
+	ike.remote = this->settings->get_str(this->settings, "connection.server",
+										 NULL);
+	ike.remote_port = this->settings->get_int(this->settings, "connection.port",
+											  IKEV2_UDP_PORT);
+	ike.no_certreq = !this->settings->get_bool(this->settings,
+											   "connection.certreq", TRUE);
+	ike_cfg = ike_cfg_create(&ike);
+	proposal = parse_proposal(this, PROTO_IKE, "connection.ike_proposal");
+	if (proposal)
+	{
+		ike_cfg->add_proposal(ike_cfg, proposal);
+	}
+	else
+	{
+		ike_cfg->add_proposal(ike_cfg, proposal_create_default(PROTO_IKE));
+		ike_cfg->add_proposal(ike_cfg, proposal_create_default_aead(PROTO_IKE));
+	}
+
+	peer_cfg = peer_cfg_create("android", ike_cfg, &peer);
+	peer_cfg->add_virtual_ip(peer_cfg, host_create_any(AF_INET));
+	peer_cfg->add_virtual_ip(peer_cfg, host_create_any(AF_INET6));
+
+	type = this->settings->get_str(this->settings, "connection.type", NULL);
+	/* local auth config */
+	if (streq("ikev2-cert", type) ||
+		streq("ikev2-cert-eap", type) ||
+		streq("ikev2-eap-tls", type))
+	{
+		if (!add_auth_cfg_cert(this, peer_cfg))
+		{
+			peer_cfg->destroy(peer_cfg);
+			charonservice->update_status(charonservice,
+										 CHARONSERVICE_CERTIFICATE_UNAVAILABLE);
+			return JOB_REQUEUE_NONE;
+		}
+	}
+	if (streq("ikev2-eap", type) ||
+		streq("ikev2-cert-eap", type) ||
+		streq("ikev2-byod-eap", type))
+	{
+		add_auth_cfg_pw(this, peer_cfg, strpfx(type, "ikev2-byod"));
+	}
+
+	/* remote auth config */
+	auth = auth_cfg_create();
+	remote_id = this->settings->get_str(this->settings, "connection.remote_id",
+										NULL);
+	if (remote_id)
+	{
+		gateway = identification_create_from_string(remote_id);
+	}
+	if (!gateway || gateway->get_type(gateway) == ID_ANY)
+	{
+		DESTROY_IF(gateway);
+		gateway = identification_create_from_string(ike.remote);
+		/* only use this if remote ID was not configured explicitly */
+		auth->add(auth, AUTH_RULE_IDENTITY_LOOSE, TRUE);
+	}
+	auth->add(auth, AUTH_RULE_IDENTITY, gateway);
+	auth->add(auth, AUTH_RULE_AUTH_CLASS, AUTH_CLASS_PUBKEY);
+	if (this->settings->get_bool(this->settings, "connection.strict_revocation", FALSE))
+	{
+		auth->add(auth, AUTH_RULE_CRL_VALIDATION, VALIDATION_GOOD);
+	}
+	peer_cfg->add_auth_cfg(peer_cfg, auth, FALSE);
+
+	child_cfg = child_cfg_create("android", &child);
+	proposal = parse_proposal(this, PROTO_ESP, "connection.esp_proposal");
+	if (proposal)
+	{
+		child_cfg->add_proposal(child_cfg, proposal);
+	}
+	else
+	{	/* create ESP proposals with and without DH groups, let responder decide
+		 * if PFS is used */
+		child_cfg->add_proposal(child_cfg, proposal_create_from_string(PROTO_ESP,
+								"aes256gcm16-aes128gcm16-chacha20poly1305-"
+								"curve25519-ecp384-ecp521-modp3072-modp4096-ecp256-modp8192"));
+		child_cfg->add_proposal(child_cfg, proposal_create_from_string(PROTO_ESP,
+								"aes256-aes192-aes128-sha384-sha256-sha512-sha1-"
+								"curve25519-ecp384-ecp521-modp3072-modp4096-ecp256-modp2048-"
+								"modp8192"));
+		child_cfg->add_proposal(child_cfg, proposal_create_from_string(PROTO_ESP,
+								"aes256gcm16-aes128gcm16-chacha20poly1305"));
+		child_cfg->add_proposal(child_cfg, proposal_create_from_string(PROTO_ESP,
+								"aes256-aes192-aes128-sha384-sha256-sha512-sha1"));
+	}
+	ts = traffic_selector_create_from_cidr("0.0.0.0/0", 0, 0, 65535);
+	child_cfg->add_traffic_selector(child_cfg, TRUE, ts);
+	ts = traffic_selector_create_from_cidr("0.0.0.0/0", 0, 0, 65535);
+	child_cfg->add_traffic_selector(child_cfg, FALSE, ts);
+	ts = traffic_selector_create_from_cidr("::/0", 0, 0, 65535);
+	child_cfg->add_traffic_selector(child_cfg, TRUE, ts);
+	ts = traffic_selector_create_from_cidr("::/0", 0, 0, 65535);
+	child_cfg->add_traffic_selector(child_cfg, FALSE, ts);
+	peer_cfg->add_child_cfg(peer_cfg, child_cfg);
+
+	/* get us an IKE_SA */
+	ike_sa = charon->ike_sa_manager->checkout_by_config(charon->ike_sa_manager,
+														peer_cfg);
+	if (!ike_sa)
+	{
+		peer_cfg->destroy(peer_cfg);
+		charonservice->update_status(charonservice,
+									 CHARONSERVICE_GENERIC_ERROR);
+		return JOB_REQUEUE_NONE;
+	}
+	if (!ike_sa->get_peer_cfg(ike_sa))
+	{
+		ike_sa->set_peer_cfg(ike_sa, peer_cfg);
+	}
+	peer_cfg->destroy(peer_cfg);
+
+	/* store the IKE_SA so we can track its progress */
+	this->ike_sa = ike_sa;
+
+	/* get an additional reference because initiate consumes one */
+	child_cfg->get_ref(child_cfg);
+	if (ike_sa->initiate(ike_sa, child_cfg, 0, NULL, NULL) != SUCCESS)
+	{
+		DBG1(DBG_CFG, "failed to initiate tunnel");
+		charon->ike_sa_manager->checkin_and_destroy(charon->ike_sa_manager,
+			ike_sa);
+		return JOB_REQUEUE_NONE;
+	}
+	charon->ike_sa_manager->checkin(charon->ike_sa_manager, ike_sa);
+	return JOB_REQUEUE_NONE;
+}
+
+METHOD(android_service_t, destroy, void,
+	private_android_service_t *this)
+{
+	charon->bus->remove_listener(charon->bus, &this->public.listener);
+	/* make sure the tun device is actually closed */
+	close_tun_device(this);
+	this->dns_proxy->destroy(this->dns_proxy);
+	this->lock->destroy(this->lock);
+	this->settings->destroy(this->settings);
+	free(this);
+}
+
+/**
+ * See header
+ */
+android_service_t *android_service_create(android_creds_t *creds,
+										  settings_t *settings)
+{
+	private_android_service_t *this;
+
+	INIT(this,
+		.public = {
+			.listener = {
+				.ike_rekey = _ike_rekey,
+				.ike_reestablish_post = _ike_reestablish_post_redirect,
+				.ike_updown = _ike_updown,
+				.child_updown = _child_updown,
+				.alert = _alert,
+			},
+			.destroy = _destroy,
+		},
+		.lock = rwlock_create(RWLOCK_TYPE_DEFAULT),
+		.dns_proxy = android_dns_proxy_create(),
+		.settings = settings,
+		.creds = creds,
+		.tunfd = -1,
+		.mtu = settings->get_int(settings, "global.mtu", ANDROID_DEFAULT_MTU),
+	);
+	/* only allow queries for the VPN gateway */
+	this->dns_proxy->add_hostname(this->dns_proxy,
+			this->settings->get_str(this->settings, "connection.server", NULL));
+
+	charon->bus->add_listener(charon->bus, &this->public.listener);
+
+	lib->processor->queue_job(lib->processor,
+		(job_t*)callback_job_create((callback_job_cb_t)initiate, this,
+									NULL, NULL));
+	return &this->public;
+}

+ 60 - 0
app/src/main/jni/libandroidbridge/backend/android_service.h

@@ -0,0 +1,60 @@
+/*
+ * Copyright (C) 2010-2015 Tobias Brunner
+ * Copyright (C) 2012 Giuliano Grassi
+ * Copyright (C) 2012 Ralf Sager
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+/**
+ * @defgroup android_service android_service
+ * @{ @ingroup android_backend
+ */
+
+#ifndef ANDROID_SERVICE_H_
+#define ANDROID_SERVICE_H_
+
+#include "android_creds.h"
+
+#include <library.h>
+#include <bus/listeners/listener.h>
+
+typedef struct android_service_t android_service_t;
+
+/**
+ * Service that sets up an IKE_SA/CHILD_SA and handles events
+ */
+struct android_service_t {
+
+	/**
+	 * Implements listener_t.
+	 */
+	listener_t listener;
+
+	/**
+	 * Destroy a android_service_t.
+	 */
+	void (*destroy)(android_service_t *this);
+
+};
+
+/**
+ * Create an Android service instance. Queues a job that starts initiation of a
+ * new IKE SA.
+ *
+ * @param creds					Android specific credential set
+ * @param settings				configuration settings (gets adopted)
+ */
+android_service_t *android_service_create(android_creds_t *creds,
+										  settings_t *settings);
+
+#endif /** ANDROID_SERVICE_H_ @}*/

+ 722 - 0
app/src/main/jni/libandroidbridge/byod/imc_android.c

@@ -0,0 +1,722 @@
+/*
+ * Copyright (C) 2012-2013 Tobias Brunner
+ * Copyright (C) 2012 Christoph Buehler
+ * Copyright (C) 2012 Patrick Loetscher
+ * Copyright (C) 2011-2012 Andreas Steffen
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+#include "imc_android_state.h"
+#include "../android_jni.h"
+#include "../charonservice.h"
+
+#include <tnc/tnc.h>
+#include <imcv.h>
+#include <imc/imc_agent.h>
+#include <imc/imc_msg.h>
+#include <pa_tnc/pa_tnc_msg.h>
+#include <ietf/ietf_attr.h>
+#include <ietf/ietf_attr_attr_request.h>
+#include <ietf/ietf_attr_installed_packages.h>
+#include <ietf/ietf_attr_pa_tnc_error.h>
+#include <ietf/ietf_attr_product_info.h>
+#include <ietf/ietf_attr_remediation_instr.h>
+#include <ietf/ietf_attr_string_version.h>
+#include <ita/ita_attr.h>
+#include <ita/ita_attr_get_settings.h>
+#include <tcg/pts/tcg_pts_attr_file_meas.h>
+#include <tcg/pts/tcg_pts_attr_meas_algo.h>
+#include <tcg/pts/tcg_pts_attr_proto_caps.h>
+#include <tcg/pts/tcg_pts_attr_req_file_meas.h>
+#include <os_info/os_info.h>
+
+#include <tncif_pa_subtypes.h>
+
+#include <pen/pen.h>
+#include <utils/debug.h>
+
+#include <stdio.h>
+
+/* IMC definitions */
+
+static const char imc_name[] = "Android";
+
+static pen_type_t msg_types[] = {
+	{ PEN_IETF, PA_SUBTYPE_IETF_OPERATING_SYSTEM },
+	{ PEN_IETF, PA_SUBTYPE_IETF_VPN },
+	{ PEN_TCG, PA_SUBTYPE_TCG_PTS },
+};
+
+static imc_agent_t *imc_android;
+
+/**
+ * AndroidImc object accessed via JNI
+ */
+static jobject android_imc;
+
+/**
+ * AndroidImc class object
+ */
+static jclass android_imc_cls;
+
+/**
+ * see section 3.8.1 of TCG TNC IF-IMC Specification 1.3
+ */
+static TNC_Result tnc_imc_initialize(TNC_IMCID imc_id,
+									 TNC_Version min_version,
+									 TNC_Version max_version,
+									 TNC_Version *actual_version)
+{
+	if (imc_android)
+	{
+		DBG1(DBG_IMC, "IMC \"%s\" has already been initialized", imc_name);
+		return TNC_RESULT_ALREADY_INITIALIZED;
+	}
+	imc_android = imc_agent_create(imc_name, msg_types, countof(msg_types),
+								   imc_id, actual_version);
+	if (!imc_android)
+	{
+		return TNC_RESULT_FATAL;
+	}
+
+	if (min_version > TNC_IFIMC_VERSION_1 || max_version < TNC_IFIMC_VERSION_1)
+	{
+		DBG1(DBG_IMC, "no common IF-IMC version");
+		return TNC_RESULT_NO_COMMON_VERSION;
+	}
+	return TNC_RESULT_SUCCESS;
+}
+
+/**
+ * Update the state in the GUI.
+ */
+static void update_imc_state(TNC_ConnectionState state)
+{
+	android_imc_state_t imc_state = ANDROID_IMC_STATE_UNKNOWN;
+
+	switch (state)
+	{	/* map connection states to the values used by the GUI */
+		case TNC_CONNECTION_STATE_ACCESS_ALLOWED:
+			imc_state = ANDROID_IMC_STATE_ALLOW;
+			break;
+		case TNC_CONNECTION_STATE_ACCESS_ISOLATED:
+			imc_state = ANDROID_IMC_STATE_ISOLATE;
+			break;
+		case TNC_CONNECTION_STATE_ACCESS_NONE:
+			imc_state = ANDROID_IMC_STATE_BLOCK;
+			break;
+	}
+
+	charonservice->update_imc_state(charonservice, imc_state);
+}
+
+/**
+ * see section 3.8.2 of TCG TNC IF-IMC Specification 1.3
+ */
+static TNC_Result tnc_imc_notifyconnectionchange(TNC_IMCID imc_id,
+												 TNC_ConnectionID connection_id,
+												 TNC_ConnectionState new_state)
+{
+	imc_state_t *state;
+
+	if (!imc_android)
+	{
+		DBG1(DBG_IMC, "IMC \"%s\" has not been initialized", imc_name);
+		return TNC_RESULT_NOT_INITIALIZED;
+	}
+	switch (new_state)
+	{
+		case TNC_CONNECTION_STATE_CREATE:
+			state = imc_android_state_create(connection_id);
+			return imc_android->create_state(imc_android, state);
+		case TNC_CONNECTION_STATE_HANDSHAKE:
+			if (imc_android->change_state(imc_android, connection_id, new_state,
+										  &state) != TNC_RESULT_SUCCESS)
+			{
+				return TNC_RESULT_FATAL;
+			}
+			state->set_result(state, imc_id,
+							  TNC_IMV_EVALUATION_RESULT_DONT_KNOW);
+			return TNC_RESULT_SUCCESS;
+		case TNC_CONNECTION_STATE_DELETE:
+			return imc_android->delete_state(imc_android, connection_id);
+		case TNC_CONNECTION_STATE_ACCESS_ALLOWED:
+		case TNC_CONNECTION_STATE_ACCESS_ISOLATED:
+		case TNC_CONNECTION_STATE_ACCESS_NONE:
+			update_imc_state(new_state);
+			/* fall-through */
+		default:
+			return imc_android->change_state(imc_android, connection_id,
+											 new_state, NULL);
+	}
+}
+
+/**
+ * Convert the native C strings in the enumerator to a Java String array.
+ * The given enumerator gets destroyed.
+ */
+static jobjectArray string_array_create(JNIEnv *env, enumerator_t *enumerator)
+{
+	linked_list_t *list;
+	jobjectArray jarray;
+	jstring jstring;
+	char *native;
+	jclass cls;
+	int i = 0;
+
+	cls = (*env)->FindClass(env, "java/lang/String");
+	list = linked_list_create_from_enumerator(enumerator);
+	jarray = (*env)->NewObjectArray(env, list->get_count(list), cls, NULL);
+	if (!jarray)
+	{
+		goto failed;
+	}
+	enumerator = list->create_enumerator(list);
+	while (enumerator->enumerate(enumerator, (void**)&native))
+	{
+		jstring = (*env)->NewStringUTF(env, native);
+		if (!jstring)
+		{
+			enumerator->destroy(enumerator);
+			goto failed;
+		}
+		(*env)->SetObjectArrayElement(env, jarray, i++, jstring);
+	}
+	enumerator->destroy(enumerator);
+	list->destroy(list);
+	return jarray;
+
+failed:
+	androidjni_exception_occurred(env);
+	list->destroy(list);
+	return NULL;
+}
+
+/**
+ * Get a measurement for the given attribute type from the Android IMC.
+ * NULL is returned if no measurement is available or an error occurred.
+ *
+ * The optional args is an enumerator over char* (gets destroyed).
+ */
+static pa_tnc_attr_t *get_measurement(pen_type_t attr_type, enumerator_t *args)
+{
+	JNIEnv *env;
+	pa_tnc_attr_t *attr;
+	jmethodID method_id;
+	jbyteArray jmeasurement;
+	jobjectArray jargs = NULL;
+	chunk_t data;
+
+	androidjni_attach_thread(&env);
+	if (args)
+	{
+		jargs = string_array_create(env, args);
+		if (!jargs)
+		{
+			goto failed;
+		}
+		method_id = (*env)->GetMethodID(env, android_imc_cls, "getMeasurement",
+										"(II[Ljava/lang/String;)[B");
+	}
+	else
+	{
+		method_id = (*env)->GetMethodID(env, android_imc_cls, "getMeasurement",
+										"(II)[B");
+	}
+	if (!method_id)
+	{
+		goto failed;
+	}
+	jmeasurement = (*env)->CallObjectMethod(env, android_imc, method_id,
+											attr_type.vendor_id, attr_type.type,
+											jargs);
+	if (!jmeasurement || androidjni_exception_occurred(env))
+	{
+		goto failed;
+	}
+	data = chunk_create((*env)->GetByteArrayElements(env, jmeasurement, NULL),
+						(*env)->GetArrayLength(env, jmeasurement));
+	if (!data.ptr)
+	{
+		goto failed;
+	}
+	attr = imcv_pa_tnc_attributes->construct(imcv_pa_tnc_attributes,
+									attr_type.vendor_id, attr_type.type, data);
+	(*env)->ReleaseByteArrayElements(env, jmeasurement, data.ptr, JNI_ABORT);
+	androidjni_detach_thread();
+	return attr;
+
+failed:
+	androidjni_exception_occurred(env);
+	androidjni_detach_thread();
+	return NULL;
+}
+
+/**
+ * Add the measurement for the requested attribute type with optional
+ * arguments (enumerator over char*, gets destroyed).
+ */
+static void add_measurement(pen_type_t attr_type, imc_msg_t *msg,
+							enumerator_t *args)
+{
+	pa_tnc_attr_t *attr;
+	enum_name_t *pa_attr_names;
+
+	attr = get_measurement(attr_type, args);
+	if (attr)
+	{
+		msg->add_attribute(msg, attr);
+		return;
+	}
+	pa_attr_names = imcv_pa_tnc_attributes->get_names(imcv_pa_tnc_attributes,
+													  attr_type.vendor_id);
+	if (pa_attr_names)
+	{
+		DBG1(DBG_IMC, "no measurement available for PA-TNC attribute type "
+			 "'%N/%N' 0x%06x/0x%08x", pen_names, attr_type.vendor_id,
+			 pa_attr_names, attr_type.type, attr_type.vendor_id, attr_type.type);
+	}
+	else
+	{
+		DBG1(DBG_IMC, "no measurement available for PA-TNC attribute type '%N' "
+			 "0x%06x/0x%08x", pen_names, attr_type.vendor_id,
+			 attr_type.vendor_id, attr_type.type);
+	}
+}
+
+/**
+ * Handle an IETF attribute
+ */
+static void handle_ietf_attribute(pen_type_t attr_type, pa_tnc_attr_t *attr,
+								  imc_msg_t *out_msg)
+{
+	if (attr_type.type == IETF_ATTR_ATTRIBUTE_REQUEST)
+	{
+		ietf_attr_attr_request_t *attr_cast;
+		pen_type_t *entry;
+		enumerator_t *enumerator;
+
+		attr_cast = (ietf_attr_attr_request_t*)attr;
+		enumerator = attr_cast->create_enumerator(attr_cast);
+		while (enumerator->enumerate(enumerator, &entry))
+		{
+			add_measurement(*entry, out_msg, NULL);
+		}
+		enumerator->destroy(enumerator);
+	}
+	else if (attr_type.type == IETF_ATTR_REMEDIATION_INSTRUCTIONS)
+	{
+		ietf_attr_remediation_instr_t *attr_cast;
+		pen_type_t param;
+		chunk_t str;
+		char *instr;
+
+		attr_cast = (ietf_attr_remediation_instr_t*)attr;
+		param = attr_cast->get_parameters_type(attr_cast);
+
+		if (pen_type_is(param, PEN_IETF, IETF_REMEDIATION_PARAMETERS_STRING))
+		{
+			str = attr_cast->get_string(attr_cast, NULL);
+			instr = strndup(str.ptr, str.len);
+			charonservice->add_remediation_instr(charonservice, instr);
+			free (instr);
+		}
+	}
+}
+
+/**
+ * Handle an ITA attribute
+ */
+static void handle_ita_attribute(pen_type_t attr_type, pa_tnc_attr_t *attr,
+								 imc_msg_t *out_msg)
+{
+	if (attr_type.type == ITA_ATTR_GET_SETTINGS)
+	{
+		ita_attr_get_settings_t *attr_cast;
+
+		attr_cast = (ita_attr_get_settings_t*)attr;
+		add_measurement((pen_type_t){ PEN_ITA, ITA_ATTR_SETTINGS },
+						out_msg, attr_cast->create_enumerator(attr_cast));
+	}
+}
+
+/**
+ * Handle a TCG attribute
+ */
+static void handle_tcg_attribute(imc_android_state_t *state,
+								 pen_type_t attr_type, pa_tnc_attr_t *attr,
+								 imc_msg_t *out_msg)
+{
+	pts_t *pts;
+
+	pts = state->get_pts(state);
+	switch (attr_type.type)
+	{
+		case TCG_PTS_REQ_PROTO_CAPS:
+		{
+			tcg_pts_attr_proto_caps_t *attr_cast;
+			pts_proto_caps_flag_t caps;
+
+			attr_cast = (tcg_pts_attr_proto_caps_t*)attr;
+			caps = attr_cast->get_flags(attr_cast) & pts->get_proto_caps(pts);
+			pts->set_proto_caps(pts, caps);
+			attr = tcg_pts_attr_proto_caps_create(caps, FALSE);
+			out_msg->add_attribute(out_msg, attr);
+			break;
+		}
+		case TCG_PTS_MEAS_ALGO:
+		{
+			tcg_pts_attr_meas_algo_t *attr_cast;
+			pts_meas_algorithms_t supported, algo;
+
+			if (!pts_meas_algo_probe(&supported))
+			{
+				attr = pts_hash_alg_error_create(PTS_MEAS_ALGO_NONE);
+				out_msg->add_attribute(out_msg, attr);
+				break;
+			}
+			attr_cast = (tcg_pts_attr_meas_algo_t*)attr;
+			algo = pts_meas_algo_select(supported,
+										attr_cast->get_algorithms(attr_cast));
+			if (algo == PTS_MEAS_ALGO_NONE)
+			{
+				attr = pts_hash_alg_error_create(supported);
+				out_msg->add_attribute(out_msg, attr);
+				break;
+			}
+			pts->set_meas_algorithm(pts, algo);
+			attr = tcg_pts_attr_meas_algo_create(algo, TRUE);
+			out_msg->add_attribute(out_msg, attr);
+			break;
+		}
+		case TCG_PTS_REQ_FILE_MEAS:
+		{
+			tcg_pts_attr_req_file_meas_t *attr_cast;
+			pts_file_meas_t *measurements;
+			pts_error_code_t pts_error;
+			uint32_t delim;
+			uint16_t req_id;
+			bool is_dir;
+			char *path;
+
+			attr_cast = (tcg_pts_attr_req_file_meas_t*)attr;
+			path = attr_cast->get_pathname(attr_cast);
+			if (!pts->is_path_valid(pts, path, &pts_error))
+			{	/* silently ignore internal errors */
+				break;
+			}
+			else if (pts_error)
+			{
+				attr = ietf_attr_pa_tnc_error_create(pen_type_create(PEN_TCG,
+											pts_error), attr->get_value(attr));
+				out_msg->add_attribute(out_msg, attr);
+				break;
+			}
+			delim = attr_cast->get_delimiter(attr_cast);
+			if (delim != SOLIDUS_UTF && delim != REVERSE_SOLIDUS_UTF)
+			{
+				attr = ietf_attr_pa_tnc_error_create(pen_type_create(PEN_TCG,
+							TCG_PTS_INVALID_DELIMITER), attr->get_value(attr));
+				out_msg->add_attribute(out_msg, attr);
+				break;
+			}
+			req_id = attr_cast->get_request_id(attr_cast);
+			is_dir = attr_cast->get_directory_flag(attr_cast);
+
+			DBG1(DBG_IMC, "measurement request %d for %s '%s'", req_id,
+				 is_dir ? "directory" : "file", path);
+			measurements = pts_file_meas_create_from_path(req_id, path, is_dir,
+											TRUE, pts->get_meas_algorithm(pts));
+			if (!measurements)
+			{
+				attr = ietf_attr_pa_tnc_error_create(pen_type_create(PEN_TCG,
+								TCG_PTS_FILE_NOT_FOUND), attr->get_value(attr));
+				out_msg->add_attribute(out_msg, attr);
+				break;
+			}
+			attr = tcg_pts_attr_file_meas_create(measurements);
+			attr->set_noskip_flag(attr, TRUE);
+			out_msg->add_attribute(out_msg, attr);
+			break;
+		}
+		default:
+			DBG1(DBG_IMC, "received unsupported TCG attribute '%N'",
+				 tcg_attr_names, attr_type.type);
+			break;
+	}
+}
+
+/**
+ * see section 3.8.3 of TCG TNC IF-IMC Specification 1.3
+ */
+static TNC_Result tnc_imc_beginhandshake(TNC_IMCID imc_id,
+										 TNC_ConnectionID connection_id)
+{
+	imc_state_t *state;
+	imc_msg_t *out_msg;
+	TNC_Result result = TNC_RESULT_SUCCESS;
+
+	if (!imc_android)
+	{
+		DBG1(DBG_IMC, "IMC \"%s\" has not been initialized", imc_name);
+		return TNC_RESULT_NOT_INITIALIZED;
+	}
+	if (!imc_android->get_state(imc_android, connection_id, &state))
+	{
+		return TNC_RESULT_FATAL;
+	}
+	if (lib->settings->get_bool(lib->settings,
+								"android.imc.send_os_info", TRUE))
+	{
+		out_msg = imc_msg_create(imc_android, state, connection_id, imc_id,
+								 TNC_IMVID_ANY, msg_types[0]);
+		add_measurement((pen_type_t){ PEN_IETF, IETF_ATTR_PRODUCT_INFORMATION },
+						out_msg, NULL);
+		add_measurement((pen_type_t){ PEN_IETF, IETF_ATTR_STRING_VERSION },
+						out_msg, NULL);
+		add_measurement((pen_type_t){ PEN_ITA, ITA_ATTR_DEVICE_ID },
+						out_msg, NULL);
+		/* send PA-TNC message with the excl flag not set */
+		result = out_msg->send(out_msg, FALSE);
+		out_msg->destroy(out_msg);
+	}
+
+	return result;
+}
+
+static TNC_Result receive_message(imc_android_state_t *state, imc_msg_t *in_msg)
+{
+	imc_msg_t *out_msg;
+	enumerator_t *enumerator;
+	pa_tnc_attr_t *attr;
+	pen_type_t attr_type;
+	TNC_Result result;
+	bool fatal_error = FALSE;
+
+	out_msg = imc_msg_create_as_reply(in_msg);
+
+	/* parse received PA-TNC message and handle local and remote errors */
+	result = in_msg->receive(in_msg, out_msg, &fatal_error);
+	if (result != TNC_RESULT_SUCCESS)
+	{
+		out_msg->destroy(out_msg);
+		return result;
+	}
+
+	/* analyze PA-TNC attributes */
+	enumerator = in_msg->create_attribute_enumerator(in_msg);
+	while (enumerator->enumerate(enumerator, &attr))
+	{
+		attr_type = attr->get_type(attr);
+
+		switch (attr_type.vendor_id)
+		{
+			case PEN_IETF:
+				handle_ietf_attribute(attr_type, attr, out_msg);
+				continue;
+			case PEN_ITA:
+				handle_ita_attribute(attr_type, attr, out_msg);
+				continue;
+			case PEN_TCG:
+				handle_tcg_attribute(state, attr_type, attr, out_msg);
+				continue;
+			default:
+				continue;
+		}
+	}
+	enumerator->destroy(enumerator);
+
+	if (fatal_error)
+	{
+		result = TNC_RESULT_FATAL;
+	}
+	else
+	{
+		result = out_msg->send(out_msg, TRUE);
+	}
+	out_msg->destroy(out_msg);
+
+	return result;
+}
+
+/**
+ * see section 3.8.4 of TCG TNC IF-IMC Specification 1.3
+
+ */
+static TNC_Result tnc_imc_receivemessage(TNC_IMCID imc_id,
+										 TNC_ConnectionID connection_id,
+										 TNC_BufferReference msg,
+										 TNC_UInt32 msg_len,
+										 TNC_MessageType msg_type)
+{
+	imc_state_t *state;
+	imc_msg_t *in_msg;
+	TNC_Result result;
+
+	if (!imc_android)
+	{
+		DBG1(DBG_IMC, "IMC \"%s\" has not been initialized", imc_name);
+		return TNC_RESULT_NOT_INITIALIZED;
+	}
+	if (!imc_android->get_state(imc_android, connection_id, &state))
+	{
+		return TNC_RESULT_FATAL;
+	}
+	in_msg = imc_msg_create_from_data(imc_android, state, connection_id,
+									  msg_type, chunk_create(msg, msg_len));
+	result = receive_message((imc_android_state_t*)state, in_msg);
+	in_msg->destroy(in_msg);
+
+	return result;
+}
+
+/**
+ * see section 3.8.6 of TCG TNC IF-IMV Specification 1.3
+ */
+static TNC_Result tnc_imc_receivemessagelong(TNC_IMCID imc_id,
+											 TNC_ConnectionID connection_id,
+											 TNC_UInt32 msg_flags,
+											 TNC_BufferReference msg,
+											 TNC_UInt32 msg_len,
+											 TNC_VendorID msg_vid,
+											 TNC_MessageSubtype msg_subtype,
+											 TNC_UInt32 src_imv_id,
+											 TNC_UInt32 dst_imc_id)
+{
+	imc_state_t *state;
+	imc_msg_t *in_msg;
+	TNC_Result result;
+
+	if (!imc_android)
+	{
+		DBG1(DBG_IMC, "IMC \"%s\" has not been initialized", imc_name);
+		return TNC_RESULT_NOT_INITIALIZED;
+	}
+	if (!imc_android->get_state(imc_android, connection_id, &state))
+	{
+		return TNC_RESULT_FATAL;
+	}
+	in_msg = imc_msg_create_from_long_data(imc_android, state, connection_id,
+								src_imv_id, dst_imc_id,msg_vid, msg_subtype,
+								chunk_create(msg, msg_len));
+	result = receive_message((imc_android_state_t*)state, in_msg);
+	in_msg->destroy(in_msg);
+
+	return result;
+}
+
+/**
+ * see section 3.8.7 of TCG TNC IF-IMC Specification 1.3
+ */
+static TNC_Result tnc_imc_batchending(TNC_IMCID imc_id,
+									  TNC_ConnectionID connection_id)
+{
+	if (!imc_android)
+	{
+		DBG1(DBG_IMC, "IMC \"%s\" has not been initialized", imc_name);
+		return TNC_RESULT_NOT_INITIALIZED;
+	}
+	return TNC_RESULT_SUCCESS;
+}
+
+/**
+ * see section 3.8.8 of TCG TNC IF-IMC Specification 1.3
+ */
+static TNC_Result tnc_imc_terminate(TNC_IMCID imc_id)
+{
+	if (!imc_android)
+	{
+		DBG1(DBG_IMC, "IMC \"%s\" has not been initialized", imc_name);
+		return TNC_RESULT_NOT_INITIALIZED;
+	}
+	imc_android->destroy(imc_android);
+	imc_android = NULL;
+	return TNC_RESULT_SUCCESS;
+}
+
+/**
+ * see section 4.2.8.1 of TCG TNC IF-IMC Specification 1.3
+ */
+static TNC_Result tnc_imc_providebindfunction(TNC_IMCID imc_id,
+											  TNC_TNCC_BindFunctionPointer bind_function)
+{
+	if (!imc_android)
+	{
+		DBG1(DBG_IMC, "IMC \"%s\" has not been initialized", imc_name);
+		return TNC_RESULT_NOT_INITIALIZED;
+	}
+	return imc_android->bind_functions(imc_android, bind_function);
+}
+
+/*
+ * Described in header
+ */
+bool imc_android_register(plugin_t *plugin, plugin_feature_t *feature,
+						  bool reg, void *data)
+{
+	JNIEnv *env;
+	jmethodID method_id;
+	jobject obj, context = (jobject)data;
+	jclass cls;
+	bool success = TRUE;
+
+	androidjni_attach_thread(&env);
+	if (reg)
+	{
+		cls = (*env)->FindClass(env, JNI_PACKAGE_STRING "/imc/AndroidImc");
+		if (!cls)
+		{
+			goto failed;
+		}
+		android_imc_cls = (*env)->NewGlobalRef(env, cls);
+		method_id = (*env)->GetMethodID(env, cls, "<init>",
+										"(Landroid/content/Context;)V");
+		if (!method_id)
+		{
+			goto failed;
+		}
+		obj = (*env)->NewObject(env, cls, method_id, context);
+		if (!obj)
+		{
+			goto failed;
+		}
+		android_imc = (*env)->NewGlobalRef(env, obj);
+		androidjni_detach_thread();
+
+		if (tnc->imcs->load_from_functions(tnc->imcs, "Android",
+							tnc_imc_initialize, tnc_imc_notifyconnectionchange,
+							tnc_imc_beginhandshake, tnc_imc_receivemessage,
+							tnc_imc_receivemessagelong, tnc_imc_batchending,
+							tnc_imc_terminate, tnc_imc_providebindfunction))
+		{
+			return TRUE;
+		}
+failed:
+		DBG1(DBG_IMC, "initialization of Android IMC failed");
+		androidjni_exception_occurred(env);
+		success = FALSE;
+	}
+
+	if (android_imc)
+	{
+		(*env)->DeleteGlobalRef(env, android_imc);
+		android_imc = NULL;
+	}
+	if (android_imc_cls)
+	{
+		(*env)->DeleteGlobalRef(env, android_imc_cls);
+		android_imc_cls = NULL;
+	}
+	androidjni_detach_thread();
+	return success;
+}

+ 30 - 0
app/src/main/jni/libandroidbridge/byod/imc_android.h

@@ -0,0 +1,30 @@
+/*
+ * Copyright (C) 2013 Tobias Brunner
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+/**
+ * @defgroup android_imc android_imc
+ * @{ @ingroup android_byod
+ */
+
+#ifndef ANDROID_IMC_H_
+#define ANDROID_IMC_H_
+
+/**
+ * Callback for the Android IMC plugin
+ */
+bool imc_android_register(plugin_t *plugin, plugin_feature_t *feature,
+						  bool reg, void *data);
+
+#endif /** ANDROID_IMC_H_ @}*/

+ 191 - 0
app/src/main/jni/libandroidbridge/byod/imc_android_state.c

@@ -0,0 +1,191 @@
+/*
+ * Copyright (C) 2012 Tobias Brunner
+ * Copyright (C) 2012 Andreas Steffen
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+#include "imc_android_state.h"
+
+#include <tncif_names.h>
+
+#include <utils/debug.h>
+
+typedef struct private_imc_android_state_t private_imc_android_state_t;
+
+/**
+ * Private data of an imc_state_t object.
+ */
+struct private_imc_android_state_t {
+
+	/**
+	 * Public interface
+	 */
+	imc_android_state_t public;
+
+	/**
+	 * TNCCS connection ID
+	 */
+	TNC_ConnectionID connection_id;
+
+	/**
+	 * TNCCS connection state
+	 */
+	TNC_ConnectionState state;
+
+	/**
+	 * Assessment/Evaluation Result
+	 */
+	TNC_IMV_Evaluation_Result result;
+
+	/**
+	 * Does the TNCCS connection support long message types?
+	 */
+	bool has_long;
+
+	/**
+	 * Does the TNCCS connection support exclusive delivery?
+	 */
+	bool has_excl;
+
+	/**
+	 * Maximum PA-TNC message size for this TNCCS connection
+	 */
+	uint32_t max_msg_len;
+
+	/**
+	 * PA-TNC attribute segmentation contracts associated with TNCCS connection
+	 */
+	seg_contract_manager_t *contracts;
+
+	/**
+	 * TCG Platform Trust Service (PTS)
+	 */
+	pts_t *pts;
+};
+
+METHOD(imc_state_t, get_connection_id, TNC_ConnectionID,
+	private_imc_android_state_t *this)
+{
+	return this->connection_id;
+}
+
+METHOD(imc_state_t, has_long, bool,
+	private_imc_android_state_t *this)
+{
+	return this->has_long;
+}
+
+METHOD(imc_state_t, has_excl, bool,
+	private_imc_android_state_t *this)
+{
+	return this->has_excl;
+}
+
+METHOD(imc_state_t, set_flags, void,
+	private_imc_android_state_t *this, bool has_long, bool has_excl)
+{
+	this->has_long = has_long;
+	this->has_excl = has_excl;
+}
+
+METHOD(imc_state_t, set_max_msg_len, void,
+	private_imc_android_state_t *this, uint32_t max_msg_len)
+{
+	this->max_msg_len = max_msg_len;
+}
+
+METHOD(imc_state_t, get_max_msg_len, uint32_t,
+	private_imc_android_state_t *this)
+{
+	return this->max_msg_len;
+}
+
+METHOD(imc_state_t, get_contracts, seg_contract_manager_t*,
+	private_imc_android_state_t *this)
+{
+	return this->contracts;
+}
+
+METHOD(imc_state_t, change_state, TNC_ConnectionState,
+	private_imc_android_state_t *this, TNC_ConnectionState new_state)
+{
+	TNC_ConnectionState old;
+
+	old = this->state;
+	this->state = new_state;
+	return old;
+}
+
+METHOD(imc_state_t, set_result, void,
+	private_imc_android_state_t *this, TNC_IMCID id, TNC_IMV_Evaluation_Result result)
+{
+	this->result = result;
+}
+
+METHOD(imc_state_t, get_result, bool,
+	private_imc_android_state_t *this, TNC_IMCID id, TNC_IMV_Evaluation_Result *result)
+{
+	if (result)
+	{
+		*result = this->result;
+	}
+	return this->result != TNC_IMV_EVALUATION_RESULT_DONT_KNOW;
+}
+
+METHOD(imc_state_t, destroy, void,
+	private_imc_android_state_t *this)
+{
+	this->contracts->destroy(this->contracts);
+	this->pts->destroy(this->pts);
+	free(this);
+}
+
+METHOD(imc_android_state_t, get_pts, pts_t*,
+	private_imc_android_state_t *this)
+{
+	return this->pts;
+}
+
+/**
+ * Described in header.
+ */
+imc_state_t *imc_android_state_create(TNC_ConnectionID connection_id)
+{
+	private_imc_android_state_t *this;
+
+	INIT(this,
+		.public = {
+			.interface = {
+				.get_connection_id = _get_connection_id,
+				.has_long = _has_long,
+				.has_excl = _has_excl,
+				.set_flags = _set_flags,
+				.set_max_msg_len = _set_max_msg_len,
+				.get_max_msg_len = _get_max_msg_len,
+				.get_contracts = _get_contracts,
+				.change_state = _change_state,
+				.set_result = _set_result,
+				.get_result = _get_result,
+				.destroy = _destroy,
+			},
+			.get_pts = _get_pts,
+		},
+		.state = TNC_CONNECTION_STATE_CREATE,
+		.result = TNC_IMV_EVALUATION_RESULT_DONT_KNOW,
+		.connection_id = connection_id,
+		.contracts = seg_contract_manager_create(),
+		.pts = pts_create(TRUE),
+	);
+
+	return &this->public.interface;
+}

+ 52 - 0
app/src/main/jni/libandroidbridge/byod/imc_android_state.h

@@ -0,0 +1,52 @@
+/*
+ * Copyright (C) 2012 Tobias Brunner
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+/**
+ * @defgroup imc_android_state imc_android_state
+ * @{ @ingroup android_byod
+ */
+
+#ifndef IMC_ANDROID_STATE_H_
+#define IMC_ANDROID_STATE_H_
+
+#include <imc/imc_state.h>
+#include <pts/pts.h>
+
+typedef struct imc_android_state_t imc_android_state_t;
+
+/**
+ * Internal state of an imc_android_t connection instance
+ */
+struct imc_android_state_t {
+
+	/**
+	 * imc_state_t interface
+	 */
+	imc_state_t interface;
+
+	/**
+	 * Get TCG Platform Trust Service (PTS) object
+	 */
+	pts_t *(*get_pts)(imc_android_state_t *this);
+};
+
+/**
+ * Create an imc_android_state_t instance
+ *
+ * @param id		connection ID
+ */
+imc_state_t* imc_android_state_create(TNC_ConnectionID id);
+
+#endif /** IMC_ANDROID_STATE_H_ @}*/

+ 791 - 0
app/src/main/jni/libandroidbridge/charonservice.c

@@ -0,0 +1,791 @@
+/*
+ * Copyright (C) 2012-2019 Tobias Brunner
+ * Copyright (C) 2012 Giuliano Grassi
+ * Copyright (C) 2012 Ralf Sager
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+#include <signal.h>
+#include <string.h>
+#include <sys/utsname.h>
+#include <android/log.h>
+#include <errno.h>
+
+#include "charonservice.h"
+#include "android_jni.h"
+#include "backend/android_attr.h"
+#include "backend/android_creds.h"
+#include "backend/android_fetcher.h"
+#include "backend/android_private_key.h"
+#include "backend/android_service.h"
+#include "kernel/android_ipsec.h"
+#include "kernel/android_net.h"
+
+#ifdef USE_BYOD
+#include "byod/imc_android.h"
+#endif
+
+#include <daemon.h>
+#include <ipsec.h>
+#include <library.h>
+#include <threading/thread.h>
+
+#define ANDROID_DEBUG_LEVEL 1
+#define ANDROID_RETRASNMIT_TRIES 3
+#define ANDROID_RETRANSMIT_TIMEOUT 2.0
+#define ANDROID_RETRANSMIT_BASE 1.4
+#define ANDROID_KEEPALIVE_INTERVAL 45
+
+typedef struct private_charonservice_t private_charonservice_t;
+
+/**
+ * private data of charonservice
+ */
+struct private_charonservice_t {
+
+	/**
+	 * public interface
+	 */
+	charonservice_t public;
+
+	/**
+	 * android_attr instance
+	 */
+	android_attr_t *attr;
+
+	/**
+	 * android_creds instance
+	 */
+	android_creds_t *creds;
+
+	/**
+	 * android_service instance
+	 */
+	android_service_t *service;
+
+	/**
+	 * VpnService builder (accessed via JNI)
+	 */
+	vpnservice_builder_t *builder;
+
+	/**
+	 * NetworkManager instance (accessed via JNI)
+	 */
+	network_manager_t *network_manager;
+
+	/**
+	 * CharonVpnService reference
+	 */
+	jobject vpn_service;
+
+	/**
+	 * Sockets that were bypassed and we keep track for
+	 */
+	linked_list_t *sockets;
+};
+
+/**
+ * Single instance of charonservice_t.
+ */
+charonservice_t *charonservice;
+
+/**
+ * hook in library for debugging messages
+ */
+extern void (*dbg)(debug_t group, level_t level, char *fmt, ...);
+
+/**
+ * Logging hook for library logs, using android specific logging
+ */
+static void dbg_android(debug_t group, level_t level, char *fmt, ...)
+{
+	va_list args;
+
+	if (level <= ANDROID_DEBUG_LEVEL)
+	{
+		char sgroup[16], buffer[8192];
+		char *current = buffer, *next;
+
+		snprintf(sgroup, sizeof(sgroup), "%N", debug_names, group);
+		va_start(args, fmt);
+		vsnprintf(buffer, sizeof(buffer), fmt, args);
+		va_end(args);
+		while (current)
+		{	/* log each line separately */
+			next = strchr(current, '\n');
+			if (next)
+			{
+				*(next++) = '\0';
+			}
+			__android_log_print(ANDROID_LOG_INFO, "charon", "00[%s] %s\n",
+								sgroup, current);
+			current = next;
+		}
+	}
+}
+
+METHOD(charonservice_t, update_status, bool,
+	private_charonservice_t *this, android_vpn_state_t code)
+{
+	JNIEnv *env;
+	jmethodID method_id;
+	bool success = FALSE;
+
+	androidjni_attach_thread(&env);
+
+	method_id = (*env)->GetMethodID(env, android_charonvpnservice_class,
+									"updateStatus", "(I)V");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	(*env)->CallVoidMethod(env, this->vpn_service, method_id, (jint)code);
+	success = !androidjni_exception_occurred(env);
+
+failed:
+	androidjni_exception_occurred(env);
+	androidjni_detach_thread();
+	return success;
+}
+
+METHOD(charonservice_t, update_imc_state, bool,
+	private_charonservice_t *this, android_imc_state_t state)
+{
+	JNIEnv *env;
+	jmethodID method_id;
+	bool success = FALSE;
+
+	androidjni_attach_thread(&env);
+
+	method_id = (*env)->GetMethodID(env, android_charonvpnservice_class,
+									"updateImcState", "(I)V");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	(*env)->CallVoidMethod(env, this->vpn_service, method_id, (jint)state);
+	success = !androidjni_exception_occurred(env);
+
+failed:
+	androidjni_exception_occurred(env);
+	androidjni_detach_thread();
+	return success;
+}
+
+METHOD(charonservice_t, add_remediation_instr, bool,
+	private_charonservice_t *this, char *instr)
+{
+	JNIEnv *env;
+	jmethodID method_id;
+	jstring jinstr;
+	bool success = FALSE;
+
+	androidjni_attach_thread(&env);
+
+	method_id = (*env)->GetMethodID(env, android_charonvpnservice_class,
+									"addRemediationInstruction",
+									"(Ljava/lang/String;)V");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	jinstr = (*env)->NewStringUTF(env, instr);
+	if (!jinstr)
+	{
+		goto failed;
+	}
+	(*env)->CallVoidMethod(env, this->vpn_service, method_id, jinstr);
+	success = !androidjni_exception_occurred(env);
+
+failed:
+	androidjni_exception_occurred(env);
+	androidjni_detach_thread();
+	return success;
+}
+
+/**
+ * Bypass a single socket
+ */
+static bool bypass_single_socket(private_charonservice_t *this, int fd)
+{
+	JNIEnv *env;
+	jmethodID method_id;
+
+	androidjni_attach_thread(&env);
+
+	method_id = (*env)->GetMethodID(env, android_charonvpnservice_class,
+									"protect", "(I)Z");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	if (!(*env)->CallBooleanMethod(env, this->vpn_service, method_id, fd))
+	{
+		DBG2(DBG_KNL, "VpnService.protect() failed");
+		goto failed;
+	}
+	androidjni_detach_thread();
+	return TRUE;
+
+failed:
+	androidjni_exception_occurred(env);
+	androidjni_detach_thread();
+	return FALSE;
+}
+
+CALLBACK(bypass_single_socket_cb, void,
+	intptr_t fd, va_list args)
+{
+	private_charonservice_t *this;
+
+	VA_ARGS_VGET(args, this);
+	bypass_single_socket(this, fd);
+}
+
+METHOD(charonservice_t, bypass_socket, bool,
+	private_charonservice_t *this, int fd, int family)
+{
+	if (fd >= 0)
+	{
+		this->sockets->insert_last(this->sockets, (void*)(intptr_t)fd);
+		return bypass_single_socket(this, fd);
+	}
+	this->sockets->invoke_function(this->sockets, bypass_single_socket_cb, this);
+	return TRUE;
+}
+
+/**
+ * Converts the given Java array of byte arrays (byte[][]) to a linked list
+ * of chunk_t objects.
+ */
+static linked_list_t *convert_array_of_byte_arrays(JNIEnv *env,
+												   jobjectArray jarray)
+{
+	linked_list_t *list;
+	jsize i;
+
+	list = linked_list_create();
+	for (i = 0; i < (*env)->GetArrayLength(env, jarray); ++i)
+	{
+		chunk_t *chunk;
+		jbyteArray jbytearray;
+
+		chunk = malloc_thing(chunk_t);
+		list->insert_last(list, chunk);
+
+		jbytearray = (*env)->GetObjectArrayElement(env, jarray, i);
+		*chunk = chunk_alloc((*env)->GetArrayLength(env, jbytearray));
+		(*env)->GetByteArrayRegion(env, jbytearray, 0, chunk->len, chunk->ptr);
+		(*env)->DeleteLocalRef(env, jbytearray);
+	}
+	return list;
+}
+
+METHOD(charonservice_t, get_trusted_certificates, linked_list_t*,
+	private_charonservice_t *this)
+{
+	JNIEnv *env;
+	jmethodID method_id;
+	jobjectArray jcerts;
+	linked_list_t *list;
+
+	androidjni_attach_thread(&env);
+
+	method_id = (*env)->GetMethodID(env,
+						android_charonvpnservice_class,
+						"getTrustedCertificates", "()[[B");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	jcerts = (*env)->CallObjectMethod(env, this->vpn_service, method_id);
+	if (!jcerts || androidjni_exception_occurred(env))
+	{
+		goto failed;
+	}
+	list = convert_array_of_byte_arrays(env, jcerts);
+	androidjni_detach_thread();
+	return list;
+
+failed:
+	androidjni_exception_occurred(env);
+	androidjni_detach_thread();
+	return NULL;
+}
+
+METHOD(charonservice_t, get_user_certificate, linked_list_t*,
+	private_charonservice_t *this)
+{
+	JNIEnv *env;
+	jmethodID method_id;
+	jobjectArray jencodings;
+	linked_list_t *list;
+
+	androidjni_attach_thread(&env);
+
+	method_id = (*env)->GetMethodID(env,
+						android_charonvpnservice_class,
+						"getUserCertificate", "()[[B");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	jencodings = (*env)->CallObjectMethod(env, this->vpn_service, method_id);
+	if (!jencodings || androidjni_exception_occurred(env))
+	{
+		goto failed;
+	}
+	list = convert_array_of_byte_arrays(env, jencodings);
+	androidjni_detach_thread();
+	return list;
+
+failed:
+	androidjni_exception_occurred(env);
+	androidjni_detach_thread();
+	return NULL;
+}
+
+METHOD(charonservice_t, get_user_key, private_key_t*,
+	private_charonservice_t *this, public_key_t *pubkey)
+{
+	JNIEnv *env;
+	jmethodID method_id;
+	private_key_t *key;
+	jobject jkey;
+
+	androidjni_attach_thread(&env);
+
+	method_id = (*env)->GetMethodID(env,
+						android_charonvpnservice_class,
+						"getUserKey", "()Ljava/security/PrivateKey;");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	jkey = (*env)->CallObjectMethod(env, this->vpn_service, method_id);
+	if (!jkey || androidjni_exception_occurred(env))
+	{
+		goto failed;
+	}
+	key = android_private_key_create(jkey, pubkey);
+	androidjni_detach_thread();
+	return key;
+
+failed:
+	DESTROY_IF(pubkey);
+	androidjni_exception_occurred(env);
+	androidjni_detach_thread();
+	return NULL;
+}
+
+METHOD(charonservice_t, get_vpnservice_builder, vpnservice_builder_t*,
+	private_charonservice_t *this)
+{
+	return this->builder;
+}
+
+METHOD(charonservice_t, get_network_manager, network_manager_t*,
+	private_charonservice_t *this)
+{
+	return this->network_manager;
+}
+
+/**
+ * Initiate a new connection
+ *
+ * @param settings			configuration settings (gets owned)
+ */
+static void initiate(settings_t *settings)
+{
+	private_charonservice_t *this = (private_charonservice_t*)charonservice;
+
+	lib->settings->set_str(lib->settings,
+						"charon.plugins.tnc-imc.preferred_language",
+						settings->get_str(settings, "global.language", "en"));
+	lib->settings->set_bool(lib->settings,
+						"charon.plugins.revocation.enable_crl",
+						settings->get_bool(settings, "global.crl", TRUE));
+	lib->settings->set_bool(lib->settings,
+						"charon.plugins.revocation.enable_ocsp",
+						settings->get_bool(settings, "global.ocsp", TRUE));
+	lib->settings->set_bool(lib->settings,
+						"charon.rsa_pss",
+						settings->get_bool(settings, "global.rsa_pss", FALSE));
+	/* this is actually the size of the complete IKE/IP packet, so if the MTU
+	 * for the TUN devices has to be reduced to pass traffic the IKE packets
+	 * will be a bit smaller than necessary as there is no IPsec overhead like
+	 * for the tunneled traffic (but compensating that seems like overkill) */
+	lib->settings->set_int(lib->settings,
+						"charon.fragment_size",
+						settings->get_int(settings, "global.mtu",
+										  ANDROID_DEFAULT_MTU));
+	/* use configured interval, or an increased default to save battery power */
+	lib->settings->set_int(lib->settings,
+						"charon.keep_alive",
+						settings->get_int(settings, "global.nat_keepalive",
+										  ANDROID_KEEPALIVE_INTERVAL));
+
+	/* reload plugins after changing settings */
+	lib->plugins->reload(lib->plugins, NULL);
+
+	this->creds->clear(this->creds);
+	DESTROY_IF(this->service);
+	this->service = android_service_create(this->creds, settings);
+}
+
+/**
+ * Initialize/deinitialize Android backend
+ */
+static bool charonservice_register(plugin_t *plugin, plugin_feature_t *feature,
+								   bool reg, void *data)
+{
+	private_charonservice_t *this = (private_charonservice_t*)charonservice;
+	if (reg)
+	{
+		lib->credmgr->add_set(lib->credmgr, &this->creds->set);
+		charon->attributes->add_handler(charon->attributes,
+										&this->attr->handler);
+	}
+	else
+	{
+		lib->credmgr->remove_set(lib->credmgr, &this->creds->set);
+		charon->attributes->remove_handler(charon->attributes,
+										   &this->attr->handler);
+		if (this->service)
+		{
+			this->service->destroy(this->service);
+			this->service = NULL;
+		}
+	}
+	return TRUE;
+}
+
+/**
+ * Set strongswan.conf options
+ */
+static void set_options(char *logfile)
+{
+	lib->settings->set_int(lib->settings,
+					"charon.plugins.android_log.loglevel", ANDROID_DEBUG_LEVEL);
+	/* setup file logger */
+	lib->settings->set_str(lib->settings,
+					"charon.filelog.android.path", logfile);
+	lib->settings->set_str(lib->settings,
+					"charon.filelog.android.time_format", "%b %e %T");
+	lib->settings->set_bool(lib->settings,
+					"charon.filelog.android.append", TRUE);
+	lib->settings->set_bool(lib->settings,
+					"charon.filelog.android.flush_line", TRUE);
+	lib->settings->set_int(lib->settings,
+					"charon.filelog.android.default", ANDROID_DEBUG_LEVEL);
+
+	lib->settings->set_int(lib->settings,
+					"charon.retransmit_tries", ANDROID_RETRASNMIT_TRIES);
+	lib->settings->set_double(lib->settings,
+					"charon.retransmit_timeout", ANDROID_RETRANSMIT_TIMEOUT);
+	lib->settings->set_double(lib->settings,
+					"charon.retransmit_base", ANDROID_RETRANSMIT_BASE);
+	lib->settings->set_bool(lib->settings,
+					"charon.initiator_only", TRUE);
+	lib->settings->set_bool(lib->settings,
+					"charon.close_ike_on_child_failure", TRUE);
+	/* setting the source address breaks the VpnService.protect() function which
+	 * uses SO_BINDTODEVICE internally.  the addresses provided to the kernel as
+	 * auxiliary data have precedence over this option causing a routing loop if
+	 * the gateway is contained in the VPN routes.  alternatively, providing an
+	 * explicit device (in addition or instead of the source address) in the
+	 * auxiliary data would also work, but we currently don't have that
+	 * information */
+	lib->settings->set_bool(lib->settings,
+					"charon.plugins.socket-default.set_source", FALSE);
+	/* the Linux kernel does currently not support UDP encaspulation for IPv6
+	 * so lets disable IPv6 for now to avoid issues with dual-stack gateways */
+	lib->settings->set_bool(lib->settings,
+					"charon.plugins.socket-default.use_ipv6", FALSE);
+
+#ifdef USE_BYOD
+	lib->settings->set_str(lib->settings,
+					"charon.plugins.eap-tnc.protocol", "tnccs-2.0");
+	lib->settings->set_int(lib->settings,
+					"charon.plugins.eap-ttls.max_message_count", 0);
+	lib->settings->set_bool(lib->settings,
+					"android.imc.send_os_info", TRUE);
+	lib->settings->set_str(lib->settings,
+					"libtnccs.tnc_config", "");
+#endif
+}
+
+/**
+ * Initialize the charonservice object
+ */
+static void charonservice_init(JNIEnv *env, jobject service, jobject builder,
+							   char *appdir, jboolean byod)
+{
+	private_charonservice_t *this;
+	static plugin_feature_t features[] = {
+		PLUGIN_CALLBACK(kernel_ipsec_register, kernel_android_ipsec_create),
+			PLUGIN_PROVIDE(CUSTOM, "kernel-ipsec"),
+		PLUGIN_CALLBACK(kernel_net_register, kernel_android_net_create),
+			PLUGIN_PROVIDE(CUSTOM, "kernel-net"),
+		PLUGIN_CALLBACK(charonservice_register, NULL),
+			PLUGIN_PROVIDE(CUSTOM, "android-backend"),
+				PLUGIN_DEPENDS(CUSTOM, "libcharon"),
+				PLUGIN_DEPENDS(CERT_DECODE, CERT_X509_CRL),
+		PLUGIN_REGISTER(FETCHER, android_fetcher_create),
+			PLUGIN_PROVIDE(FETCHER, "http://"),
+			PLUGIN_PROVIDE(FETCHER, "https://"),
+	};
+
+	INIT(this,
+		.public = {
+			.update_status = _update_status,
+			.update_imc_state = _update_imc_state,
+			.add_remediation_instr = _add_remediation_instr,
+			.bypass_socket = _bypass_socket,
+			.get_trusted_certificates = _get_trusted_certificates,
+			.get_user_certificate = _get_user_certificate,
+			.get_user_key = _get_user_key,
+			.get_vpnservice_builder = _get_vpnservice_builder,
+			.get_network_manager = _get_network_manager,
+		},
+		.attr = android_attr_create(),
+		.creds = android_creds_create(appdir),
+		.builder = vpnservice_builder_create(builder),
+		.network_manager = network_manager_create(service),
+		.sockets = linked_list_create(),
+		.vpn_service = (*env)->NewGlobalRef(env, service),
+	);
+	charonservice = &this->public;
+
+	lib->plugins->add_static_features(lib->plugins, "androidbridge", features,
+									  countof(features), TRUE, NULL, NULL);
+
+#ifdef USE_BYOD
+	if (byod)
+	{
+		plugin_feature_t byod_features[] = {
+			PLUGIN_CALLBACK(imc_android_register, this->vpn_service),
+				PLUGIN_PROVIDE(CUSTOM, "android-imc"),
+					PLUGIN_DEPENDS(CUSTOM, "android-backend"),
+					PLUGIN_DEPENDS(CUSTOM, "imc-manager"),
+		};
+
+		lib->plugins->add_static_features(lib->plugins, "android-byod",
+					byod_features, countof(byod_features), TRUE, NULL, NULL);
+	}
+#endif
+}
+
+/**
+ * Deinitialize the charonservice object
+ */
+static void charonservice_deinit(JNIEnv *env)
+{
+	private_charonservice_t *this = (private_charonservice_t*)charonservice;
+
+	this->network_manager->destroy(this->network_manager);
+	this->sockets->destroy(this->sockets);
+	this->builder->destroy(this->builder);
+	this->creds->destroy(this->creds);
+	this->attr->destroy(this->attr);
+	(*env)->DeleteGlobalRef(env, this->vpn_service);
+	free(this);
+	charonservice = NULL;
+}
+
+/**
+ * Handle SIGSEGV/SIGILL signals raised by threads
+ */
+static void segv_handler(int signal)
+{
+	dbg_android(DBG_DMN, 1, "thread %u received %d", thread_current_id(),
+				signal);
+	exit(1);
+}
+
+/**
+ * Initialize charon and the libraries via JNI
+ */
+JNI_METHOD(CharonVpnService, initializeCharon, jboolean,
+	jobject builder, jstring jlogfile, jstring jappdir, jboolean byod)
+{
+	struct sigaction action;
+	struct utsname utsname;
+	char *logfile, *appdir, *plugins;
+
+	/* logging for library during initialization, as we have no bus yet */
+	dbg = dbg_android;
+
+	/* initialize library */
+	if (!library_init(NULL, "charon"))
+	{
+		library_deinit();
+		return FALSE;
+	}
+
+	/* set options before initializing other libraries that might read them */
+	logfile = androidjni_convert_jstring(env, jlogfile);
+
+	set_options(logfile);
+	free(logfile);
+
+	if (!libipsec_init())
+	{
+		libipsec_deinit();
+		library_deinit();
+		return FALSE;
+	}
+
+	if (!libcharon_init())
+	{
+		libcharon_deinit();
+		libipsec_deinit();
+		library_deinit();
+		return FALSE;
+	}
+
+	charon->load_loggers(charon);
+
+	appdir = androidjni_convert_jstring(env, jappdir);
+	charonservice_init(env, this, builder, appdir, byod);
+	free(appdir);
+
+	if (uname(&utsname) != 0)
+	{
+		memset(&utsname, 0, sizeof(utsname));
+	}
+	DBG1(DBG_DMN, "+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+");
+	DBG1(DBG_DMN, "Starting IKE service (strongSwan "VERSION", %s, %s, "
+		 "%s %s, %s)", android_version_string, android_device_string,
+		  utsname.sysname, utsname.release, utsname.machine);
+
+#ifdef PLUGINS_BYOD
+	if (byod)
+	{
+		plugins = PLUGINS " " PLUGINS_BYOD;
+	}
+	else
+#endif
+	{
+		plugins = PLUGINS;
+	}
+
+	if (!charon->initialize(charon, plugins))
+	{
+		libcharon_deinit();
+		charonservice_deinit(env);
+		libipsec_deinit();
+		library_deinit();
+		return FALSE;
+	}
+	lib->plugins->status(lib->plugins, LEVEL_CTRL);
+
+	/* add handler for SEGV and ILL etc. */
+	action.sa_handler = segv_handler;
+	action.sa_flags = 0;
+	sigemptyset(&action.sa_mask);
+	sigaction(SIGSEGV, &action, NULL);
+	sigaction(SIGILL, &action, NULL);
+	sigaction(SIGBUS, &action, NULL);
+	action.sa_handler = SIG_IGN;
+	sigaction(SIGPIPE, &action, NULL);
+
+	/* start daemon (i.e. the threads in the thread-pool) */
+	charon->start(charon);
+	return TRUE;
+}
+
+/**
+ * Deinitialize charon and all libraries
+ */
+JNI_METHOD(CharonVpnService, deinitializeCharon, void)
+{
+	/* deinitialize charon before we destroy our own objects */
+	libcharon_deinit();
+	charonservice_deinit(env);
+	libipsec_deinit();
+	library_deinit();
+}
+
+/**
+ * Initiate SA
+ */
+JNI_METHOD(CharonVpnService, initiate, void,
+	jstring jconfig)
+{
+	settings_t *settings;
+	char *config;
+
+	config = androidjni_convert_jstring(env, jconfig);
+	settings = settings_create_string(config);
+	free(config);
+
+	initiate(settings);
+}
+
+/**
+ * Utility function to verify proposal strings (static, so `this` is the class)
+ */
+JNI_METHOD_P(org_strongswan_android_utils, Utils, isProposalValid, jboolean,
+	jboolean ike, jstring proposal)
+{
+	proposal_t *prop;
+	char *str;
+	bool valid;
+
+	dbg = dbg_android;
+
+	if (!library_init(NULL, "charon"))
+	{
+		library_deinit();
+		return FALSE;
+	}
+	str = androidjni_convert_jstring(env, proposal);
+	prop = proposal_create_from_string(ike ? PROTO_IKE : PROTO_ESP, str);
+	valid = prop != NULL;
+	DESTROY_IF(prop);
+	free(str);
+	library_deinit();
+	return valid;
+}
+
+/**
+ * Utility function to parse an IP address from a string (static, so `this` is the class)
+ */
+JNI_METHOD_P(org_strongswan_android_utils, Utils, parseInetAddressBytes, jbyteArray,
+	jstring address)
+{
+	jbyteArray bytes;
+	host_t *host;
+	char *str;
+
+	dbg = dbg_android;
+
+	if (!library_init(NULL, "charon"))
+	{
+		library_deinit();
+		return NULL;
+	}
+	str = androidjni_convert_jstring(env, address);
+	host = host_create_from_string(str, 0);
+	if (!host)
+	{
+		free(str);
+		return NULL;
+	}
+	bytes = byte_array_from_chunk(env, host->get_address(host));
+	host->destroy(host);
+	free(str);
+	library_deinit();
+	return bytes;
+}

+ 168 - 0
app/src/main/jni/libandroidbridge/charonservice.h

@@ -0,0 +1,168 @@
+/*
+ * Copyright (C) 2012-2013 Tobias Brunner
+ * Copyright (C) 2012 Giuliano Grassi
+ * Copyright (C) 2012 Ralf Sager
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+/**
+ * @defgroup libandroidbridge libandroidbridge
+ *
+ * @defgroup android_backend backend
+ * @ingroup libandroidbridge
+ *
+ * @defgroup android_byod byod
+ * @ingroup libandroidbridge
+ *
+ * @defgroup android_kernel kernel
+ * @ingroup libandroidbridge
+ *
+ * @defgroup charonservice charonservice
+ * @{ @ingroup libandroidbridge
+ */
+
+#ifndef CHARONSERVICE_H_
+#define CHARONSERVICE_H_
+
+#include "vpnservice_builder.h"
+#include "kernel/network_manager.h"
+
+#include <library.h>
+#include <collections/linked_list.h>
+
+typedef enum android_vpn_state_t android_vpn_state_t;
+typedef enum android_imc_state_t android_imc_state_t;
+typedef struct charonservice_t charonservice_t;
+
+/**
+ * Default value for the MTU of TUN device and the size of IKE fragments
+ */
+#define ANDROID_DEFAULT_MTU 1400
+
+/**
+ * VPN status codes. As defined in CharonVpnService.java
+ */
+enum android_vpn_state_t {
+	CHARONSERVICE_CHILD_STATE_UP = 1,
+	CHARONSERVICE_CHILD_STATE_DOWN,
+	CHARONSERVICE_AUTH_ERROR,
+	CHARONSERVICE_PEER_AUTH_ERROR,
+	CHARONSERVICE_LOOKUP_ERROR,
+	CHARONSERVICE_UNREACHABLE_ERROR,
+	CHARONSERVICE_CERTIFICATE_UNAVAILABLE,
+	CHARONSERVICE_GENERIC_ERROR,
+};
+
+/**
+ * Final IMC state as defined in ImcState.java
+ */
+enum android_imc_state_t {
+	ANDROID_IMC_STATE_UNKNOWN = 0,
+	ANDROID_IMC_STATE_ALLOW = 1,
+	ANDROID_IMC_STATE_BLOCK = 2,
+	ANDROID_IMC_STATE_ISOLATE = 3,
+};
+
+/**
+ * Public interface of charonservice.
+ *
+ * Used to communicate with CharonVpnService via JNI
+ */
+struct charonservice_t {
+
+	/**
+	 * Update the status in the Java domain (UI)
+	 *
+	 * @param code			status code
+	 * @return				TRUE on success
+	 */
+	bool (*update_status)(charonservice_t *this, android_vpn_state_t code);
+
+	/**
+	 * Update final IMC state in the Java domain (UI)
+	 *
+	 * @param state			IMC state
+	 * @return				TRUE on success
+	 */
+	bool (*update_imc_state)(charonservice_t *this, android_imc_state_t state);
+
+	/**
+	 * Add a remediation instruction via JNI
+	 *
+	 * @param instr			remediation instruction
+	 * @return				TRUE on success
+	 */
+	bool (*add_remediation_instr)(charonservice_t *this, char *instr);
+
+	/**
+	 * Install a bypass policy for the given socket using the protect() Method
+	 * of the Android VpnService interface.
+	 *
+	 * Use -1 as fd to re-bypass previously bypassed sockets.
+	 *
+	 * @param fd			socket file descriptor
+	 * @param family		socket protocol family
+	 * @return				TRUE if operation successful
+	 */
+	bool (*bypass_socket)(charonservice_t *this, int fd, int family);
+
+	/**
+	 * Get a list of trusted certificates via JNI
+	 *
+	 * @return				list of DER encoded certificates (as chunk_t*),
+	 *						NULL on failure
+	 */
+	linked_list_t *(*get_trusted_certificates)(charonservice_t *this);
+
+	/**
+	 * Get the configured user certificate chain via JNI
+	 *
+	 * The first item in the returned list is the  user certificate followed
+	 * by any remaining elements of the certificate chain.
+	 *
+	 * @return				list of DER encoded certificates (as chunk_t*),
+	 *						NULL on failure
+	 */
+	linked_list_t *(*get_user_certificate)(charonservice_t *this);
+
+	/**
+	 * Get the configured private key via JNI
+	 *
+	 * @param pubkey		the public key as extracted from the certificate
+	 * @return				PrivateKey object, NULL on failure
+	 */
+	private_key_t *(*get_user_key)(charonservice_t *this, public_key_t *pubkey);
+
+	/**
+	 * Get the current vpnservice_builder_t object
+	 *
+	 * @return				VpnService.Builder instance
+	 */
+	vpnservice_builder_t *(*get_vpnservice_builder)(charonservice_t *this);
+
+	/**
+	 * Get the current network_manager_t object
+	 *
+	 * @return				NetworkManager instance
+	 */
+	network_manager_t *(*get_network_manager)(charonservice_t *this);
+};
+
+/**
+ * The single instance of charonservice_t.
+ *
+ * Set between JNI calls to initializeCharon() and deinitializeCharon().
+ */
+extern charonservice_t *charonservice;
+
+#endif /** CHARONSERVICE_H_ @}*/

+ 192 - 0
app/src/main/jni/libandroidbridge/kernel/android_ipsec.c

@@ -0,0 +1,192 @@
+/*
+ * Copyright (C) 2012 Tobias Brunner
+ * Copyright (C) 2012 Giuliano Grassi
+ * Copyright (C) 2012 Ralf Sager
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.  *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+#include "android_ipsec.h"
+#include "../charonservice.h"
+
+#include <utils/debug.h>
+#include <library.h>
+#include <daemon.h>
+#include <ipsec.h>
+
+typedef struct private_kernel_android_ipsec_t private_kernel_android_ipsec_t;
+
+struct private_kernel_android_ipsec_t {
+
+	/**
+	 * Public kernel interface
+	 */
+	kernel_android_ipsec_t public;
+
+	/**
+	 * Listener for lifetime expire events
+	 */
+	ipsec_event_listener_t ipsec_listener;
+};
+
+/**
+ * Callback registrered with libipsec.
+ */
+static void expire(uint8_t protocol, uint32_t spi, host_t *dst, bool hard)
+{
+	charon->kernel->expire(charon->kernel, protocol, spi, dst, hard);
+}
+
+METHOD(kernel_ipsec_t, get_spi, status_t,
+	private_kernel_android_ipsec_t *this, host_t *src, host_t *dst,
+	uint8_t protocol, uint32_t *spi)
+{
+	return ipsec->sas->get_spi(ipsec->sas, src, dst, protocol, spi);
+}
+
+METHOD(kernel_ipsec_t, get_cpi, status_t,
+	private_kernel_android_ipsec_t *this, host_t *src, host_t *dst,
+	uint16_t *cpi)
+{
+	return NOT_SUPPORTED;
+}
+
+METHOD(kernel_ipsec_t, add_sa, status_t,
+	private_kernel_android_ipsec_t *this, kernel_ipsec_sa_id_t *id,
+	kernel_ipsec_add_sa_t *data)
+{
+	return ipsec->sas->add_sa(ipsec->sas, id->src, id->dst, id->spi, id->proto,
+					data->reqid, id->mark, data->tfc, data->lifetime,
+					data->enc_alg, data->enc_key, data->int_alg, data->int_key,
+					data->mode, data->ipcomp, data->cpi, data->initiator,
+					data->encap, data->esn, data->inbound, data->update);
+}
+
+METHOD(kernel_ipsec_t, update_sa, status_t,
+	private_kernel_android_ipsec_t *this, kernel_ipsec_sa_id_t *id,
+	kernel_ipsec_update_sa_t *data)
+{
+	return ipsec->sas->update_sa(ipsec->sas, id->spi, id->proto, data->cpi,
+					id->src, id->dst, data->new_src, data->new_dst, data->encap,
+					data->new_encap, id->mark);
+}
+
+METHOD(kernel_ipsec_t, query_sa, status_t,
+	private_kernel_android_ipsec_t *this, kernel_ipsec_sa_id_t *id,
+	kernel_ipsec_query_sa_t *data, uint64_t *bytes, uint64_t *packets,
+	time_t *time)
+{
+	return ipsec->sas->query_sa(ipsec->sas, id->src, id->dst, id->spi,
+								id->proto, id->mark, bytes, packets, time);
+}
+
+METHOD(kernel_ipsec_t, del_sa, status_t,
+	private_kernel_android_ipsec_t *this, kernel_ipsec_sa_id_t *id,
+	kernel_ipsec_del_sa_t *data)
+{
+	return ipsec->sas->del_sa(ipsec->sas, id->src, id->dst, id->spi, id->proto,
+							  data->cpi, id->mark);
+}
+
+METHOD(kernel_ipsec_t, flush_sas, status_t,
+	private_kernel_android_ipsec_t *this)
+{
+	return ipsec->sas->flush_sas(ipsec->sas);
+}
+
+METHOD(kernel_ipsec_t, add_policy, status_t,
+	private_kernel_android_ipsec_t *this, kernel_ipsec_policy_id_t *id,
+	kernel_ipsec_manage_policy_t *data)
+{
+	return ipsec->policies->add_policy(ipsec->policies, data->src, data->dst,
+									   id->src_ts, id->dst_ts, id->dir,
+									   data->type, data->sa, id->mark,
+									   data->prio);
+}
+
+METHOD(kernel_ipsec_t, query_policy, status_t,
+	private_kernel_android_ipsec_t *this, kernel_ipsec_policy_id_t *id,
+	kernel_ipsec_query_policy_t *data, time_t *use_time)
+{
+	return NOT_SUPPORTED;
+}
+
+METHOD(kernel_ipsec_t, del_policy, status_t,
+	private_kernel_android_ipsec_t *this, kernel_ipsec_policy_id_t *id,
+	kernel_ipsec_manage_policy_t *data)
+{
+	return ipsec->policies->del_policy(ipsec->policies, data->src, data->dst,
+									   id->src_ts, id->dst_ts, id->dir,
+									   data->type, data->sa, id->mark,
+									   data->prio);
+}
+
+METHOD(kernel_ipsec_t, flush_policies, status_t,
+	private_kernel_android_ipsec_t *this)
+{
+	ipsec->policies->flush_policies(ipsec->policies);
+	return SUCCESS;
+}
+
+METHOD(kernel_ipsec_t, bypass_socket, bool,
+	private_kernel_android_ipsec_t *this, int fd, int family)
+{
+	return charonservice->bypass_socket(charonservice, fd, family);
+}
+
+METHOD(kernel_ipsec_t, enable_udp_decap, bool,
+	private_kernel_android_ipsec_t *this, int fd, int family, uint16_t port)
+{
+	return NOT_SUPPORTED;
+}
+
+METHOD(kernel_ipsec_t, destroy, void,
+	private_kernel_android_ipsec_t *this)
+{
+	ipsec->events->unregister_listener(ipsec->events, &this->ipsec_listener);
+	free(this);
+}
+
+/*
+ * Described in header.
+ */
+kernel_android_ipsec_t *kernel_android_ipsec_create()
+{
+	private_kernel_android_ipsec_t *this;
+
+	INIT(this,
+		.public = {
+			.interface = {
+				.get_spi = _get_spi,
+				.get_cpi = _get_cpi,
+				.add_sa  = _add_sa,
+				.update_sa = _update_sa,
+				.query_sa = _query_sa,
+				.del_sa = _del_sa,
+				.flush_sas = _flush_sas,
+				.add_policy = _add_policy,
+				.query_policy = _query_policy,
+				.del_policy = _del_policy,
+				.flush_policies = _flush_policies,
+				.bypass_socket = _bypass_socket,
+				.enable_udp_decap = _enable_udp_decap,
+				.destroy = _destroy,
+			},
+		},
+		.ipsec_listener = {
+			.expire = expire,
+		},
+	);
+
+	ipsec->events->register_listener(ipsec->events, &this->ipsec_listener);
+
+	return &this->public;
+}

+ 48 - 0
app/src/main/jni/libandroidbridge/kernel/android_ipsec.h

@@ -0,0 +1,48 @@
+/*
+ * Copyright (C) 2012 Giuliano Grassi
+ * Copyright (C) 2012 Ralf Sager
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+/**
+ * @defgroup kernel_android_ipsec kernel_android_ipsec
+ * @{ @ingroup android_kernel
+ */
+
+#ifndef KERNEL_ANDROID_IPSEC_H_
+#define KERNEL_ANDROID_IPSEC_H_
+
+#include <library.h>
+#include <kernel/kernel_ipsec.h>
+
+typedef struct kernel_android_ipsec_t kernel_android_ipsec_t;
+
+/**
+ * Implementation of the ipsec interface using libipsec on Android
+ */
+struct kernel_android_ipsec_t {
+
+	/**
+	 * Implements kernel_ipsec_t interface
+	 */
+	kernel_ipsec_t interface;
+};
+
+/**
+ * Create a android ipsec interface instance.
+ *
+ * @return			kernel_android_ipsec_t instance
+ */
+kernel_android_ipsec_t *kernel_android_ipsec_create();
+
+#endif /** KERNEL_ANDROID_IPSEC_H_ @}*/

+ 323 - 0
app/src/main/jni/libandroidbridge/kernel/android_net.c

@@ -0,0 +1,323 @@
+/*
+ * Copyright (C) 2012-2015 Tobias Brunner
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.  *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+#include <sys/types.h>
+#include <sys/socket.h>
+#include <unistd.h>
+#include <errno.h>
+
+#include "android_net.h"
+
+#include "../android_jni.h"
+#include "../charonservice.h"
+#include <daemon.h>
+#include <processing/jobs/callback_job.h>
+#include <threading/mutex.h>
+
+/** delay before firing roam events (ms) */
+#define ROAM_DELAY 100
+#define ROAM_DELAY_RECHECK 1000
+
+typedef struct private_android_net_t private_android_net_t;
+
+struct private_android_net_t {
+
+	/**
+	 * Public kernel interface
+	 */
+	kernel_net_t public;
+
+	/**
+	 * Reference to NetworkManager object
+	 */
+	network_manager_t *network_manager;
+
+	/**
+	 * Earliest time of the next roam event
+	 */
+	timeval_t next_roam;
+
+	/**
+	 * Mutex to check and update roam event time, and other private members
+	 */
+	mutex_t *mutex;
+
+	/**
+	 * List of virtual IPs
+	 */
+	linked_list_t *vips;
+
+	/**
+	 * Socket used to determine source address
+	 */
+	int socket_v4;
+
+	/**
+	 * Whether the device is currently connected
+	 */
+	bool connected;
+};
+
+/**
+ * callback function that raises the delayed roam event
+ */
+static job_requeue_t roam_event()
+{
+	/* this will fail if no connection is up */
+	charonservice->bypass_socket(charonservice, -1, 0);
+	charon->kernel->roam(charon->kernel, TRUE);
+	return JOB_REQUEUE_NONE;
+}
+
+/**
+ * Listen for connectivity change events and queue a roam event
+ */
+static void connectivity_cb(private_android_net_t *this,
+							bool disconnected)
+{
+	timeval_t now;
+	job_t *job;
+
+	time_monotonic(&now);
+	this->mutex->lock(this->mutex);
+	this->connected = !disconnected;
+	if (!timercmp(&now, &this->next_roam, >))
+	{
+		this->mutex->unlock(this->mutex);
+		return;
+	}
+	timeval_add_ms(&now, ROAM_DELAY);
+	this->next_roam = now;
+	this->mutex->unlock(this->mutex);
+
+	job = (job_t*)callback_job_create((callback_job_cb_t)roam_event, NULL,
+									   NULL, NULL);
+	lib->scheduler->schedule_job_ms(lib->scheduler, job, ROAM_DELAY);
+}
+
+METHOD(kernel_net_t, get_source_addr, host_t*,
+	private_android_net_t *this, host_t *dest, host_t *src)
+{
+	union {
+		struct sockaddr sockaddr;
+		struct sockaddr_in sin;
+		struct sockaddr_in6 sin6;
+	} addr;
+	socklen_t addrlen;
+	timeval_t now;
+	job_t *job;
+
+	addrlen = *dest->get_sockaddr_len(dest);
+	addr.sockaddr.sa_family = AF_UNSPEC;
+	if (connect(this->socket_v4, &addr.sockaddr, addrlen) < 0)
+	{
+		DBG1(DBG_KNL, "failed to disconnect socket: %s", strerror(errno));
+		return NULL;
+	}
+	if (android_sdk_version <= ANDROID_JELLY_BEAN_MR2)
+	{	/* this seems to help avoiding the VIP, unless there is no connectivity
+		 * at all */
+		charonservice->bypass_socket(charonservice, -1, 0);
+	}
+	if (connect(this->socket_v4, dest->get_sockaddr(dest), addrlen) < 0)
+	{
+		/* don't report an error if we are not connected (ENETUNREACH) */
+		if (errno != ENETUNREACH)
+		{
+			DBG1(DBG_KNL, "failed to connect socket: %s", strerror(errno));
+		}
+		else
+		{
+			time_monotonic(&now);
+			this->mutex->lock(this->mutex);
+			if (this->connected && timercmp(&now, &this->next_roam, >))
+			{	/* we were not able to find a source address but reportedly are
+				 * connected, trigger a recheck in case an IP address appears
+				 * delayed but the callback is not triggered again */
+				timeval_add_ms(&now, ROAM_DELAY_RECHECK);
+				this->next_roam = now;
+				this->mutex->unlock(this->mutex);
+				job = (job_t*)callback_job_create((callback_job_cb_t)roam_event,
+												  NULL, NULL, NULL);
+				lib->scheduler->schedule_job_ms(lib->scheduler, job,
+												ROAM_DELAY_RECHECK);
+			}
+			else
+			{
+				this->mutex->unlock(this->mutex);
+			}
+		}
+		return NULL;
+	}
+	if (getsockname(this->socket_v4, &addr.sockaddr, &addrlen) < 0)
+	{
+		DBG1(DBG_KNL, "failed to determine src address: %s", strerror(errno));
+		return NULL;
+	}
+	return host_create_from_sockaddr((sockaddr_t*)&addr);
+}
+
+CALLBACK(vip_equals, bool,
+	host_t *vip, va_list args)
+{
+	host_t *host;
+
+	VA_ARGS_VGET(args, host);
+	return host->ip_equals(host, vip);
+}
+
+METHOD(kernel_net_t, get_source_addr_old, host_t*,
+	private_android_net_t *this, host_t *dest, host_t *src)
+{
+	host_t *host;
+
+	/* on older Android versions we might get the virtual IP back because
+	 * the protect() implementation there and connect() don't properly work
+	 * together, on newer releases (using fwmarks) that's not a problem */
+	host = get_source_addr(this, dest, src);
+	if (host)
+	{
+		this->mutex->lock(this->mutex);
+		if (this->vips->find_first(this->vips, vip_equals, NULL, host))
+		{
+			host->destroy(host);
+			host = NULL;
+		}
+		this->mutex->unlock(this->mutex);
+	}
+	return host;
+}
+
+METHOD(kernel_net_t, get_nexthop, host_t*,
+	private_android_net_t *this, host_t *dest, int prefix, host_t *src,
+	char **iface)
+{
+	return NULL;
+}
+
+METHOD(kernel_net_t, get_interface, bool,
+	private_android_net_t *this, host_t *host, char **name)
+{
+	if (name)
+	{	/* the actual name does not matter in our case */
+		*name = strdup("strongswan");
+	}
+	return TRUE;
+}
+
+METHOD(kernel_net_t, create_address_enumerator, enumerator_t*,
+	private_android_net_t *this, kernel_address_type_t which)
+{
+	/* return virtual IPs if requested, nothing otherwise */
+	if (which & ADDR_TYPE_VIRTUAL)
+	{
+		this->mutex->lock(this->mutex);
+		return enumerator_create_cleaner(
+					this->vips->create_enumerator(this->vips),
+					(void*)this->mutex->unlock, this->mutex);
+	}
+	return enumerator_create_empty();
+}
+
+METHOD(kernel_net_t, add_ip, status_t,
+	private_android_net_t *this, host_t *virtual_ip, int prefix, char *iface)
+{
+	this->mutex->lock(this->mutex);
+	this->vips->insert_last(this->vips, virtual_ip->clone(virtual_ip));
+	this->mutex->unlock(this->mutex);
+	return SUCCESS;
+}
+
+METHOD(kernel_net_t, del_ip, status_t,
+	private_android_net_t *this, host_t *virtual_ip, int prefix, bool wait)
+{
+	host_t *vip;
+
+	this->mutex->lock(this->mutex);
+	if (this->vips->find_first(this->vips, vip_equals, (void**)&vip,
+							   virtual_ip))
+	{
+		this->vips->remove(this->vips, vip, NULL);
+		vip->destroy(vip);
+	}
+	this->mutex->unlock(this->mutex);
+	return SUCCESS;
+}
+
+METHOD(kernel_net_t, add_route, status_t,
+	private_android_net_t *this, chunk_t dst_net, uint8_t prefixlen,
+	host_t *gateway, host_t *src_ip, char *if_name)
+{
+	return NOT_SUPPORTED;
+}
+
+METHOD(kernel_net_t, del_route, status_t,
+	private_android_net_t *this, chunk_t dst_net, uint8_t prefixlen,
+	host_t *gateway, host_t *src_ip, char *if_name)
+{
+	return NOT_SUPPORTED;
+}
+
+METHOD(kernel_net_t, destroy, void,
+	private_android_net_t *this)
+{
+	this->network_manager->remove_connectivity_cb(this->network_manager,
+												 (void*)connectivity_cb);
+	this->mutex->destroy(this->mutex);
+	this->vips->destroy(this->vips);
+	close(this->socket_v4);
+	free(this);
+}
+
+kernel_net_t *kernel_android_net_create()
+{
+	private_android_net_t *this;
+
+	INIT(this,
+		.public = {
+			.get_source_addr = _get_source_addr,
+			.get_nexthop = _get_nexthop,
+			.get_interface = _get_interface,
+			.create_address_enumerator = _create_address_enumerator,
+			.add_ip = _add_ip,
+			.del_ip = _del_ip,
+			.add_route = _add_route,
+			.del_route = _del_route,
+			.destroy = _destroy,
+		},
+		.mutex = mutex_create(MUTEX_TYPE_DEFAULT),
+		.vips = linked_list_create(),
+		.network_manager = charonservice->get_network_manager(charonservice),
+	);
+	timerclear(&this->next_roam);
+
+	if (android_sdk_version <= ANDROID_JELLY_BEAN_MR2)
+	{
+		this->public.get_source_addr = _get_source_addr_old;
+	}
+
+	this->socket_v4 = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
+	if (this->socket_v4 < 0)
+	{
+		DBG1(DBG_KNL, "failed to create socket to lookup src addresses: %s",
+			 strerror(errno));
+	}
+	charonservice->bypass_socket(charonservice, this->socket_v4, AF_INET);
+
+	this->mutex->lock(this->mutex);
+	this->network_manager->add_connectivity_cb(
+						this->network_manager, (void*)connectivity_cb, this);
+	this->connected = this->network_manager->is_connected(this->network_manager);
+	this->mutex->unlock(this->mutex);
+	return &this->public;
+}

+ 35 - 0
app/src/main/jni/libandroidbridge/kernel/android_net.h

@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2012-2015 Tobias Brunner
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+/**
+ * @defgroup android_net android_net
+ * @{ @ingroup android_kernel
+ */
+
+#ifndef ANDROID_NET_H_
+#define ANDROID_NET_H_
+
+#include <library.h>
+#include <kernel/kernel_net.h>
+
+/**
+ * Create an Android-specific kernel_net_t instance.
+ *
+ * @return			kernel_net_t instance
+ */
+kernel_net_t *kernel_android_net_create();
+
+
+#endif /** ANDROID_NET_H_ @}*/

+ 240 - 0
app/src/main/jni/libandroidbridge/kernel/network_manager.c

@@ -0,0 +1,240 @@
+/*
+ * Copyright (C) 2012-2015 Tobias Brunner
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.  *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+#include "network_manager.h"
+
+#include "../android_jni.h"
+#include "../charonservice.h"
+#include <utils/debug.h>
+#include <threading/mutex.h>
+
+typedef struct private_network_manager_t private_network_manager_t;
+
+struct private_network_manager_t {
+
+	/**
+	 * Public interface
+	 */
+	network_manager_t public;
+
+	/**
+	 * Reference to NetworkManager object
+	 */
+	jobject obj;
+
+	/**
+	 * Java class for NetworkManager
+	 */
+	jclass cls;
+
+	/**
+	 * Registered callback
+	 */
+	struct {
+		connectivity_cb_t cb;
+		void *data;
+	} connectivity_cb;
+
+	/**
+	 * Mutex to access callback
+	 */
+	mutex_t *mutex;
+};
+
+JNI_METHOD(NetworkManager, networkChanged, void,
+	bool disconnected)
+{
+	private_network_manager_t *nm;
+
+	nm = (private_network_manager_t*)charonservice->get_network_manager(
+																charonservice);
+	nm->mutex->lock(nm->mutex);
+	if (nm->connectivity_cb.cb)
+	{
+		nm->connectivity_cb.cb(nm->connectivity_cb.data, disconnected);
+	}
+	nm->mutex->unlock(nm->mutex);
+}
+
+METHOD(network_manager_t, add_connectivity_cb, void,
+	private_network_manager_t *this, connectivity_cb_t cb, void *data)
+{
+	this->mutex->lock(this->mutex);
+	if (!this->connectivity_cb.cb)
+	{
+		JNIEnv *env;
+		jmethodID method_id;
+
+		androidjni_attach_thread(&env);
+		method_id = (*env)->GetMethodID(env, this->cls, "Register", "()V");
+		if (!method_id)
+		{
+			androidjni_exception_occurred(env);
+		}
+		else
+		{
+			(*env)->CallVoidMethod(env, this->obj, method_id);
+			if (!androidjni_exception_occurred(env))
+			{
+				this->connectivity_cb.cb = cb;
+				this->connectivity_cb.data = data;
+			}
+		}
+		androidjni_detach_thread();
+	}
+	this->mutex->unlock(this->mutex);
+}
+
+/**
+ * Unregister the NetworkManager via JNI.
+ *
+ * this->mutex has to be locked
+ */
+static void unregister_network_manager(private_network_manager_t *this)
+{
+	JNIEnv *env;
+	jmethodID method_id;
+
+	androidjni_attach_thread(&env);
+	method_id = (*env)->GetMethodID(env, this->cls, "Unregister", "()V");
+	if (!method_id)
+	{
+		androidjni_exception_occurred(env);
+	}
+	else
+	{
+		(*env)->CallVoidMethod(env, this->obj, method_id);
+		androidjni_exception_occurred(env);
+	}
+	androidjni_detach_thread();
+}
+
+METHOD(network_manager_t, remove_connectivity_cb, void,
+	private_network_manager_t *this, connectivity_cb_t cb)
+{
+	bool unregister = FALSE;
+
+	this->mutex->lock(this->mutex);
+	if (this->connectivity_cb.cb == cb)
+	{
+		this->connectivity_cb.cb = NULL;
+		unregister = TRUE;
+	}
+	this->mutex->unlock(this->mutex);
+	if (unregister)
+	{	/* this call blocks until a possible networkChanged call returned so
+		 * we can't hold the mutex */
+		unregister_network_manager(this);
+	}
+}
+
+METHOD(network_manager_t, is_connected, bool,
+	private_network_manager_t *this)
+{
+	JNIEnv *env;
+	jmethodID method_id;
+	bool connected = FALSE;
+
+	androidjni_attach_thread(&env);
+	method_id = (*env)->GetMethodID(env, this->cls, "isConnected", "()Z");
+	if (!method_id)
+	{
+		androidjni_exception_occurred(env);
+	}
+	else
+	{
+		connected = (*env)->CallBooleanMethod(env, this->obj, method_id);
+		connected = !androidjni_exception_occurred(env) && connected;
+	}
+	androidjni_detach_thread();
+	return connected;
+}
+
+METHOD(network_manager_t, destroy, void,
+	private_network_manager_t *this)
+{
+	JNIEnv *env;
+
+	this->mutex->lock(this->mutex);
+	if (this->connectivity_cb.cb)
+	{
+		this->connectivity_cb.cb = NULL;
+		unregister_network_manager(this);
+	}
+	this->mutex->unlock(this->mutex);
+
+	androidjni_attach_thread(&env);
+	if (this->obj)
+	{
+		(*env)->DeleteGlobalRef(env, this->obj);
+	}
+	if (this->cls)
+	{
+		(*env)->DeleteGlobalRef(env, this->cls);
+	}
+	androidjni_detach_thread();
+	this->mutex->destroy(this->mutex);
+	free(this);
+}
+
+/*
+ * Described in header.
+ */
+network_manager_t *network_manager_create(jobject context)
+{
+	private_network_manager_t *this;
+	JNIEnv *env;
+	jmethodID method_id;
+	jobject obj;
+	jclass cls;
+
+	INIT(this,
+		.public = {
+			.add_connectivity_cb = _add_connectivity_cb,
+			.remove_connectivity_cb = _remove_connectivity_cb,
+			.is_connected = _is_connected,
+			.destroy = _destroy,
+		},
+		.mutex = mutex_create(MUTEX_TYPE_DEFAULT),
+	);
+
+	androidjni_attach_thread(&env);
+	cls = (*env)->FindClass(env, JNI_PACKAGE_STRING "/NetworkManager");
+	if (!cls)
+	{
+		goto failed;
+	}
+	this->cls = (*env)->NewGlobalRef(env, cls);
+	method_id = (*env)->GetMethodID(env, cls, "<init>",
+									"(Landroid/content/Context;)V");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	obj = (*env)->NewObject(env, cls, method_id, context);
+	if (!obj)
+	{
+		goto failed;
+	}
+	this->obj = (*env)->NewGlobalRef(env, obj);
+	androidjni_detach_thread();
+	return &this->public;
+
+failed:
+	DBG1(DBG_KNL, "failed to build NetworkManager object");
+	androidjni_exception_occurred(env);
+	androidjni_detach_thread();
+	destroy(this);
+	return NULL;
+};

+ 89 - 0
app/src/main/jni/libandroidbridge/kernel/network_manager.h

@@ -0,0 +1,89 @@
+/*
+ * Copyright (C) 2012-2015 Tobias Brunner
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+/**
+ * @defgroup network_manager network_manager
+ * @{ @ingroup android_kernel
+ */
+
+#ifndef NETWORK_MANAGER_H_
+#define NETWORK_MANAGER_H_
+
+#include <jni.h>
+
+#include <library.h>
+#include <networking/host.h>
+
+typedef struct network_manager_t network_manager_t;
+
+/**
+ * Callback called if connectivity changes somehow.
+ *
+ * Implementation should be quick as the call is made by the Java apps main
+ * thread.
+ *
+ * @param data					data supplied during registration
+ * @param disconnected			TRUE if currently disconnected
+ */
+typedef void (*connectivity_cb_t)(void *data, bool disconnected);
+
+/**
+ * NetworkManager, used to listen for network changes.
+ *
+ * Communicates with NetworkManager via JNI
+ */
+struct network_manager_t {
+
+	/**
+	 * Register a callback that is called if connectivity changes
+	 *
+	 * @note Only the first registered callback is currently used
+	 *
+	 * @param cb				callback to register
+	 * @param data				data provided to callback
+	 */
+	void (*add_connectivity_cb)(network_manager_t *this, connectivity_cb_t cb,
+								void *data);
+
+	/**
+	 * Unregister a previously registered callback for connectivity changes
+	 *
+	 * @param cb				previously registered callback
+	 */
+	void (*remove_connectivity_cb)(network_manager_t *this,
+								   connectivity_cb_t cb);
+
+	/**
+	 * Check whether we currently have connectivity
+	 *
+	 * @return					TRUE if currently connected
+	 */
+	bool (*is_connected)(network_manager_t *this);
+
+	/**
+	 * Destroy a network_manager_t instance
+	 */
+	void (*destroy)(network_manager_t *this);
+};
+
+/**
+ * Create a network_manager_t instance
+ *
+ * @param context				Context object
+ * @return						network_manager_t instance
+ */
+network_manager_t *network_manager_create(jobject context);
+
+#endif /** NETWORK_MANAGER_H_ @}*/

+ 279 - 0
app/src/main/jni/libandroidbridge/vpnservice_builder.c

@@ -0,0 +1,279 @@
+/*
+ * Copyright (C) 2012-2014 Tobias Brunner
+ * Copyright (C) 2012 Giuliano Grassi
+ * Copyright (C) 2012 Ralf Sager
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+#include "vpnservice_builder.h"
+#include "android_jni.h"
+
+#include <utils/debug.h>
+#include <library.h>
+
+typedef struct private_vpnservice_builder_t private_vpnservice_builder_t;
+
+/**
+ * private data of vpnservice_builder
+ */
+struct private_vpnservice_builder_t {
+
+	/**
+	 * public interface
+	 */
+	vpnservice_builder_t public;
+
+	/**
+	 * Java object
+	 */
+	jobject builder;
+};
+
+METHOD(vpnservice_builder_t, add_address, bool,
+	private_vpnservice_builder_t *this, host_t *addr)
+{
+	JNIEnv *env;
+	jmethodID method_id;
+	jstring str;
+	char buf[INET6_ADDRSTRLEN];
+	int prefix;
+
+	androidjni_attach_thread(&env);
+
+	DBG2(DBG_LIB, "builder: adding interface address %H", addr);
+
+	prefix = addr->get_family(addr) == AF_INET ? 32 : 128;
+	if (snprintf(buf, sizeof(buf), "%H", addr) >= sizeof(buf))
+	{
+		goto failed;
+	}
+
+	method_id = (*env)->GetMethodID(env, android_charonvpnservice_builder_class,
+									"addAddress", "(Ljava/lang/String;I)Z");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	str = (*env)->NewStringUTF(env, buf);
+	if (!str)
+	{
+		goto failed;
+	}
+	if (!(*env)->CallBooleanMethod(env, this->builder, method_id, str, prefix))
+	{
+		goto failed;
+	}
+	androidjni_detach_thread();
+	return TRUE;
+
+failed:
+	DBG1(DBG_LIB, "builder: failed to add address");
+	androidjni_exception_occurred(env);
+	androidjni_detach_thread();
+	return FALSE;
+}
+
+METHOD(vpnservice_builder_t, set_mtu, bool,
+	private_vpnservice_builder_t *this, int mtu)
+{
+	JNIEnv *env;
+	jmethodID method_id;
+
+	androidjni_attach_thread(&env);
+
+	DBG2(DBG_LIB, "builder: setting MTU to %d", mtu);
+
+	method_id = (*env)->GetMethodID(env, android_charonvpnservice_builder_class,
+									"setMtu", "(I)Z");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	if (!(*env)->CallBooleanMethod(env, this->builder, method_id, mtu))
+	{
+		goto failed;
+	}
+	androidjni_detach_thread();
+	return TRUE;
+
+failed:
+	DBG1(DBG_LIB, "builder: failed to set MTU");
+	androidjni_exception_occurred(env);
+	androidjni_detach_thread();
+	return FALSE;
+}
+
+METHOD(vpnservice_builder_t, add_route, bool,
+	private_vpnservice_builder_t *this, host_t *net, int prefix)
+{
+	JNIEnv *env;
+	jmethodID method_id;
+	jstring str;
+	char buf[INET6_ADDRSTRLEN];
+
+	androidjni_attach_thread(&env);
+
+	DBG2(DBG_LIB, "builder: adding route %+H/%d", net, prefix);
+
+	if (snprintf(buf, sizeof(buf), "%+H", net) >= sizeof(buf))
+	{
+		goto failed;
+	}
+
+	method_id = (*env)->GetMethodID(env, android_charonvpnservice_builder_class,
+									"addRoute", "(Ljava/lang/String;I)Z");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	str = (*env)->NewStringUTF(env, buf);
+	if (!str)
+	{
+		goto failed;
+	}
+	if (!(*env)->CallBooleanMethod(env, this->builder, method_id, str, prefix))
+	{
+		goto failed;
+	}
+	androidjni_detach_thread();
+	return TRUE;
+
+failed:
+	DBG1(DBG_LIB, "builder: failed to add route");
+	androidjni_exception_occurred(env);
+	androidjni_detach_thread();
+	return FALSE;
+}
+
+METHOD(vpnservice_builder_t, add_dns, bool,
+	private_vpnservice_builder_t *this, host_t *dns)
+{
+	JNIEnv *env;
+	jmethodID method_id;
+	jstring str;
+	char buf[INET6_ADDRSTRLEN];
+
+	androidjni_attach_thread(&env);
+
+	DBG2(DBG_LIB, "builder: adding DNS server %H", dns);
+
+	if (snprintf(buf, sizeof(buf), "%H", dns) >= sizeof(buf))
+	{
+		goto failed;
+	}
+
+	method_id = (*env)->GetMethodID(env, android_charonvpnservice_builder_class,
+									"addDnsServer", "(Ljava/lang/String;)Z");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	str = (*env)->NewStringUTF(env, buf);
+	if (!str)
+	{
+		goto failed;
+	}
+	if (!(*env)->CallBooleanMethod(env, this->builder, method_id, str))
+	{
+		goto failed;
+	}
+	androidjni_detach_thread();
+	return TRUE;
+
+failed:
+	DBG1(DBG_LIB, "builder: failed to add DNS server");
+	androidjni_exception_occurred(env);
+	androidjni_detach_thread();
+	return FALSE;
+}
+
+/**
+ * Establish or reestablish the TUN device
+ */
+static int establish_internal(private_vpnservice_builder_t *this, char *method)
+{
+	JNIEnv *env;
+	jmethodID method_id;
+	int fd;
+
+	androidjni_attach_thread(&env);
+
+	DBG2(DBG_LIB, "builder: building TUN device");
+
+	method_id = (*env)->GetMethodID(env, android_charonvpnservice_builder_class,
+									method, "()I");
+	if (!method_id)
+	{
+		goto failed;
+	}
+	fd = (*env)->CallIntMethod(env, this->builder, method_id);
+	if (fd == -1)
+	{
+		goto failed;
+	}
+	androidjni_detach_thread();
+	return fd;
+
+failed:
+	DBG1(DBG_LIB, "builder: failed to build TUN device");
+	androidjni_exception_occurred(env);
+	androidjni_detach_thread();
+	return -1;
+}
+
+METHOD(vpnservice_builder_t, establish, int,
+	private_vpnservice_builder_t *this)
+{
+	return establish_internal(this, "establish");
+}
+
+METHOD(vpnservice_builder_t, establish_no_dns, int,
+	private_vpnservice_builder_t *this)
+{
+	return establish_internal(this, "establishNoDns");
+}
+
+METHOD(vpnservice_builder_t, destroy, void,
+	private_vpnservice_builder_t *this)
+{
+	JNIEnv *env;
+
+	androidjni_attach_thread(&env);
+	(*env)->DeleteGlobalRef(env, this->builder);
+	androidjni_detach_thread();
+	free(this);
+}
+
+vpnservice_builder_t *vpnservice_builder_create(jobject builder)
+{
+	JNIEnv *env;
+	private_vpnservice_builder_t *this;
+
+	INIT(this,
+		.public = {
+			.add_address = _add_address,
+			.add_route = _add_route,
+			.add_dns = _add_dns,
+			.set_mtu = _set_mtu,
+			.establish = _establish,
+			.establish_no_dns = _establish_no_dns,
+			.destroy = _destroy,
+		},
+	);
+
+	androidjni_attach_thread(&env);
+	this->builder = (*env)->NewGlobalRef(env, builder);
+	androidjni_detach_thread();
+
+	return &this->public;
+}

+ 102 - 0
app/src/main/jni/libandroidbridge/vpnservice_builder.h

@@ -0,0 +1,102 @@
+/*
+ * Copyright (C) 2012-2014 Tobias Brunner
+ * Copyright (C) 2012 Giuliano Grassi
+ * Copyright (C) 2012 Ralf Sager
+ * HSR Hochschule fuer Technik Rapperswil
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * for more details.
+ */
+
+/**
+ * @defgroup vpnservice_builder vpnservice_builder
+ * @{ @ingroup libandroidbridge
+ */
+
+#ifndef VPNSERVICE_BUILDER_H_
+#define VPNSERVICE_BUILDER_H_
+
+#include <jni.h>
+
+#include <library.h>
+#include <networking/host.h>
+
+typedef struct vpnservice_builder_t vpnservice_builder_t;
+
+/**
+ * VpnService.Builder, used to build a TUN device.
+ *
+ * Communicates with CharonVpnService.BuilderAdapter via JNI
+ */
+struct vpnservice_builder_t {
+
+	/**
+	 * Add an interface address
+	 *
+	 * @param addr				the desired interface address
+	 * @return					TRUE on success
+	 */
+	bool (*add_address)(vpnservice_builder_t *this, host_t *addr);
+
+	/**
+	 * Add a route
+	 *
+	 * @param net				the network address
+	 * @param prefix_length		the prefix length
+	 * @return					TRUE on success
+	 */
+	bool (*add_route)(vpnservice_builder_t *this, host_t *net, int prefix);
+
+	/**
+	 * Add a DNS server
+	 *
+	 * @param dns				the address of the DNS server
+	 * @return					TRUE on success
+	 */
+	bool (*add_dns)(vpnservice_builder_t *this, host_t *dns);
+
+	/**
+	 * Set the MTU for the TUN device
+	 *
+	 * @param mtu				the MTU to set
+	 * @return					TRUE on success
+	 */
+	bool (*set_mtu)(vpnservice_builder_t *this,	int mtu);
+
+	/**
+	 * Build the TUN device
+	 *
+	 * @return					the TUN file descriptor, -1 if failed
+	 */
+	int (*establish)(vpnservice_builder_t *this);
+
+	/**
+	 * Build the TUN device without DNS related data
+	 *
+	 * @return					the TUN file descriptor, -1 if failed
+	 */
+	int (*establish_no_dns)(vpnservice_builder_t *this);
+
+	/**
+	 * Destroy a vpnservice_builder
+	 */
+	void (*destroy)(vpnservice_builder_t *this);
+
+};
+
+/**
+ * Create a vpnservice_builder instance
+ *
+ * @param builder				CharonVpnService.BuilderAdapter object
+ * @return						vpnservice_builder_t instance
+ */
+vpnservice_builder_t *vpnservice_builder_create(jobject builder);
+
+#endif /** VPNSERVICE_BUILDER_H_ @}*/

+ 25 - 0
app/src/main/jni/openssl/Android.mk

@@ -0,0 +1,25 @@
+# Note that some host libraries have the same module name as the target
+# libraries. This is currently needed to build, for example, adb. But it's
+# probably something that should be changed.
+
+LOCAL_PATH := $(call my-dir)
+
+## libcrypto
+
+# Target static library
+include $(CLEAR_VARS)
+LOCAL_MODULE_TAGS := optional
+LOCAL_MODULE := libcrypto_static
+LOCAL_EXPORT_C_INCLUDE_DIRS := $(LOCAL_PATH)/src/include
+LOCAL_ADDITIONAL_DEPENDENCIES := $(LOCAL_PATH)/Android.mk $(LOCAL_PATH)/crypto-sources.mk
+LOCAL_SDK_VERSION := 9
+LOCAL_CFLAGS += -fvisibility=hidden -DBORINGSSL_SHARED_LIBRARY -DBORINGSSL_IMPLEMENTATION -DOPENSSL_SMALL -Wno-unused-parameter
+# sha256-armv4.S does not compile with clang.
+ifneq ($(filter $(TARGET_ARCH_ABI), armeabi-v7a arm64-v8a),)
+	LOCAL_ASFLAGS += -no-integrated-as
+endif
+ifeq ($(TARGET_ARCH_ABI),arm64-v8a)
+	LOCAL_ASFLAGS += -march=armv8-a+crypto
+endif
+include $(LOCAL_PATH)/crypto-sources.mk
+include $(BUILD_STATIC_LIBRARY)

+ 127 - 0
app/src/main/jni/openssl/NOTICE

@@ -0,0 +1,127 @@
+
+  LICENSE ISSUES
+  ==============
+
+  The OpenSSL toolkit stays under a dual license, i.e. both the conditions of
+  the OpenSSL License and the original SSLeay license apply to the toolkit.
+  See below for the actual license texts. Actually both licenses are BSD-style
+  Open Source licenses. In case of any license issues related to OpenSSL
+  please contact openssl-core@openssl.org.
+
+  OpenSSL License
+  ---------------
+
+/* ====================================================================
+ * Copyright (c) 1998-2011 The OpenSSL Project.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer. 
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. All advertising materials mentioning features or use of this
+ *    software must display the following acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
+ *
+ * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
+ *    endorse or promote products derived from this software without
+ *    prior written permission. For written permission, please contact
+ *    openssl-core@openssl.org.
+ *
+ * 5. Products derived from this software may not be called "OpenSSL"
+ *    nor may "OpenSSL" appear in their names without prior written
+ *    permission of the OpenSSL Project.
+ *
+ * 6. Redistributions of any form whatsoever must retain the following
+ *    acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
+ * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This product includes cryptographic software written by Eric Young
+ * (eay@cryptsoft.com).  This product includes software written by Tim
+ * Hudson (tjh@cryptsoft.com).
+ *
+ */
+
+ Original SSLeay License
+ -----------------------
+
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ * 
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ * 
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ * 
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from 
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ * 
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ * 
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.]
+ */
+

+ 12 - 0
app/src/main/jni/openssl/README.ndk

@@ -0,0 +1,12 @@
+This is a version of the official Android BoringSSL sources slightly modified
+to be used as static library within the Android NDK.
+
+It is intended to be used as subdirectory of a project's jni directory, it
+just has to be included from the top Android.mk.  Afterwards it can be built
+as part of the project directly with $NDK/ndk-build.
+
+To update it to the latest upstream version add the following remote:
+
+  git remote add upstream https://android.googlesource.com/platform/external/boringssl
+
+NOTE: This branch might get rebased!

+ 9 - 0
app/src/main/jni/openssl/UPDATING

@@ -0,0 +1,9 @@
+rm -Rf src
+git clone https://boringssl.googlesource.com/boringssl src
+cd src
+git show -s --pretty=%H > ../BORINGSSL_REVISION
+cd ..
+rm -Rf src/.git
+rm -Rf src/fuzz
+rm -Rf linux-aarch64/ linux-arm/ linux-x86/ linux-x86_64/ mac-x86/ mac-x86_64/ win-x86_64/ win-x86/
+python src/util/generate_build_files.py android

+ 4 - 0
app/src/main/jni/openssl/flavor.mk

@@ -0,0 +1,4 @@
+# This makefile exists to be included by makefiles in other directories so that
+# they can detect whether BoringSSL or OpenSSL is being used.
+
+OPENSSL_FLAVOR=BoringSSL

+ 346 - 0
app/src/main/jni/openssl/include/openssl/aead.h

@@ -0,0 +1,346 @@
+/* Copyright (c) 2014, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+#ifndef OPENSSL_HEADER_AEAD_H
+#define OPENSSL_HEADER_AEAD_H
+
+#include <openssl/base.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* Authenticated Encryption with Additional Data.
+ *
+ * AEAD couples confidentiality and integrity in a single primitive. AEAD
+ * algorithms take a key and then can seal and open individual messages. Each
+ * message has a unique, per-message nonce and, optionally, additional data
+ * which is authenticated but not included in the ciphertext.
+ *
+ * The |EVP_AEAD_CTX_init| function initialises an |EVP_AEAD_CTX| structure and
+ * performs any precomputation needed to use |aead| with |key|. The length of
+ * the key, |key_len|, is given in bytes.
+ *
+ * The |tag_len| argument contains the length of the tags, in bytes, and allows
+ * for the processing of truncated authenticators. A zero value indicates that
+ * the default tag length should be used and this is defined as
+ * |EVP_AEAD_DEFAULT_TAG_LENGTH| in order to make the code clear. Using
+ * truncated tags increases an attacker's chance of creating a valid forgery.
+ * Be aware that the attacker's chance may increase more than exponentially as
+ * would naively be expected.
+ *
+ * When no longer needed, the initialised |EVP_AEAD_CTX| structure must be
+ * passed to |EVP_AEAD_CTX_cleanup|, which will deallocate any memory used.
+ *
+ * With an |EVP_AEAD_CTX| in hand, one can seal and open messages. These
+ * operations are intended to meet the standard notions of privacy and
+ * authenticity for authenticated encryption. For formal definitions see
+ * Bellare and Namprempre, "Authenticated encryption: relations among notions
+ * and analysis of the generic composition paradigm," Lecture Notes in Computer
+ * Science B<1976> (2000), 531–545,
+ * http://www-cse.ucsd.edu/~mihir/papers/oem.html.
+ *
+ * When sealing messages, a nonce must be given. The length of the nonce is
+ * fixed by the AEAD in use and is returned by |EVP_AEAD_nonce_length|. *The
+ * nonce must be unique for all messages with the same key*. This is critically
+ * important - nonce reuse may completely undermine the security of the AEAD.
+ * Nonces may be predictable and public, so long as they are unique. Uniqueness
+ * may be achieved with a simple counter or, if large enough, may be generated
+ * randomly. The nonce must be passed into the "open" operation by the receiver
+ * so must either be implicit (e.g. a counter), or must be transmitted along
+ * with the sealed message.
+ *
+ * The "seal" and "open" operations are atomic - an entire message must be
+ * encrypted or decrypted in a single call. Large messages may have to be split
+ * up in order to accomodate this. When doing so, be mindful of the need not to
+ * repeat nonces and the possibility that an attacker could duplicate, reorder
+ * or drop message chunks. For example, using a single key for a given (large)
+ * message and sealing chunks with nonces counting from zero would be secure as
+ * long as the number of chunks was securely transmitted. (Otherwise an
+ * attacker could truncate the message by dropping chunks from the end.)
+ *
+ * The number of chunks could be transmitted by prefixing it to the plaintext,
+ * for example. This also assumes that no other message would ever use the same
+ * key otherwise the rule that nonces must be unique for a given key would be
+ * violated.
+ *
+ * The "seal" and "open" operations also permit additional data to be
+ * authenticated via the |ad| parameter. This data is not included in the
+ * ciphertext and must be identical for both the "seal" and "open" call. This
+ * permits implicit context to be authenticated but may be empty if not needed.
+ *
+ * The "seal" and "open" operations may work in-place if the |out| and |in|
+ * arguments are equal. They may also be used to shift the data left inside the
+ * same buffer if |out| is less than |in|. However, |out| may not point inside
+ * the input data otherwise the input may be overwritten before it has been
+ * read. This situation will cause an error.
+ *
+ * The "seal" and "open" operations return one on success and zero on error. */
+
+
+/* AEAD algorithms. */
+
+/* EVP_aead_aes_128_gcm is AES-128 in Galois Counter Mode. */
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_aes_128_gcm(void);
+
+/* EVP_aead_aes_256_gcm is AES-256 in Galois Counter Mode. */
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_aes_256_gcm(void);
+
+/* EVP_aead_chacha20_poly1305 is the AEAD built from ChaCha20 and
+ * Poly1305 as described in RFC 7539. */
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_chacha20_poly1305(void);
+
+/* EVP_aead_chacha20_poly1305_old is an AEAD built from ChaCha20 and
+ * Poly1305 that is used in the experimental ChaCha20-Poly1305 TLS cipher
+ * suites. */
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_chacha20_poly1305_old(void);
+
+/* EVP_aead_aes_128_key_wrap is AES-128 Key Wrap mode. This should never be
+ * used except to interoperate with existing systems that use this mode.
+ *
+ * If the nonce is empty then the default nonce will be used, otherwise it must
+ * be eight bytes long. The input must be a multiple of eight bytes long. No
+ * additional data can be given to this mode. */
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_aes_128_key_wrap(void);
+
+/* EVP_aead_aes_256_key_wrap is AES-256 in Key Wrap mode. This should never be
+ * used except to interoperate with existing systems that use this mode.
+ *
+ * See |EVP_aead_aes_128_key_wrap| for details. */
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_aes_256_key_wrap(void);
+
+/* EVP_aead_aes_128_ctr_hmac_sha256 is AES-128 in CTR mode with HMAC-SHA256 for
+ * authentication. The nonce is 12 bytes; the bottom 32-bits are used as the
+ * block counter, thus the maximum plaintext size is 64GB. */
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_aes_128_ctr_hmac_sha256(void);
+
+/* EVP_aead_aes_256_ctr_hmac_sha256 is AES-256 in CTR mode with HMAC-SHA256 for
+ * authentication. See |EVP_aead_aes_128_ctr_hmac_sha256| for details. */
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_aes_256_ctr_hmac_sha256(void);
+
+/* EVP_has_aes_hardware returns one if we enable hardware support for fast and
+ * constant-time AES-GCM. */
+OPENSSL_EXPORT int EVP_has_aes_hardware(void);
+
+
+/* TLS-specific AEAD algorithms.
+ *
+ * These AEAD primitives do not meet the definition of generic AEADs. They are
+ * all specific to TLS and should not be used outside of that context. They must
+ * be initialized with |EVP_AEAD_CTX_init_with_direction|, are stateful, and may
+ * not be used concurrently. Any nonces are used as IVs, so they must be
+ * unpredictable. They only accept an |ad| parameter of length 11 (the standard
+ * TLS one with length omitted). */
+
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_rc4_md5_tls(void);
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_rc4_sha1_tls(void);
+
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_aes_128_cbc_sha1_tls(void);
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_aes_128_cbc_sha1_tls_implicit_iv(void);
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_aes_128_cbc_sha256_tls(void);
+
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_aes_256_cbc_sha1_tls(void);
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_aes_256_cbc_sha1_tls_implicit_iv(void);
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_aes_256_cbc_sha256_tls(void);
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_aes_256_cbc_sha384_tls(void);
+
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_des_ede3_cbc_sha1_tls(void);
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_des_ede3_cbc_sha1_tls_implicit_iv(void);
+
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_null_sha1_tls(void);
+
+
+/* SSLv3-specific AEAD algorithms.
+ *
+ * These AEAD primitives do not meet the definition of generic AEADs. They are
+ * all specific to SSLv3 and should not be used outside of that context. They
+ * must be initialized with |EVP_AEAD_CTX_init_with_direction|, are stateful,
+ * and may not be used concurrently. They only accept an |ad| parameter of
+ * length 9 (the standard TLS one with length and version omitted). */
+
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_rc4_md5_ssl3(void);
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_rc4_sha1_ssl3(void);
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_aes_128_cbc_sha1_ssl3(void);
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_aes_256_cbc_sha1_ssl3(void);
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_des_ede3_cbc_sha1_ssl3(void);
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_null_sha1_ssl3(void);
+
+
+/* Utility functions. */
+
+/* EVP_AEAD_key_length returns the length, in bytes, of the keys used by
+ * |aead|. */
+OPENSSL_EXPORT size_t EVP_AEAD_key_length(const EVP_AEAD *aead);
+
+/* EVP_AEAD_nonce_length returns the length, in bytes, of the per-message nonce
+ * for |aead|. */
+OPENSSL_EXPORT size_t EVP_AEAD_nonce_length(const EVP_AEAD *aead);
+
+/* EVP_AEAD_max_overhead returns the maximum number of additional bytes added
+ * by the act of sealing data with |aead|. */
+OPENSSL_EXPORT size_t EVP_AEAD_max_overhead(const EVP_AEAD *aead);
+
+/* EVP_AEAD_max_tag_len returns the maximum tag length when using |aead|. This
+ * is the largest value that can be passed as |tag_len| to
+ * |EVP_AEAD_CTX_init|. */
+OPENSSL_EXPORT size_t EVP_AEAD_max_tag_len(const EVP_AEAD *aead);
+
+
+/* AEAD operations. */
+
+/* An EVP_AEAD_CTX represents an AEAD algorithm configured with a specific key
+ * and message-independent IV. */
+typedef struct evp_aead_ctx_st {
+  const EVP_AEAD *aead;
+  /* aead_state is an opaque pointer to whatever state the AEAD needs to
+   * maintain. */
+  void *aead_state;
+} EVP_AEAD_CTX;
+
+/* EVP_AEAD_MAX_KEY_LENGTH contains the maximum key length used by
+ * any AEAD defined in this header. */
+#define EVP_AEAD_MAX_KEY_LENGTH 80
+
+/* EVP_AEAD_MAX_NONCE_LENGTH contains the maximum nonce length used by
+ * any AEAD defined in this header. */
+#define EVP_AEAD_MAX_NONCE_LENGTH 16
+
+/* EVP_AEAD_MAX_OVERHEAD contains the maximum overhead used by any AEAD
+ * defined in this header. */
+#define EVP_AEAD_MAX_OVERHEAD 64
+
+/* EVP_AEAD_DEFAULT_TAG_LENGTH is a magic value that can be passed to
+ * EVP_AEAD_CTX_init to indicate that the default tag length for an AEAD should
+ * be used. */
+#define EVP_AEAD_DEFAULT_TAG_LENGTH 0
+
+/* evp_aead_direction_t denotes the direction of an AEAD operation. */
+enum evp_aead_direction_t {
+  evp_aead_open,
+  evp_aead_seal,
+};
+
+/* EVP_AEAD_CTX_zero sets an uninitialized |ctx| to the zero state. It must be
+ * initialized with |EVP_AEAD_CTX_init| before use. It is safe, but not
+ * necessary, to call |EVP_AEAD_CTX_cleanup| in this state. This may be used for
+ * more uniform cleanup of |EVP_AEAD_CTX|. */
+OPENSSL_EXPORT void EVP_AEAD_CTX_zero(EVP_AEAD_CTX *ctx);
+
+/* EVP_AEAD_CTX_init initializes |ctx| for the given AEAD algorithm. The |impl|
+ * argument is ignored and should be NULL. Authentication tags may be truncated
+ * by passing a size as |tag_len|. A |tag_len| of zero indicates the default
+ * tag length and this is defined as EVP_AEAD_DEFAULT_TAG_LENGTH for
+ * readability.
+ *
+ * Returns 1 on success. Otherwise returns 0 and pushes to the error stack. In
+ * the error case, you do not need to call |EVP_AEAD_CTX_cleanup|, but it's
+ * harmless to do so. */
+OPENSSL_EXPORT int EVP_AEAD_CTX_init(EVP_AEAD_CTX *ctx, const EVP_AEAD *aead,
+                                     const uint8_t *key, size_t key_len,
+                                     size_t tag_len, ENGINE *impl);
+
+/* EVP_AEAD_CTX_init_with_direction calls |EVP_AEAD_CTX_init| for normal
+ * AEADs. For TLS-specific and SSL3-specific AEADs, it initializes |ctx| for a
+ * given direction. */
+OPENSSL_EXPORT int EVP_AEAD_CTX_init_with_direction(
+    EVP_AEAD_CTX *ctx, const EVP_AEAD *aead, const uint8_t *key, size_t key_len,
+    size_t tag_len, enum evp_aead_direction_t dir);
+
+/* EVP_AEAD_CTX_cleanup frees any data allocated by |ctx|. It is a no-op to
+ * call |EVP_AEAD_CTX_cleanup| on a |EVP_AEAD_CTX| that has been |memset| to
+ * all zeros. */
+OPENSSL_EXPORT void EVP_AEAD_CTX_cleanup(EVP_AEAD_CTX *ctx);
+
+/* EVP_AEAD_CTX_seal encrypts and authenticates |in_len| bytes from |in| and
+ * authenticates |ad_len| bytes from |ad| and writes the result to |out|. It
+ * returns one on success and zero otherwise.
+ *
+ * This function may be called (with the same |EVP_AEAD_CTX|) concurrently with
+ * itself or |EVP_AEAD_CTX_open|.
+ *
+ * At most |max_out_len| bytes are written to |out| and, in order to ensure
+ * success, |max_out_len| should be |in_len| plus the result of
+ * |EVP_AEAD_max_overhead|. On successful return, |*out_len| is set to the
+ * actual number of bytes written.
+ *
+ * The length of |nonce|, |nonce_len|, must be equal to the result of
+ * |EVP_AEAD_nonce_length| for this AEAD.
+ *
+ * |EVP_AEAD_CTX_seal| never results in a partial output. If |max_out_len| is
+ * insufficient, zero will be returned. (In this case, |*out_len| is set to
+ * zero.)
+ *
+ * If |in| and |out| alias then |out| must be <= |in|. */
+OPENSSL_EXPORT int EVP_AEAD_CTX_seal(const EVP_AEAD_CTX *ctx, uint8_t *out,
+                                     size_t *out_len, size_t max_out_len,
+                                     const uint8_t *nonce, size_t nonce_len,
+                                     const uint8_t *in, size_t in_len,
+                                     const uint8_t *ad, size_t ad_len);
+
+/* EVP_AEAD_CTX_open authenticates |in_len| bytes from |in| and |ad_len| bytes
+ * from |ad| and decrypts at most |in_len| bytes into |out|. It returns one on
+ * success and zero otherwise.
+ *
+ * This function may be called (with the same |EVP_AEAD_CTX|) concurrently with
+ * itself or |EVP_AEAD_CTX_seal|.
+ *
+ * At most |in_len| bytes are written to |out|. In order to ensure success,
+ * |max_out_len| should be at least |in_len|. On successful return, |*out_len|
+ * is set to the the actual number of bytes written.
+ *
+ * The length of |nonce|, |nonce_len|, must be equal to the result of
+ * |EVP_AEAD_nonce_length| for this AEAD.
+ *
+ * |EVP_AEAD_CTX_open| never results in a partial output. If |max_out_len| is
+ * insufficient, zero will be returned. (In this case, |*out_len| is set to
+ * zero.)
+ *
+ * If |in| and |out| alias then |out| must be <= |in|. */
+OPENSSL_EXPORT int EVP_AEAD_CTX_open(const EVP_AEAD_CTX *ctx, uint8_t *out,
+                                     size_t *out_len, size_t max_out_len,
+                                     const uint8_t *nonce, size_t nonce_len,
+                                     const uint8_t *in, size_t in_len,
+                                     const uint8_t *ad, size_t ad_len);
+
+
+/* Obscure functions. */
+
+/* EVP_AEAD_CTX_get_rc4_state sets |*out_key| to point to an RC4 key structure.
+ * It returns one on success or zero if |ctx| doesn't have an RC4 key. */
+OPENSSL_EXPORT int EVP_AEAD_CTX_get_rc4_state(const EVP_AEAD_CTX *ctx,
+                                              const RC4_KEY **out_key);
+
+/* EVP_AEAD_CTX_get_iv sets |*out_len| to the length of the IV for |ctx| and
+ * sets |*out_iv| to point to that many bytes of the current IV. This is only
+ * meaningful for AEADs with implicit IVs (i.e. CBC mode in SSLv3 and TLS 1.0).
+ *
+ * It returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_AEAD_CTX_get_iv(const EVP_AEAD_CTX *ctx,
+                                       const uint8_t **out_iv, size_t *out_len);
+
+
+/* Deprecated functions. */
+
+/* EVP_aead_chacha20_poly1305_rfc7539 calls |EVP_aead_chacha20_poly1305|.
+ *
+ * TODO(davidben): Remove this. */
+OPENSSL_EXPORT const EVP_AEAD *EVP_aead_chacha20_poly1305_rfc7539(void);
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_AEAD_H */

+ 158 - 0
app/src/main/jni/openssl/include/openssl/aes.h

@@ -0,0 +1,158 @@
+/* ====================================================================
+ * Copyright (c) 2002-2006 The OpenSSL Project.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer. 
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. All advertising materials mentioning features or use of this
+ *    software must display the following acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
+ *
+ * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
+ *    endorse or promote products derived from this software without
+ *    prior written permission. For written permission, please contact
+ *    openssl-core@openssl.org.
+ *
+ * 5. Products derived from this software may not be called "OpenSSL"
+ *    nor may "OpenSSL" appear in their names without prior written
+ *    permission of the OpenSSL Project.
+ *
+ * 6. Redistributions of any form whatsoever must retain the following
+ *    acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
+ * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ==================================================================== */
+
+#ifndef OPENSSL_HEADER_AES_H
+#define OPENSSL_HEADER_AES_H
+
+#include <openssl/base.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* Raw AES functions. */
+
+
+#define AES_ENCRYPT 1
+#define AES_DECRYPT 0
+
+/* AES_MAXNR is the maximum number of AES rounds. */
+#define AES_MAXNR 14
+
+#define AES_BLOCK_SIZE 16
+
+/* aes_key_st should be an opaque type, but EVP requires that the size be
+ * known. */
+struct aes_key_st {
+  uint32_t rd_key[4 * (AES_MAXNR + 1)];
+  unsigned rounds;
+};
+typedef struct aes_key_st AES_KEY;
+
+/* AES_set_encrypt_key configures |aeskey| to encrypt with the |bits|-bit key,
+ * |key|.
+ *
+ * WARNING: unlike other OpenSSL functions, this returns zero on success and a
+ * negative number on error. */
+OPENSSL_EXPORT int AES_set_encrypt_key(const uint8_t *key, unsigned bits,
+                                       AES_KEY *aeskey);
+
+/* AES_set_decrypt_key configures |aeskey| to decrypt with the |bits|-bit key,
+ * |key|.
+ *
+ * WARNING: unlike other OpenSSL functions, this returns zero on success and a
+ * negative number on error. */
+OPENSSL_EXPORT int AES_set_decrypt_key(const uint8_t *key, unsigned bits,
+                                       AES_KEY *aeskey);
+
+/* AES_encrypt encrypts a single block from |in| to |out| with |key|. The |in|
+ * and |out| pointers may overlap. */
+OPENSSL_EXPORT void AES_encrypt(const uint8_t *in, uint8_t *out,
+                                const AES_KEY *key);
+
+/* AES_decrypt decrypts a single block from |in| to |out| with |key|. The |in|
+ * and |out| pointers may overlap. */
+OPENSSL_EXPORT void AES_decrypt(const uint8_t *in, uint8_t *out,
+                                const AES_KEY *key);
+
+
+/* Block cipher modes. */
+
+/* AES_ctr128_encrypt encrypts (or decrypts, it's the same in CTR mode) |len|
+ * bytes from |in| to |out|. The |num| parameter must be set to zero on the
+ * first call and |ivec| will be incremented. */
+OPENSSL_EXPORT void AES_ctr128_encrypt(const uint8_t *in, uint8_t *out,
+                                       size_t len, const AES_KEY *key,
+                                       uint8_t ivec[AES_BLOCK_SIZE],
+                                       uint8_t ecount_buf[AES_BLOCK_SIZE],
+                                       unsigned int *num);
+
+/* AES_ecb_encrypt encrypts (or decrypts, if |enc| == |AES_DECRYPT|) a single,
+ * 16 byte block from |in| to |out|. */
+OPENSSL_EXPORT void AES_ecb_encrypt(const uint8_t *in, uint8_t *out,
+                                    const AES_KEY *key, const int enc);
+
+/* AES_cbc_encrypt encrypts (or decrypts, if |enc| == |AES_DECRYPT|) |len|
+ * bytes from |in| to |out|. The length must be a multiple of the block size. */
+OPENSSL_EXPORT void AES_cbc_encrypt(const uint8_t *in, uint8_t *out, size_t len,
+                                    const AES_KEY *key, uint8_t *ivec,
+                                    const int enc);
+
+/* AES_ofb128_encrypt encrypts (or decrypts, it's the same in OFB mode) |len|
+ * bytes from |in| to |out|. The |num| parameter must be set to zero on the
+ * first call. */
+OPENSSL_EXPORT void AES_ofb128_encrypt(const uint8_t *in, uint8_t *out,
+                                       size_t len, const AES_KEY *key,
+                                       uint8_t *ivec, int *num);
+
+/* AES_cfb128_encrypt encrypts (or decrypts, if |enc| == |AES_DECRYPT|) |len|
+ * bytes from |in| to |out|. The |num| parameter must be set to zero on the
+ * first call. */
+OPENSSL_EXPORT void AES_cfb128_encrypt(const uint8_t *in, uint8_t *out,
+                                       size_t len, const AES_KEY *key,
+                                       uint8_t *ivec, int *num, int enc);
+
+
+/* Android compatibility section.
+ *
+ * These functions are declared, temporarily, for Android because
+ * wpa_supplicant will take a little time to sync with upstream. Outside of
+ * Android they'll have no definition. */
+
+OPENSSL_EXPORT int AES_wrap_key(AES_KEY *key, const uint8_t *iv, uint8_t *out,
+                                const uint8_t *in, unsigned in_len);
+OPENSSL_EXPORT int AES_unwrap_key(AES_KEY *key, const uint8_t *iv, uint8_t *out,
+                                  const uint8_t *in, unsigned in_len);
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_AES_H */

+ 127 - 0
app/src/main/jni/openssl/include/openssl/arm_arch.h

@@ -0,0 +1,127 @@
+/* ====================================================================
+ * Copyright (c) 1998-2011 The OpenSSL Project.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. All advertising materials mentioning features or use of this
+ *    software must display the following acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
+ *
+ * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
+ *    endorse or promote products derived from this software without
+ *    prior written permission. For written permission, please contact
+ *    openssl-core@openssl.org.
+ *
+ * 5. Products derived from this software may not be called "OpenSSL"
+ *    nor may "OpenSSL" appear in their names without prior written
+ *    permission of the OpenSSL Project.
+ *
+ * 6. Redistributions of any form whatsoever must retain the following
+ *    acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
+ * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This product includes cryptographic software written by Eric Young
+ * (eay@cryptsoft.com).  This product includes software written by Tim
+ * Hudson (tjh@cryptsoft.com). */
+
+#ifndef OPENSSL_HEADER_ARM_ARCH_H
+#define OPENSSL_HEADER_ARM_ARCH_H
+
+#if !defined(__ARM_ARCH__)
+# if defined(__CC_ARM)
+#  define __ARM_ARCH__ __TARGET_ARCH_ARM
+#  if defined(__BIG_ENDIAN)
+#   define __ARMEB__
+#  else
+#   define __ARMEL__
+#  endif
+# elif defined(__GNUC__)
+#  if defined(__aarch64__)
+#    define __ARM_ARCH__ 8
+#    if __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__
+#      define __ARMEB__
+#    else
+#      define __ARMEL__
+#    endif
+  /* Why doesn't gcc define __ARM_ARCH__? Instead it defines
+   * bunch of below macros. See all_architectires[] table in
+   * gcc/config/arm/arm.c. On a side note it defines
+   * __ARMEL__/__ARMEB__ for little-/big-endian. */
+#  elif	defined(__ARM_ARCH)
+#    define __ARM_ARCH__ __ARM_ARCH
+#  elif	defined(__ARM_ARCH_8A__)
+#    define __ARM_ARCH__ 8
+#  elif	defined(__ARM_ARCH_7__)	|| defined(__ARM_ARCH_7A__)	|| \
+	defined(__ARM_ARCH_7R__)|| defined(__ARM_ARCH_7M__)	|| \
+	defined(__ARM_ARCH_7EM__)
+#   define __ARM_ARCH__ 7
+#  elif	defined(__ARM_ARCH_6__)	|| defined(__ARM_ARCH_6J__)	|| \
+	defined(__ARM_ARCH_6K__)|| defined(__ARM_ARCH_6M__)	|| \
+	defined(__ARM_ARCH_6Z__)|| defined(__ARM_ARCH_6ZK__)	|| \
+	defined(__ARM_ARCH_6T2__)
+#   define __ARM_ARCH__ 6
+#  elif	defined(__ARM_ARCH_5__)	|| defined(__ARM_ARCH_5T__)	|| \
+	defined(__ARM_ARCH_5E__)|| defined(__ARM_ARCH_5TE__)	|| \
+	defined(__ARM_ARCH_5TEJ__)
+#   define __ARM_ARCH__ 5
+#  elif	defined(__ARM_ARCH_4__)	|| defined(__ARM_ARCH_4T__)
+#   define __ARM_ARCH__ 4
+#  else
+#   error "unsupported ARM architecture"
+#  endif
+# endif
+#endif
+
+/* Even when building for 32-bit ARM, support for aarch64 crypto instructions
+ * will be included. */
+#define __ARM_MAX_ARCH__ 8
+
+/* ARMV7_NEON is true when a NEON unit is present in the current CPU. */
+#define ARMV7_NEON (1 << 0)
+
+/* ARMV7_NEON_FUNCTIONAL is true when the NEON unit doesn't contain subtle bugs.
+ * The Poly1305 NEON code is known to trigger bugs in the NEON units of some
+ * phones. If this bit isn't set then the Poly1305 NEON code won't be used.
+ * See https://code.google.com/p/chromium/issues/detail?id=341598. */
+#define ARMV7_NEON_FUNCTIONAL (1 << 10)
+
+/* ARMV8_AES indicates support for hardware AES instructions. */
+#define ARMV8_AES (1 << 2)
+
+/* ARMV8_SHA1 indicates support for hardware SHA-1 instructions. */
+#define ARMV8_SHA1 (1 << 3)
+
+/* ARMV8_SHA256 indicates support for hardware SHA-256 instructions. */
+#define ARMV8_SHA256 (1 << 4)
+
+/* ARMV8_PMULL indicates support for carryless multiplication. */
+#define ARMV8_PMULL (1 << 5)
+
+
+#endif  /* OPENSSL_HEADER_ARM_ARCH_H */

File diff suppressed because it is too large
+ 1167 - 0
app/src/main/jni/openssl/include/openssl/asn1.h


+ 75 - 0
app/src/main/jni/openssl/include/openssl/asn1_mac.h

@@ -0,0 +1,75 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ * 
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ * 
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ * 
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from 
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ * 
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ * 
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.]
+ */
+
+#ifndef HEADER_ASN1_MAC_H
+#define HEADER_ASN1_MAC_H
+
+#include <openssl/asn1.h>
+
+#ifdef  __cplusplus
+extern "C" {
+#endif
+
+
+OPENSSL_EXPORT int asn1_GetSequence(ASN1_const_CTX *c, long *length);
+
+
+#ifdef  __cplusplus
+}
+#endif
+
+#endif

+ 906 - 0
app/src/main/jni/openssl/include/openssl/asn1t.h

@@ -0,0 +1,906 @@
+/* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
+ * project 2000.
+ */
+/* ====================================================================
+ * Copyright (c) 2000-2005 The OpenSSL Project.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer. 
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. All advertising materials mentioning features or use of this
+ *    software must display the following acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
+ *
+ * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
+ *    endorse or promote products derived from this software without
+ *    prior written permission. For written permission, please contact
+ *    licensing@OpenSSL.org.
+ *
+ * 5. Products derived from this software may not be called "OpenSSL"
+ *    nor may "OpenSSL" appear in their names without prior written
+ *    permission of the OpenSSL Project.
+ *
+ * 6. Redistributions of any form whatsoever must retain the following
+ *    acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
+ * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This product includes cryptographic software written by Eric Young
+ * (eay@cryptsoft.com).  This product includes software written by Tim
+ * Hudson (tjh@cryptsoft.com).
+ *
+ */
+#ifndef HEADER_ASN1T_H
+#define HEADER_ASN1T_H
+
+#include <openssl/base.h>
+#include <openssl/asn1.h>
+
+#ifdef OPENSSL_BUILD_SHLIBCRYPTO
+# undef OPENSSL_EXTERN
+# define OPENSSL_EXTERN OPENSSL_EXPORT
+#endif
+
+/* ASN1 template defines, structures and functions */
+
+#ifdef  __cplusplus
+extern "C" {
+#endif
+
+
+/* Macro to obtain ASN1_ADB pointer from a type (only used internally) */
+#define ASN1_ADB_ptr(iptr) ((const ASN1_ADB *)(iptr))
+
+
+/* Macros for start and end of ASN1_ITEM definition */
+
+#define ASN1_ITEM_start(itname) \
+	const ASN1_ITEM itname##_it = {
+
+#define ASN1_ITEM_end(itname) \
+		};
+
+/* Macros to aid ASN1 template writing */
+
+#define ASN1_ITEM_TEMPLATE(tname) \
+	static const ASN1_TEMPLATE tname##_item_tt 
+
+#define ASN1_ITEM_TEMPLATE_END(tname) \
+	;\
+	ASN1_ITEM_start(tname) \
+		ASN1_ITYPE_PRIMITIVE,\
+		-1,\
+		&tname##_item_tt,\
+		0,\
+		NULL,\
+		0,\
+		#tname \
+	ASN1_ITEM_end(tname)
+
+
+/* This is a ASN1 type which just embeds a template */
+ 
+/* This pair helps declare a SEQUENCE. We can do:
+ *
+ * 	ASN1_SEQUENCE(stname) = {
+ * 		... SEQUENCE components ...
+ * 	} ASN1_SEQUENCE_END(stname)
+ *
+ * 	This will produce an ASN1_ITEM called stname_it
+ *	for a structure called stname.
+ *
+ * 	If you want the same structure but a different
+ *	name then use:
+ *
+ * 	ASN1_SEQUENCE(itname) = {
+ * 		... SEQUENCE components ...
+ * 	} ASN1_SEQUENCE_END_name(stname, itname)
+ *
+ *	This will create an item called itname_it using
+ *	a structure called stname.
+ */
+
+#define ASN1_SEQUENCE(tname) \
+	static const ASN1_TEMPLATE tname##_seq_tt[] 
+
+#define ASN1_SEQUENCE_END(stname) ASN1_SEQUENCE_END_name(stname, stname)
+
+#define ASN1_SEQUENCE_END_name(stname, tname) \
+	;\
+	ASN1_ITEM_start(tname) \
+		ASN1_ITYPE_SEQUENCE,\
+		V_ASN1_SEQUENCE,\
+		tname##_seq_tt,\
+		sizeof(tname##_seq_tt) / sizeof(ASN1_TEMPLATE),\
+		NULL,\
+		sizeof(stname),\
+		#stname \
+	ASN1_ITEM_end(tname)
+
+#define ASN1_NDEF_SEQUENCE(tname) \
+	ASN1_SEQUENCE(tname)
+
+#define ASN1_NDEF_SEQUENCE_cb(tname, cb) \
+	ASN1_SEQUENCE_cb(tname, cb)
+
+#define ASN1_SEQUENCE_cb(tname, cb) \
+	static const ASN1_AUX tname##_aux = {NULL, 0, 0, cb, 0}; \
+	ASN1_SEQUENCE(tname)
+
+#define ASN1_BROKEN_SEQUENCE(tname) \
+	static const ASN1_AUX tname##_aux = {NULL, ASN1_AFLG_BROKEN, 0, 0, 0}; \
+	ASN1_SEQUENCE(tname)
+
+#define ASN1_SEQUENCE_ref(tname, cb) \
+	static const ASN1_AUX tname##_aux = {NULL, ASN1_AFLG_REFCOUNT, offsetof(tname, references), cb, 0}; \
+	ASN1_SEQUENCE(tname)
+
+#define ASN1_SEQUENCE_enc(tname, enc, cb) \
+	static const ASN1_AUX tname##_aux = {NULL, ASN1_AFLG_ENCODING, 0, cb, offsetof(tname, enc)}; \
+	ASN1_SEQUENCE(tname)
+
+#define ASN1_NDEF_SEQUENCE_END(tname) \
+	;\
+	ASN1_ITEM_start(tname) \
+		ASN1_ITYPE_NDEF_SEQUENCE,\
+		V_ASN1_SEQUENCE,\
+		tname##_seq_tt,\
+		sizeof(tname##_seq_tt) / sizeof(ASN1_TEMPLATE),\
+		NULL,\
+		sizeof(tname),\
+		#tname \
+	ASN1_ITEM_end(tname)
+
+#define ASN1_BROKEN_SEQUENCE_END(stname) ASN1_SEQUENCE_END_ref(stname, stname)
+
+#define ASN1_SEQUENCE_END_enc(stname, tname) ASN1_SEQUENCE_END_ref(stname, tname)
+
+#define ASN1_SEQUENCE_END_cb(stname, tname) ASN1_SEQUENCE_END_ref(stname, tname)
+
+#define ASN1_SEQUENCE_END_ref(stname, tname) \
+	;\
+	ASN1_ITEM_start(tname) \
+		ASN1_ITYPE_SEQUENCE,\
+		V_ASN1_SEQUENCE,\
+		tname##_seq_tt,\
+		sizeof(tname##_seq_tt) / sizeof(ASN1_TEMPLATE),\
+		&tname##_aux,\
+		sizeof(stname),\
+		#stname \
+	ASN1_ITEM_end(tname)
+
+#define ASN1_NDEF_SEQUENCE_END_cb(stname, tname) \
+	;\
+	ASN1_ITEM_start(tname) \
+		ASN1_ITYPE_NDEF_SEQUENCE,\
+		V_ASN1_SEQUENCE,\
+		tname##_seq_tt,\
+		sizeof(tname##_seq_tt) / sizeof(ASN1_TEMPLATE),\
+		&tname##_aux,\
+		sizeof(stname),\
+		#stname \
+	ASN1_ITEM_end(tname)
+
+
+/* This pair helps declare a CHOICE type. We can do:
+ *
+ * 	ASN1_CHOICE(chname) = {
+ * 		... CHOICE options ...
+ * 	ASN1_CHOICE_END(chname)
+ *
+ * 	This will produce an ASN1_ITEM called chname_it
+ *	for a structure called chname. The structure
+ *	definition must look like this:
+ *	typedef struct {
+ *		int type;
+ *		union {
+ *			ASN1_SOMETHING *opt1;
+ *			ASN1_SOMEOTHER *opt2;
+ *		} value;
+ *	} chname;
+ *	
+ *	the name of the selector must be 'type'.
+ * 	to use an alternative selector name use the
+ *      ASN1_CHOICE_END_selector() version.
+ */
+
+#define ASN1_CHOICE(tname) \
+	static const ASN1_TEMPLATE tname##_ch_tt[] 
+
+#define ASN1_CHOICE_cb(tname, cb) \
+	static const ASN1_AUX tname##_aux = {NULL, 0, 0, cb, 0}; \
+	ASN1_CHOICE(tname)
+
+#define ASN1_CHOICE_END(stname) ASN1_CHOICE_END_name(stname, stname)
+
+#define ASN1_CHOICE_END_name(stname, tname) ASN1_CHOICE_END_selector(stname, tname, type)
+
+#define ASN1_CHOICE_END_selector(stname, tname, selname) \
+	;\
+	ASN1_ITEM_start(tname) \
+		ASN1_ITYPE_CHOICE,\
+		offsetof(stname,selname) ,\
+		tname##_ch_tt,\
+		sizeof(tname##_ch_tt) / sizeof(ASN1_TEMPLATE),\
+		NULL,\
+		sizeof(stname),\
+		#stname \
+	ASN1_ITEM_end(tname)
+
+#define ASN1_CHOICE_END_cb(stname, tname, selname) \
+	;\
+	ASN1_ITEM_start(tname) \
+		ASN1_ITYPE_CHOICE,\
+		offsetof(stname,selname) ,\
+		tname##_ch_tt,\
+		sizeof(tname##_ch_tt) / sizeof(ASN1_TEMPLATE),\
+		&tname##_aux,\
+		sizeof(stname),\
+		#stname \
+	ASN1_ITEM_end(tname)
+
+/* This helps with the template wrapper form of ASN1_ITEM */
+
+#define ASN1_EX_TEMPLATE_TYPE(flags, tag, name, type) { \
+	(flags), (tag), 0,\
+	#name, ASN1_ITEM_ref(type) }
+
+/* These help with SEQUENCE or CHOICE components */
+
+/* used to declare other types */
+
+#define ASN1_EX_TYPE(flags, tag, stname, field, type) { \
+	(flags), (tag), offsetof(stname, field),\
+	#field, ASN1_ITEM_ref(type) }
+
+/* used when the structure is combined with the parent */
+
+#define ASN1_EX_COMBINE(flags, tag, type) { \
+	(flags)|ASN1_TFLG_COMBINE, (tag), 0, NULL, ASN1_ITEM_ref(type) }
+
+/* implicit and explicit helper macros */
+
+#define ASN1_IMP_EX(stname, field, type, tag, ex) \
+		ASN1_EX_TYPE(ASN1_TFLG_IMPLICIT | ex, tag, stname, field, type)
+
+#define ASN1_EXP_EX(stname, field, type, tag, ex) \
+		ASN1_EX_TYPE(ASN1_TFLG_EXPLICIT | ex, tag, stname, field, type)
+
+/* Any defined by macros: the field used is in the table itself */
+
+#define ASN1_ADB_OBJECT(tblname) { ASN1_TFLG_ADB_OID, -1, 0, #tblname, (const ASN1_ITEM *)&(tblname##_adb) }
+#define ASN1_ADB_INTEGER(tblname) { ASN1_TFLG_ADB_INT, -1, 0, #tblname, (const ASN1_ITEM *)&(tblname##_adb) }
+/* Plain simple type */
+#define ASN1_SIMPLE(stname, field, type) ASN1_EX_TYPE(0,0, stname, field, type)
+
+/* OPTIONAL simple type */
+#define ASN1_OPT(stname, field, type) ASN1_EX_TYPE(ASN1_TFLG_OPTIONAL, 0, stname, field, type)
+
+/* IMPLICIT tagged simple type */
+#define ASN1_IMP(stname, field, type, tag) ASN1_IMP_EX(stname, field, type, tag, 0)
+
+/* IMPLICIT tagged OPTIONAL simple type */
+#define ASN1_IMP_OPT(stname, field, type, tag) ASN1_IMP_EX(stname, field, type, tag, ASN1_TFLG_OPTIONAL)
+
+/* Same as above but EXPLICIT */
+
+#define ASN1_EXP(stname, field, type, tag) ASN1_EXP_EX(stname, field, type, tag, 0)
+#define ASN1_EXP_OPT(stname, field, type, tag) ASN1_EXP_EX(stname, field, type, tag, ASN1_TFLG_OPTIONAL)
+
+/* SEQUENCE OF type */
+#define ASN1_SEQUENCE_OF(stname, field, type) \
+		ASN1_EX_TYPE(ASN1_TFLG_SEQUENCE_OF, 0, stname, field, type)
+
+/* OPTIONAL SEQUENCE OF */
+#define ASN1_SEQUENCE_OF_OPT(stname, field, type) \
+		ASN1_EX_TYPE(ASN1_TFLG_SEQUENCE_OF|ASN1_TFLG_OPTIONAL, 0, stname, field, type)
+
+/* Same as above but for SET OF */
+
+#define ASN1_SET_OF(stname, field, type) \
+		ASN1_EX_TYPE(ASN1_TFLG_SET_OF, 0, stname, field, type)
+
+#define ASN1_SET_OF_OPT(stname, field, type) \
+		ASN1_EX_TYPE(ASN1_TFLG_SET_OF|ASN1_TFLG_OPTIONAL, 0, stname, field, type)
+
+/* Finally compound types of SEQUENCE, SET, IMPLICIT, EXPLICIT and OPTIONAL */
+
+#define ASN1_IMP_SET_OF(stname, field, type, tag) \
+			ASN1_IMP_EX(stname, field, type, tag, ASN1_TFLG_SET_OF)
+
+#define ASN1_EXP_SET_OF(stname, field, type, tag) \
+			ASN1_EXP_EX(stname, field, type, tag, ASN1_TFLG_SET_OF)
+
+#define ASN1_IMP_SET_OF_OPT(stname, field, type, tag) \
+			ASN1_IMP_EX(stname, field, type, tag, ASN1_TFLG_SET_OF|ASN1_TFLG_OPTIONAL)
+
+#define ASN1_EXP_SET_OF_OPT(stname, field, type, tag) \
+			ASN1_EXP_EX(stname, field, type, tag, ASN1_TFLG_SET_OF|ASN1_TFLG_OPTIONAL)
+
+#define ASN1_IMP_SEQUENCE_OF(stname, field, type, tag) \
+			ASN1_IMP_EX(stname, field, type, tag, ASN1_TFLG_SEQUENCE_OF)
+
+#define ASN1_IMP_SEQUENCE_OF_OPT(stname, field, type, tag) \
+			ASN1_IMP_EX(stname, field, type, tag, ASN1_TFLG_SEQUENCE_OF|ASN1_TFLG_OPTIONAL)
+
+#define ASN1_EXP_SEQUENCE_OF(stname, field, type, tag) \
+			ASN1_EXP_EX(stname, field, type, tag, ASN1_TFLG_SEQUENCE_OF)
+
+#define ASN1_EXP_SEQUENCE_OF_OPT(stname, field, type, tag) \
+			ASN1_EXP_EX(stname, field, type, tag, ASN1_TFLG_SEQUENCE_OF|ASN1_TFLG_OPTIONAL)
+
+/* EXPLICIT using indefinite length constructed form */
+#define ASN1_NDEF_EXP(stname, field, type, tag) \
+			ASN1_EXP_EX(stname, field, type, tag, ASN1_TFLG_NDEF)
+
+/* EXPLICIT OPTIONAL using indefinite length constructed form */
+#define ASN1_NDEF_EXP_OPT(stname, field, type, tag) \
+			ASN1_EXP_EX(stname, field, type, tag, ASN1_TFLG_OPTIONAL|ASN1_TFLG_NDEF)
+
+/* Macros for the ASN1_ADB structure */
+
+#define ASN1_ADB(name) \
+	static const ASN1_ADB_TABLE name##_adbtbl[] 
+
+#define ASN1_ADB_END(name, flags, field, app_table, def, none) \
+	;\
+	static const ASN1_ADB name##_adb = {\
+		flags,\
+		offsetof(name, field),\
+		app_table,\
+		name##_adbtbl,\
+		sizeof(name##_adbtbl) / sizeof(ASN1_ADB_TABLE),\
+		def,\
+		none\
+	}
+
+#define ADB_ENTRY(val, template) {val, template}
+
+#define ASN1_ADB_TEMPLATE(name) \
+	static const ASN1_TEMPLATE name##_tt 
+
+/* This is the ASN1 template structure that defines
+ * a wrapper round the actual type. It determines the
+ * actual position of the field in the value structure,
+ * various flags such as OPTIONAL and the field name.
+ */
+
+struct ASN1_TEMPLATE_st {
+unsigned long flags;		/* Various flags */
+long tag;			/* tag, not used if no tagging */
+unsigned long offset;		/* Offset of this field in structure */
+#ifndef NO_ASN1_FIELD_NAMES
+const char *field_name;		/* Field name */
+#endif
+ASN1_ITEM_EXP *item;		/* Relevant ASN1_ITEM or ASN1_ADB */
+};
+
+/* Macro to extract ASN1_ITEM and ASN1_ADB pointer from ASN1_TEMPLATE */
+
+#define ASN1_TEMPLATE_item(t) (t->item_ptr)
+#define ASN1_TEMPLATE_adb(t) (t->item_ptr)
+
+typedef struct ASN1_ADB_TABLE_st ASN1_ADB_TABLE;
+typedef struct ASN1_ADB_st ASN1_ADB;
+
+struct ASN1_ADB_st {
+	unsigned long flags;	/* Various flags */
+	unsigned long offset;	/* Offset of selector field */
+	STACK_OF(ASN1_ADB_TABLE) **app_items; /* Application defined items */
+	const ASN1_ADB_TABLE *tbl;	/* Table of possible types */
+	long tblcount;		/* Number of entries in tbl */
+	const ASN1_TEMPLATE *default_tt;  /* Type to use if no match */
+	const ASN1_TEMPLATE *null_tt;  /* Type to use if selector is NULL */
+};
+
+struct ASN1_ADB_TABLE_st {
+	long value;		/* NID for an object or value for an int */
+	const ASN1_TEMPLATE tt;		/* item for this value */
+};
+
+/* template flags */
+
+/* Field is optional */
+#define ASN1_TFLG_OPTIONAL	(0x1)
+
+/* Field is a SET OF */
+#define ASN1_TFLG_SET_OF	(0x1 << 1)
+
+/* Field is a SEQUENCE OF */
+#define ASN1_TFLG_SEQUENCE_OF	(0x2 << 1)
+
+/* Special case: this refers to a SET OF that
+ * will be sorted into DER order when encoded *and*
+ * the corresponding STACK will be modified to match
+ * the new order.
+ */
+#define ASN1_TFLG_SET_ORDER	(0x3 << 1)
+
+/* Mask for SET OF or SEQUENCE OF */
+#define ASN1_TFLG_SK_MASK	(0x3 << 1)
+
+/* These flags mean the tag should be taken from the
+ * tag field. If EXPLICIT then the underlying type
+ * is used for the inner tag.
+ */
+
+/* IMPLICIT tagging */
+#define ASN1_TFLG_IMPTAG	(0x1 << 3)
+
+
+/* EXPLICIT tagging, inner tag from underlying type */
+#define ASN1_TFLG_EXPTAG	(0x2 << 3)
+
+#define ASN1_TFLG_TAG_MASK	(0x3 << 3)
+
+/* context specific IMPLICIT */
+#define ASN1_TFLG_IMPLICIT	ASN1_TFLG_IMPTAG|ASN1_TFLG_CONTEXT
+
+/* context specific EXPLICIT */
+#define ASN1_TFLG_EXPLICIT	ASN1_TFLG_EXPTAG|ASN1_TFLG_CONTEXT
+
+/* If tagging is in force these determine the
+ * type of tag to use. Otherwise the tag is
+ * determined by the underlying type. These 
+ * values reflect the actual octet format.
+ */
+
+/* Universal tag */ 
+#define ASN1_TFLG_UNIVERSAL	(0x0<<6)
+/* Application tag */ 
+#define ASN1_TFLG_APPLICATION	(0x1<<6)
+/* Context specific tag */ 
+#define ASN1_TFLG_CONTEXT	(0x2<<6)
+/* Private tag */ 
+#define ASN1_TFLG_PRIVATE	(0x3<<6)
+
+#define ASN1_TFLG_TAG_CLASS	(0x3<<6)
+
+/* These are for ANY DEFINED BY type. In this case
+ * the 'item' field points to an ASN1_ADB structure
+ * which contains a table of values to decode the
+ * relevant type
+ */
+
+#define ASN1_TFLG_ADB_MASK	(0x3<<8)
+
+#define ASN1_TFLG_ADB_OID	(0x1<<8)
+
+#define ASN1_TFLG_ADB_INT	(0x1<<9)
+
+/* This flag means a parent structure is passed
+ * instead of the field: this is useful is a
+ * SEQUENCE is being combined with a CHOICE for
+ * example. Since this means the structure and
+ * item name will differ we need to use the
+ * ASN1_CHOICE_END_name() macro for example.
+ */
+
+#define ASN1_TFLG_COMBINE	(0x1<<10)
+
+/* This flag when present in a SEQUENCE OF, SET OF
+ * or EXPLICIT causes indefinite length constructed
+ * encoding to be used if required.
+ */
+
+#define ASN1_TFLG_NDEF		(0x1<<11)
+
+/* This is the actual ASN1 item itself */
+
+struct ASN1_ITEM_st {
+char itype;			/* The item type, primitive, SEQUENCE, CHOICE or extern */
+long utype;			/* underlying type */
+const ASN1_TEMPLATE *templates;	/* If SEQUENCE or CHOICE this contains the contents */
+long tcount;			/* Number of templates if SEQUENCE or CHOICE */
+const void *funcs;		/* functions that handle this type */
+long size;			/* Structure size (usually)*/
+#ifndef NO_ASN1_FIELD_NAMES
+const char *sname;		/* Structure name */
+#endif
+};
+
+/* These are values for the itype field and
+ * determine how the type is interpreted.
+ *
+ * For PRIMITIVE types the underlying type
+ * determines the behaviour if items is NULL.
+ *
+ * Otherwise templates must contain a single 
+ * template and the type is treated in the
+ * same way as the type specified in the template.
+ *
+ * For SEQUENCE types the templates field points
+ * to the members, the size field is the
+ * structure size.
+ *
+ * For CHOICE types the templates field points
+ * to each possible member (typically a union)
+ * and the 'size' field is the offset of the
+ * selector.
+ *
+ * The 'funcs' field is used for application
+ * specific functions. 
+ *
+ * For COMPAT types the funcs field gives a
+ * set of functions that handle this type, this
+ * supports the old d2i, i2d convention.
+ *
+ * The EXTERN type uses a new style d2i/i2d.
+ * The new style should be used where possible
+ * because it avoids things like the d2i IMPLICIT
+ * hack.
+ *
+ * MSTRING is a multiple string type, it is used
+ * for a CHOICE of character strings where the
+ * actual strings all occupy an ASN1_STRING
+ * structure. In this case the 'utype' field
+ * has a special meaning, it is used as a mask
+ * of acceptable types using the B_ASN1 constants.
+ *
+ * NDEF_SEQUENCE is the same as SEQUENCE except
+ * that it will use indefinite length constructed
+ * encoding if requested.
+ *
+ */
+
+#define ASN1_ITYPE_PRIMITIVE		0x0
+
+#define ASN1_ITYPE_SEQUENCE		0x1
+
+#define ASN1_ITYPE_CHOICE		0x2
+
+#define ASN1_ITYPE_COMPAT		0x3
+
+#define ASN1_ITYPE_EXTERN		0x4
+
+#define ASN1_ITYPE_MSTRING		0x5
+
+#define ASN1_ITYPE_NDEF_SEQUENCE	0x6
+
+/* Cache for ASN1 tag and length, so we
+ * don't keep re-reading it for things
+ * like CHOICE
+ */
+
+struct ASN1_TLC_st{
+	char valid;	/* Values below are valid */
+	int ret;	/* return value */
+	long plen;	/* length */
+	int ptag;	/* class value */
+	int pclass;	/* class value */
+	int hdrlen;	/* header length */
+};
+
+/* Typedefs for ASN1 function pointers */
+
+typedef ASN1_VALUE * ASN1_new_func(void);
+typedef void ASN1_free_func(ASN1_VALUE *a);
+typedef ASN1_VALUE * ASN1_d2i_func(ASN1_VALUE **a, const unsigned char ** in, long length);
+typedef int ASN1_i2d_func(ASN1_VALUE * a, unsigned char **in);
+
+typedef int ASN1_ex_d2i(ASN1_VALUE **pval, const unsigned char **in, long len, const ASN1_ITEM *it,
+					int tag, int aclass, char opt, ASN1_TLC *ctx);
+
+typedef int ASN1_ex_i2d(ASN1_VALUE **pval, unsigned char **out, const ASN1_ITEM *it, int tag, int aclass);
+typedef int ASN1_ex_new_func(ASN1_VALUE **pval, const ASN1_ITEM *it);
+typedef void ASN1_ex_free_func(ASN1_VALUE **pval, const ASN1_ITEM *it);
+
+typedef int ASN1_ex_print_func(BIO *out, ASN1_VALUE **pval, 
+						int indent, const char *fname, 
+						const ASN1_PCTX *pctx);
+
+typedef int ASN1_primitive_i2c(ASN1_VALUE **pval, unsigned char *cont, int *putype, const ASN1_ITEM *it);
+typedef int ASN1_primitive_c2i(ASN1_VALUE **pval, const unsigned char *cont, int len, int utype, char *free_cont, const ASN1_ITEM *it);
+typedef int ASN1_primitive_print(BIO *out, ASN1_VALUE **pval, const ASN1_ITEM *it, int indent, const ASN1_PCTX *pctx);
+
+typedef struct ASN1_COMPAT_FUNCS_st {
+	ASN1_new_func *asn1_new;
+	ASN1_free_func *asn1_free;
+	ASN1_d2i_func *asn1_d2i;
+	ASN1_i2d_func *asn1_i2d;
+} ASN1_COMPAT_FUNCS;
+
+typedef struct ASN1_EXTERN_FUNCS_st {
+	void *app_data;
+	ASN1_ex_new_func *asn1_ex_new;
+	ASN1_ex_free_func *asn1_ex_free;
+	ASN1_ex_free_func *asn1_ex_clear;
+	ASN1_ex_d2i *asn1_ex_d2i;
+	ASN1_ex_i2d *asn1_ex_i2d;
+	ASN1_ex_print_func *asn1_ex_print;
+} ASN1_EXTERN_FUNCS;
+
+typedef struct ASN1_PRIMITIVE_FUNCS_st {
+	void *app_data;
+	unsigned long flags;
+	ASN1_ex_new_func *prim_new;
+	ASN1_ex_free_func *prim_free;
+	ASN1_ex_free_func *prim_clear;
+	ASN1_primitive_c2i *prim_c2i;
+	ASN1_primitive_i2c *prim_i2c;
+	ASN1_primitive_print *prim_print;
+} ASN1_PRIMITIVE_FUNCS;
+
+/* This is the ASN1_AUX structure: it handles various
+ * miscellaneous requirements. For example the use of
+ * reference counts and an informational callback.
+ *
+ * The "informational callback" is called at various
+ * points during the ASN1 encoding and decoding. It can
+ * be used to provide minor customisation of the structures
+ * used. This is most useful where the supplied routines
+ * *almost* do the right thing but need some extra help
+ * at a few points. If the callback returns zero then
+ * it is assumed a fatal error has occurred and the 
+ * main operation should be abandoned.
+ *
+ * If major changes in the default behaviour are required
+ * then an external type is more appropriate.
+ */
+
+typedef int ASN1_aux_cb(int operation, ASN1_VALUE **in, const ASN1_ITEM *it,
+				void *exarg);
+
+typedef struct ASN1_AUX_st {
+	void *app_data;
+	int flags;
+	int ref_offset;		/* Offset of reference value */
+	ASN1_aux_cb *asn1_cb;
+	int enc_offset;		/* Offset of ASN1_ENCODING structure */
+} ASN1_AUX;
+
+/* For print related callbacks exarg points to this structure */
+typedef struct ASN1_PRINT_ARG_st {
+	BIO *out;
+	int indent;
+	const ASN1_PCTX *pctx;
+} ASN1_PRINT_ARG;
+
+/* For streaming related callbacks exarg points to this structure */
+typedef struct ASN1_STREAM_ARG_st {
+	/* BIO to stream through */
+	BIO *out;
+	/* BIO with filters appended */
+	BIO *ndef_bio;
+	/* Streaming I/O boundary */
+	unsigned char **boundary;
+} ASN1_STREAM_ARG;
+
+/* Flags in ASN1_AUX */
+
+/* Use a reference count */
+#define ASN1_AFLG_REFCOUNT	1
+/* Save the encoding of structure (useful for signatures) */
+#define ASN1_AFLG_ENCODING	2
+/* The Sequence length is invalid */
+#define ASN1_AFLG_BROKEN	4
+
+/* operation values for asn1_cb */
+
+#define ASN1_OP_NEW_PRE		0
+#define ASN1_OP_NEW_POST	1
+#define ASN1_OP_FREE_PRE	2
+#define ASN1_OP_FREE_POST	3
+#define ASN1_OP_D2I_PRE		4
+#define ASN1_OP_D2I_POST	5
+#define ASN1_OP_I2D_PRE		6
+#define ASN1_OP_I2D_POST	7
+#define ASN1_OP_PRINT_PRE	8
+#define ASN1_OP_PRINT_POST	9
+#define ASN1_OP_STREAM_PRE	10
+#define ASN1_OP_STREAM_POST	11
+#define ASN1_OP_DETACHED_PRE	12
+#define ASN1_OP_DETACHED_POST	13
+
+/* Macro to implement a primitive type */
+#define IMPLEMENT_ASN1_TYPE(stname) IMPLEMENT_ASN1_TYPE_ex(stname, stname, 0)
+#define IMPLEMENT_ASN1_TYPE_ex(itname, vname, ex) \
+				ASN1_ITEM_start(itname) \
+					ASN1_ITYPE_PRIMITIVE, V_##vname, NULL, 0, NULL, ex, #itname \
+				ASN1_ITEM_end(itname)
+
+/* Macro to implement a multi string type */
+#define IMPLEMENT_ASN1_MSTRING(itname, mask) \
+				ASN1_ITEM_start(itname) \
+					ASN1_ITYPE_MSTRING, mask, NULL, 0, NULL, sizeof(ASN1_STRING), #itname \
+				ASN1_ITEM_end(itname)
+
+/* Macro to implement an ASN1_ITEM in terms of old style funcs */
+
+#define IMPLEMENT_COMPAT_ASN1(sname) IMPLEMENT_COMPAT_ASN1_type(sname, V_ASN1_SEQUENCE)
+
+#define IMPLEMENT_COMPAT_ASN1_type(sname, tag) \
+	static const ASN1_COMPAT_FUNCS sname##_ff = { \
+		(ASN1_new_func *)sname##_new, \
+		(ASN1_free_func *)sname##_free, \
+		(ASN1_d2i_func *)d2i_##sname, \
+		(ASN1_i2d_func *)i2d_##sname, \
+	}; \
+	ASN1_ITEM_start(sname) \
+		ASN1_ITYPE_COMPAT, \
+		tag, \
+		NULL, \
+		0, \
+		&sname##_ff, \
+		0, \
+		#sname \
+	ASN1_ITEM_end(sname)
+
+#define IMPLEMENT_EXTERN_ASN1(sname, tag, fptrs) \
+	ASN1_ITEM_start(sname) \
+		ASN1_ITYPE_EXTERN, \
+		tag, \
+		NULL, \
+		0, \
+		&fptrs, \
+		0, \
+		#sname \
+	ASN1_ITEM_end(sname)
+
+/* Macro to implement standard functions in terms of ASN1_ITEM structures */
+
+#define IMPLEMENT_ASN1_FUNCTIONS(stname) IMPLEMENT_ASN1_FUNCTIONS_fname(stname, stname, stname)
+
+#define IMPLEMENT_ASN1_FUNCTIONS_name(stname, itname) IMPLEMENT_ASN1_FUNCTIONS_fname(stname, itname, itname)
+
+#define IMPLEMENT_ASN1_FUNCTIONS_ENCODE_name(stname, itname) \
+			IMPLEMENT_ASN1_FUNCTIONS_ENCODE_fname(stname, itname, itname)
+
+#define IMPLEMENT_STATIC_ASN1_ALLOC_FUNCTIONS(stname) \
+		IMPLEMENT_ASN1_ALLOC_FUNCTIONS_pfname(static, stname, stname, stname)
+
+#define IMPLEMENT_ASN1_ALLOC_FUNCTIONS(stname) \
+		IMPLEMENT_ASN1_ALLOC_FUNCTIONS_fname(stname, stname, stname)
+
+#define IMPLEMENT_ASN1_ALLOC_FUNCTIONS_pfname(pre, stname, itname, fname) \
+	pre stname *fname##_new(void) \
+	{ \
+		return (stname *)ASN1_item_new(ASN1_ITEM_rptr(itname)); \
+	} \
+	pre void fname##_free(stname *a) \
+	{ \
+		ASN1_item_free((ASN1_VALUE *)a, ASN1_ITEM_rptr(itname)); \
+	}
+
+#define IMPLEMENT_ASN1_ALLOC_FUNCTIONS_fname(stname, itname, fname) \
+	stname *fname##_new(void) \
+	{ \
+		return (stname *)ASN1_item_new(ASN1_ITEM_rptr(itname)); \
+	} \
+	void fname##_free(stname *a) \
+	{ \
+		ASN1_item_free((ASN1_VALUE *)a, ASN1_ITEM_rptr(itname)); \
+	}
+
+#define IMPLEMENT_ASN1_FUNCTIONS_fname(stname, itname, fname) \
+	IMPLEMENT_ASN1_ENCODE_FUNCTIONS_fname(stname, itname, fname) \
+	IMPLEMENT_ASN1_ALLOC_FUNCTIONS_fname(stname, itname, fname)
+
+#define IMPLEMENT_ASN1_ENCODE_FUNCTIONS_fname(stname, itname, fname) \
+	stname *d2i_##fname(stname **a, const unsigned char **in, long len) \
+	{ \
+		return (stname *)ASN1_item_d2i((ASN1_VALUE **)a, in, len, ASN1_ITEM_rptr(itname));\
+	} \
+	int i2d_##fname(stname *a, unsigned char **out) \
+	{ \
+		return ASN1_item_i2d((ASN1_VALUE *)a, out, ASN1_ITEM_rptr(itname));\
+	} 
+
+#define IMPLEMENT_ASN1_NDEF_FUNCTION(stname) \
+	int i2d_##stname##_NDEF(stname *a, unsigned char **out) \
+	{ \
+		return ASN1_item_ndef_i2d((ASN1_VALUE *)a, out, ASN1_ITEM_rptr(stname));\
+	} 
+
+/* This includes evil casts to remove const: they will go away when full
+ * ASN1 constification is done.
+ */
+#define IMPLEMENT_ASN1_ENCODE_FUNCTIONS_const_fname(stname, itname, fname) \
+	stname *d2i_##fname(stname **a, const unsigned char **in, long len) \
+	{ \
+		return (stname *)ASN1_item_d2i((ASN1_VALUE **)a, in, len, ASN1_ITEM_rptr(itname));\
+	} \
+	int i2d_##fname(const stname *a, unsigned char **out) \
+	{ \
+		return ASN1_item_i2d((ASN1_VALUE *)a, out, ASN1_ITEM_rptr(itname));\
+	} 
+
+#define IMPLEMENT_ASN1_DUP_FUNCTION(stname) \
+	stname * stname##_dup(stname *x) \
+        { \
+        return ASN1_item_dup(ASN1_ITEM_rptr(stname), x); \
+        }
+
+#define IMPLEMENT_ASN1_PRINT_FUNCTION(stname) \
+	IMPLEMENT_ASN1_PRINT_FUNCTION_fname(stname, stname, stname)
+
+#define IMPLEMENT_ASN1_PRINT_FUNCTION_fname(stname, itname, fname) \
+	int fname##_print_ctx(BIO *out, stname *x, int indent, \
+						const ASN1_PCTX *pctx) \
+	{ \
+		return ASN1_item_print(out, (ASN1_VALUE *)x, indent, \
+			ASN1_ITEM_rptr(itname), pctx); \
+	} 
+
+#define IMPLEMENT_ASN1_FUNCTIONS_const(name) \
+		IMPLEMENT_ASN1_FUNCTIONS_const_fname(name, name, name)
+
+#define IMPLEMENT_ASN1_FUNCTIONS_const_fname(stname, itname, fname) \
+	IMPLEMENT_ASN1_ENCODE_FUNCTIONS_const_fname(stname, itname, fname) \
+	IMPLEMENT_ASN1_ALLOC_FUNCTIONS_fname(stname, itname, fname)
+
+/* external definitions for primitive types */
+
+DECLARE_ASN1_ITEM(ASN1_BOOLEAN)
+DECLARE_ASN1_ITEM(ASN1_TBOOLEAN)
+DECLARE_ASN1_ITEM(ASN1_FBOOLEAN)
+DECLARE_ASN1_ITEM(ASN1_SEQUENCE)
+DECLARE_ASN1_ITEM(CBIGNUM)
+DECLARE_ASN1_ITEM(BIGNUM)
+DECLARE_ASN1_ITEM(LONG)
+DECLARE_ASN1_ITEM(ZLONG)
+
+DECLARE_STACK_OF(ASN1_VALUE)
+
+/* Functions used internally by the ASN1 code */
+
+int ASN1_item_ex_new(ASN1_VALUE **pval, const ASN1_ITEM *it);
+void ASN1_item_ex_free(ASN1_VALUE **pval, const ASN1_ITEM *it);
+int ASN1_template_new(ASN1_VALUE **pval, const ASN1_TEMPLATE *tt);
+int ASN1_primitive_new(ASN1_VALUE **pval, const ASN1_ITEM *it);
+
+void ASN1_template_free(ASN1_VALUE **pval, const ASN1_TEMPLATE *tt);
+int ASN1_template_d2i(ASN1_VALUE **pval, const unsigned char **in, long len, const ASN1_TEMPLATE *tt);
+int ASN1_item_ex_d2i(ASN1_VALUE **pval, const unsigned char **in, long len, const ASN1_ITEM *it,
+				int tag, int aclass, char opt, ASN1_TLC *ctx);
+
+int ASN1_item_ex_i2d(ASN1_VALUE **pval, unsigned char **out, const ASN1_ITEM *it, int tag, int aclass);
+int ASN1_template_i2d(ASN1_VALUE **pval, unsigned char **out, const ASN1_TEMPLATE *tt);
+void ASN1_primitive_free(ASN1_VALUE **pval, const ASN1_ITEM *it);
+
+int asn1_ex_i2c(ASN1_VALUE **pval, unsigned char *cont, int *putype, const ASN1_ITEM *it);
+int asn1_ex_c2i(ASN1_VALUE **pval, const unsigned char *cont, int len, int utype, char *free_cont, const ASN1_ITEM *it);
+
+int asn1_get_choice_selector(ASN1_VALUE **pval, const ASN1_ITEM *it);
+int asn1_set_choice_selector(ASN1_VALUE **pval, int value, const ASN1_ITEM *it);
+
+ASN1_VALUE ** asn1_get_field_ptr(ASN1_VALUE **pval, const ASN1_TEMPLATE *tt);
+
+const ASN1_TEMPLATE *asn1_do_adb(ASN1_VALUE **pval, const ASN1_TEMPLATE *tt, int nullerr);
+
+void asn1_refcount_set_one(ASN1_VALUE **pval, const ASN1_ITEM *it);
+int asn1_refcount_dec_and_test_zero(ASN1_VALUE **pval, const ASN1_ITEM *it);
+
+void asn1_enc_init(ASN1_VALUE **pval, const ASN1_ITEM *it);
+void asn1_enc_free(ASN1_VALUE **pval, const ASN1_ITEM *it);
+int asn1_enc_restore(int *len, unsigned char **out, ASN1_VALUE **pval, const ASN1_ITEM *it);
+int asn1_enc_save(ASN1_VALUE **pval, const unsigned char *in, int inlen, const ASN1_ITEM *it);
+
+#ifdef  __cplusplus
+}
+#endif
+#endif

+ 261 - 0
app/src/main/jni/openssl/include/openssl/base.h

@@ -0,0 +1,261 @@
+/* ====================================================================
+ * Copyright (c) 1998-2001 The OpenSSL Project.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer. 
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. All advertising materials mentioning features or use of this
+ *    software must display the following acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
+ *
+ * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
+ *    endorse or promote products derived from this software without
+ *    prior written permission. For written permission, please contact
+ *    openssl-core@openssl.org.
+ *
+ * 5. Products derived from this software may not be called "OpenSSL"
+ *    nor may "OpenSSL" appear in their names without prior written
+ *    permission of the OpenSSL Project.
+ *
+ * 6. Redistributions of any form whatsoever must retain the following
+ *    acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
+ * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This product includes cryptographic software written by Eric Young
+ * (eay@cryptsoft.com).  This product includes software written by Tim
+ * Hudson (tjh@cryptsoft.com). */
+
+#ifndef OPENSSL_HEADER_BASE_H
+#define OPENSSL_HEADER_BASE_H
+
+
+/* This file should be the first included by all BoringSSL headers. */
+
+#include <stddef.h>
+#include <stdint.h>
+#include <sys/types.h>
+
+#include <openssl/opensslconf.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+#if defined(__x86_64) || defined(_M_AMD64) || defined(_M_X64)
+#define OPENSSL_64_BIT
+#define OPENSSL_X86_64
+#elif defined(__x86) || defined(__i386) || defined(__i386__) || defined(_M_IX86)
+#define OPENSSL_32_BIT
+#define OPENSSL_X86
+#elif defined(__aarch64__)
+#define OPENSSL_64_BIT
+#define OPENSSL_AARCH64
+#elif defined(__arm) || defined(__arm__) || defined(_M_ARM)
+#define OPENSSL_32_BIT
+#define OPENSSL_ARM
+#elif defined(__PPC64__) || defined(__powerpc64__)
+#define OPENSSL_64_BIT
+#elif defined(__mips__) && !defined(__LP64__)
+#define OPENSSL_32_BIT
+#define OPENSSL_MIPS
+#elif defined(__mips__) && defined(__LP64__)
+#define OPENSSL_64_BIT
+#define OPENSSL_MIPS64
+#elif defined(__pnacl__)
+#define OPENSSL_32_BIT
+#define OPENSSL_PNACL
+#else
+#error "Unknown target CPU"
+#endif
+
+#if defined(__APPLE__)
+#define OPENSSL_APPLE
+#endif
+
+#if defined(_WIN32)
+#define OPENSSL_WINDOWS
+#endif
+
+#if defined(TRUSTY)
+#define OPENSSL_TRUSTY
+#define OPENSSL_NO_THREADS
+#endif
+
+#define OPENSSL_IS_BORINGSSL
+#define BORINGSSL_201510
+#define OPENSSL_VERSION_NUMBER 0x10002000
+#define SSLEAY_VERSION_NUMBER OPENSSL_VERSION_NUMBER
+
+#if defined(BORINGSSL_SHARED_LIBRARY)
+
+#if defined(OPENSSL_WINDOWS)
+
+#if defined(BORINGSSL_IMPLEMENTATION)
+#define OPENSSL_EXPORT __declspec(dllexport)
+#else
+#define OPENSSL_EXPORT __declspec(dllimport)
+#endif
+
+#else  /* defined(OPENSSL_WINDOWS) */
+
+#if defined(BORINGSSL_IMPLEMENTATION)
+#define OPENSSL_EXPORT __attribute__((visibility("default")))
+#else
+#define OPENSSL_EXPORT
+#endif
+
+#endif  /* defined(OPENSSL_WINDOWS) */
+
+#else  /* defined(BORINGSSL_SHARED_LIBRARY) */
+
+#define OPENSSL_EXPORT
+
+#endif  /* defined(BORINGSSL_SHARED_LIBRARY) */
+
+/* CRYPTO_THREADID is a dummy value. */
+typedef int CRYPTO_THREADID;
+
+typedef int ASN1_BOOLEAN;
+typedef int ASN1_NULL;
+typedef struct ASN1_ITEM_st ASN1_ITEM;
+typedef struct asn1_object_st ASN1_OBJECT;
+typedef struct asn1_pctx_st ASN1_PCTX;
+typedef struct asn1_string_st ASN1_BIT_STRING;
+typedef struct asn1_string_st ASN1_BMPSTRING;
+typedef struct asn1_string_st ASN1_ENUMERATED;
+typedef struct asn1_string_st ASN1_GENERALIZEDTIME;
+typedef struct asn1_string_st ASN1_GENERALSTRING;
+typedef struct asn1_string_st ASN1_IA5STRING;
+typedef struct asn1_string_st ASN1_INTEGER;
+typedef struct asn1_string_st ASN1_OCTET_STRING;
+typedef struct asn1_string_st ASN1_PRINTABLESTRING;
+typedef struct asn1_string_st ASN1_STRING;
+typedef struct asn1_string_st ASN1_T61STRING;
+typedef struct asn1_string_st ASN1_TIME;
+typedef struct asn1_string_st ASN1_UNIVERSALSTRING;
+typedef struct asn1_string_st ASN1_UTCTIME;
+typedef struct asn1_string_st ASN1_UTF8STRING;
+typedef struct asn1_string_st ASN1_VISIBLESTRING;
+
+typedef struct AUTHORITY_KEYID_st AUTHORITY_KEYID;
+typedef struct DIST_POINT_st DIST_POINT;
+typedef struct ISSUING_DIST_POINT_st ISSUING_DIST_POINT;
+typedef struct NAME_CONSTRAINTS_st NAME_CONSTRAINTS;
+typedef struct Netscape_certificate_sequence NETSCAPE_CERT_SEQUENCE;
+typedef struct Netscape_spkac_st NETSCAPE_SPKAC;
+typedef struct Netscape_spki_st NETSCAPE_SPKI;
+typedef struct PBE2PARAM_st PBE2PARAM;
+typedef struct PBEPARAM_st PBEPARAM;
+typedef struct PBKDF2PARAM_st PBKDF2PARAM;
+typedef struct X509_POLICY_CACHE_st X509_POLICY_CACHE;
+typedef struct X509_POLICY_LEVEL_st X509_POLICY_LEVEL;
+typedef struct X509_POLICY_NODE_st X509_POLICY_NODE;
+typedef struct X509_POLICY_TREE_st X509_POLICY_TREE;
+typedef struct X509_algor_st X509_ALGOR;
+typedef struct X509_crl_info_st X509_CRL_INFO;
+typedef struct X509_crl_st X509_CRL;
+typedef struct X509_extension_st X509_EXTENSION;
+typedef struct X509_info_st X509_INFO;
+typedef struct X509_name_entry_st X509_NAME_ENTRY;
+typedef struct X509_name_st X509_NAME;
+typedef struct X509_objects_st X509_OBJECTS;
+typedef struct X509_pubkey_st X509_PUBKEY;
+typedef struct X509_req_info_st X509_REQ_INFO;
+typedef struct X509_req_st X509_REQ;
+typedef struct X509_sig_st X509_SIG;
+typedef struct X509_val_st X509_VAL;
+typedef struct bignum_ctx BN_CTX;
+typedef struct bignum_st BIGNUM;
+typedef struct bio_method_st BIO_METHOD;
+typedef struct bio_st BIO;
+typedef struct bn_gencb_st BN_GENCB;
+typedef struct bn_mont_ctx_st BN_MONT_CTX;
+typedef struct buf_mem_st BUF_MEM;
+typedef struct cbb_st CBB;
+typedef struct cbs_st CBS;
+typedef struct cmac_ctx_st CMAC_CTX;
+typedef struct conf_st CONF;
+typedef struct conf_value_st CONF_VALUE;
+typedef struct dh_st DH;
+typedef struct dsa_st DSA;
+typedef struct ec_key_st EC_KEY;
+typedef struct ecdsa_method_st ECDSA_METHOD;
+typedef struct ecdsa_sig_st ECDSA_SIG;
+typedef struct engine_st ENGINE;
+typedef struct env_md_ctx_st EVP_MD_CTX;
+typedef struct env_md_st EVP_MD;
+typedef struct evp_aead_st EVP_AEAD;
+typedef struct evp_cipher_ctx_st EVP_CIPHER_CTX;
+typedef struct evp_cipher_st EVP_CIPHER;
+typedef struct evp_encode_ctx_st EVP_ENCODE_CTX;
+typedef struct evp_pkey_asn1_method_st EVP_PKEY_ASN1_METHOD;
+typedef struct evp_pkey_ctx_st EVP_PKEY_CTX;
+typedef struct evp_pkey_method_st EVP_PKEY_METHOD;
+typedef struct evp_pkey_st EVP_PKEY;
+typedef struct hmac_ctx_st HMAC_CTX;
+typedef struct md4_state_st MD4_CTX;
+typedef struct md5_state_st MD5_CTX;
+typedef struct pkcs12_st PKCS12;
+typedef struct pkcs8_priv_key_info_st PKCS8_PRIV_KEY_INFO;
+typedef struct private_key_st X509_PKEY;
+typedef struct rand_meth_st RAND_METHOD;
+typedef struct rc4_key_st RC4_KEY;
+typedef struct rsa_meth_st RSA_METHOD;
+typedef struct rsa_st RSA;
+typedef struct sha256_state_st SHA256_CTX;
+typedef struct sha512_state_st SHA512_CTX;
+typedef struct sha_state_st SHA_CTX;
+typedef struct srtp_protection_profile_st SRTP_PROTECTION_PROFILE;
+typedef struct ssl_cipher_st SSL_CIPHER;
+typedef struct ssl_ctx_st SSL_CTX;
+typedef struct ssl_custom_extension SSL_CUSTOM_EXTENSION;
+typedef struct ssl_method_st SSL_METHOD;
+typedef struct ssl_session_st SSL_SESSION;
+typedef struct ssl_st SSL;
+typedef struct st_ERR_FNS ERR_FNS;
+typedef struct v3_ext_ctx X509V3_CTX;
+typedef struct x509_attributes_st X509_ATTRIBUTE;
+typedef struct x509_cert_aux_st X509_CERT_AUX;
+typedef struct x509_cert_pair_st X509_CERT_PAIR;
+typedef struct x509_cinf_st X509_CINF;
+typedef struct x509_crl_method_st X509_CRL_METHOD;
+typedef struct x509_revoked_st X509_REVOKED;
+typedef struct x509_st X509;
+typedef struct x509_store_ctx_st X509_STORE_CTX;
+typedef struct x509_store_st X509_STORE;
+typedef struct x509_trust_st X509_TRUST;
+
+typedef void *OPENSSL_BLOCK;
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_BASE_H */

+ 184 - 0
app/src/main/jni/openssl/include/openssl/base64.h

@@ -0,0 +1,184 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_BASE64_H
+#define OPENSSL_HEADER_BASE64_H
+
+#include <openssl/base.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* base64 functions.
+ *
+ * For historical reasons, these functions have the EVP_ prefix but just do
+ * base64 encoding and decoding. */
+
+
+/* Encoding */
+
+/* EVP_EncodeBlock encodes |src_len| bytes from |src| and writes the
+ * result to |dst| with a trailing NUL. It returns the number of bytes
+ * written, not including this trailing NUL. */
+OPENSSL_EXPORT size_t EVP_EncodeBlock(uint8_t *dst, const uint8_t *src,
+                                      size_t src_len);
+
+/* EVP_EncodedLength sets |*out_len| to the number of bytes that will be needed
+ * to call |EVP_EncodeBlock| on an input of length |len|. This includes the
+ * final NUL that |EVP_EncodeBlock| writes. It returns one on success or zero
+ * on error. */
+OPENSSL_EXPORT int EVP_EncodedLength(size_t *out_len, size_t len);
+
+
+/* Decoding */
+
+/* EVP_DecodedLength sets |*out_len| to the maximum number of bytes
+ * that will be needed to call |EVP_DecodeBase64| on an input of
+ * length |len|. */
+OPENSSL_EXPORT int EVP_DecodedLength(size_t *out_len, size_t len);
+
+/* EVP_DecodeBase64 decodes |in_len| bytes from base64 and writes
+ * |*out_len| bytes to |out|. |max_out| is the size of the output
+ * buffer. If it is not enough for the maximum output size, the
+ * operation fails. */
+OPENSSL_EXPORT int EVP_DecodeBase64(uint8_t *out, size_t *out_len,
+                                    size_t max_out, const uint8_t *in,
+                                    size_t in_len);
+
+
+/* Deprecated functions.
+ *
+ * OpenSSL provides a streaming base64 implementation, however its behavior is
+ * very specific to PEM. It is also very lenient of invalid input. Use of any of
+ * these functions is thus deprecated.
+ *
+ * TODO(davidben): Import upstream's rewrite that rejects the invalid input. */
+
+/* EVP_EncodeInit initialises |*ctx|, which is typically stack
+ * allocated, for an encoding operation.
+ *
+ * NOTE: The encoding operation breaks its output with newlines every
+ * 64 characters of output (48 characters of input). Use
+ * EVP_EncodeBlock to encode raw base64. */
+OPENSSL_EXPORT void EVP_EncodeInit(EVP_ENCODE_CTX *ctx);
+
+/* EVP_EncodeUpdate encodes |in_len| bytes from |in| and writes an encoded
+ * version of them to |out| and sets |*out_len| to the number of bytes written.
+ * Some state may be contained in |ctx| so |EVP_EncodeFinal| must be used to
+ * flush it before using the encoded data. */
+OPENSSL_EXPORT void EVP_EncodeUpdate(EVP_ENCODE_CTX *ctx, uint8_t *out,
+                                     int *out_len, const uint8_t *in,
+                                     size_t in_len);
+
+/* EVP_EncodeFinal flushes any remaining output bytes from |ctx| to |out| and
+ * sets |*out_len| to the number of bytes written. */
+OPENSSL_EXPORT void EVP_EncodeFinal(EVP_ENCODE_CTX *ctx, uint8_t *out,
+                                    int *out_len);
+
+/* EVP_DecodeInit initialises |*ctx|, which is typically stack allocated, for
+ * a decoding operation.
+ *
+ * TODO(davidben): This isn't a straight-up base64 decode either. Document
+ * and/or fix exactly what's going on here; maximum line length and such. */
+OPENSSL_EXPORT void EVP_DecodeInit(EVP_ENCODE_CTX *ctx);
+
+/* EVP_DecodeUpdate decodes |in_len| bytes from |in| and writes the decoded
+ * data to |out| and sets |*out_len| to the number of bytes written. Some state
+ * may be contained in |ctx| so |EVP_DecodeFinal| must be used to flush it
+ * before using the encoded data.
+ *
+ * It returns -1 on error, one if a full line of input was processed and zero
+ * if the line was short (i.e. it was the last line). */
+OPENSSL_EXPORT int EVP_DecodeUpdate(EVP_ENCODE_CTX *ctx, uint8_t *out,
+                                    int *out_len, const uint8_t *in,
+                                    size_t in_len);
+
+/* EVP_DecodeFinal flushes any remaining output bytes from |ctx| to |out| and
+ * sets |*out_len| to the number of bytes written. It returns one on success
+ * and minus one on error. */
+OPENSSL_EXPORT int EVP_DecodeFinal(EVP_ENCODE_CTX *ctx, uint8_t *out,
+                                   int *out_len);
+
+/* EVP_DecodeBlock encodes |src_len| bytes from |src| and writes the result to
+ * |dst|. It returns the number of bytes written or -1 on error.
+ *
+ * WARNING: EVP_DecodeBlock's return value does not take padding into
+ * account. It also strips leading whitespace and trailing
+ * whitespace. */
+OPENSSL_EXPORT int EVP_DecodeBlock(uint8_t *dst, const uint8_t *src,
+                                   size_t src_len);
+
+
+struct evp_encode_ctx_st {
+  unsigned num;    /* number saved in a partial encode/decode */
+  unsigned length; /* The length is either the output line length
+               * (in input bytes) or the shortest input line
+               * length that is ok.  Once decoding begins,
+               * the length is adjusted up each time a longer
+               * line is decoded */
+  uint8_t enc_data[80]; /* data to encode */
+  unsigned line_num;    /* number read on current line */
+  int expect_nl;
+};
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_BASE64_H */

+ 902 - 0
app/src/main/jni/openssl/include/openssl/bio.h

@@ -0,0 +1,902 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_BIO_H
+#define OPENSSL_HEADER_BIO_H
+
+#include <openssl/base.h>
+
+#include <stdio.h>  /* For FILE */
+
+#include <openssl/err.h> /* for ERR_print_errors_fp */
+#include <openssl/ex_data.h>
+#include <openssl/stack.h>
+#include <openssl/thread.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* BIO abstracts over a file-descriptor like interface. */
+
+
+/* Allocation and freeing. */
+
+/* BIO_new creates a new BIO with the given type and a reference count of one.
+ * It returns the fresh |BIO|, or NULL on error. */
+OPENSSL_EXPORT BIO *BIO_new(const BIO_METHOD *type);
+
+/* BIO_free decrements the reference count of |bio|. If the reference count
+ * drops to zero, it (optionally) calls the BIO's callback with |BIO_CB_FREE|,
+ * frees the ex_data and then, if the BIO has a destroy callback for the
+ * method, calls it. Finally it frees |bio| itself. It then repeats that for
+ * the next BIO in the chain, if any.
+ *
+ * It returns one on success or zero otherwise. */
+OPENSSL_EXPORT int BIO_free(BIO *bio);
+
+/* BIO_vfree performs the same actions as |BIO_free|, but has a void return
+ * value. This is provided for API-compat.
+ *
+ * TODO(fork): remove. */
+OPENSSL_EXPORT void BIO_vfree(BIO *bio);
+
+/* BIO_up_ref increments the reference count of |bio| and returns it. */
+OPENSSL_EXPORT BIO *BIO_up_ref(BIO *bio);
+
+
+/* Basic I/O. */
+
+/* BIO_read attempts to read |len| bytes into |data|. It returns the number of
+ * bytes read, zero on EOF, or a negative number on error. */
+OPENSSL_EXPORT int BIO_read(BIO *bio, void *data, int len);
+
+/* BIO_gets "reads a line" from |bio| and puts at most |size| bytes into |buf|.
+ * It returns the number of bytes read or a negative number on error. The
+ * phrase "reads a line" is in quotes in the previous sentence because the
+ * exact operation depends on the BIO's method. For example, a digest BIO will
+ * return the digest in response to a |BIO_gets| call.
+ *
+ * TODO(fork): audit the set of BIOs that we end up needing. If all actually
+ * return a line for this call, remove the warning above. */
+OPENSSL_EXPORT int BIO_gets(BIO *bio, char *buf, int size);
+
+/* BIO_write writes |len| bytes from |data| to BIO. It returns the number of
+ * bytes written or a negative number on error. */
+OPENSSL_EXPORT int BIO_write(BIO *bio, const void *data, int len);
+
+/* BIO_puts writes a NUL terminated string from |buf| to |bio|. It returns the
+ * number of bytes written or a negative number on error. */
+OPENSSL_EXPORT int BIO_puts(BIO *bio, const char *buf);
+
+/* BIO_flush flushes any buffered output. It returns one on success and zero
+ * otherwise. */
+OPENSSL_EXPORT int BIO_flush(BIO *bio);
+
+
+/* Low-level control functions.
+ *
+ * These are generic functions for sending control requests to a BIO. In
+ * general one should use the wrapper functions like |BIO_get_close|. */
+
+/* BIO_ctrl sends the control request |cmd| to |bio|. The |cmd| argument should
+ * be one of the |BIO_C_*| values. */
+OPENSSL_EXPORT long BIO_ctrl(BIO *bio, int cmd, long larg, void *parg);
+
+/* BIO_ptr_ctrl acts like |BIO_ctrl| but passes the address of a |void*|
+ * pointer as |parg| and returns the value that is written to it, or NULL if
+ * the control request returns <= 0. */
+OPENSSL_EXPORT char *BIO_ptr_ctrl(BIO *bp, int cmd, long larg);
+
+/* BIO_int_ctrl acts like |BIO_ctrl| but passes the address of a copy of |iarg|
+ * as |parg|. */
+OPENSSL_EXPORT long BIO_int_ctrl(BIO *bp, int cmd, long larg, int iarg);
+
+/* BIO_reset resets |bio| to its initial state, the precise meaning of which
+ * depends on the concrete type of |bio|. It returns one on success and zero
+ * otherwise. */
+OPENSSL_EXPORT int BIO_reset(BIO *bio);
+
+/* BIO_set_flags ORs |flags| with |bio->flags|. */
+OPENSSL_EXPORT void BIO_set_flags(BIO *bio, int flags);
+
+/* BIO_test_flags returns |bio->flags| AND |flags|. */
+OPENSSL_EXPORT int BIO_test_flags(const BIO *bio, int flags);
+
+/* BIO_should_read returns non-zero if |bio| encountered a temporary error
+ * while reading (i.e. EAGAIN), indicating that the caller should retry the
+ * read. */
+OPENSSL_EXPORT int BIO_should_read(const BIO *bio);
+
+/* BIO_should_write returns non-zero if |bio| encountered a temporary error
+ * while writing (i.e. EAGAIN), indicating that the caller should retry the
+ * write. */
+OPENSSL_EXPORT int BIO_should_write(const BIO *bio);
+
+/* BIO_should_retry returns non-zero if the reason that caused a failed I/O
+ * operation is temporary and thus the operation should be retried. Otherwise,
+ * it was a permanent error and it returns zero. */
+OPENSSL_EXPORT int BIO_should_retry(const BIO *bio);
+
+/* BIO_should_io_special returns non-zero if |bio| encountered a temporary
+ * error while performing a special I/O operation, indicating that the caller
+ * should retry. The operation that caused the error is returned by
+ * |BIO_get_retry_reason|. */
+OPENSSL_EXPORT int BIO_should_io_special(const BIO *bio);
+
+/* BIO_RR_SSL_X509_LOOKUP indicates that an SSL BIO blocked because the SSL
+ * library returned with SSL_ERROR_WANT_X509_LOOKUP.
+ *
+ * TODO(fork): remove. */
+#define BIO_RR_SSL_X509_LOOKUP 0x01
+
+/* BIO_RR_CONNECT indicates that a connect would have blocked */
+#define BIO_RR_CONNECT 0x02
+
+/* BIO_RR_ACCEPT indicates that an accept would have blocked */
+#define BIO_RR_ACCEPT 0x03
+
+/* BIO_RR_SSL_CHANNEL_ID_LOOKUP indicates that the ChannelID code cannot find
+ * a private key for a TLS connection. */
+#define BIO_RR_SSL_CHANNEL_ID_LOOKUP 0x04
+
+/* BIO_get_retry_reason returns the special I/O operation that needs to be
+ * retried. The return value is one of the |BIO_RR_*| values. */
+OPENSSL_EXPORT int BIO_get_retry_reason(const BIO *bio);
+
+/* BIO_clear_flags ANDs |bio->flags| with the bitwise-complement of |flags|. */
+OPENSSL_EXPORT void BIO_clear_flags(BIO *bio, int flags);
+
+/* BIO_set_retry_read sets the |BIO_FLAGS_READ| and |BIO_FLAGS_SHOULD_RETRY|
+ * flags on |bio|. */
+OPENSSL_EXPORT void BIO_set_retry_read(BIO *bio);
+
+/* BIO_set_retry_write sets the |BIO_FLAGS_WRITE| and |BIO_FLAGS_SHOULD_RETRY|
+ * flags on |bio|. */
+OPENSSL_EXPORT void BIO_set_retry_write(BIO *bio);
+
+/* BIO_get_retry_flags gets the |BIO_FLAGS_READ|, |BIO_FLAGS_WRITE|,
+ * |BIO_FLAGS_IO_SPECIAL| and |BIO_FLAGS_SHOULD_RETRY| flags from |bio|. */
+OPENSSL_EXPORT int BIO_get_retry_flags(BIO *bio);
+
+/* BIO_clear_retry_flags clears the |BIO_FLAGS_READ|, |BIO_FLAGS_WRITE|,
+ * |BIO_FLAGS_IO_SPECIAL| and |BIO_FLAGS_SHOULD_RETRY| flags from |bio|. */
+OPENSSL_EXPORT void BIO_clear_retry_flags(BIO *bio);
+
+/* BIO_method_type returns the type of |bio|, which is one of the |BIO_TYPE_*|
+ * values. */
+OPENSSL_EXPORT int BIO_method_type(const BIO *bio);
+
+/* bio_info_cb is the type of a callback function that can be called for most
+ * BIO operations. The |event| argument is one of |BIO_CB_*| and can be ORed
+ * with |BIO_CB_RETURN| if the callback is being made after the operation in
+ * question. In that case, |return_value| will contain the return value from
+ * the operation. */
+typedef long (*bio_info_cb)(BIO *bio, int event, const char *parg, int cmd,
+                            long larg, long return_value);
+
+/* BIO_callback_ctrl allows the callback function to be manipulated. The |cmd|
+ * arg will generally be |BIO_CTRL_SET_CALLBACK| but arbitary command values
+ * can be interpreted by the |BIO|. */
+OPENSSL_EXPORT long BIO_callback_ctrl(BIO *bio, int cmd, bio_info_cb fp);
+
+/* BIO_pending returns the number of bytes pending to be read. */
+OPENSSL_EXPORT size_t BIO_pending(const BIO *bio);
+
+/* BIO_ctrl_pending calls |BIO_pending| and exists only for compatibility with
+ * OpenSSL. */
+OPENSSL_EXPORT size_t BIO_ctrl_pending(const BIO *bio);
+
+/* BIO_wpending returns the number of bytes pending to be written. */
+OPENSSL_EXPORT size_t BIO_wpending(const BIO *bio);
+
+/* BIO_set_close sets the close flag for |bio|. The meaning of which depends on
+ * the type of |bio| but, for example, a memory BIO interprets the close flag
+ * as meaning that it owns its buffer. It returns one on success and zero
+ * otherwise. */
+OPENSSL_EXPORT int BIO_set_close(BIO *bio, int close_flag);
+
+/* BIO_set_callback sets a callback function that will be called before and
+ * after most operations. See the comment above |bio_info_cb|. */
+OPENSSL_EXPORT void BIO_set_callback(BIO *bio, bio_info_cb callback_func);
+
+/* BIO_set_callback_arg sets the opaque pointer value that can be read within a
+ * callback with |BIO_get_callback_arg|. */
+OPENSSL_EXPORT void BIO_set_callback_arg(BIO *bio, char *arg);
+
+/* BIO_get_callback_arg returns the last value of the opaque callback pointer
+ * set by |BIO_set_callback_arg|. */
+OPENSSL_EXPORT char *BIO_get_callback_arg(const BIO *bio);
+
+/* BIO_number_read returns the number of bytes that have been read from
+ * |bio|. */
+OPENSSL_EXPORT size_t BIO_number_read(const BIO *bio);
+
+/* BIO_number_written returns the number of bytes that have been written to
+ * |bio|. */
+OPENSSL_EXPORT size_t BIO_number_written(const BIO *bio);
+
+
+/* Managing chains of BIOs.
+ *
+ * BIOs can be put into chains where the output of one is used as the input of
+ * the next etc. The most common case is a buffering BIO, which accepts and
+ * buffers writes until flushed into the next BIO in the chain. */
+
+/* BIO_push adds |appended_bio| to the end of the chain with |bio| at the head.
+ * It returns |bio|. Note that |appended_bio| may be the head of a chain itself
+ * and thus this function can be used to join two chains.
+ *
+ * BIO_push takes ownership of the caller's reference to |appended_bio|. */
+OPENSSL_EXPORT BIO *BIO_push(BIO *bio, BIO *appended_bio);
+
+/* BIO_pop removes |bio| from the head of a chain and returns the next BIO in
+ * the chain, or NULL if there is no next BIO.
+ *
+ * The caller takes ownership of the chain's reference to |bio|. */
+OPENSSL_EXPORT BIO *BIO_pop(BIO *bio);
+
+/* BIO_next returns the next BIO in the chain after |bio|, or NULL if there is
+ * no such BIO. */
+OPENSSL_EXPORT BIO *BIO_next(BIO *bio);
+
+/* BIO_free_all calls |BIO_free|.
+ *
+ * TODO(fork): update callers and remove. */
+OPENSSL_EXPORT void BIO_free_all(BIO *bio);
+
+/* BIO_find_type walks a chain of BIOs and returns the first that matches
+ * |type|, which is one of the |BIO_TYPE_*| values. */
+OPENSSL_EXPORT BIO *BIO_find_type(BIO *bio, int type);
+
+/* BIO_copy_next_retry sets the retry flags and |retry_reason| of |bio| from
+ * the next BIO in the chain. */
+OPENSSL_EXPORT void BIO_copy_next_retry(BIO *bio);
+
+
+/* Printf functions.
+ *
+ * These functions are versions of printf functions that output to a BIO rather
+ * than a FILE. */
+#ifdef __GNUC__
+#define __bio_h__attr__ __attribute__
+#else
+#define __bio_h__attr__(x)
+#endif
+OPENSSL_EXPORT int BIO_printf(BIO *bio, const char *format, ...)
+    __bio_h__attr__((__format__(__printf__, 2, 3)));
+#undef __bio_h__attr__
+
+
+/* Utility functions. */
+
+/* BIO_indent prints min(|indent|, |max_indent|) spaces. It returns one on
+ * success and zero otherwise. */
+OPENSSL_EXPORT int BIO_indent(BIO *bio, unsigned indent, unsigned max_indent);
+
+/* BIO_hexdump writes a hex dump of |data| to |bio|. Each line will be indented
+ * by |indent| spaces. */
+OPENSSL_EXPORT int BIO_hexdump(BIO *bio, const uint8_t *data, size_t len,
+                               unsigned indent);
+
+/* BIO_print_errors prints the current contents of the error stack to |bio|
+ * using human readable strings where possible. */
+OPENSSL_EXPORT void BIO_print_errors(BIO *bio);
+
+/* BIO_read_asn1 reads a single ASN.1 object from |bio|. If successful it sets
+ * |*out| to be an allocated buffer (that should be freed with |OPENSSL_free|),
+ * |*out_size| to the length, in bytes, of that buffer and returns one.
+ * Otherwise it returns zero.
+ *
+ * If the length of the object is greater than |max_len| or 2^32 then the
+ * function will fail. Long-form tags are not supported. If the length of the
+ * object is indefinite the full contents of |bio| are read, unless it would be
+ * greater than |max_len|, in which case the function fails.
+ *
+ * If the function fails then some unknown amount of data may have been read
+ * from |bio|. */
+OPENSSL_EXPORT int BIO_read_asn1(BIO *bio, uint8_t **out, size_t *out_len,
+                                 size_t max_len);
+
+
+/* Memory BIOs.
+ *
+ * Memory BIOs can be used as a read-only source (with |BIO_new_mem_buf|) or a
+ * writable sink (with |BIO_new|, |BIO_s_mem| and |BIO_get_mem_buf|). Data
+ * written to a writable, memory BIO can be recalled by reading from it.
+ *
+ * Calling |BIO_reset| on a read-only BIO resets it to the original contents.
+ * On a writable BIO, it clears any data.
+ *
+ * If the close flag is set to |BIO_NOCLOSE| (not the default) then the
+ * underlying |BUF_MEM| will not be freed when the |BIO| is freed.
+ *
+ * Memory BIOs support |BIO_gets| and |BIO_puts|.
+ *
+ * |BIO_eof| is true if no data is in the BIO.
+ *
+ * |BIO_ctrl_pending| returns the number of bytes currently stored. */
+
+/* BIO_s_mem returns a |BIO_METHOD| that uses a in-memory buffer. */
+OPENSSL_EXPORT const BIO_METHOD *BIO_s_mem(void);
+
+/* BIO_new_mem_buf creates BIO that reads and writes from |len| bytes at |buf|.
+ * It does not take ownership of |buf|. It returns the BIO or NULL on error.
+ *
+ * If |len| is negative, then |buf| is treated as a NUL-terminated string, but
+ * don't depend on this in new code. */
+OPENSSL_EXPORT BIO *BIO_new_mem_buf(void *buf, int len);
+
+/* BIO_mem_contents sets |*out_contents| to point to the current contents of
+ * |bio| and |*out_len| to contain the length of that data. It returns one on
+ * success and zero otherwise. */
+OPENSSL_EXPORT int BIO_mem_contents(const BIO *bio,
+                                    const uint8_t **out_contents,
+                                    size_t *out_len);
+
+/* BIO_get_mem_data sets |*contents| to point to the current contents of |bio|
+ * and returns the length of the data.
+ *
+ * WARNING: don't use this, use |BIO_mem_contents|. A return value of zero from
+ * this function can mean either that it failed or that the memory buffer is
+ * empty. */
+OPENSSL_EXPORT long BIO_get_mem_data(BIO *bio, char **contents);
+
+/* BIO_get_mem_ptr sets |*out| to a BUF_MEM containing the current contents of
+ * |bio|. It returns one on success or zero on error. */
+OPENSSL_EXPORT int BIO_get_mem_ptr(BIO *bio, BUF_MEM **out);
+
+/* BIO_set_mem_buf sets |b| as the contents of |bio|. If |take_ownership| is
+ * non-zero, then |b| will be freed when |bio| is closed. Returns one on
+ * success or zero otherwise. */
+OPENSSL_EXPORT int BIO_set_mem_buf(BIO *bio, BUF_MEM *b, int take_ownership);
+
+/* BIO_set_mem_eof_return sets the value that will be returned from reading
+ * |bio| when empty. If |eof_value| is zero then an empty memory BIO will
+ * return EOF (that is it will return zero and |BIO_should_retry| will be
+ * false). If |eof_value| is non zero then it will return |eof_value| when it
+ * is empty and it will set the read retry flag (that is |BIO_read_retry| is
+ * true). To avoid ambiguity with a normal positive return value, |eof_value|
+ * should be set to a negative value, typically -1.
+ *
+ * For a read-only BIO, the default is zero (EOF). For a writable BIO, the
+ * default is -1 so that additional data can be written once exhausted. */
+OPENSSL_EXPORT int BIO_set_mem_eof_return(BIO *bio, int eof_value);
+
+
+/* File descriptor BIOs.
+ *
+ * File descriptor BIOs are wrappers around the system's |read| and |write|
+ * functions. If the close flag is set then then |close| is called on the
+ * underlying file descriptor when the BIO is freed.
+ *
+ * |BIO_reset| attempts to seek the file pointer to the start of file using
+ * |lseek|.
+ *
+ * |BIO_seek| sets the file pointer to position |off| from start of file using
+ * |lseek|.
+ *
+ * |BIO_tell| returns the current file position. */
+
+/* BIO_s_fd returns a |BIO_METHOD| for file descriptor fds. */
+OPENSSL_EXPORT const BIO_METHOD *BIO_s_fd(void);
+
+/* BIO_new_fd creates a new file descriptor BIO wrapping |fd|. If |close_flag|
+ * is non-zero, then |fd| will be closed when the BIO is. */
+OPENSSL_EXPORT BIO *BIO_new_fd(int fd, int close_flag);
+
+/* BIO_set_fd sets the file descriptor of |bio| to |fd|. If |close_flag| is
+ * non-zero then |fd| will be closed when |bio| is. It returns one on success
+ * or zero on error. */
+OPENSSL_EXPORT int BIO_set_fd(BIO *bio, int fd, int close_flag);
+
+/* BIO_get_fd returns the file descriptor currently in use by |bio| or -1 if
+ * |bio| does not wrap a file descriptor. If there is a file descriptor and
+ * |out_fd| is not NULL, it also sets |*out_fd| to the file descriptor. */
+OPENSSL_EXPORT int BIO_get_fd(BIO *bio, int *out_fd);
+
+
+/* File BIOs.
+ *
+ * File BIOs are wrappers around a C |FILE| object.
+ *
+ * |BIO_flush| on a file BIO calls |fflush| on the wrapped stream.
+ *
+ * |BIO_reset| attempts to seek the file pointer to the start of file using
+ * |fseek|.
+ *
+ * |BIO_seek| sets the file pointer to the given position from the start of
+ * file using |fseek|.
+ *
+ * |BIO_eof| calls |feof|.
+ *
+ * Setting the close flag causes |fclose| to be called on the stream when the
+ * BIO is freed. */
+
+/* BIO_s_file returns a BIO_METHOD that wraps a |FILE|. */
+OPENSSL_EXPORT const BIO_METHOD *BIO_s_file(void);
+
+/* BIO_new_file creates a file BIO by opening |filename| with the given mode.
+ * See the |fopen| manual page for details of the mode argument. */
+OPENSSL_EXPORT BIO *BIO_new_file(const char *filename, const char *mode);
+
+/* BIO_new_fp creates a new file BIO that wraps the given |FILE|. If
+ * |close_flag| is |BIO_CLOSE|, then |fclose| will be called on |stream| when
+ * the BIO is closed. */
+OPENSSL_EXPORT BIO *BIO_new_fp(FILE *stream, int close_flag);
+
+/* BIO_get_fp sets |*out_file| to the current |FILE| for |bio|. It returns one
+ * on success and zero otherwise. */
+OPENSSL_EXPORT int BIO_get_fp(BIO *bio, FILE **out_file);
+
+/* BIO_set_fp sets the |FILE| for |bio|. If |close_flag| is |BIO_CLOSE| then
+ * |fclose| will be called on |file| when |bio| is closed. It returns one on
+ * sucess and zero otherwise. */
+OPENSSL_EXPORT int BIO_set_fp(BIO *bio, FILE *file, int close_flag);
+
+/* BIO_read_filename opens |filename| for reading and sets the result as the
+ * |FILE| for |bio|. It returns one on success and zero otherwise. The |FILE|
+ * will be closed when |bio| is freed. */
+OPENSSL_EXPORT int BIO_read_filename(BIO *bio, const char *filename);
+
+/* BIO_write_filename opens |filename| for writing and sets the result as the
+ * |FILE| for |bio|. It returns one on success and zero otherwise. The |FILE|
+ * will be closed when |bio| is freed. */
+OPENSSL_EXPORT int BIO_write_filename(BIO *bio, const char *filename);
+
+/* BIO_append_filename opens |filename| for appending and sets the result as
+ * the |FILE| for |bio|. It returns one on success and zero otherwise. The
+ * |FILE| will be closed when |bio| is freed. */
+OPENSSL_EXPORT int BIO_append_filename(BIO *bio, const char *filename);
+
+/* BIO_rw_filename opens |filename| for reading and writing and sets the result
+ * as the |FILE| for |bio|. It returns one on success and zero otherwise. The
+ * |FILE| will be closed when |bio| is freed. */
+OPENSSL_EXPORT int BIO_rw_filename(BIO *bio, const char *filename);
+
+
+/* Buffer BIOs.
+ *
+ * Buffer BIOs are a filter-type BIO, i.e. they are designed to be used in a
+ * chain of BIOs. They provide buffering to reduce the number of operations on
+ * the underlying BIOs. */
+
+OPENSSL_EXPORT const BIO_METHOD *BIO_f_buffer(void);
+
+/* BIO_set_read_buffer_size sets the size, in bytes, of the read buffer and
+ * clears it. It returns one on success and zero on failure. */
+OPENSSL_EXPORT int BIO_set_read_buffer_size(BIO *bio, int buffer_size);
+
+/* BIO_set_write_buffer_size sets the size, in bytes, of the write buffer and
+ * clears it. It returns one on success and zero on failure. */
+OPENSSL_EXPORT int BIO_set_write_buffer_size(BIO *bio, int buffer_size);
+
+
+/* Socket BIOs. */
+
+OPENSSL_EXPORT const BIO_METHOD *BIO_s_socket(void);
+
+/* BIO_new_socket allocates and initialises a fresh BIO which will read and
+ * write to the socket |fd|. If |close_flag| is |BIO_CLOSE| then closing the
+ * BIO will close |fd|. It returns the fresh |BIO| or NULL on error. */
+OPENSSL_EXPORT BIO *BIO_new_socket(int fd, int close_flag);
+
+
+/* Connect BIOs.
+ *
+ * A connection BIO creates a network connection and transfers data over the
+ * resulting socket. */
+
+OPENSSL_EXPORT const BIO_METHOD *BIO_s_connect(void);
+
+/* BIO_new_connect returns a BIO that connects to the given hostname and port.
+ * The |host_and_optional_port| argument should be of the form
+ * "www.example.com" or "www.example.com:443". If the port is omitted, it must
+ * be provided with |BIO_set_conn_port|.
+ *
+ * It returns the new BIO on success, or NULL on error. */
+OPENSSL_EXPORT BIO *BIO_new_connect(const char *host_and_optional_port);
+
+/* BIO_set_conn_hostname sets |host_and_optional_port| as the hostname and
+ * optional port that |bio| will connect to. If the port is omitted, it must be
+ * provided with |BIO_set_conn_port|.
+ *
+ * It returns one on success and zero otherwise. */
+OPENSSL_EXPORT int BIO_set_conn_hostname(BIO *bio,
+                                         const char *host_and_optional_port);
+
+/* BIO_set_conn_port sets |port_str| as the port or service name that |bio|
+ * will connect to. It returns one on success and zero otherwise. */
+OPENSSL_EXPORT int BIO_set_conn_port(BIO *bio, const char *port_str);
+
+/* BIO_set_nbio sets whether |bio| will use non-blocking I/O operations. It
+ * returns one on success and zero otherwise. */
+OPENSSL_EXPORT int BIO_set_nbio(BIO *bio, int on);
+
+
+/* Datagram BIOs.
+ *
+ * TODO(fork): not implemented. */
+
+#define BIO_CTRL_DGRAM_QUERY_MTU 40 /* as kernel for current MTU */
+
+#define BIO_CTRL_DGRAM_SET_MTU 42 /* set cached value for  MTU. want to use
+                                     this if asking the kernel fails */
+
+#define BIO_CTRL_DGRAM_MTU_EXCEEDED 43 /* check whether the MTU was exceed in
+                                          the previous write operation. */
+
+#define BIO_CTRL_DGRAM_SET_NEXT_TIMEOUT \
+  45 /* Next DTLS handshake timeout to adjust socket timeouts */
+
+#define BIO_CTRL_DGRAM_GET_PEER           46
+
+#define BIO_CTRL_DGRAM_GET_FALLBACK_MTU   47
+
+
+/* BIO Pairs.
+ *
+ * BIO pairs provide a "loopback" like system: a pair of BIOs where data
+ * written to one can be read from the other and vice versa. */
+
+/* BIO_new_bio_pair sets |*out1| and |*out2| to two freshly created BIOs where
+ * data written to one can be read from the other and vice versa. The
+ * |writebuf1| argument gives the size of the buffer used in |*out1| and
+ * |writebuf2| for |*out2|. It returns one on success and zero on error. */
+OPENSSL_EXPORT int BIO_new_bio_pair(BIO **out1, size_t writebuf1, BIO **out2,
+                                    size_t writebuf2);
+
+/* BIO_new_bio_pair_external_buf is the same as |BIO_new_bio_pair| with the
+ * difference that the caller keeps ownership of the write buffers
+ * |ext_writebuf1_len| and |ext_writebuf2_len|. This is useful when using zero
+ * copy API for read and write operations, in cases where the buffers need to
+ * outlive the BIO pairs. It returns one on success and zero on error. */
+OPENSSL_EXPORT int BIO_new_bio_pair_external_buf(BIO** bio1_p,
+                                                 size_t writebuf1_len,
+                                                 uint8_t* ext_writebuf1,
+                                                 BIO** bio2_p,
+                                                 size_t writebuf2_len,
+                                                 uint8_t* ext_writebuf2);
+
+/* BIO_ctrl_get_read_request returns the number of bytes that the other side of
+ * |bio| tried (unsuccessfully) to read. */
+OPENSSL_EXPORT size_t BIO_ctrl_get_read_request(BIO *bio);
+
+/* BIO_ctrl_get_write_guarantee returns the number of bytes that |bio| (which
+ * must have been returned by |BIO_new_bio_pair|) will accept on the next
+ * |BIO_write| call. */
+OPENSSL_EXPORT size_t BIO_ctrl_get_write_guarantee(BIO *bio);
+
+/* BIO_shutdown_wr marks |bio| as closed, from the point of view of the other
+ * side of the pair. Future |BIO_write| calls on |bio| will fail. It returns
+ * one on success and zero otherwise. */
+OPENSSL_EXPORT int BIO_shutdown_wr(BIO *bio);
+
+
+/* Zero copy versions of BIO_read and BIO_write for BIO pairs. */
+
+/* BIO_zero_copy_get_read_buf initiates a zero copy read operation.
+ * |out_read_buf| is set to the internal read buffer, and |out_buf_offset| is
+ * set to the current read position of |out_read_buf|. The number of bytes
+ * available for read from |out_read_buf| + |out_buf_offset| is returned in
+ * |out_available_bytes|. Note that this function might report fewer bytes
+ * available than |BIO_pending|, if the internal ring buffer is wrapped. It
+ * returns one on success. In case of error it returns zero and pushes to the
+ * error stack.
+ *
+ * The zero copy read operation is completed by calling
+ * |BIO_zero_copy_get_read_buf_done|. Neither |BIO_zero_copy_get_read_buf| nor
+ * any other I/O read operation may be called while a zero copy read operation
+ * is active. */
+OPENSSL_EXPORT int BIO_zero_copy_get_read_buf(BIO* bio,
+                                              uint8_t** out_read_buf,
+                                              size_t* out_buf_offset,
+                                              size_t* out_available_bytes);
+
+/* BIO_zero_copy_get_read_buf_done must be called after reading from a BIO using
+ * |BIO_zero_copy_get_read_buf| to finish the read operation. The |bytes_read|
+ * argument is the number of bytes read.
+ *
+ * It returns one on success. In case of error it returns zero and pushes to the
+ * error stack. */
+OPENSSL_EXPORT int BIO_zero_copy_get_read_buf_done(BIO* bio, size_t bytes_read);
+
+/* BIO_zero_copy_get_write_buf initiates a zero copy write operation.
+ * |out_write_buf| is set to to the internal write buffer, and |out_buf_offset|
+ * is set to the current write position of |out_write_buf|.
+ * The number of bytes available for write from |out_write_buf| +
+ * |out_buf_offset| is returned in |out_available_bytes|. Note that this
+ * function might report fewer bytes available than
+ * |BIO_ctrl_get_write_guarantee|, if the internal buffer is wrapped. It returns
+ * one on success. In case of error it returns zero and pushes to the error
+ * stack.
+ *
+ * The zero copy write operation is completed by calling
+ * |BIO_zero_copy_get_write_buf_done|. Neither |BIO_zero_copy_get_write_buf|
+ * nor any other I/O write operation may be called while a zero copy write
+ * operation is active. */
+OPENSSL_EXPORT int BIO_zero_copy_get_write_buf(BIO* bio,
+                                               uint8_t** out_write_buf,
+                                               size_t* out_buf_offset,
+                                               size_t* out_available_bytes);
+
+/* BIO_zero_copy_get_write_buf_done must be called after writing to a BIO using
+ * |BIO_zero_copy_get_write_buf| to finish the write operation. The
+ * |bytes_written| argument gives the number of bytes written.
+ *
+ * It returns one on success. In case of error it returns zero and pushes to the
+ * error stack. */
+OPENSSL_EXPORT int BIO_zero_copy_get_write_buf_done(BIO* bio,
+                                                    size_t bytes_written);
+
+
+/* BIO_NOCLOSE and |BIO_CLOSE| can be used as symbolic arguments when a "close
+ * flag" is passed to a BIO function. */
+#define BIO_NOCLOSE 0
+#define BIO_CLOSE 1
+
+/* These are passed to the BIO callback */
+#define BIO_CB_FREE 0x01
+#define BIO_CB_READ 0x02
+#define BIO_CB_WRITE 0x03
+#define BIO_CB_PUTS 0x04
+#define BIO_CB_GETS 0x05
+#define BIO_CB_CTRL 0x06
+
+/* The callback is called before and after the underling operation,
+ * The BIO_CB_RETURN flag indicates if it is after the call */
+#define BIO_CB_RETURN 0x80
+
+/* These are values of the |cmd| argument to |BIO_ctrl|. */
+#define BIO_CTRL_RESET		1  /* opt - rewind/zero etc */
+#define BIO_CTRL_EOF		2  /* opt - are we at the eof */
+#define BIO_CTRL_INFO		3  /* opt - extra tit-bits */
+#define BIO_CTRL_SET		4  /* man - set the 'IO' type */
+#define BIO_CTRL_GET		5  /* man - get the 'IO' type */
+#define BIO_CTRL_GET_CLOSE	8  /* man - set the 'close' on free */
+#define BIO_CTRL_SET_CLOSE	9  /* man - set the 'close' on free */
+#define BIO_CTRL_PENDING	10  /* opt - is their more data buffered */
+#define BIO_CTRL_FLUSH		11  /* opt - 'flush' buffered output */
+#define BIO_CTRL_WPENDING	13  /* opt - number of bytes still to write */
+/* callback is int cb(BIO *bio,state,ret); */
+#define BIO_CTRL_SET_CALLBACK	14  /* opt - set callback function */
+#define BIO_CTRL_GET_CALLBACK	15  /* opt - set callback function */
+#define BIO_CTRL_SET_FILENAME	30	/* BIO_s_file special */
+
+
+/* Android compatibility section.
+ *
+ * A previous version of BoringSSL used in Android renamed ERR_print_errors_fp
+ * to BIO_print_errors_fp. It has subsequently been renamed back to
+ * ERR_print_errors_fp. */
+#define BIO_print_errors_fp ERR_print_errors_fp
+
+
+/* Deprecated functions. */
+
+/* BIO_f_base64 returns a filter |BIO| that base64-encodes data written into
+ * it, and decodes data read from it. |BIO_gets| is not supported. Call
+ * |BIO_flush| when done writing, to signal that no more data are to be
+ * encoded. The flag |BIO_FLAGS_BASE64_NO_NL| may be set to encode all the data
+ * on one line. */
+OPENSSL_EXPORT const BIO_METHOD *BIO_f_base64(void);
+
+/* ERR_print_errors is an alias for |BIO_print_errors|. */
+OPENSSL_EXPORT void ERR_print_errors(BIO *bio);
+
+
+/* Private functions */
+
+#define BIO_FLAGS_READ 0x01
+#define BIO_FLAGS_WRITE 0x02
+#define BIO_FLAGS_IO_SPECIAL 0x04
+#define BIO_FLAGS_RWS (BIO_FLAGS_READ | BIO_FLAGS_WRITE | BIO_FLAGS_IO_SPECIAL)
+#define BIO_FLAGS_SHOULD_RETRY 0x08
+#define BIO_FLAGS_BASE64_NO_NL 0x100
+/* This is used with memory BIOs: it means we shouldn't free up or change the
+ * data in any way. */
+#define BIO_FLAGS_MEM_RDONLY 0x200
+
+/* These are the 'types' of BIOs */
+#define BIO_TYPE_NONE 0
+#define BIO_TYPE_MEM (1 | 0x0400)
+#define BIO_TYPE_FILE (2 | 0x0400)
+#define BIO_TYPE_FD (4 | 0x0400 | 0x0100)
+#define BIO_TYPE_SOCKET (5 | 0x0400 | 0x0100)
+#define BIO_TYPE_NULL (6 | 0x0400)
+#define BIO_TYPE_SSL (7 | 0x0200)
+#define BIO_TYPE_MD (8 | 0x0200)                /* passive filter */
+#define BIO_TYPE_BUFFER (9 | 0x0200)            /* filter */
+#define BIO_TYPE_CIPHER (10 | 0x0200)           /* filter */
+#define BIO_TYPE_BASE64 (11 | 0x0200)           /* filter */
+#define BIO_TYPE_CONNECT (12 | 0x0400 | 0x0100) /* socket - connect */
+#define BIO_TYPE_ACCEPT (13 | 0x0400 | 0x0100)  /* socket for accept */
+#define BIO_TYPE_PROXY_CLIENT (14 | 0x0200)     /* client proxy BIO */
+#define BIO_TYPE_PROXY_SERVER (15 | 0x0200)     /* server proxy BIO */
+#define BIO_TYPE_NBIO_TEST (16 | 0x0200)        /* server proxy BIO */
+#define BIO_TYPE_NULL_FILTER (17 | 0x0200)
+#define BIO_TYPE_BER (18 | 0x0200)        /* BER -> bin filter */
+#define BIO_TYPE_BIO (19 | 0x0400)        /* (half a) BIO pair */
+#define BIO_TYPE_LINEBUFFER (20 | 0x0200) /* filter */
+#define BIO_TYPE_DGRAM (21 | 0x0400 | 0x0100)
+#define BIO_TYPE_ASN1 (22 | 0x0200) /* filter */
+#define BIO_TYPE_COMP (23 | 0x0200) /* filter */
+
+#define BIO_TYPE_DESCRIPTOR 0x0100 /* socket, fd, connect or accept */
+#define BIO_TYPE_FILTER 0x0200
+#define BIO_TYPE_SOURCE_SINK 0x0400
+
+struct bio_method_st {
+  int type;
+  const char *name;
+  int (*bwrite)(BIO *, const char *, int);
+  int (*bread)(BIO *, char *, int);
+  /* TODO(fork): remove bputs. */
+  int (*bputs)(BIO *, const char *);
+  int (*bgets)(BIO *, char *, int);
+  long (*ctrl)(BIO *, int, long, void *);
+  int (*create)(BIO *);
+  int (*destroy)(BIO *);
+  long (*callback_ctrl)(BIO *, int, bio_info_cb);
+};
+
+struct bio_st {
+  const BIO_METHOD *method;
+  /* bio, mode, argp, argi, argl, ret */
+  long (*callback)(BIO *, int, const char *, int, long, long);
+  char *cb_arg; /* first argument for the callback */
+
+  /* init is non-zero if this |BIO| has been initialised. */
+  int init;
+  /* shutdown is often used by specific |BIO_METHOD|s to determine whether
+   * they own some underlying resource. This flag can often by controlled by
+   * |BIO_set_close|. For example, whether an fd BIO closes the underlying fd
+   * when it, itself, is closed. */
+  int shutdown;
+  int flags;
+  int retry_reason;
+  /* num is a BIO-specific value. For example, in fd BIOs it's used to store a
+   * file descriptor. */
+  int num;
+  CRYPTO_refcount_t references;
+  void *ptr;
+  /* next_bio points to the next |BIO| in a chain. This |BIO| owns a reference
+   * to |next_bio|. */
+  BIO *next_bio; /* used by filter BIOs */
+  size_t num_read, num_write;
+};
+
+#define BIO_C_SET_CONNECT			100
+#define BIO_C_DO_STATE_MACHINE			101
+#define BIO_C_SET_NBIO				102
+#define BIO_C_SET_PROXY_PARAM			103
+#define BIO_C_SET_FD				104
+#define BIO_C_GET_FD				105
+#define BIO_C_SET_FILE_PTR			106
+#define BIO_C_GET_FILE_PTR			107
+#define BIO_C_SET_FILENAME			108
+#define BIO_C_SET_SSL				109
+#define BIO_C_GET_SSL				110
+#define BIO_C_SET_MD				111
+#define BIO_C_GET_MD				112
+#define BIO_C_GET_CIPHER_STATUS			113
+#define BIO_C_SET_BUF_MEM			114
+#define BIO_C_GET_BUF_MEM_PTR			115
+#define BIO_C_GET_BUFF_NUM_LINES		116
+#define BIO_C_SET_BUFF_SIZE			117
+#define BIO_C_SET_ACCEPT			118
+#define BIO_C_SSL_MODE				119
+#define BIO_C_GET_MD_CTX			120
+#define BIO_C_GET_PROXY_PARAM			121
+#define BIO_C_SET_BUFF_READ_DATA		122 /* data to read first */
+#define BIO_C_GET_ACCEPT			124
+#define BIO_C_SET_SSL_RENEGOTIATE_BYTES		125
+#define BIO_C_GET_SSL_NUM_RENEGOTIATES		126
+#define BIO_C_SET_SSL_RENEGOTIATE_TIMEOUT	127
+#define BIO_C_FILE_SEEK				128
+#define BIO_C_GET_CIPHER_CTX			129
+#define BIO_C_SET_BUF_MEM_EOF_RETURN		130/*return end of input value*/
+#define BIO_C_SET_BIND_MODE			131
+#define BIO_C_GET_BIND_MODE			132
+#define BIO_C_FILE_TELL				133
+#define BIO_C_GET_SOCKS				134
+#define BIO_C_SET_SOCKS				135
+
+#define BIO_C_SET_WRITE_BUF_SIZE		136/* for BIO_s_bio */
+#define BIO_C_GET_WRITE_BUF_SIZE		137
+#define BIO_C_GET_WRITE_GUARANTEE		140
+#define BIO_C_GET_READ_REQUEST			141
+#define BIO_C_SHUTDOWN_WR			142
+#define BIO_C_NREAD0				143
+#define BIO_C_NREAD				144
+#define BIO_C_NWRITE0				145
+#define BIO_C_NWRITE				146
+#define BIO_C_RESET_READ_REQUEST		147
+#define BIO_C_SET_MD_CTX			148
+
+#define BIO_C_SET_PREFIX			149
+#define BIO_C_GET_PREFIX			150
+#define BIO_C_SET_SUFFIX			151
+#define BIO_C_GET_SUFFIX			152
+
+#define BIO_C_SET_EX_ARG			153
+#define BIO_C_GET_EX_ARG			154
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#define BIO_R_BAD_FOPEN_MODE 100
+#define BIO_R_BROKEN_PIPE 101
+#define BIO_R_CONNECT_ERROR 102
+#define BIO_R_ERROR_SETTING_NBIO 103
+#define BIO_R_INVALID_ARGUMENT 104
+#define BIO_R_IN_USE 105
+#define BIO_R_KEEPALIVE 106
+#define BIO_R_NBIO_CONNECT_ERROR 107
+#define BIO_R_NO_HOSTNAME_SPECIFIED 108
+#define BIO_R_NO_PORT_SPECIFIED 109
+#define BIO_R_NO_SUCH_FILE 110
+#define BIO_R_NULL_PARAMETER 111
+#define BIO_R_SYS_LIB 112
+#define BIO_R_UNABLE_TO_CREATE_SOCKET 113
+#define BIO_R_UNINITIALIZED 114
+#define BIO_R_UNSUPPORTED_METHOD 115
+#define BIO_R_WRITE_TO_READ_ONLY_BIO 116
+
+#endif  /* OPENSSL_HEADER_BIO_H */

+ 93 - 0
app/src/main/jni/openssl/include/openssl/blowfish.h

@@ -0,0 +1,93 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_BLOWFISH_H
+#define OPENSSL_HEADER_BLOWFISH_H
+
+#include <openssl/base.h>
+
+#ifdef  __cplusplus
+extern "C" {
+#endif
+
+
+#define BF_ENCRYPT 1
+#define BF_DECRYPT 0
+
+#define BF_ROUNDS 16
+#define BF_BLOCK 8
+
+typedef struct bf_key_st {
+  uint32_t P[BF_ROUNDS + 2];
+  uint32_t S[4 * 256];
+} BF_KEY;
+
+OPENSSL_EXPORT void BF_set_key(BF_KEY *key, size_t len, const uint8_t *data);
+OPENSSL_EXPORT void BF_encrypt(uint32_t *data, const BF_KEY *key);
+OPENSSL_EXPORT void BF_decrypt(uint32_t *data, const BF_KEY *key);
+
+OPENSSL_EXPORT void BF_ecb_encrypt(const uint8_t *in, uint8_t *out,
+                                   const BF_KEY *key, int enc);
+OPENSSL_EXPORT void BF_cbc_encrypt(const uint8_t *in, uint8_t *out, long length,
+                                   const BF_KEY *schedule, uint8_t *ivec,
+                                   int enc);
+
+
+#ifdef  __cplusplus
+}
+#endif
+
+#endif  /* OPENSSL_HEADER_BLOWFISH_H */

+ 888 - 0
app/src/main/jni/openssl/include/openssl/bn.h

@@ -0,0 +1,888 @@
+/* Copyright (C) 1995-1997 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.]
+ */
+/* ====================================================================
+ * Copyright (c) 1998-2006 The OpenSSL Project.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. All advertising materials mentioning features or use of this
+ *    software must display the following acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
+ *
+ * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
+ *    endorse or promote products derived from this software without
+ *    prior written permission. For written permission, please contact
+ *    openssl-core@openssl.org.
+ *
+ * 5. Products derived from this software may not be called "OpenSSL"
+ *    nor may "OpenSSL" appear in their names without prior written
+ *    permission of the OpenSSL Project.
+ *
+ * 6. Redistributions of any form whatsoever must retain the following
+ *    acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
+ * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This product includes cryptographic software written by Eric Young
+ * (eay@cryptsoft.com).  This product includes software written by Tim
+ * Hudson (tjh@cryptsoft.com).
+ *
+ */
+/* ====================================================================
+ * Copyright 2002 Sun Microsystems, Inc. ALL RIGHTS RESERVED.
+ *
+ * Portions of the attached software ("Contribution") are developed by
+ * SUN MICROSYSTEMS, INC., and are contributed to the OpenSSL project.
+ *
+ * The Contribution is licensed pursuant to the Eric Young open source
+ * license provided above.
+ *
+ * The binary polynomial arithmetic software is originally written by
+ * Sheueling Chang Shantz and Douglas Stebila of Sun Microsystems
+ * Laboratories. */
+
+#ifndef OPENSSL_HEADER_BN_H
+#define OPENSSL_HEADER_BN_H
+
+#include <openssl/base.h>
+#include <openssl/thread.h>
+
+#include <inttypes.h>  /* for PRIu64 and friends */
+#include <stdio.h>  /* for FILE* */
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* BN provides support for working with arbitary sized integers. For example,
+ * although the largest integer supported by the compiler might be 64 bits, BN
+ * will allow you to work with numbers until you run out of memory. */
+
+
+/* BN_ULONG is the native word size when working with big integers.
+ *
+ * Note: on some platforms, inttypes.h does not define print format macros in
+ * C++ unless |__STDC_FORMAT_MACROS| defined. As this is a public header, bn.h
+ * does not define |__STDC_FORMAT_MACROS| itself. C++ source files which use the
+ * FMT macros must define it externally. */
+#if defined(OPENSSL_64_BIT)
+#define BN_ULONG uint64_t
+#define BN_BITS2 64
+#define BN_DEC_FMT1	"%" PRIu64
+#define BN_DEC_FMT2	"%019" PRIu64
+#define BN_HEX_FMT1	"%" PRIx64
+#elif defined(OPENSSL_32_BIT)
+#define BN_ULONG uint32_t
+#define BN_BITS2 32
+#define BN_DEC_FMT1	"%" PRIu32
+#define BN_DEC_FMT2	"%09" PRIu32
+#define BN_HEX_FMT1	"%" PRIx32
+#else
+#error "Must define either OPENSSL_32_BIT or OPENSSL_64_BIT"
+#endif
+
+
+/* Allocation and freeing. */
+
+/* BN_new creates a new, allocated BIGNUM and initialises it. */
+OPENSSL_EXPORT BIGNUM *BN_new(void);
+
+/* BN_init initialises a stack allocated |BIGNUM|. */
+OPENSSL_EXPORT void BN_init(BIGNUM *bn);
+
+/* BN_free frees the data referenced by |bn| and, if |bn| was originally
+ * allocated on the heap, frees |bn| also. */
+OPENSSL_EXPORT void BN_free(BIGNUM *bn);
+
+/* BN_clear_free erases and frees the data referenced by |bn| and, if |bn| was
+ * originally allocated on the heap, frees |bn| also. */
+OPENSSL_EXPORT void BN_clear_free(BIGNUM *bn);
+
+/* BN_dup allocates a new BIGNUM and sets it equal to |src|. It returns the
+ * allocated BIGNUM on success or NULL otherwise. */
+OPENSSL_EXPORT BIGNUM *BN_dup(const BIGNUM *src);
+
+/* BN_copy sets |dest| equal to |src| and returns |dest| or NULL on allocation
+ * failure. */
+OPENSSL_EXPORT BIGNUM *BN_copy(BIGNUM *dest, const BIGNUM *src);
+
+/* BN_clear sets |bn| to zero and erases the old data. */
+OPENSSL_EXPORT void BN_clear(BIGNUM *bn);
+
+/* BN_value_one returns a static BIGNUM with value 1. */
+OPENSSL_EXPORT const BIGNUM *BN_value_one(void);
+
+/* BN_with_flags initialises a stack allocated |BIGNUM| with pointers to the
+ * contents of |in| but with |flags| ORed into the flags field.
+ *
+ * Note: the two BIGNUMs share state and so |out| should /not/ be passed to
+ * |BN_free|. */
+OPENSSL_EXPORT void BN_with_flags(BIGNUM *out, const BIGNUM *in, int flags);
+
+
+/* Basic functions. */
+
+/* BN_num_bits returns the minimum number of bits needed to represent the
+ * absolute value of |bn|. */
+OPENSSL_EXPORT unsigned BN_num_bits(const BIGNUM *bn);
+
+/* BN_num_bytes returns the minimum number of bytes needed to represent the
+ * absolute value of |bn|. */
+OPENSSL_EXPORT unsigned BN_num_bytes(const BIGNUM *bn);
+
+/* BN_zero sets |bn| to zero. */
+OPENSSL_EXPORT void BN_zero(BIGNUM *bn);
+
+/* BN_one sets |bn| to one. It returns one on success or zero on allocation
+ * failure. */
+OPENSSL_EXPORT int BN_one(BIGNUM *bn);
+
+/* BN_set_word sets |bn| to |value|. It returns one on success or zero on
+ * allocation failure. */
+OPENSSL_EXPORT int BN_set_word(BIGNUM *bn, BN_ULONG value);
+
+/* BN_set_negative sets the sign of |bn|. */
+OPENSSL_EXPORT void BN_set_negative(BIGNUM *bn, int sign);
+
+/* BN_is_negative returns one if |bn| is negative and zero otherwise. */
+OPENSSL_EXPORT int BN_is_negative(const BIGNUM *bn);
+
+/* BN_get_flags returns |bn->flags| & |flags|. */
+OPENSSL_EXPORT int BN_get_flags(const BIGNUM *bn, int flags);
+
+/* BN_set_flags sets |flags| on |bn|. */
+OPENSSL_EXPORT void BN_set_flags(BIGNUM *bn, int flags);
+
+
+/* Conversion functions. */
+
+/* BN_bin2bn sets |*ret| to the value of |len| bytes from |in|, interpreted as
+ * a big-endian number, and returns |ret|. If |ret| is NULL then a fresh
+ * |BIGNUM| is allocated and returned. It returns NULL on allocation
+ * failure. */
+OPENSSL_EXPORT BIGNUM *BN_bin2bn(const uint8_t *in, size_t len, BIGNUM *ret);
+
+/* BN_bn2bin serialises the absolute value of |in| to |out| as a big-endian
+ * integer, which must have |BN_num_bytes| of space available. It returns the
+ * number of bytes written. */
+OPENSSL_EXPORT size_t BN_bn2bin(const BIGNUM *in, uint8_t *out);
+
+/* BN_bn2bin_padded serialises the absolute value of |in| to |out| as a
+ * big-endian integer. The integer is padded with leading zeros up to size
+ * |len|. If |len| is smaller than |BN_num_bytes|, the function fails and
+ * returns 0. Otherwise, it returns 1. */
+OPENSSL_EXPORT int BN_bn2bin_padded(uint8_t *out, size_t len, const BIGNUM *in);
+
+/* BN_bn2cbb_padded behaves like |BN_bn2bin_padded| but writes to a |CBB|. */
+OPENSSL_EXPORT int BN_bn2cbb_padded(CBB *out, size_t len, const BIGNUM *in);
+
+/* BN_bn2hex returns an allocated string that contains a NUL-terminated, hex
+ * representation of |bn|. If |bn| is negative, the first char in the resulting
+ * string will be '-'. Returns NULL on allocation failure. */
+OPENSSL_EXPORT char *BN_bn2hex(const BIGNUM *bn);
+
+/* BN_hex2bn parses the leading hex number from |in|, which may be proceeded by
+ * a '-' to indicate a negative number and may contain trailing, non-hex data.
+ * If |outp| is not NULL, it constructs a BIGNUM equal to the hex number and
+ * stores it in |*outp|. If |*outp| is NULL then it allocates a new BIGNUM and
+ * updates |*outp|. It returns the number of bytes of |in| processed or zero on
+ * error. */
+OPENSSL_EXPORT int BN_hex2bn(BIGNUM **outp, const char *in);
+
+/* BN_bn2dec returns an allocated string that contains a NUL-terminated,
+ * decimal representation of |bn|. If |bn| is negative, the first char in the
+ * resulting string will be '-'. Returns NULL on allocation failure. */
+OPENSSL_EXPORT char *BN_bn2dec(const BIGNUM *a);
+
+/* BN_dec2bn parses the leading decimal number from |in|, which may be
+ * proceeded by a '-' to indicate a negative number and may contain trailing,
+ * non-decimal data. If |outp| is not NULL, it constructs a BIGNUM equal to the
+ * decimal number and stores it in |*outp|. If |*outp| is NULL then it
+ * allocates a new BIGNUM and updates |*outp|. It returns the number of bytes
+ * of |in| processed or zero on error. */
+OPENSSL_EXPORT int BN_dec2bn(BIGNUM **outp, const char *in);
+
+/* BN_asc2bn acts like |BN_dec2bn| or |BN_hex2bn| depending on whether |in|
+ * begins with "0X" or "0x" (indicating hex) or not (indicating decimal). A
+ * leading '-' is still permitted and comes before the optional 0X/0x. It
+ * returns one on success or zero on error. */
+OPENSSL_EXPORT int BN_asc2bn(BIGNUM **outp, const char *in);
+
+/* BN_print writes a hex encoding of |a| to |bio|. It returns one on success
+ * and zero on error. */
+OPENSSL_EXPORT int BN_print(BIO *bio, const BIGNUM *a);
+
+/* BN_print_fp acts like |BIO_print|, but wraps |fp| in a |BIO| first. */
+OPENSSL_EXPORT int BN_print_fp(FILE *fp, const BIGNUM *a);
+
+/* BN_get_word returns the absolute value of |bn| as a single word. If |bn| is
+ * too large to be represented as a single word, the maximum possible value
+ * will be returned. */
+OPENSSL_EXPORT BN_ULONG BN_get_word(const BIGNUM *bn);
+
+
+/* ASN.1 functions. */
+
+/* BN_cbs2unsigned parses a non-negative DER INTEGER from |cbs| writes the
+ * result to |ret|. It returns one on success and zero on failure. */
+OPENSSL_EXPORT int BN_cbs2unsigned(CBS *cbs, BIGNUM *ret);
+
+/* BN_cbs2unsigned_buggy acts like |BN_cbs2unsigned| but tolerates some invalid
+ * encodings. Do not use this function. */
+OPENSSL_EXPORT int BN_cbs2unsigned_buggy(CBS *cbs, BIGNUM *ret);
+
+/* BN_bn2cbb marshals |bn| as a non-negative DER INTEGER and appends the result
+ * to |cbb|. It returns one on success and zero on failure. */
+OPENSSL_EXPORT int BN_bn2cbb(CBB *cbb, const BIGNUM *bn);
+
+
+/* Internal functions.
+ *
+ * These functions are useful for code that is doing low-level manipulations of
+ * BIGNUM values. However, be sure that no other function in this file does
+ * what you want before turning to these. */
+
+/* bn_correct_top decrements |bn->top| until |bn->d[top-1]| is non-zero or
+ * until |top| is zero. */
+OPENSSL_EXPORT void bn_correct_top(BIGNUM *bn);
+
+/* bn_wexpand ensures that |bn| has at least |words| works of space without
+ * altering its value. It returns one on success or zero on allocation
+ * failure. */
+OPENSSL_EXPORT BIGNUM *bn_wexpand(BIGNUM *bn, size_t words);
+
+
+/* BIGNUM pools.
+ *
+ * Certain BIGNUM operations need to use many temporary variables and
+ * allocating and freeing them can be quite slow. Thus such opertions typically
+ * take a |BN_CTX| parameter, which contains a pool of |BIGNUMs|. The |ctx|
+ * argument to a public function may be NULL, in which case a local |BN_CTX|
+ * will be created just for the lifetime of that call.
+ *
+ * A function must call |BN_CTX_start| first. Then, |BN_CTX_get| may be called
+ * repeatedly to obtain temporary |BIGNUM|s. All |BN_CTX_get| calls must be made
+ * before calling any other functions that use the |ctx| as an argument.
+ *
+ * Finally, |BN_CTX_end| must be called before returning from the function.
+ * When |BN_CTX_end| is called, the |BIGNUM| pointers obtained from
+ * |BN_CTX_get| become invalid. */
+
+/* BN_CTX_new returns a new, empty BN_CTX or NULL on allocation failure. */
+OPENSSL_EXPORT BN_CTX *BN_CTX_new(void);
+
+/* BN_CTX_free frees all BIGNUMs contained in |ctx| and then frees |ctx|
+ * itself. */
+OPENSSL_EXPORT void BN_CTX_free(BN_CTX *ctx);
+
+/* BN_CTX_start "pushes" a new entry onto the |ctx| stack and allows future
+ * calls to |BN_CTX_get|. */
+OPENSSL_EXPORT void BN_CTX_start(BN_CTX *ctx);
+
+/* BN_CTX_get returns a new |BIGNUM|, or NULL on allocation failure. Once
+ * |BN_CTX_get| has returned NULL, all future calls will also return NULL until
+ * |BN_CTX_end| is called. */
+OPENSSL_EXPORT BIGNUM *BN_CTX_get(BN_CTX *ctx);
+
+/* BN_CTX_end invalidates all |BIGNUM|s returned from |BN_CTX_get| since the
+ * matching |BN_CTX_start| call. */
+OPENSSL_EXPORT void BN_CTX_end(BN_CTX *ctx);
+
+
+/* Simple arithmetic */
+
+/* BN_add sets |r| = |a| + |b|, where |r| may be the same pointer as either |a|
+ * or |b|. It returns one on success and zero on allocation failure. */
+OPENSSL_EXPORT int BN_add(BIGNUM *r, const BIGNUM *a, const BIGNUM *b);
+
+/* BN_uadd sets |r| = |a| + |b|, where |a| and |b| are non-negative and |r| may
+ * be the same pointer as either |a| or |b|. It returns one on success and zero
+ * on allocation failure. */
+OPENSSL_EXPORT int BN_uadd(BIGNUM *r, const BIGNUM *a, const BIGNUM *b);
+
+/* BN_add_word adds |w| to |a|. It returns one on success and zero otherwise. */
+OPENSSL_EXPORT int BN_add_word(BIGNUM *a, BN_ULONG w);
+
+/* BN_sub sets |r| = |a| - |b|, where |r| must be a distinct pointer from |a|
+ * and |b|. It returns one on success and zero on allocation failure. */
+OPENSSL_EXPORT int BN_sub(BIGNUM *r, const BIGNUM *a, const BIGNUM *b);
+
+/* BN_usub sets |r| = |a| - |b|, where |a| and |b| are non-negative integers,
+ * |b| < |a| and |r| must be a distinct pointer from |a| and |b|. It returns
+ * one on success and zero on allocation failure. */
+OPENSSL_EXPORT int BN_usub(BIGNUM *r, const BIGNUM *a, const BIGNUM *b);
+
+/* BN_sub_word subtracts |w| from |a|. It returns one on success and zero on
+ * allocation failure. */
+OPENSSL_EXPORT int BN_sub_word(BIGNUM *a, BN_ULONG w);
+
+/* BN_mul sets |r| = |a| * |b|, where |r| may be the same pointer as |a| or
+ * |b|. Returns one on success and zero otherwise. */
+OPENSSL_EXPORT int BN_mul(BIGNUM *r, const BIGNUM *a, const BIGNUM *b,
+                          BN_CTX *ctx);
+
+/* BN_mul_word sets |bn| = |bn| * |w|. It returns one on success or zero on
+ * allocation failure. */
+OPENSSL_EXPORT int BN_mul_word(BIGNUM *bn, BN_ULONG w);
+
+/* BN_sqr sets |r| = |a|^2 (i.e. squares), where |r| may be the same pointer as
+ * |a|. Returns one on success and zero otherwise. This is more efficient than
+ * BN_mul(r, a, a, ctx). */
+OPENSSL_EXPORT int BN_sqr(BIGNUM *r, const BIGNUM *a, BN_CTX *ctx);
+
+/* BN_div divides |numerator| by |divisor| and places the result in |quotient|
+ * and the remainder in |rem|. Either of |quotient| or |rem| may be NULL, in
+ * which case the respective value is not returned. The result is rounded
+ * towards zero; thus if |numerator| is negative, the remainder will be zero or
+ * negative. It returns one on success or zero on error. */
+OPENSSL_EXPORT int BN_div(BIGNUM *quotient, BIGNUM *rem,
+                          const BIGNUM *numerator, const BIGNUM *divisor,
+                          BN_CTX *ctx);
+
+/* BN_div_word sets |numerator| = |numerator|/|divisor| and returns the
+ * remainder or (BN_ULONG)-1 on error. */
+OPENSSL_EXPORT BN_ULONG BN_div_word(BIGNUM *numerator, BN_ULONG divisor);
+
+/* BN_sqrt sets |*out_sqrt| (which may be the same |BIGNUM| as |in|) to the
+ * square root of |in|, using |ctx|. It returns one on success or zero on
+ * error. Negative numbers and non-square numbers will result in an error with
+ * appropriate errors on the error queue. */
+OPENSSL_EXPORT int BN_sqrt(BIGNUM *out_sqrt, const BIGNUM *in, BN_CTX *ctx);
+
+
+/* Comparison functions */
+
+/* BN_cmp returns a value less than, equal to or greater than zero if |a| is
+ * less than, equal to or greater than |b|, respectively. */
+OPENSSL_EXPORT int BN_cmp(const BIGNUM *a, const BIGNUM *b);
+
+/* BN_ucmp returns a value less than, equal to or greater than zero if the
+ * absolute value of |a| is less than, equal to or greater than the absolute
+ * value of |b|, respectively. */
+OPENSSL_EXPORT int BN_ucmp(const BIGNUM *a, const BIGNUM *b);
+
+/* BN_abs_is_word returns one if the absolute value of |bn| equals |w| and zero
+ * otherwise. */
+OPENSSL_EXPORT int BN_abs_is_word(const BIGNUM *bn, BN_ULONG w);
+
+/* BN_is_zero returns one if |bn| is zero and zero otherwise. */
+OPENSSL_EXPORT int BN_is_zero(const BIGNUM *bn);
+
+/* BN_is_one returns one if |bn| equals one and zero otherwise. */
+OPENSSL_EXPORT int BN_is_one(const BIGNUM *bn);
+
+/* BN_is_word returns one if |bn| is exactly |w| and zero otherwise. */
+OPENSSL_EXPORT int BN_is_word(const BIGNUM *bn, BN_ULONG w);
+
+/* BN_is_odd returns one if |bn| is odd and zero otherwise. */
+OPENSSL_EXPORT int BN_is_odd(const BIGNUM *bn);
+
+
+/* Bitwise operations. */
+
+/* BN_lshift sets |r| equal to |a| << n. The |a| and |r| arguments may be the
+ * same |BIGNUM|. It returns one on success and zero on allocation failure. */
+OPENSSL_EXPORT int BN_lshift(BIGNUM *r, const BIGNUM *a, int n);
+
+/* BN_lshift1 sets |r| equal to |a| << 1, where |r| and |a| may be the same
+ * pointer. It returns one on success and zero on allocation failure. */
+OPENSSL_EXPORT int BN_lshift1(BIGNUM *r, const BIGNUM *a);
+
+/* BN_rshift sets |r| equal to |a| >> n, where |r| and |a| may be the same
+ * pointer. It returns one on success and zero on allocation failure. */
+OPENSSL_EXPORT int BN_rshift(BIGNUM *r, const BIGNUM *a, int n);
+
+/* BN_rshift1 sets |r| equal to |a| >> 1, where |r| and |a| may be the same
+ * pointer. It returns one on success and zero on allocation failure. */
+OPENSSL_EXPORT int BN_rshift1(BIGNUM *r, const BIGNUM *a);
+
+/* BN_set_bit sets the |n|th, least-significant bit in |a|. For example, if |a|
+ * is 2 then setting bit zero will make it 3. It returns one on success or zero
+ * on allocation failure. */
+OPENSSL_EXPORT int BN_set_bit(BIGNUM *a, int n);
+
+/* BN_clear_bit clears the |n|th, least-significant bit in |a|. For example, if
+ * |a| is 3, clearing bit zero will make it two. It returns one on success or
+ * zero on allocation failure. */
+OPENSSL_EXPORT int BN_clear_bit(BIGNUM *a, int n);
+
+/* BN_is_bit_set returns the value of the |n|th, least-significant bit in |a|,
+ * or zero if the bit doesn't exist. */
+OPENSSL_EXPORT int BN_is_bit_set(const BIGNUM *a, int n);
+
+/* BN_mask_bits truncates |a| so that it is only |n| bits long. It returns one
+ * on success or zero if |n| is greater than the length of |a| already. */
+OPENSSL_EXPORT int BN_mask_bits(BIGNUM *a, int n);
+
+
+/* Modulo arithmetic. */
+
+/* BN_mod_word returns |a| mod |w|. */
+OPENSSL_EXPORT BN_ULONG BN_mod_word(const BIGNUM *a, BN_ULONG w);
+
+/* BN_mod is a helper macro that calls |BN_div| and discards the quotient. */
+#define BN_mod(rem, numerator, divisor, ctx) \
+  BN_div(NULL, (rem), (numerator), (divisor), (ctx))
+
+/* BN_nnmod is a non-negative modulo function. It acts like |BN_mod|, but 0 <=
+ * |rem| < |divisor| is always true. It returns one on success and zero on
+ * error. */
+OPENSSL_EXPORT int BN_nnmod(BIGNUM *rem, const BIGNUM *numerator,
+                            const BIGNUM *divisor, BN_CTX *ctx);
+
+/* BN_mod_add sets |r| = |a| + |b| mod |m|. It returns one on success and zero
+ * on error. */
+OPENSSL_EXPORT int BN_mod_add(BIGNUM *r, const BIGNUM *a, const BIGNUM *b,
+                              const BIGNUM *m, BN_CTX *ctx);
+
+/* BN_mod_add_quick acts like |BN_mod_add| but requires that |a| and |b| be
+ * non-negative and less than |m|. */
+OPENSSL_EXPORT int BN_mod_add_quick(BIGNUM *r, const BIGNUM *a, const BIGNUM *b,
+                                    const BIGNUM *m);
+
+/* BN_mod_sub sets |r| = |a| - |b| mod |m|. It returns one on success and zero
+ * on error. */
+OPENSSL_EXPORT int BN_mod_sub(BIGNUM *r, const BIGNUM *a, const BIGNUM *b,
+                              const BIGNUM *m, BN_CTX *ctx);
+
+/* BN_mod_sub_quick acts like |BN_mod_sub| but requires that |a| and |b| be
+ * non-negative and less than |m|. */
+OPENSSL_EXPORT int BN_mod_sub_quick(BIGNUM *r, const BIGNUM *a, const BIGNUM *b,
+                                    const BIGNUM *m);
+
+/* BN_mod_mul sets |r| = |a|*|b| mod |m|. It returns one on success and zero
+ * on error. */
+OPENSSL_EXPORT int BN_mod_mul(BIGNUM *r, const BIGNUM *a, const BIGNUM *b,
+                              const BIGNUM *m, BN_CTX *ctx);
+
+/* BN_mod_sqr sets |r| = |a|^2 mod |m|. It returns one on success and zero
+ * on error. */
+OPENSSL_EXPORT int BN_mod_sqr(BIGNUM *r, const BIGNUM *a, const BIGNUM *m,
+                              BN_CTX *ctx);
+
+/* BN_mod_lshift sets |r| = (|a| << n) mod |m|, where |r| and |a| may be the
+ * same pointer. It returns one on success and zero on error. */
+OPENSSL_EXPORT int BN_mod_lshift(BIGNUM *r, const BIGNUM *a, int n,
+                                 const BIGNUM *m, BN_CTX *ctx);
+
+/* BN_mod_lshift_quick acts like |BN_mod_lshift| but requires that |a| be
+ * non-negative and less than |m|. */
+OPENSSL_EXPORT int BN_mod_lshift_quick(BIGNUM *r, const BIGNUM *a, int n,
+                                       const BIGNUM *m);
+
+/* BN_mod_lshift1 sets |r| = (|a| << 1) mod |m|, where |r| and |a| may be the
+ * same pointer. It returns one on success and zero on error. */
+OPENSSL_EXPORT int BN_mod_lshift1(BIGNUM *r, const BIGNUM *a, const BIGNUM *m,
+                                  BN_CTX *ctx);
+
+/* BN_mod_lshift1_quick acts like |BN_mod_lshift1| but requires that |a| be
+ * non-negative and less than |m|. */
+OPENSSL_EXPORT int BN_mod_lshift1_quick(BIGNUM *r, const BIGNUM *a,
+                                        const BIGNUM *m);
+
+/* BN_mod_sqrt returns a |BIGNUM|, r, such that r^2 == a (mod p). */
+OPENSSL_EXPORT BIGNUM *BN_mod_sqrt(BIGNUM *in, const BIGNUM *a, const BIGNUM *p,
+                                   BN_CTX *ctx);
+
+
+/* Random and prime number generation. */
+
+/* BN_rand sets |rnd| to a random number of length |bits|. If |top| is zero, the
+ * most-significant bit, if any, will be set. If |top| is one, the two most
+ * significant bits, if any, will be set.
+ *
+ * If |top| is -1 then no extra action will be taken and |BN_num_bits(rnd)| may
+ * not equal |bits| if the most significant bits randomly ended up as zeros.
+ *
+ * If |bottom| is non-zero, the least-significant bit, if any, will be set. The
+ * function returns one on success or zero otherwise. */
+OPENSSL_EXPORT int BN_rand(BIGNUM *rnd, int bits, int top, int bottom);
+
+/* BN_pseudo_rand is an alias for |BN_rand|. */
+OPENSSL_EXPORT int BN_pseudo_rand(BIGNUM *rnd, int bits, int top, int bottom);
+
+/* BN_rand_range sets |rnd| to a random value [0..range). It returns one on
+ * success and zero otherwise. */
+OPENSSL_EXPORT int BN_rand_range(BIGNUM *rnd, const BIGNUM *range);
+
+/* BN_pseudo_rand_range is an alias for BN_rand_range. */
+OPENSSL_EXPORT int BN_pseudo_rand_range(BIGNUM *rnd, const BIGNUM *range);
+
+/* BN_generate_dsa_nonce generates a random number 0 <= out < range. Unlike
+ * BN_rand_range, it also includes the contents of |priv| and |message| in the
+ * generation so that an RNG failure isn't fatal as long as |priv| remains
+ * secret. This is intended for use in DSA and ECDSA where an RNG weakness
+ * leads directly to private key exposure unless this function is used.
+ * It returns one on success and zero on error. */
+OPENSSL_EXPORT int BN_generate_dsa_nonce(BIGNUM *out, const BIGNUM *range,
+                                         const BIGNUM *priv,
+                                         const uint8_t *message,
+                                         size_t message_len, BN_CTX *ctx);
+
+/* BN_GENCB holds a callback function that is used by generation functions that
+ * can take a very long time to complete. Use |BN_GENCB_set| to initialise a
+ * |BN_GENCB| structure.
+ *
+ * The callback receives the address of that |BN_GENCB| structure as its last
+ * argument and the user is free to put an arbitary pointer in |arg|. The other
+ * arguments are set as follows:
+ *   event=BN_GENCB_GENERATED, n=i:   after generating the i'th possible prime
+ *                                    number.
+ *   event=BN_GENCB_PRIME_TEST, n=-1: when finished trial division primality
+ *                                    checks.
+ *   event=BN_GENCB_PRIME_TEST, n=i:  when the i'th primality test has finished.
+ *
+ * The callback can return zero to abort the generation progress or one to
+ * allow it to continue.
+ *
+ * When other code needs to call a BN generation function it will often take a
+ * BN_GENCB argument and may call the function with other argument values. */
+#define BN_GENCB_GENERATED 0
+#define BN_GENCB_PRIME_TEST 1
+
+struct bn_gencb_st {
+  void *arg;        /* callback-specific data */
+  int (*callback)(int event, int n, struct bn_gencb_st *);
+};
+
+/* BN_GENCB_set configures |callback| to call |f| and sets |callout->arg| to
+ * |arg|. */
+OPENSSL_EXPORT void BN_GENCB_set(BN_GENCB *callback,
+                                 int (*f)(int event, int n,
+                                          struct bn_gencb_st *),
+                                 void *arg);
+
+/* BN_GENCB_call calls |callback|, if not NULL, and returns the return value of
+ * the callback, or 1 if |callback| is NULL. */
+OPENSSL_EXPORT int BN_GENCB_call(BN_GENCB *callback, int event, int n);
+
+/* BN_generate_prime_ex sets |ret| to a prime number of |bits| length. If safe
+ * is non-zero then the prime will be such that (ret-1)/2 is also a prime.
+ * (This is needed for Diffie-Hellman groups to ensure that the only subgroups
+ * are of size 2 and (p-1)/2.).
+ *
+ * If |add| is not NULL, the prime will fulfill the condition |ret| % |add| ==
+ * |rem| in order to suit a given generator. (If |rem| is NULL then |ret| %
+ * |add| == 1.)
+ *
+ * If |cb| is not NULL, it will be called during processing to give an
+ * indication of progress. See the comments for |BN_GENCB|. It returns one on
+ * success and zero otherwise. */
+OPENSSL_EXPORT int BN_generate_prime_ex(BIGNUM *ret, int bits, int safe,
+                                        const BIGNUM *add, const BIGNUM *rem,
+                                        BN_GENCB *cb);
+
+/* BN_prime_checks is magic value that can be used as the |checks| argument to
+ * the primality testing functions in order to automatically select a number of
+ * Miller-Rabin checks that gives a false positive rate of ~2^{-80}. */
+#define BN_prime_checks 0
+
+/* BN_primality_test sets |*is_probably_prime| to one if |candidate| is
+ * probably a prime number by the Miller-Rabin test or zero if it's certainly
+ * not.
+ *
+ * If |do_trial_division| is non-zero then |candidate| will be tested against a
+ * list of small primes before Miller-Rabin tests. The probability of this
+ * function returning a false positive is 2^{2*checks}. If |checks| is
+ * |BN_prime_checks| then a value that results in approximately 2^{-80} false
+ * positive probability is used. If |cb| is not NULL then it is called during
+ * the checking process. See the comment above |BN_GENCB|.
+ *
+ * The function returns one on success and zero on error.
+ *
+ * (If you are unsure whether you want |do_trial_division|, don't set it.) */
+OPENSSL_EXPORT int BN_primality_test(int *is_probably_prime,
+                                     const BIGNUM *candidate, int checks,
+                                     BN_CTX *ctx, int do_trial_division,
+                                     BN_GENCB *cb);
+
+/* BN_is_prime_fasttest_ex returns one if |candidate| is probably a prime
+ * number by the Miller-Rabin test, zero if it's certainly not and -1 on error.
+ *
+ * If |do_trial_division| is non-zero then |candidate| will be tested against a
+ * list of small primes before Miller-Rabin tests. The probability of this
+ * function returning one when |candidate| is composite is 2^{2*checks}. If
+ * |checks| is |BN_prime_checks| then a value that results in approximately
+ * 2^{-80} false positive probability is used. If |cb| is not NULL then it is
+ * called during the checking process. See the comment above |BN_GENCB|.
+ *
+ * WARNING: deprecated. Use |BN_primality_test|. */
+OPENSSL_EXPORT int BN_is_prime_fasttest_ex(const BIGNUM *candidate, int checks,
+                                           BN_CTX *ctx, int do_trial_division,
+                                           BN_GENCB *cb);
+
+/* BN_is_prime_ex acts the same as |BN_is_prime_fasttest_ex| with
+ * |do_trial_division| set to zero.
+ *
+ * WARNING: deprecated: Use |BN_primality_test|. */
+OPENSSL_EXPORT int BN_is_prime_ex(const BIGNUM *candidate, int checks,
+                                  BN_CTX *ctx, BN_GENCB *cb);
+
+
+/* Number theory functions */
+
+/* BN_gcd sets |r| = gcd(|a|, |b|). It returns one on success and zero
+ * otherwise. */
+OPENSSL_EXPORT int BN_gcd(BIGNUM *r, const BIGNUM *a, const BIGNUM *b,
+                          BN_CTX *ctx);
+
+/* BN_mod_inverse sets |out| equal to |a|^-1, mod |n|. If either of |a| or |n|
+ * have |BN_FLG_CONSTTIME| set then the operation is performed in constant
+ * time. If |out| is NULL, a fresh BIGNUM is allocated. It returns the result
+ * or NULL on error. */
+OPENSSL_EXPORT BIGNUM *BN_mod_inverse(BIGNUM *out, const BIGNUM *a,
+                                      const BIGNUM *n, BN_CTX *ctx);
+
+/* BN_mod_inverse_ex acts like |BN_mod_inverse| except that, when it returns
+ * zero, it will set |*out_no_inverse| to one if the failure was caused because
+ * |a| has no inverse mod |n|. Otherwise it will set |*out_no_inverse| to
+ * zero. */
+OPENSSL_EXPORT BIGNUM *BN_mod_inverse_ex(BIGNUM *out, int *out_no_inverse,
+                                         const BIGNUM *a, const BIGNUM *n,
+                                         BN_CTX *ctx);
+
+/* BN_kronecker returns the Kronecker symbol of |a| and |b| (which is -1, 0 or
+ * 1), or -2 on error. */
+OPENSSL_EXPORT int BN_kronecker(const BIGNUM *a, const BIGNUM *b, BN_CTX *ctx);
+
+
+/* Montgomery arithmetic. */
+
+/* BN_MONT_CTX contains the precomputed values needed to work in a specific
+ * Montgomery domain. */
+
+/* BN_MONT_CTX_new returns a fresh BN_MONT_CTX or NULL on allocation failure. */
+OPENSSL_EXPORT BN_MONT_CTX *BN_MONT_CTX_new(void);
+
+/* BN_MONT_CTX_free frees memory associated with |mont|. */
+OPENSSL_EXPORT void BN_MONT_CTX_free(BN_MONT_CTX *mont);
+
+/* BN_MONT_CTX_copy sets |to| equal to |from|. It returns |to| on success or
+ * NULL on error. */
+OPENSSL_EXPORT BN_MONT_CTX *BN_MONT_CTX_copy(BN_MONT_CTX *to,
+                                             const BN_MONT_CTX *from);
+
+/* BN_MONT_CTX_set sets up a Montgomery context given the modulus, |mod|. It
+ * returns one on success and zero on error. */
+OPENSSL_EXPORT int BN_MONT_CTX_set(BN_MONT_CTX *mont, const BIGNUM *mod,
+                                   BN_CTX *ctx);
+
+/* BN_MONT_CTX_set_locked takes |lock| and checks whether |*pmont| is NULL. If
+ * so, it creates a new |BN_MONT_CTX| and sets the modulus for it to |mod|. It
+ * then stores it as |*pmont| and returns it, or NULL on error.
+ *
+ * If |*pmont| is already non-NULL then the existing value is returned. */
+BN_MONT_CTX *BN_MONT_CTX_set_locked(BN_MONT_CTX **pmont, CRYPTO_MUTEX *lock,
+                                    const BIGNUM *mod, BN_CTX *bn_ctx);
+
+/* BN_to_montgomery sets |ret| equal to |a| in the Montgomery domain. It
+ * returns one on success and zero on error. */
+OPENSSL_EXPORT int BN_to_montgomery(BIGNUM *ret, const BIGNUM *a,
+                                    const BN_MONT_CTX *mont, BN_CTX *ctx);
+
+/* BN_from_montgomery sets |ret| equal to |a| * R^-1, i.e. translates values
+ * out of the Montgomery domain. It returns one on success or zero on error. */
+OPENSSL_EXPORT int BN_from_montgomery(BIGNUM *ret, const BIGNUM *a,
+                                      const BN_MONT_CTX *mont, BN_CTX *ctx);
+
+/* BN_mod_mul_montgomery set |r| equal to |a| * |b|, in the Montgomery domain.
+ * Both |a| and |b| must already be in the Montgomery domain (by
+ * |BN_to_montgomery|). It returns one on success or zero on error. */
+OPENSSL_EXPORT int BN_mod_mul_montgomery(BIGNUM *r, const BIGNUM *a,
+                                         const BIGNUM *b,
+                                         const BN_MONT_CTX *mont, BN_CTX *ctx);
+
+
+/* Exponentiation. */
+
+/* BN_exp sets |r| equal to |a|^{|p|}. It does so with a square-and-multiply
+ * algorithm that leaks side-channel information. It returns one on success or
+ * zero otherwise. */
+OPENSSL_EXPORT int BN_exp(BIGNUM *r, const BIGNUM *a, const BIGNUM *p,
+                          BN_CTX *ctx);
+
+/* BN_mod_exp sets |r| equal to |a|^{|p|} mod |m|. It does so with the best
+ * algorithm for the values provided and can run in constant time if
+ * |BN_FLG_CONSTTIME| is set for |p|. It returns one on success or zero
+ * otherwise. */
+OPENSSL_EXPORT int BN_mod_exp(BIGNUM *r, const BIGNUM *a, const BIGNUM *p,
+                              const BIGNUM *m, BN_CTX *ctx);
+
+OPENSSL_EXPORT int BN_mod_exp_mont(BIGNUM *r, const BIGNUM *a, const BIGNUM *p,
+                                   const BIGNUM *m, BN_CTX *ctx,
+                                   const BN_MONT_CTX *mont);
+
+OPENSSL_EXPORT int BN_mod_exp_mont_consttime(BIGNUM *rr, const BIGNUM *a,
+                                             const BIGNUM *p, const BIGNUM *m,
+                                             BN_CTX *ctx,
+                                             const BN_MONT_CTX *mont);
+
+OPENSSL_EXPORT int BN_mod_exp_mont_word(BIGNUM *r, BN_ULONG a, const BIGNUM *p,
+                                        const BIGNUM *m, BN_CTX *ctx,
+                                        const BN_MONT_CTX *mont);
+OPENSSL_EXPORT int BN_mod_exp2_mont(BIGNUM *r, const BIGNUM *a1,
+                                    const BIGNUM *p1, const BIGNUM *a2,
+                                    const BIGNUM *p2, const BIGNUM *m,
+                                    BN_CTX *ctx, const BN_MONT_CTX *mont);
+
+
+/* Deprecated functions */
+
+/* BN_bn2mpi serialises the value of |in| to |out|, using a format that consists
+ * of the number's length in bytes represented as a 4-byte big-endian number,
+ * and the number itself in big-endian format, where the most significant bit
+ * signals a negative number. (The representation of numbers with the MSB set is
+ * prefixed with null byte). |out| must have sufficient space available; to
+ * find the needed amount of space, call the function with |out| set to NULL. */
+OPENSSL_EXPORT size_t BN_bn2mpi(const BIGNUM *in, uint8_t *out);
+
+/* BN_mpi2bn parses |len| bytes from |in| and returns the resulting value. The
+ * bytes at |in| are expected to be in the format emitted by |BN_bn2mpi|.
+ *
+ * If |out| is NULL then a fresh |BIGNUM| is allocated and returned, otherwise
+ * |out| is reused and returned. On error, NULL is returned and the error queue
+ * is updated. */
+OPENSSL_EXPORT BIGNUM *BN_mpi2bn(const uint8_t *in, size_t len, BIGNUM *out);
+
+
+/* Private functions */
+
+struct bignum_st {
+  BN_ULONG *d; /* Pointer to an array of 'BN_BITS2' bit chunks in little-endian
+                  order. */
+  int top;   /* Index of last used element in |d|, plus one. */
+  int dmax;  /* Size of |d|, in words. */
+  int neg;   /* one if the number is negative */
+  int flags; /* bitmask of BN_FLG_* values */
+};
+
+struct bn_mont_ctx_st {
+  BIGNUM RR; /* used to convert to montgomery form */
+  BIGNUM N;  /* The modulus */
+  BN_ULONG n0[2]; /* least significant words of (R*Ri-1)/N */
+};
+
+OPENSSL_EXPORT unsigned BN_num_bits_word(BN_ULONG l);
+
+#define BN_FLG_MALLOCED 0x01
+#define BN_FLG_STATIC_DATA 0x02
+/* avoid leaking exponent information through timing, BN_mod_exp_mont() will
+ * call BN_mod_exp_mont_consttime, BN_div() will call BN_div_no_branch,
+ * BN_mod_inverse() will call BN_mod_inverse_no_branch. */
+#define BN_FLG_CONSTTIME 0x04
+
+
+/* Android compatibility section.
+ *
+ * These functions are declared, temporarily, for Android because
+ * wpa_supplicant will take a little time to sync with upstream. Outside of
+ * Android they'll have no definition. */
+
+OPENSSL_EXPORT BIGNUM *get_rfc3526_prime_1536(BIGNUM *bn);
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#define BN_R_ARG2_LT_ARG3 100
+#define BN_R_BAD_RECIPROCAL 101
+#define BN_R_BIGNUM_TOO_LONG 102
+#define BN_R_BITS_TOO_SMALL 103
+#define BN_R_CALLED_WITH_EVEN_MODULUS 104
+#define BN_R_DIV_BY_ZERO 105
+#define BN_R_EXPAND_ON_STATIC_BIGNUM_DATA 106
+#define BN_R_INPUT_NOT_REDUCED 107
+#define BN_R_INVALID_RANGE 108
+#define BN_R_NEGATIVE_NUMBER 109
+#define BN_R_NOT_A_SQUARE 110
+#define BN_R_NOT_INITIALIZED 111
+#define BN_R_NO_INVERSE 112
+#define BN_R_PRIVATE_KEY_TOO_LARGE 113
+#define BN_R_P_IS_NOT_PRIME 114
+#define BN_R_TOO_MANY_ITERATIONS 115
+#define BN_R_TOO_MANY_TEMPORARY_VARIABLES 116
+#define BN_R_BAD_ENCODING 117
+#define BN_R_ENCODE_ERROR 118
+
+#endif  /* OPENSSL_HEADER_BN_H */

+ 118 - 0
app/src/main/jni/openssl/include/openssl/buf.h

@@ -0,0 +1,118 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_BUFFER_H
+#define OPENSSL_HEADER_BUFFER_H
+
+#include <openssl/base.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* Memory and string functions, see also mem.h. */
+
+
+/* BUF_MEM is a generic buffer object used by OpenSSL. */
+struct buf_mem_st {
+  size_t length; /* current number of bytes */
+  char *data;
+  size_t max; /* size of buffer */
+};
+
+/* BUF_MEM_new creates a new BUF_MEM which has no allocated data buffer. */
+OPENSSL_EXPORT BUF_MEM *BUF_MEM_new(void);
+
+/* BUF_MEM_free frees |buf->data| if needed and then frees |buf| itself. */
+OPENSSL_EXPORT void BUF_MEM_free(BUF_MEM *buf);
+
+/* BUF_MEM_grow ensures that |buf| has length |len| and allocates memory if
+ * needed. If the length of |buf| increased, the new bytes are filled with
+ * zeros. It returns the length of |buf|, or zero if there's an error. */
+OPENSSL_EXPORT size_t BUF_MEM_grow(BUF_MEM *buf, size_t len);
+
+/* BUF_MEM_grow_clean acts the same as |BUF_MEM_grow|, but clears the previous
+ * contents of memory if reallocing. */
+OPENSSL_EXPORT size_t BUF_MEM_grow_clean(BUF_MEM *str, size_t len);
+
+/* BUF_strdup returns an allocated, duplicate of |str|. */
+OPENSSL_EXPORT char *BUF_strdup(const char *str);
+
+/* BUF_strnlen returns the number of characters in |str|, excluding the NUL
+ * byte, but at most |max_len|. This function never reads more than |max_len|
+ * bytes from |str|. */
+OPENSSL_EXPORT size_t BUF_strnlen(const char *str, size_t max_len);
+
+/* BUF_strndup returns an allocated, duplicate of |str|, which is, at most,
+ * |size| bytes. The result is always NUL terminated. */
+OPENSSL_EXPORT char *BUF_strndup(const char *str, size_t size);
+
+/* BUF_memdup returns an allocated, duplicate of |size| bytes from |data|. */
+OPENSSL_EXPORT void *BUF_memdup(const void *data, size_t size);
+
+/* BUF_strlcpy acts like strlcpy(3). */
+OPENSSL_EXPORT size_t BUF_strlcpy(char *dst, const char *src, size_t dst_size);
+
+/* BUF_strlcat acts like strlcat(3). */
+OPENSSL_EXPORT size_t BUF_strlcat(char *dst, const char *src, size_t size);
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_BUFFER_H */

+ 18 - 0
app/src/main/jni/openssl/include/openssl/buffer.h

@@ -0,0 +1,18 @@
+/* Copyright (c) 2015, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+/* This header is provided in order to make compiling against code that expects
+   OpenSSL easier. */
+
+#include "buf.h"

+ 378 - 0
app/src/main/jni/openssl/include/openssl/bytestring.h

@@ -0,0 +1,378 @@
+/* Copyright (c) 2014, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+#ifndef OPENSSL_HEADER_BYTESTRING_H
+#define OPENSSL_HEADER_BYTESTRING_H
+
+#include <openssl/base.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* Bytestrings are used for parsing and building TLS and ASN.1 messages.
+ *
+ * A "CBS" (CRYPTO ByteString) represents a string of bytes in memory and
+ * provides utility functions for safely parsing length-prefixed structures
+ * like TLS and ASN.1 from it.
+ *
+ * A "CBB" (CRYPTO ByteBuilder) is a memory buffer that grows as needed and
+ * provides utility functions for building length-prefixed messages. */
+
+
+/* CRYPTO ByteString */
+
+struct cbs_st {
+  const uint8_t *data;
+  size_t len;
+};
+
+/* CBS_init sets |cbs| to point to |data|. It does not take ownership of
+ * |data|. */
+OPENSSL_EXPORT void CBS_init(CBS *cbs, const uint8_t *data, size_t len);
+
+/* CBS_skip advances |cbs| by |len| bytes. It returns one on success and zero
+ * otherwise. */
+OPENSSL_EXPORT int CBS_skip(CBS *cbs, size_t len);
+
+/* CBS_data returns a pointer to the contents of |cbs|. */
+OPENSSL_EXPORT const uint8_t *CBS_data(const CBS *cbs);
+
+/* CBS_len returns the number of bytes remaining in |cbs|. */
+OPENSSL_EXPORT size_t CBS_len(const CBS *cbs);
+
+/* CBS_stow copies the current contents of |cbs| into |*out_ptr| and
+ * |*out_len|. If |*out_ptr| is not NULL, the contents are freed with
+ * OPENSSL_free. It returns one on success and zero on allocation failure. On
+ * success, |*out_ptr| should be freed with OPENSSL_free. If |cbs| is empty,
+ * |*out_ptr| will be NULL. */
+OPENSSL_EXPORT int CBS_stow(const CBS *cbs, uint8_t **out_ptr, size_t *out_len);
+
+/* CBS_strdup copies the current contents of |cbs| into |*out_ptr| as a
+ * NUL-terminated C string. If |*out_ptr| is not NULL, the contents are freed
+ * with OPENSSL_free. It returns one on success and zero on allocation
+ * failure. On success, |*out_ptr| should be freed with OPENSSL_free.
+ *
+ * NOTE: If |cbs| contains NUL bytes, the string will be truncated. Call
+ * |CBS_contains_zero_byte(cbs)| to check for NUL bytes. */
+OPENSSL_EXPORT int CBS_strdup(const CBS *cbs, char **out_ptr);
+
+/* CBS_contains_zero_byte returns one if the current contents of |cbs| contains
+ * a NUL byte and zero otherwise. */
+OPENSSL_EXPORT int CBS_contains_zero_byte(const CBS *cbs);
+
+/* CBS_mem_equal compares the current contents of |cbs| with the |len| bytes
+ * starting at |data|. If they're equal, it returns one, otherwise zero. If the
+ * lengths match, it uses a constant-time comparison. */
+OPENSSL_EXPORT int CBS_mem_equal(const CBS *cbs, const uint8_t *data,
+                                 size_t len);
+
+/* CBS_get_u8 sets |*out| to the next uint8_t from |cbs| and advances |cbs|. It
+ * returns one on success and zero on error. */
+OPENSSL_EXPORT int CBS_get_u8(CBS *cbs, uint8_t *out);
+
+/* CBS_get_u16 sets |*out| to the next, big-endian uint16_t from |cbs| and
+ * advances |cbs|. It returns one on success and zero on error. */
+OPENSSL_EXPORT int CBS_get_u16(CBS *cbs, uint16_t *out);
+
+/* CBS_get_u24 sets |*out| to the next, big-endian 24-bit value from |cbs| and
+ * advances |cbs|. It returns one on success and zero on error. */
+OPENSSL_EXPORT int CBS_get_u24(CBS *cbs, uint32_t *out);
+
+/* CBS_get_u32 sets |*out| to the next, big-endian uint32_t value from |cbs|
+ * and advances |cbs|. It returns one on success and zero on error. */
+OPENSSL_EXPORT int CBS_get_u32(CBS *cbs, uint32_t *out);
+
+/* CBS_get_bytes sets |*out| to the next |len| bytes from |cbs| and advances
+ * |cbs|. It returns one on success and zero on error. */
+OPENSSL_EXPORT int CBS_get_bytes(CBS *cbs, CBS *out, size_t len);
+
+/* CBS_copy_bytes copies the next |len| bytes from |cbs| to |out| and advances
+ * |cbs|. It returns one on success and zero on error. */
+OPENSSL_EXPORT int CBS_copy_bytes(CBS *cbs, uint8_t *out, size_t len);
+
+/* CBS_get_u8_length_prefixed sets |*out| to the contents of an 8-bit,
+ * length-prefixed value from |cbs| and advances |cbs| over it. It returns one
+ * on success and zero on error. */
+OPENSSL_EXPORT int CBS_get_u8_length_prefixed(CBS *cbs, CBS *out);
+
+/* CBS_get_u16_length_prefixed sets |*out| to the contents of a 16-bit,
+ * big-endian, length-prefixed value from |cbs| and advances |cbs| over it. It
+ * returns one on success and zero on error. */
+OPENSSL_EXPORT int CBS_get_u16_length_prefixed(CBS *cbs, CBS *out);
+
+/* CBS_get_u24_length_prefixed sets |*out| to the contents of a 24-bit,
+ * big-endian, length-prefixed value from |cbs| and advances |cbs| over it. It
+ * returns one on success and zero on error. */
+OPENSSL_EXPORT int CBS_get_u24_length_prefixed(CBS *cbs, CBS *out);
+
+
+/* Parsing ASN.1 */
+
+#define CBS_ASN1_BOOLEAN 0x1
+#define CBS_ASN1_INTEGER 0x2
+#define CBS_ASN1_BITSTRING 0x3
+#define CBS_ASN1_OCTETSTRING 0x4
+#define CBS_ASN1_NULL 0x5
+#define CBS_ASN1_OBJECT 0x6
+#define CBS_ASN1_ENUMERATED 0xa
+#define CBS_ASN1_SEQUENCE (0x10 | CBS_ASN1_CONSTRUCTED)
+#define CBS_ASN1_SET (0x11 | CBS_ASN1_CONSTRUCTED)
+#define CBS_ASN1_GENERALIZEDTIME 0x18
+
+#define CBS_ASN1_CONSTRUCTED 0x20
+#define CBS_ASN1_CONTEXT_SPECIFIC 0x80
+
+/* CBS_get_asn1 sets |*out| to the contents of DER-encoded, ASN.1 element (not
+ * including tag and length bytes) and advances |cbs| over it. The ASN.1
+ * element must match |tag_value|. It returns one on success and zero
+ * on error.
+ *
+ * Tag numbers greater than 30 are not supported (i.e. short form only). */
+OPENSSL_EXPORT int CBS_get_asn1(CBS *cbs, CBS *out, unsigned tag_value);
+
+/* CBS_get_asn1_element acts like |CBS_get_asn1| but |out| will include the
+ * ASN.1 header bytes too. */
+OPENSSL_EXPORT int CBS_get_asn1_element(CBS *cbs, CBS *out, unsigned tag_value);
+
+/* CBS_peek_asn1_tag looks ahead at the next ASN.1 tag and returns one
+ * if the next ASN.1 element on |cbs| would have tag |tag_value|. If
+ * |cbs| is empty or the tag does not match, it returns zero. Note: if
+ * it returns one, CBS_get_asn1 may still fail if the rest of the
+ * element is malformed. */
+OPENSSL_EXPORT int CBS_peek_asn1_tag(const CBS *cbs, unsigned tag_value);
+
+/* CBS_get_any_asn1_element sets |*out| to contain the next ASN.1 element from
+ * |*cbs| (including header bytes) and advances |*cbs|. It sets |*out_tag| to
+ * the tag number and |*out_header_len| to the length of the ASN.1 header. Each
+ * of |out|, |out_tag|, and |out_header_len| may be NULL to ignore the value.
+ *
+ * Tag numbers greater than 30 are not supported (i.e. short form only). */
+OPENSSL_EXPORT int CBS_get_any_asn1_element(CBS *cbs, CBS *out,
+                                            unsigned *out_tag,
+                                            size_t *out_header_len);
+
+/* CBS_get_any_ber_asn1_element acts the same as |CBS_get_any_asn1_element| but
+ * also allows indefinite-length elements to be returned. In that case,
+ * |*out_header_len| and |CBS_len(out)| will both be two as only the header is
+ * returned, otherwise it behaves the same as the previous function. */
+OPENSSL_EXPORT int CBS_get_any_ber_asn1_element(CBS *cbs, CBS *out,
+                                                unsigned *out_tag,
+                                                size_t *out_header_len);
+
+/* CBS_get_asn1_uint64 gets an ASN.1 INTEGER from |cbs| using |CBS_get_asn1|
+ * and sets |*out| to its value. It returns one on success and zero on error,
+ * where error includes the integer being negative, or too large to represent
+ * in 64 bits. */
+OPENSSL_EXPORT int CBS_get_asn1_uint64(CBS *cbs, uint64_t *out);
+
+/* CBS_get_optional_asn1 gets an optional explicitly-tagged element from |cbs|
+ * tagged with |tag| and sets |*out| to its contents. If present and if
+ * |out_present| is not NULL, it sets |*out_present| to one, otherwise zero. It
+ * returns one on success, whether or not the element was present, and zero on
+ * decode failure. */
+OPENSSL_EXPORT int CBS_get_optional_asn1(CBS *cbs, CBS *out, int *out_present,
+                                         unsigned tag);
+
+/* CBS_get_optional_asn1_octet_string gets an optional
+ * explicitly-tagged OCTET STRING from |cbs|. If present, it sets
+ * |*out| to the string and |*out_present| to one. Otherwise, it sets
+ * |*out| to empty and |*out_present| to zero. |out_present| may be
+ * NULL. It returns one on success, whether or not the element was
+ * present, and zero on decode failure. */
+OPENSSL_EXPORT int CBS_get_optional_asn1_octet_string(CBS *cbs, CBS *out,
+                                                      int *out_present,
+                                                      unsigned tag);
+
+/* CBS_get_optional_asn1_uint64 gets an optional explicitly-tagged
+ * INTEGER from |cbs|. If present, it sets |*out| to the
+ * value. Otherwise, it sets |*out| to |default_value|. It returns one
+ * on success, whether or not the element was present, and zero on
+ * decode failure. */
+OPENSSL_EXPORT int CBS_get_optional_asn1_uint64(CBS *cbs, uint64_t *out,
+                                                unsigned tag,
+                                                uint64_t default_value);
+
+/* CBS_get_optional_asn1_bool gets an optional, explicitly-tagged BOOLEAN from
+ * |cbs|. If present, it sets |*out| to either zero or one, based on the
+ * boolean. Otherwise, it sets |*out| to |default_value|. It returns one on
+ * success, whether or not the element was present, and zero on decode
+ * failure. */
+OPENSSL_EXPORT int CBS_get_optional_asn1_bool(CBS *cbs, int *out, unsigned tag,
+                                              int default_value);
+
+
+/* CRYPTO ByteBuilder.
+ *
+ * |CBB| objects allow one to build length-prefixed serialisations. A |CBB|
+ * object is associated with a buffer and new buffers are created with
+ * |CBB_init|. Several |CBB| objects can point at the same buffer when a
+ * length-prefix is pending, however only a single |CBB| can be 'current' at
+ * any one time. For example, if one calls |CBB_add_u8_length_prefixed| then
+ * the new |CBB| points at the same buffer as the original. But if the original
+ * |CBB| is used then the length prefix is written out and the new |CBB| must
+ * not be used again.
+ *
+ * If one needs to force a length prefix to be written out because a |CBB| is
+ * going out of scope, use |CBB_flush|. */
+
+struct cbb_buffer_st {
+  uint8_t *buf;
+  size_t len;      /* The number of valid bytes. */
+  size_t cap;      /* The size of buf. */
+  char can_resize; /* One iff |buf| is owned by this object. If not then |buf|
+                      cannot be resized. */
+};
+
+struct cbb_st {
+  struct cbb_buffer_st *base;
+  /* child points to a child CBB if a length-prefix is pending. */
+  CBB *child;
+  /* offset is the number of bytes from the start of |base->buf| to this |CBB|'s
+   * pending length prefix. */
+  size_t offset;
+  /* pending_len_len contains the number of bytes in this |CBB|'s pending
+   * length-prefix, or zero if no length-prefix is pending. */
+  uint8_t pending_len_len;
+  char pending_is_asn1;
+  /* is_top_level is true iff this is a top-level |CBB| (as opposed to a child
+   * |CBB|). Top-level objects are valid arguments for |CBB_finish|. */
+  char is_top_level;
+};
+
+/* CBB_zero sets an uninitialised |cbb| to the zero state. It must be
+ * initialised with |CBB_init| or |CBB_init_fixed| before use, but it is safe to
+ * call |CBB_cleanup| without a successful |CBB_init|. This may be used for more
+ * uniform cleanup of a |CBB|. */
+OPENSSL_EXPORT void CBB_zero(CBB *cbb);
+
+/* CBB_init initialises |cbb| with |initial_capacity|. Since a |CBB| grows as
+ * needed, the |initial_capacity| is just a hint. It returns one on success or
+ * zero on error. */
+OPENSSL_EXPORT int CBB_init(CBB *cbb, size_t initial_capacity);
+
+/* CBB_init_fixed initialises |cbb| to write to |len| bytes at |buf|. Since
+ * |buf| cannot grow, trying to write more than |len| bytes will cause CBB
+ * functions to fail. It returns one on success or zero on error. */
+OPENSSL_EXPORT int CBB_init_fixed(CBB *cbb, uint8_t *buf, size_t len);
+
+/* CBB_cleanup frees all resources owned by |cbb| and other |CBB| objects
+ * writing to the same buffer. This should be used in an error case where a
+ * serialisation is abandoned.
+ *
+ * This function can only be called on a "top level" |CBB|, i.e. one initialised
+ * with |CBB_init| or |CBB_init_fixed|, or a |CBB| set to the zero state with
+ * |CBB_zero|. */
+OPENSSL_EXPORT void CBB_cleanup(CBB *cbb);
+
+/* CBB_finish completes any pending length prefix and sets |*out_data| to a
+ * malloced buffer and |*out_len| to the length of that buffer. The caller
+ * takes ownership of the buffer and, unless the buffer was fixed with
+ * |CBB_init_fixed|, must call |OPENSSL_free| when done.
+ *
+ * It can only be called on a "top level" |CBB|, i.e. one initialised with
+ * |CBB_init| or |CBB_init_fixed|. It returns one on success and zero on
+ * error. */
+OPENSSL_EXPORT int CBB_finish(CBB *cbb, uint8_t **out_data, size_t *out_len);
+
+/* CBB_flush causes any pending length prefixes to be written out and any child
+ * |CBB| objects of |cbb| to be invalidated. It returns one on success or zero
+ * on error. */
+OPENSSL_EXPORT int CBB_flush(CBB *cbb);
+
+/* CBB_data returns a pointer to the bytes written to |cbb|. It does not flush
+ * |cbb|. The pointer is valid until the next operation to |cbb|.
+ *
+ * To avoid unfinalized length prefixes, it is a fatal error to call this on a
+ * CBB with any active children. */
+OPENSSL_EXPORT const uint8_t *CBB_data(const CBB *cbb);
+
+/* CBB_len returns the number of bytes written to |cbb|. It does not flush
+ * |cbb|.
+ *
+ * To avoid unfinalized length prefixes, it is a fatal error to call this on a
+ * CBB with any active children. */
+OPENSSL_EXPORT size_t CBB_len(const CBB *cbb);
+
+/* CBB_add_u8_length_prefixed sets |*out_contents| to a new child of |cbb|. The
+ * data written to |*out_contents| will be prefixed in |cbb| with an 8-bit
+ * length. It returns one on success or zero on error. */
+OPENSSL_EXPORT int CBB_add_u8_length_prefixed(CBB *cbb, CBB *out_contents);
+
+/* CBB_add_u16_length_prefixed sets |*out_contents| to a new child of |cbb|.
+ * The data written to |*out_contents| will be prefixed in |cbb| with a 16-bit,
+ * big-endian length. It returns one on success or zero on error. */
+OPENSSL_EXPORT int CBB_add_u16_length_prefixed(CBB *cbb, CBB *out_contents);
+
+/* CBB_add_u24_length_prefixed sets |*out_contents| to a new child of |cbb|.
+ * The data written to |*out_contents| will be prefixed in |cbb| with a 24-bit,
+ * big-endian length. It returns one on success or zero on error. */
+OPENSSL_EXPORT int CBB_add_u24_length_prefixed(CBB *cbb, CBB *out_contents);
+
+/* CBB_add_asn1 sets |*out_contents| to a |CBB| into which the contents of an
+ * ASN.1 object can be written. The |tag| argument will be used as the tag for
+ * the object. Passing in |tag| number 31 will return in an error since only
+ * single octet identifiers are supported. It returns one on success or zero
+ * on error. */
+OPENSSL_EXPORT int CBB_add_asn1(CBB *cbb, CBB *out_contents, uint8_t tag);
+
+/* CBB_add_bytes appends |len| bytes from |data| to |cbb|. It returns one on
+ * success and zero otherwise. */
+OPENSSL_EXPORT int CBB_add_bytes(CBB *cbb, const uint8_t *data, size_t len);
+
+/* CBB_add_space appends |len| bytes to |cbb| and sets |*out_data| to point to
+ * the beginning of that space. The caller must then write |len| bytes of
+ * actual contents to |*out_data|. It returns one on success and zero
+ * otherwise. */
+OPENSSL_EXPORT int CBB_add_space(CBB *cbb, uint8_t **out_data, size_t len);
+
+/* CBB_reserve ensures |cbb| has room for |len| additional bytes and sets
+ * |*out_data| to point to the beginning of that space. It returns one on
+ * success and zero otherwise. The caller may write up to |len| bytes to
+ * |*out_data| and call |CBB_did_write| to complete the write. |*out_data| is
+ * valid until the next operation on |cbb| or an ancestor |CBB|. */
+OPENSSL_EXPORT int CBB_reserve(CBB *cbb, uint8_t **out_data, size_t len);
+
+/* CBB_did_write advances |cbb| by |len| bytes, assuming the space has been
+ * written to by the caller. It returns one on success and zero on error. */
+OPENSSL_EXPORT int CBB_did_write(CBB *cbb, size_t len);
+
+/* CBB_add_u8 appends an 8-bit number from |value| to |cbb|. It returns one on
+ * success and zero otherwise. */
+OPENSSL_EXPORT int CBB_add_u8(CBB *cbb, uint8_t value);
+
+/* CBB_add_u16 appends a 16-bit, big-endian number from |value| to |cbb|. It
+ * returns one on success and zero otherwise. */
+OPENSSL_EXPORT int CBB_add_u16(CBB *cbb, uint16_t value);
+
+/* CBB_add_u24 appends a 24-bit, big-endian number from |value| to |cbb|. It
+ * returns one on success and zero otherwise. */
+OPENSSL_EXPORT int CBB_add_u24(CBB *cbb, uint32_t value);
+
+/* CBB_discard_child discards the current unflushed child of |cbb|. Neither the
+ * child's contents nor the length prefix will be included in the output. */
+OPENSSL_EXPORT void CBB_discard_child(CBB *cbb);
+
+/* CBB_add_asn1_uint64 writes an ASN.1 INTEGER into |cbb| using |CBB_add_asn1|
+ * and writes |value| in its contents. It returns one on success and zero on
+ * error. */
+OPENSSL_EXPORT int CBB_add_asn1_uint64(CBB *cbb, uint64_t value);
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_BYTESTRING_H */

+ 96 - 0
app/src/main/jni/openssl/include/openssl/cast.h

@@ -0,0 +1,96 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_CAST_H
+#define OPENSSL_HEADER_CAST_H
+
+#include <openssl/base.h>
+
+#ifdef  __cplusplus
+extern "C" {
+#endif
+
+
+#define CAST_ENCRYPT 1
+#define CAST_DECRYPT 0
+
+#define CAST_BLOCK 8
+#define CAST_KEY_LENGTH 16
+
+typedef struct cast_key_st {
+  uint32_t data[32];
+  int short_key; /* Use reduced rounds for short key */
+} CAST_KEY;
+
+OPENSSL_EXPORT void CAST_set_key(CAST_KEY *key, size_t len,
+                                 const uint8_t *data);
+OPENSSL_EXPORT void CAST_ecb_encrypt(const uint8_t *in, uint8_t *out,
+                                     const CAST_KEY *key, int enc);
+OPENSSL_EXPORT void CAST_encrypt(uint32_t *data, const CAST_KEY *key);
+OPENSSL_EXPORT void CAST_decrypt(uint32_t *data, const CAST_KEY *key);
+OPENSSL_EXPORT void CAST_cbc_encrypt(const uint8_t *in, uint8_t *out,
+                                     long length, const CAST_KEY *ks,
+                                     uint8_t *iv, int enc);
+
+OPENSSL_EXPORT void CAST_cfb64_encrypt(const uint8_t *in, uint8_t *out,
+                                       long length, const CAST_KEY *schedule,
+                                       uint8_t *ivec, int *num, int enc);
+
+#ifdef  __cplusplus
+}
+#endif
+
+#endif  /* OPENSSL_HEADER_CAST_H */

+ 37 - 0
app/src/main/jni/openssl/include/openssl/chacha.h

@@ -0,0 +1,37 @@
+/* Copyright (c) 2014, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+#ifndef OPENSSL_HEADER_CHACHA_H
+#define OPENSSL_HEADER_CHACHA_H
+
+#include <openssl/base.h>
+
+#ifdef  __cplusplus
+extern "C" {
+#endif
+
+
+/* CRYPTO_chacha_20 encrypts |in_len| bytes from |in| with the given key and
+ * nonce and writes the result to |out|, which may be equal to |in|. The
+ * initial block counter is specified by |counter|. */
+OPENSSL_EXPORT void CRYPTO_chacha_20(uint8_t *out, const uint8_t *in,
+                                     size_t in_len, const uint8_t key[32],
+                                     const uint8_t nonce[12], uint32_t counter);
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_CHACHA_H */

+ 571 - 0
app/src/main/jni/openssl/include/openssl/cipher.h

@@ -0,0 +1,571 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_CIPHER_H
+#define OPENSSL_HEADER_CIPHER_H
+
+#include <openssl/base.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* Ciphers. */
+
+
+/* Cipher primitives.
+ *
+ * The following functions return |EVP_CIPHER| objects that implement the named
+ * cipher algorithm. */
+
+OPENSSL_EXPORT const EVP_CIPHER *EVP_rc4(void);
+
+OPENSSL_EXPORT const EVP_CIPHER *EVP_des_cbc(void);
+OPENSSL_EXPORT const EVP_CIPHER *EVP_des_ecb(void);
+OPENSSL_EXPORT const EVP_CIPHER *EVP_des_ede(void);
+OPENSSL_EXPORT const EVP_CIPHER *EVP_des_ede_cbc(void);
+OPENSSL_EXPORT const EVP_CIPHER *EVP_des_ede3_cbc(void);
+
+OPENSSL_EXPORT const EVP_CIPHER *EVP_aes_128_ecb(void);
+OPENSSL_EXPORT const EVP_CIPHER *EVP_aes_128_cbc(void);
+OPENSSL_EXPORT const EVP_CIPHER *EVP_aes_128_ctr(void);
+OPENSSL_EXPORT const EVP_CIPHER *EVP_aes_128_ofb(void);
+
+OPENSSL_EXPORT const EVP_CIPHER *EVP_aes_256_ecb(void);
+OPENSSL_EXPORT const EVP_CIPHER *EVP_aes_256_cbc(void);
+OPENSSL_EXPORT const EVP_CIPHER *EVP_aes_256_ctr(void);
+OPENSSL_EXPORT const EVP_CIPHER *EVP_aes_256_ofb(void);
+OPENSSL_EXPORT const EVP_CIPHER *EVP_aes_256_xts(void);
+
+/* EVP_enc_null returns a 'cipher' that passes plaintext through as
+ * ciphertext. */
+OPENSSL_EXPORT const EVP_CIPHER *EVP_enc_null(void);
+
+/* EVP_rc2_cbc returns a cipher that implements 128-bit RC2 in CBC mode. */
+OPENSSL_EXPORT const EVP_CIPHER *EVP_rc2_cbc(void);
+
+/* EVP_rc2_40_cbc returns a cipher that implements 40-bit RC2 in CBC mode. This
+ * is obviously very, very weak and is included only in order to read PKCS#12
+ * files, which often encrypt the certificate chain using this cipher. It is
+ * deliberately not exported. */
+const EVP_CIPHER *EVP_rc2_40_cbc(void);
+
+/* EVP_get_cipherbynid returns the cipher corresponding to the given NID, or
+ * NULL if no such cipher is known. */
+OPENSSL_EXPORT const EVP_CIPHER *EVP_get_cipherbynid(int nid);
+
+
+/* Cipher context allocation.
+ *
+ * An |EVP_CIPHER_CTX| represents the state of an encryption or decryption in
+ * progress. */
+
+/* EVP_CIPHER_CTX_init initialises an, already allocated, |EVP_CIPHER_CTX|. */
+OPENSSL_EXPORT void EVP_CIPHER_CTX_init(EVP_CIPHER_CTX *ctx);
+
+/* EVP_CIPHER_CTX_new allocates a fresh |EVP_CIPHER_CTX|, calls
+ * |EVP_CIPHER_CTX_init| and returns it, or NULL on allocation failure. */
+OPENSSL_EXPORT EVP_CIPHER_CTX *EVP_CIPHER_CTX_new(void);
+
+/* EVP_CIPHER_CTX_cleanup frees any memory referenced by |ctx|. It returns
+ * one. */
+OPENSSL_EXPORT int EVP_CIPHER_CTX_cleanup(EVP_CIPHER_CTX *ctx);
+
+/* EVP_CIPHER_CTX_free calls |EVP_CIPHER_CTX_cleanup| on |ctx| and then frees
+ * |ctx| itself. */
+OPENSSL_EXPORT void EVP_CIPHER_CTX_free(EVP_CIPHER_CTX *ctx);
+
+/* EVP_CIPHER_CTX_copy sets |out| to be a duplicate of the current state of
+ * |in|. The |out| argument must have been previously initialised. */
+OPENSSL_EXPORT int EVP_CIPHER_CTX_copy(EVP_CIPHER_CTX *out,
+                                       const EVP_CIPHER_CTX *in);
+
+
+/* Cipher context configuration. */
+
+/* EVP_CipherInit_ex configures |ctx| for a fresh encryption (or decryption, if
+ * |enc| is zero) operation using |cipher|. If |ctx| has been previously
+ * configured with a cipher then |cipher|, |key| and |iv| may be |NULL| and
+ * |enc| may be -1 to reuse the previous values. The operation will use |key|
+ * as the key and |iv| as the IV (if any). These should have the correct
+ * lengths given by |EVP_CIPHER_key_length| and |EVP_CIPHER_iv_length|. It
+ * returns one on success and zero on error. */
+OPENSSL_EXPORT int EVP_CipherInit_ex(EVP_CIPHER_CTX *ctx,
+                                     const EVP_CIPHER *cipher, ENGINE *engine,
+                                     const uint8_t *key, const uint8_t *iv,
+                                     int enc);
+
+/* EVP_EncryptInit_ex calls |EVP_CipherInit_ex| with |enc| equal to one. */
+OPENSSL_EXPORT int EVP_EncryptInit_ex(EVP_CIPHER_CTX *ctx,
+                                      const EVP_CIPHER *cipher, ENGINE *impl,
+                                      const uint8_t *key, const uint8_t *iv);
+
+/* EVP_DecryptInit_ex calls |EVP_CipherInit_ex| with |enc| equal to zero. */
+OPENSSL_EXPORT int EVP_DecryptInit_ex(EVP_CIPHER_CTX *ctx,
+                                      const EVP_CIPHER *cipher, ENGINE *impl,
+                                      const uint8_t *key, const uint8_t *iv);
+
+
+/* Cipher operations. */
+
+/* EVP_EncryptUpdate encrypts |in_len| bytes from |in| to |out|. The number
+ * of output bytes may be up to |in_len| plus the block length minus one and
+ * |out| must have sufficient space. The number of bytes actually output is
+ * written to |*out_len|. It returns one on success and zero otherwise. */
+OPENSSL_EXPORT int EVP_EncryptUpdate(EVP_CIPHER_CTX *ctx, uint8_t *out,
+                                     int *out_len, const uint8_t *in,
+                                     int in_len);
+
+/* EVP_EncryptFinal_ex writes at most a block of ciphertext to |out| and sets
+ * |*out_len| to the number of bytes written. If padding is enabled (the
+ * default) then standard padding is applied to create the final block. If
+ * padding is disabled (with |EVP_CIPHER_CTX_set_padding|) then any partial
+ * block remaining will cause an error. The function returns one on success and
+ * zero otherwise. */
+OPENSSL_EXPORT int EVP_EncryptFinal_ex(EVP_CIPHER_CTX *ctx, uint8_t *out,
+                                       int *out_len);
+
+/* EVP_DecryptUpdate decrypts |in_len| bytes from |in| to |out|. The number of
+ * output bytes may be up to |in_len| plus the block length minus one and |out|
+ * must have sufficient space. The number of bytes actually output is written
+ * to |*out_len|. It returns one on success and zero otherwise. */
+OPENSSL_EXPORT int EVP_DecryptUpdate(EVP_CIPHER_CTX *ctx, uint8_t *out,
+                                     int *out_len, const uint8_t *in,
+                                     int in_len);
+
+/* EVP_DecryptFinal_ex writes at most a block of ciphertext to |out| and sets
+ * |*out_len| to the number of bytes written. If padding is enabled (the
+ * default) then padding is removed from the final block.
+ *
+ * WARNING: it is unsafe to call this function with unauthenticted
+ * ciphertext if padding is enabled. */
+OPENSSL_EXPORT int EVP_DecryptFinal_ex(EVP_CIPHER_CTX *ctx, unsigned char *out,
+                                       int *out_len);
+
+/* EVP_Cipher performs a one-shot encryption/decryption operation. No partial
+ * blocks are maintained between calls. However, any internal cipher state is
+ * still updated. For CBC-mode ciphers, the IV is updated to the final
+ * ciphertext block. For stream ciphers, the stream is advanced past the bytes
+ * used. It returns one on success and zero otherwise, unless |EVP_CIPHER_flags|
+ * has |EVP_CIPH_FLAG_CUSTOM_CIPHER| set. Then it returns the number of bytes
+ * written or -1 on error.
+ *
+ * WARNING: this differs from the usual return value convention when using
+ * |EVP_CIPH_FLAG_CUSTOM_CIPHER|.
+ *
+ * TODO(davidben): The normal ciphers currently never fail, even if, e.g.,
+ * |in_len| is not a multiple of the block size for CBC-mode decryption. The
+ * input just gets rounded up while the output gets truncated. This should
+ * either be officially documented or fail. */
+OPENSSL_EXPORT int EVP_Cipher(EVP_CIPHER_CTX *ctx, uint8_t *out,
+                              const uint8_t *in, size_t in_len);
+
+/* EVP_CipherUpdate calls either |EVP_EncryptUpdate| or |EVP_DecryptUpdate|
+ * depending on how |ctx| has been setup. */
+OPENSSL_EXPORT int EVP_CipherUpdate(EVP_CIPHER_CTX *ctx, uint8_t *out,
+                                    int *out_len, const uint8_t *in,
+                                    int in_len);
+
+/* EVP_CipherFinal_ex calls either |EVP_EncryptFinal_ex| or
+ * |EVP_DecryptFinal_ex| depending on how |ctx| has been setup. */
+OPENSSL_EXPORT int EVP_CipherFinal_ex(EVP_CIPHER_CTX *ctx, uint8_t *out,
+                                      int *out_len);
+
+
+/* Cipher context accessors. */
+
+/* EVP_CIPHER_CTX_cipher returns the |EVP_CIPHER| underlying |ctx|, or NULL if
+ * none has been set. */
+OPENSSL_EXPORT const EVP_CIPHER *EVP_CIPHER_CTX_cipher(
+    const EVP_CIPHER_CTX *ctx);
+
+/* EVP_CIPHER_CTX_nid returns a NID identifying the |EVP_CIPHER| underlying
+ * |ctx| (e.g. |NID_aes_128_gcm|). It will crash if no cipher has been
+ * configured. */
+OPENSSL_EXPORT int EVP_CIPHER_CTX_nid(const EVP_CIPHER_CTX *ctx);
+
+/* EVP_CIPHER_CTX_block_size returns the block size, in bytes, of the cipher
+ * underlying |ctx|, or one if the cipher is a stream cipher. It will crash if
+ * no cipher has been configured. */
+OPENSSL_EXPORT unsigned EVP_CIPHER_CTX_block_size(const EVP_CIPHER_CTX *ctx);
+
+/* EVP_CIPHER_CTX_key_length returns the key size, in bytes, of the cipher
+ * underlying |ctx| or zero if no cipher has been configured. */
+OPENSSL_EXPORT unsigned EVP_CIPHER_CTX_key_length(const EVP_CIPHER_CTX *ctx);
+
+/* EVP_CIPHER_CTX_iv_length returns the IV size, in bytes, of the cipher
+ * underlying |ctx|. It will crash if no cipher has been configured. */
+OPENSSL_EXPORT unsigned EVP_CIPHER_CTX_iv_length(const EVP_CIPHER_CTX *ctx);
+
+/* EVP_CIPHER_CTX_get_app_data returns the opaque, application data pointer for
+ * |ctx|, or NULL if none has been set. */
+OPENSSL_EXPORT void *EVP_CIPHER_CTX_get_app_data(const EVP_CIPHER_CTX *ctx);
+
+/* EVP_CIPHER_CTX_set_app_data sets the opaque, application data pointer for
+ * |ctx| to |data|. */
+OPENSSL_EXPORT void EVP_CIPHER_CTX_set_app_data(EVP_CIPHER_CTX *ctx,
+                                                void *data);
+
+/* EVP_CIPHER_CTX_flags returns a value which is the OR of zero or more
+ * |EVP_CIPH_*| flags. It will crash if no cipher has been configured. */
+OPENSSL_EXPORT uint32_t EVP_CIPHER_CTX_flags(const EVP_CIPHER_CTX *ctx);
+
+/* EVP_CIPHER_CTX_mode returns one of the |EVP_CIPH_*| cipher mode values
+ * enumerated below. It will crash if no cipher has been configured. */
+OPENSSL_EXPORT uint32_t EVP_CIPHER_CTX_mode(const EVP_CIPHER_CTX *ctx);
+
+/* EVP_CIPHER_CTX_ctrl is an |ioctl| like function. The |command| argument
+ * should be one of the |EVP_CTRL_*| values. The |arg| and |ptr| arguments are
+ * specific to the command in question. */
+OPENSSL_EXPORT int EVP_CIPHER_CTX_ctrl(EVP_CIPHER_CTX *ctx, int command,
+                                       int arg, void *ptr);
+
+/* EVP_CIPHER_CTX_set_padding sets whether padding is enabled for |ctx| and
+ * returns one. Pass a non-zero |pad| to enable padding (the default) or zero
+ * to disable. */
+OPENSSL_EXPORT int EVP_CIPHER_CTX_set_padding(EVP_CIPHER_CTX *ctx, int pad);
+
+/* EVP_CIPHER_CTX_set_key_length sets the key length for |ctx|. This is only
+ * valid for ciphers that can take a variable length key. It returns one on
+ * success and zero on error. */
+OPENSSL_EXPORT int EVP_CIPHER_CTX_set_key_length(EVP_CIPHER_CTX *ctx, unsigned key_len);
+
+
+/* Cipher accessors. */
+
+/* EVP_CIPHER_nid returns a NID identifing |cipher|. (For example,
+ * |NID_aes_128_gcm|.) */
+OPENSSL_EXPORT int EVP_CIPHER_nid(const EVP_CIPHER *cipher);
+
+/* EVP_CIPHER_block_size returns the block size, in bytes, for |cipher|, or one
+ * if |cipher| is a stream cipher. */
+OPENSSL_EXPORT unsigned EVP_CIPHER_block_size(const EVP_CIPHER *cipher);
+
+/* EVP_CIPHER_key_length returns the key size, in bytes, for |cipher|. If
+ * |cipher| can take a variable key length then this function returns the
+ * default key length and |EVP_CIPHER_flags| will return a value with
+ * |EVP_CIPH_VARIABLE_LENGTH| set. */
+OPENSSL_EXPORT unsigned EVP_CIPHER_key_length(const EVP_CIPHER *cipher);
+
+/* EVP_CIPHER_iv_length returns the IV size, in bytes, of |cipher|, or zero if
+ * |cipher| doesn't take an IV. */
+OPENSSL_EXPORT unsigned EVP_CIPHER_iv_length(const EVP_CIPHER *cipher);
+
+/* EVP_CIPHER_flags returns a value which is the OR of zero or more
+ * |EVP_CIPH_*| flags. */
+OPENSSL_EXPORT uint32_t EVP_CIPHER_flags(const EVP_CIPHER *cipher);
+
+/* EVP_CIPHER_mode returns one of the cipher mode values enumerated below. */
+OPENSSL_EXPORT uint32_t EVP_CIPHER_mode(const EVP_CIPHER *cipher);
+
+
+/* Key derivation. */
+
+/* EVP_BytesToKey generates a key and IV for the cipher |type| by iterating
+ * |md| |count| times using |data| and |salt|. On entry, the |key| and |iv|
+ * buffers must have enough space to hold a key and IV for |type|. It returns
+ * the length of the key on success or zero on error. */
+OPENSSL_EXPORT int EVP_BytesToKey(const EVP_CIPHER *type, const EVP_MD *md,
+                                  const uint8_t *salt, const uint8_t *data,
+                                  size_t data_len, unsigned count, uint8_t *key,
+                                  uint8_t *iv);
+
+
+/* Cipher modes (for |EVP_CIPHER_mode|). */
+
+#define EVP_CIPH_STREAM_CIPHER 0x0
+#define EVP_CIPH_ECB_MODE 0x1
+#define EVP_CIPH_CBC_MODE 0x2
+#define EVP_CIPH_CFB_MODE 0x3
+#define EVP_CIPH_OFB_MODE 0x4
+#define EVP_CIPH_CTR_MODE 0x5
+#define EVP_CIPH_GCM_MODE 0x6
+#define EVP_CIPH_XTS_MODE 0x7
+
+
+/* Cipher flags (for |EVP_CIPHER_flags|). */
+
+/* EVP_CIPH_VARIABLE_LENGTH indicates that the cipher takes a variable length
+ * key. */
+#define EVP_CIPH_VARIABLE_LENGTH 0x40
+
+/* EVP_CIPH_ALWAYS_CALL_INIT indicates that the |init| function for the cipher
+ * should always be called when initialising a new operation, even if the key
+ * is NULL to indicate that the same key is being used. */
+#define EVP_CIPH_ALWAYS_CALL_INIT 0x80
+
+/* EVP_CIPH_CUSTOM_IV indicates that the cipher manages the IV itself rather
+ * than keeping it in the |iv| member of |EVP_CIPHER_CTX|. */
+#define EVP_CIPH_CUSTOM_IV 0x100
+
+/* EVP_CIPH_CTRL_INIT indicates that EVP_CTRL_INIT should be used when
+ * initialising an |EVP_CIPHER_CTX|. */
+#define EVP_CIPH_CTRL_INIT 0x200
+
+/* EVP_CIPH_FLAG_CUSTOM_CIPHER indicates that the cipher manages blocking
+ * itself. This causes EVP_(En|De)crypt_ex to be simple wrapper functions. */
+#define EVP_CIPH_FLAG_CUSTOM_CIPHER 0x400
+
+/* EVP_CIPH_FLAG_AEAD_CIPHER specifies that the cipher is an AEAD. This is an
+ * older version of the proper AEAD interface. See aead.h for the current
+ * one. */
+#define EVP_CIPH_FLAG_AEAD_CIPHER 0x800
+
+/* EVP_CIPH_CUSTOM_COPY indicates that the |ctrl| callback should be called
+ * with |EVP_CTRL_COPY| at the end of normal |EVP_CIPHER_CTX_copy|
+ * processing. */
+#define EVP_CIPH_CUSTOM_COPY 0x1000
+
+
+/* Deprecated functions */
+
+/* EVP_CipherInit acts like EVP_CipherInit_ex except that |EVP_CIPHER_CTX_init|
+ * is called on |cipher| first, if |cipher| is not NULL. */
+OPENSSL_EXPORT int EVP_CipherInit(EVP_CIPHER_CTX *ctx, const EVP_CIPHER *cipher,
+                                  const uint8_t *key, const uint8_t *iv,
+                                  int enc);
+
+/* EVP_EncryptInit calls |EVP_CipherInit| with |enc| equal to one. */
+OPENSSL_EXPORT int EVP_EncryptInit(EVP_CIPHER_CTX *ctx,
+                                   const EVP_CIPHER *cipher, const uint8_t *key,
+                                   const uint8_t *iv);
+
+/* EVP_DecryptInit calls |EVP_CipherInit| with |enc| equal to zero. */
+OPENSSL_EXPORT int EVP_DecryptInit(EVP_CIPHER_CTX *ctx,
+                                   const EVP_CIPHER *cipher, const uint8_t *key,
+                                   const uint8_t *iv);
+
+/* EVP_add_cipher_alias does nothing and returns one. */
+OPENSSL_EXPORT int EVP_add_cipher_alias(const char *a, const char *b);
+
+/* EVP_get_cipherbyname returns an |EVP_CIPHER| given a human readable name in
+ * |name|, or NULL if the name is unknown. */
+OPENSSL_EXPORT const EVP_CIPHER *EVP_get_cipherbyname(const char *name);
+
+/* These AEADs are deprecated AES-GCM implementations that set
+ * |EVP_CIPH_FLAG_CUSTOM_CIPHER|. Use |EVP_aead_aes_128_gcm| and
+ * |EVP_aead_aes_256_gcm| instead. */
+OPENSSL_EXPORT const EVP_CIPHER *EVP_aes_128_gcm(void);
+OPENSSL_EXPORT const EVP_CIPHER *EVP_aes_256_gcm(void);
+
+/* These are deprecated, 192-bit version of AES. */
+OPENSSL_EXPORT const EVP_CIPHER *EVP_aes_192_ecb(void);
+OPENSSL_EXPORT const EVP_CIPHER *EVP_aes_192_cbc(void);
+OPENSSL_EXPORT const EVP_CIPHER *EVP_aes_192_ctr(void);
+OPENSSL_EXPORT const EVP_CIPHER *EVP_aes_192_gcm(void);
+
+
+/* Private functions. */
+
+/* EVP_CIPH_NO_PADDING disables padding in block ciphers. */
+#define EVP_CIPH_NO_PADDING 0x800
+
+/* EVP_CIPHER_CTX_ctrl commands. */
+#define EVP_CTRL_INIT 0x0
+#define EVP_CTRL_SET_KEY_LENGTH 0x1
+#define EVP_CTRL_GET_RC2_KEY_BITS 0x2
+#define EVP_CTRL_SET_RC2_KEY_BITS 0x3
+#define EVP_CTRL_GET_RC5_ROUNDS 0x4
+#define EVP_CTRL_SET_RC5_ROUNDS 0x5
+#define EVP_CTRL_RAND_KEY 0x6
+#define EVP_CTRL_PBE_PRF_NID 0x7
+#define EVP_CTRL_COPY 0x8
+#define EVP_CTRL_GCM_SET_IVLEN 0x9
+#define EVP_CTRL_GCM_GET_TAG 0x10
+#define EVP_CTRL_GCM_SET_TAG 0x11
+#define EVP_CTRL_GCM_SET_IV_FIXED 0x12
+#define EVP_CTRL_GCM_IV_GEN 0x13
+#define EVP_CTRL_AEAD_SET_MAC_KEY 0x17
+/* Set the GCM invocation field, decrypt only */
+#define EVP_CTRL_GCM_SET_IV_INV 0x18
+
+/* GCM TLS constants */
+/* Length of fixed part of IV derived from PRF */
+#define EVP_GCM_TLS_FIXED_IV_LEN 4
+/* Length of explicit part of IV part of TLS records */
+#define EVP_GCM_TLS_EXPLICIT_IV_LEN 8
+/* Length of tag for TLS */
+#define EVP_GCM_TLS_TAG_LEN 16
+
+#define EVP_MAX_KEY_LENGTH 64
+#define EVP_MAX_IV_LENGTH 16
+#define EVP_MAX_BLOCK_LENGTH 32
+
+struct evp_cipher_ctx_st {
+  /* cipher contains the underlying cipher for this context. */
+  const EVP_CIPHER *cipher;
+
+  /* app_data is a pointer to opaque, user data. */
+  void *app_data;      /* application stuff */
+
+  /* cipher_data points to the |cipher| specific state. */
+  void *cipher_data;
+
+  /* key_len contains the length of the key, which may differ from
+   * |cipher->key_len| if the cipher can take a variable key length. */
+  unsigned key_len;
+
+  /* encrypt is one if encrypting and zero if decrypting. */
+  int encrypt;
+
+  /* flags contains the OR of zero or more |EVP_CIPH_*| flags, above. */
+  uint32_t flags;
+
+  /* oiv contains the original IV value. */
+  uint8_t oiv[EVP_MAX_IV_LENGTH];
+
+  /* iv contains the current IV value, which may have been updated. */
+  uint8_t iv[EVP_MAX_IV_LENGTH];
+
+  /* buf contains a partial block which is used by, for example, CTR mode to
+   * store unused keystream bytes. */
+  uint8_t buf[EVP_MAX_BLOCK_LENGTH];
+
+  /* buf_len contains the number of bytes of a partial block contained in
+   * |buf|. */
+  int buf_len;
+
+  /* num contains the number of bytes of |iv| which are valid for modes that
+   * manage partial blocks themselves. */
+  int num;
+
+  /* final_used is non-zero if the |final| buffer contains plaintext. */
+  int final_used;
+
+  /* block_mask contains |cipher->block_size| minus one. (The block size
+   * assumed to be a power of two.) */
+  int block_mask;
+
+  uint8_t final[EVP_MAX_BLOCK_LENGTH]; /* possible final block */
+} /* EVP_CIPHER_CTX */;
+
+typedef struct evp_cipher_info_st {
+  const EVP_CIPHER *cipher;
+  unsigned char iv[EVP_MAX_IV_LENGTH];
+} EVP_CIPHER_INFO;
+
+struct evp_cipher_st {
+  /* type contains a NID identifing the cipher. (e.g. NID_aes_128_gcm.) */
+  int nid;
+
+  /* block_size contains the block size, in bytes, of the cipher, or 1 for a
+   * stream cipher. */
+  unsigned block_size;
+
+  /* key_len contains the key size, in bytes, for the cipher. If the cipher
+   * takes a variable key size then this contains the default size. */
+  unsigned key_len;
+
+  /* iv_len contains the IV size, in bytes, or zero if inapplicable. */
+  unsigned iv_len;
+
+  /* ctx_size contains the size, in bytes, of the per-key context for this
+   * cipher. */
+  unsigned ctx_size;
+
+  /* flags contains the OR of a number of flags. See |EVP_CIPH_*|. */
+  uint32_t flags;
+
+  /* app_data is a pointer to opaque, user data. */
+  void *app_data;
+
+  int (*init)(EVP_CIPHER_CTX *ctx, const uint8_t *key, const uint8_t *iv,
+              int enc);
+
+  int (*cipher)(EVP_CIPHER_CTX *ctx, uint8_t *out, const uint8_t *in,
+                size_t inl);
+
+  /* cleanup, if non-NULL, releases memory associated with the context. It is
+   * called if |EVP_CTRL_INIT| succeeds. Note that |init| may not have been
+   * called at this point. */
+  void (*cleanup)(EVP_CIPHER_CTX *);
+
+  int (*ctrl)(EVP_CIPHER_CTX *, int type, int arg, void *ptr);
+};
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#define CIPHER_R_AES_KEY_SETUP_FAILED 100
+#define CIPHER_R_BAD_DECRYPT 101
+#define CIPHER_R_BAD_KEY_LENGTH 102
+#define CIPHER_R_BUFFER_TOO_SMALL 103
+#define CIPHER_R_CTRL_NOT_IMPLEMENTED 104
+#define CIPHER_R_CTRL_OPERATION_NOT_IMPLEMENTED 105
+#define CIPHER_R_DATA_NOT_MULTIPLE_OF_BLOCK_LENGTH 106
+#define CIPHER_R_INITIALIZATION_ERROR 107
+#define CIPHER_R_INPUT_NOT_INITIALIZED 108
+#define CIPHER_R_INVALID_AD_SIZE 109
+#define CIPHER_R_INVALID_KEY_LENGTH 110
+#define CIPHER_R_INVALID_NONCE_SIZE 111
+#define CIPHER_R_INVALID_OPERATION 112
+#define CIPHER_R_IV_TOO_LARGE 113
+#define CIPHER_R_NO_CIPHER_SET 114
+#define CIPHER_R_OUTPUT_ALIASES_INPUT 115
+#define CIPHER_R_TAG_TOO_LARGE 116
+#define CIPHER_R_TOO_LARGE 117
+#define CIPHER_R_UNSUPPORTED_AD_SIZE 118
+#define CIPHER_R_UNSUPPORTED_INPUT_SIZE 119
+#define CIPHER_R_UNSUPPORTED_KEY_SIZE 120
+#define CIPHER_R_UNSUPPORTED_NONCE_SIZE 121
+#define CIPHER_R_UNSUPPORTED_TAG_SIZE 122
+#define CIPHER_R_WRONG_FINAL_BLOCK_LENGTH 123
+#define CIPHER_R_NO_DIRECTION_SET 124
+
+#endif  /* OPENSSL_HEADER_CIPHER_H */

+ 76 - 0
app/src/main/jni/openssl/include/openssl/cmac.h

@@ -0,0 +1,76 @@
+/* Copyright (c) 2015, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+#ifndef OPENSSL_HEADER_CMAC_H
+#define OPENSSL_HEADER_CMAC_H
+
+#include <openssl/base.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* CMAC.
+ *
+ * CMAC is a MAC based on AES-CBC and defined in
+ * https://tools.ietf.org/html/rfc4493#section-2.3. */
+
+
+/* One-shot functions. */
+
+/* AES_CMAC calculates the 16-byte, CMAC authenticator of |in_len| bytes of
+ * |in| and writes it to |out|. The |key_len| may be 16 or 32 bytes to select
+ * between AES-128 and AES-256. It returns one on success or zero on error. */
+OPENSSL_EXPORT int AES_CMAC(uint8_t out[16], const uint8_t *key, size_t key_len,
+                            const uint8_t *in, size_t in_len);
+
+
+/* Incremental interface. */
+
+/* CMAC_CTX_new allocates a fresh |CMAC_CTX| and returns it, or NULL on
+ * error. */
+OPENSSL_EXPORT CMAC_CTX *CMAC_CTX_new(void);
+
+/* CMAC_CTX_free frees a |CMAC_CTX|. */
+OPENSSL_EXPORT void CMAC_CTX_free(CMAC_CTX *ctx);
+
+/* CMAC_Init configures |ctx| to use the given |key| and |cipher|. The CMAC RFC
+ * only specifies the use of AES-128 thus |key_len| should be 16 and |cipher|
+ * should be |EVP_aes_128_cbc()|. However, this implementation also supports
+ * AES-256 by setting |key_len| to 32 and |cipher| to |EVP_aes_256_cbc()|. The
+ * |engine| argument is ignored.
+ *
+ * It returns one on success or zero on error. */
+OPENSSL_EXPORT int CMAC_Init(CMAC_CTX *ctx, const void *key, size_t key_len,
+                             const EVP_CIPHER *cipher, ENGINE *engine);
+
+
+/* CMAC_Reset resets |ctx| so that a fresh message can be authenticated. */
+OPENSSL_EXPORT int CMAC_Reset(CMAC_CTX *ctx);
+
+/* CMAC_Update processes |in_len| bytes of message from |in|. It returns one on
+ * success or zero on error. */
+OPENSSL_EXPORT int CMAC_Update(CMAC_CTX *ctx, const uint8_t *in, size_t in_len);
+
+/* CMAC_Final sets |*out_len| to 16 and, if |out| is not NULL, writes 16 bytes
+ * of authenticator to it. It returns one on success or zero on error. */
+OPENSSL_EXPORT int CMAC_Final(CMAC_CTX *ctx, uint8_t *out, size_t *out_len);
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_CMAC_H */

+ 145 - 0
app/src/main/jni/openssl/include/openssl/conf.h

@@ -0,0 +1,145 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_CONF_H
+#define OPENSSL_HEADER_CONF_H
+
+#include <openssl/base.h>
+
+#include <openssl/stack.h>
+#include <openssl/lhash.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* Config files look like:
+ *
+ *   # Comment
+ *
+ *   # This key is in the default section.
+ *   key=value
+ *
+ *   [section_name]
+ *   key2=value2
+ *
+ * Config files are representated by a |CONF|. */
+
+struct conf_value_st {
+  char *section;
+  char *name;
+  char *value;
+};
+
+struct conf_st {
+  LHASH_OF(CONF_VALUE) *data;
+};
+
+
+/* NCONF_new returns a fresh, empty |CONF|, or NULL on error. The |method|
+ * argument must be NULL. */
+CONF *NCONF_new(void *method);
+
+/* NCONF_free frees all the data owned by |conf| and then |conf| itself. */
+void NCONF_free(CONF *conf);
+
+/* NCONF_load parses the file named |filename| and adds the values found to
+ * |conf|. It returns one on success and zero on error. In the event of an
+ * error, if |out_error_line| is not NULL, |*out_error_line| is set to the
+ * number of the line that contained the error. */
+int NCONF_load(CONF *conf, const char *filename, long *out_error_line);
+
+/* NCONF_load_bio acts like |NCONF_load| but reads from |bio| rather than from
+ * a named file. */
+int NCONF_load_bio(CONF *conf, BIO *bio, long *out_error_line);
+
+/* NCONF_get_section returns a stack of values for a given section in |conf|.
+ * If |section| is NULL, the default section is returned. It returns NULL on
+ * error. */
+STACK_OF(CONF_VALUE) *NCONF_get_section(const CONF *conf, const char *section);
+
+/* NCONF_get_string returns the value of the key |name|, in section |section|.
+ * The |section| argument may be NULL to indicate the default section. It
+ * returns the value or NULL on error. */
+const char *NCONF_get_string(const CONF *conf, const char *section,
+                             const char *name);
+
+
+/* Utility functions */
+
+/* CONF_parse_list takes a list separated by 'sep' and calls |list_cb| giving
+ * the start and length of each member, optionally stripping leading and
+ * trailing whitespace. This can be used to parse comma separated lists for
+ * example. If |list_cb| returns <= 0, then the iteration is halted and that
+ * value is returned immediately. Otherwise it returns one. Note that |list_cb|
+ * may be called on an empty member. */
+int CONF_parse_list(const char *list, char sep, int remove_whitespace,
+                    int (*list_cb)(const char *elem, int len, void *usr),
+                    void *arg);
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#define CONF_R_LIST_CANNOT_BE_NULL 100
+#define CONF_R_MISSING_CLOSE_SQUARE_BRACKET 101
+#define CONF_R_MISSING_EQUAL_SIGN 102
+#define CONF_R_NO_CLOSE_BRACE 103
+#define CONF_R_UNABLE_TO_CREATE_NEW_SECTION 104
+#define CONF_R_VARIABLE_HAS_NO_VALUE 105
+
+#endif  /* OPENSSL_HEADER_THREAD_H */

+ 184 - 0
app/src/main/jni/openssl/include/openssl/cpu.h

@@ -0,0 +1,184 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.]
+ *
+ * This product includes cryptographic software written by Eric Young
+ * (eay@cryptsoft.com).  This product includes software written by Tim
+ * Hudson (tjh@cryptsoft.com). */
+
+#ifndef OPENSSL_HEADER_CPU_H
+#define OPENSSL_HEADER_CPU_H
+
+#include <openssl/base.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* Runtime CPU feature support */
+
+
+#if defined(OPENSSL_X86) || defined(OPENSSL_X86_64)
+/* OPENSSL_ia32cap_P contains the Intel CPUID bits when running on an x86 or
+ * x86-64 system.
+ *
+ *   Index 0:
+ *     EDX for CPUID where EAX = 1
+ *     Bit 20 is always zero
+ *     Bit 28 is adjusted to reflect whether the data cache is shared between
+ *       multiple logical cores
+ *     Bit 30 is used to indicate an Intel CPU
+ *   Index 1:
+ *     ECX for CPUID where EAX = 1
+ *     Bit 11 is used to indicate AMD XOP support, not SDBG
+ *   Index 2:
+ *     EBX for CPUID where EAX = 7
+ *   Index 3 is set to zero.
+ *
+ * Note: the CPUID bits are pre-adjusted for the OSXSAVE bit and the YMM and XMM
+ * bits in XCR0, so it is not necessary to check those. */
+extern uint32_t OPENSSL_ia32cap_P[4];
+#endif
+
+#if defined(OPENSSL_ARM) || defined(OPENSSL_AARCH64)
+
+#if defined(OPENSSL_APPLE)
+/* iOS builds use the static ARM configuration. */
+#define OPENSSL_STATIC_ARMCAP
+#endif
+
+#if !defined(OPENSSL_STATIC_ARMCAP)
+
+/* CRYPTO_is_NEON_capable_at_runtime returns true if the current CPU has a NEON
+ * unit. Note that |OPENSSL_armcap_P| also exists and contains the same
+ * information in a form that's easier for assembly to use. */
+OPENSSL_EXPORT char CRYPTO_is_NEON_capable_at_runtime(void);
+
+/* CRYPTO_is_NEON_capable returns true if the current CPU has a NEON unit. If
+ * this is known statically then it returns one immediately. */
+static inline int CRYPTO_is_NEON_capable(void) {
+#if defined(__ARM_NEON__)
+  return 1;
+#else
+  return CRYPTO_is_NEON_capable_at_runtime();
+#endif
+}
+
+/* CRYPTO_set_NEON_capable sets the return value of |CRYPTO_is_NEON_capable|.
+ * By default, unless the code was compiled with |-mfpu=neon|, NEON is assumed
+ * not to be present. It is not autodetected. Calling this with a zero
+ * argument also causes |CRYPTO_is_NEON_functional| to return false. */
+OPENSSL_EXPORT void CRYPTO_set_NEON_capable(char neon_capable);
+
+/* CRYPTO_is_NEON_functional returns true if the current CPU has a /working/
+ * NEON unit. Some phones have a NEON unit, but the Poly1305 NEON code causes
+ * it to fail. See https://code.google.com/p/chromium/issues/detail?id=341598 */
+OPENSSL_EXPORT char CRYPTO_is_NEON_functional(void);
+
+/* CRYPTO_set_NEON_functional sets the "NEON functional" flag. For
+ * |CRYPTO_is_NEON_functional| to return true, both this flag and the NEON flag
+ * must be true. By default NEON is assumed to be functional if the code was
+ * compiled with |-mfpu=neon| or if |CRYPTO_set_NEON_capable| has been called
+ * with a non-zero argument. */
+OPENSSL_EXPORT void CRYPTO_set_NEON_functional(char neon_functional);
+
+/* CRYPTO_is_ARMv8_AES_capable returns true if the current CPU supports the
+ * ARMv8 AES instruction. */
+int CRYPTO_is_ARMv8_AES_capable(void);
+
+/* CRYPTO_is_ARMv8_PMULL_capable returns true if the current CPU supports the
+ * ARMv8 PMULL instruction. */
+int CRYPTO_is_ARMv8_PMULL_capable(void);
+
+#else
+
+static inline int CRYPTO_is_NEON_capable(void) {
+#if defined(OPENSSL_STATIC_ARMCAP_NEON) || defined(__ARM_NEON__)
+  return 1;
+#else
+  return 0;
+#endif
+}
+
+static inline int CRYPTO_is_NEON_functional(void) {
+  return CRYPTO_is_NEON_capable();
+}
+
+static inline int CRYPTO_is_ARMv8_AES_capable(void) {
+#if defined(OPENSSL_STATIC_ARMCAP_AES)
+  return 1;
+#else
+  return 0;
+#endif
+}
+
+static inline int CRYPTO_is_ARMv8_PMULL_capable(void) {
+#if defined(OPENSSL_STATIC_ARMCAP_PMULL)
+  return 1;
+#else
+  return 0;
+#endif
+}
+
+#endif  /* OPENSSL_STATIC_ARMCAP */
+#endif  /* OPENSSL_ARM */
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_CPU_H */

+ 68 - 0
app/src/main/jni/openssl/include/openssl/crypto.h

@@ -0,0 +1,68 @@
+/* Copyright (c) 2014, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+#ifndef OPENSSL_HEADER_CRYPTO_H
+#define OPENSSL_HEADER_CRYPTO_H
+
+#include <openssl/base.h>
+
+/* Upstream OpenSSL defines |OPENSSL_malloc|, etc., in crypto.h rather than
+ * mem.h. */
+#include <openssl/mem.h>
+
+/* Upstream OpenSSL defines |CRYPTO_LOCK|, etc., in crypto.h rather than
+ * thread.h. */
+#include <openssl/thread.h>
+
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* crypto.h contains functions for initializing the crypto library. */
+
+
+/* CRYPTO_library_init initializes the crypto library. It must be called if the
+ * library is built with BORINGSSL_NO_STATIC_INITIALIZER. Otherwise, it does
+ * nothing and a static initializer is used instead. */
+OPENSSL_EXPORT void CRYPTO_library_init(void);
+
+
+/* Deprecated functions. */
+
+#define OPENSSL_VERSION_TEXT "BoringSSL"
+
+#define SSLEAY_VERSION 0
+
+/* SSLeay_version is a compatibility function that returns the string
+ * "BoringSSL". */
+OPENSSL_EXPORT const char *SSLeay_version(int unused);
+
+/* SSLeay is a compatibility function that returns OPENSSL_VERSION_NUMBER from
+ * base.h. */
+OPENSSL_EXPORT unsigned long SSLeay(void);
+
+/* CRYPTO_malloc_init returns one. */
+OPENSSL_EXPORT int CRYPTO_malloc_init(void);
+
+/* ENGINE_load_builtin_engines does nothing. */
+OPENSSL_EXPORT void ENGINE_load_builtin_engines(void);
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_CRYPTO_H */

+ 92 - 0
app/src/main/jni/openssl/include/openssl/curve25519.h

@@ -0,0 +1,92 @@
+/* Copyright (c) 2015, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+#ifndef OPENSSL_HEADER_CURVE25519_H
+#define OPENSSL_HEADER_CURVE25519_H
+
+#include <openssl/base.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* Curve25519.
+ *
+ * Curve25519 is an elliptic curve. See
+ * https://tools.ietf.org/html/draft-irtf-cfrg-curves-11. */
+
+
+/* X25519.
+ *
+ * Curve25519 is an elliptic curve. The same name is also sometimes used for
+ * the Diffie-Hellman primitive built from it but “X25519” is a more precise
+ * name for that, which is the one used here. See http://cr.yp.to/ecdh.html and
+ * https://tools.ietf.org/html/draft-irtf-cfrg-curves-11. */
+
+/* X25519_keypair sets |out_public_value| and |out_private_key| to a freshly
+ * generated, public–private key pair. */
+OPENSSL_EXPORT void X25519_keypair(uint8_t out_public_value[32],
+                                   uint8_t out_private_key[32]);
+
+/* X25519 writes a shared key to |out_shared_key| that is calculated from the
+ * given private key and the peer's public value. It returns one on success and
+ * zero on error.
+ *
+ * Don't use the shared key directly, rather use a KDF and also include the two
+ * public values as inputs. */
+OPENSSL_EXPORT int X25519(uint8_t out_shared_key[32],
+                          const uint8_t private_key[32],
+                          const uint8_t peers_public_value[32]);
+
+/* X25519_public_from_private calculates a Diffie-Hellman public value from the
+ * given private key and writes it to |out_public_value|. */
+OPENSSL_EXPORT void X25519_public_from_private(uint8_t out_public_value[32],
+                                               const uint8_t private_key[32]);
+
+
+/* Ed25519.
+ *
+ * Ed25519 is a signature scheme using a twisted-Edwards curve that is
+ * birationally equivalent to curve25519. */
+
+#define ED25519_PRIVATE_KEY_LEN 64
+#define ED25519_PUBLIC_KEY_LEN 32
+#define ED25519_SIGNATURE_LEN 64
+
+/* ED25519_keypair sets |out_public_key| and |out_private_key| to a freshly
+ * generated, public–private key pair. */
+OPENSSL_EXPORT void ED25519_keypair(uint8_t out_public_key[32],
+                                    uint8_t out_private_key[64]);
+
+/* ED25519_sign sets |out_sig| to be a signature of |message_len| bytes from
+ * |message| using |private_key|. It returns one on success or zero on
+ * error. */
+OPENSSL_EXPORT int ED25519_sign(uint8_t out_sig[64], const uint8_t *message,
+                                size_t message_len,
+                                const uint8_t private_key[64]);
+
+/* ED25519_verify returns one iff |signature| is a valid signature, by
+ * |public_key| of |message_len| bytes from |message|. It returns zero
+ * otherwise. */
+OPENSSL_EXPORT int ED25519_verify(const uint8_t *message, size_t message_len,
+                                  const uint8_t signature[64],
+                                  const uint8_t public_key[32]);
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_CURVE25519_H */

+ 177 - 0
app/src/main/jni/openssl/include/openssl/des.h

@@ -0,0 +1,177 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_DES_H
+#define OPENSSL_HEADER_DES_H
+
+#include <openssl/base.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* DES. */
+
+
+typedef struct DES_cblock_st {
+  uint8_t bytes[8];
+} DES_cblock;
+
+typedef struct DES_ks {
+  uint32_t subkeys[16][2];
+} DES_key_schedule;
+
+
+#define DES_KEY_SZ (sizeof(DES_cblock))
+#define DES_SCHEDULE_SZ (sizeof(DES_key_schedule))
+
+#define DES_ENCRYPT 1
+#define DES_DECRYPT 0
+
+#define DES_CBC_MODE 0
+#define DES_PCBC_MODE 1
+
+/* DES_set_key performs a key schedule and initialises |schedule| with |key|. */
+OPENSSL_EXPORT void DES_set_key(const DES_cblock *key,
+                                DES_key_schedule *schedule);
+
+/* DES_set_odd_parity sets the parity bits (the least-significant bits in each
+ * byte) of |key| given the other bits in each byte. */
+OPENSSL_EXPORT void DES_set_odd_parity(DES_cblock *key);
+
+/* DES_ecb_encrypt encrypts (or decrypts, if |is_encrypt| is |DES_DECRYPT|) a
+ * single DES block (8 bytes) from in to out, using the key configured in
+ * |schedule|. */
+OPENSSL_EXPORT void DES_ecb_encrypt(const DES_cblock *in, DES_cblock *out,
+                                    const DES_key_schedule *schedule,
+                                    int is_encrypt);
+
+/* DES_ncbc_encrypt encrypts (or decrypts, if |enc| is |DES_DECRYPT|) |len|
+ * bytes from |in| to |out| with DES in CBC mode. */
+OPENSSL_EXPORT void DES_ncbc_encrypt(const uint8_t *in, uint8_t *out,
+                                     size_t len,
+                                     const DES_key_schedule *schedule,
+                                     DES_cblock *ivec, int enc);
+
+/* DES_ecb3_encrypt encrypts (or decrypts, if |enc| is |DES_DECRYPT|) a single
+ * block (8 bytes) of data from |input| to |output| using 3DES. */
+OPENSSL_EXPORT void DES_ecb3_encrypt(const DES_cblock *input,
+                                     DES_cblock *output,
+                                     const DES_key_schedule *ks1,
+                                     const DES_key_schedule *ks2,
+                                     const DES_key_schedule *ks3,
+                                     int enc);
+
+/* DES_ede3_cbc_encrypt encrypts (or decrypts, if |enc| is |DES_DECRYPT|) |len|
+ * bytes from |in| to |out| with 3DES in CBC mode. 3DES uses three keys, thus
+ * the function takes three different |DES_key_schedule|s. */
+OPENSSL_EXPORT void DES_ede3_cbc_encrypt(const uint8_t *in, uint8_t *out,
+                                         size_t len,
+                                         const DES_key_schedule *ks1,
+                                         const DES_key_schedule *ks2,
+                                         const DES_key_schedule *ks3,
+                                         DES_cblock *ivec, int enc);
+
+/* DES_ede2_cbc_encrypt encrypts (or decrypts, if |enc| is |DES_DECRYPT|) |len|
+ * bytes from |in| to |out| with 3DES in CBC mode. With this keying option, the
+ * first and third 3DES keys are identical. Thus, this function takes only two
+ * different |DES_key_schedule|s. */
+OPENSSL_EXPORT void DES_ede2_cbc_encrypt(const uint8_t *in, uint8_t *out,
+                                         size_t len,
+                                         const DES_key_schedule *ks1,
+                                         const DES_key_schedule *ks2,
+                                         DES_cblock *ivec, int enc);
+
+
+/* Deprecated functions. */
+
+/* DES_set_key_unchecked calls |DES_set_key|. */
+OPENSSL_EXPORT void DES_set_key_unchecked(const DES_cblock *key,
+                                          DES_key_schedule *schedule);
+
+OPENSSL_EXPORT void DES_ede3_cfb64_encrypt(const uint8_t *in, uint8_t *out,
+                                           long length, DES_key_schedule *ks1,
+                                           DES_key_schedule *ks2,
+                                           DES_key_schedule *ks3,
+                                           DES_cblock *ivec, int *num, int enc);
+
+OPENSSL_EXPORT void DES_ede3_cfb_encrypt(const uint8_t *in, uint8_t *out,
+                                         int numbits, long length,
+                                         DES_key_schedule *ks1,
+                                         DES_key_schedule *ks2,
+                                         DES_key_schedule *ks3,
+                                         DES_cblock *ivec, int enc);
+
+
+/* Private functions.
+ *
+ * These functions are only exported for use in |decrepit|. */
+
+OPENSSL_EXPORT void DES_decrypt3(uint32_t *data, const DES_key_schedule *ks1,
+                                 const DES_key_schedule *ks2,
+                                 const DES_key_schedule *ks3);
+
+OPENSSL_EXPORT void DES_encrypt3(uint32_t *data, const DES_key_schedule *ks1,
+                                 const DES_key_schedule *ks2,
+                                 const DES_key_schedule *ks3);
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_DES_H */

+ 238 - 0
app/src/main/jni/openssl/include/openssl/dh.h

@@ -0,0 +1,238 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_DH_H
+#define OPENSSL_HEADER_DH_H
+
+#include <openssl/base.h>
+
+#include <openssl/engine.h>
+#include <openssl/ex_data.h>
+#include <openssl/thread.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* DH contains functions for performing Diffie-Hellman key agreement in
+ * multiplicative groups. */
+
+
+/* Allocation and destruction. */
+
+/* DH_new returns a new, empty DH object or NULL on error. */
+OPENSSL_EXPORT DH *DH_new(void);
+
+/* DH_free decrements the reference count of |dh| and frees it if the reference
+ * count drops to zero. */
+OPENSSL_EXPORT void DH_free(DH *dh);
+
+/* DH_up_ref increments the reference count of |dh|. */
+OPENSSL_EXPORT int DH_up_ref(DH *dh);
+
+
+/* Standard parameters.
+ *
+ * These functions return new DH objects with standard parameters. They return
+ * NULL on allocation failure. The |engine| parameter is ignored. */
+
+/* These parameters are taken from RFC 5114. */
+
+OPENSSL_EXPORT DH *DH_get_1024_160(const ENGINE *engine);
+OPENSSL_EXPORT DH *DH_get_2048_224(const ENGINE *engine);
+OPENSSL_EXPORT DH *DH_get_2048_256(const ENGINE *engine);
+
+
+/* Parameter generation. */
+
+#define DH_GENERATOR_2 2
+#define DH_GENERATOR_5 5
+
+/* DH_generate_parameters_ex generates a suitable Diffie-Hellman group with a
+ * prime that is |prime_bits| long and stores it in |dh|. The generator of the
+ * group will be |generator|, which should be |DH_GENERATOR_2| unless there's a
+ * good reason to use a different value. The |cb| argument contains a callback
+ * function that will be called during the generation. See the documentation in
+ * |bn.h| about this. In addition to the callback invocations from |BN|, |cb|
+ * will also be called with |event| equal to three when the generation is
+ * complete. */
+OPENSSL_EXPORT int DH_generate_parameters_ex(DH *dh, int prime_bits,
+                                             int generator, BN_GENCB *cb);
+
+
+/* Diffie-Hellman operations. */
+
+/* DH_generate_key generates a new, random, private key and stores it in
+ * |dh|. It returns one on success and zero on error. */
+OPENSSL_EXPORT int DH_generate_key(DH *dh);
+
+/* DH_compute_key calculates the shared key between |dh| and |peers_key| and
+ * writes it as a big-endian integer into |out|, which must have |DH_size|
+ * bytes of space. It returns the number of bytes written, or a negative number
+ * on error. */
+OPENSSL_EXPORT int DH_compute_key(uint8_t *out, const BIGNUM *peers_key,
+                                  DH *dh);
+
+
+/* Utility functions. */
+
+/* DH_size returns the number of bytes in the DH group's prime. */
+OPENSSL_EXPORT int DH_size(const DH *dh);
+
+/* DH_num_bits returns the minimum number of bits needed to represent the
+ * absolute value of the DH group's prime. */
+OPENSSL_EXPORT unsigned DH_num_bits(const DH *dh);
+
+#define DH_CHECK_P_NOT_PRIME 0x01
+#define DH_CHECK_P_NOT_SAFE_PRIME 0x02
+#define DH_CHECK_UNABLE_TO_CHECK_GENERATOR 0x04
+#define DH_CHECK_NOT_SUITABLE_GENERATOR 0x08
+#define DH_CHECK_Q_NOT_PRIME 0x10
+#define DH_CHECK_INVALID_Q_VALUE 0x20
+#define DH_CHECK_INVALID_J_VALUE 0x40
+
+/* These are compatibility defines. */
+#define DH_NOT_SUITABLE_GENERATOR DH_CHECK_NOT_SUITABLE_GENERATOR
+#define DH_UNABLE_TO_CHECK_GENERATOR DH_CHECK_UNABLE_TO_CHECK_GENERATOR
+
+/* DH_check checks the suitability of |dh| as a Diffie-Hellman group. and sets
+ * |DH_CHECK_*| flags in |*out_flags| if it finds any errors. It returns one if
+ * |*out_flags| was successfully set and zero on error.
+ *
+ * Note: these checks may be quite computationally expensive. */
+OPENSSL_EXPORT int DH_check(const DH *dh, int *out_flags);
+
+#define DH_CHECK_PUBKEY_TOO_SMALL 1
+#define DH_CHECK_PUBKEY_TOO_LARGE 2
+
+/* DH_check_pub_key checks the suitability of |pub_key| as a public key for the
+ * DH group in |dh| and sets |DH_CHECK_PUBKEY_*| flags in |*out_flags| if it
+ * finds any errors. It returns one if |*out_flags| was successfully set and
+ * zero on error. */
+OPENSSL_EXPORT int DH_check_pub_key(const DH *dh, const BIGNUM *pub_key,
+                                    int *out_flags);
+
+/* DHparams_dup allocates a fresh |DH| and copies the parameters from |dh| into
+ * it. It returns the new |DH| or NULL on error. */
+OPENSSL_EXPORT DH *DHparams_dup(const DH *dh);
+
+
+/* ASN.1 functions. */
+
+/* d2i_DHparams parses an ASN.1, DER encoded Diffie-Hellman parameters
+ * structure from |len| bytes at |*inp|. If |ret| is not NULL then, on exit, a
+ * pointer to the result is in |*ret|. If |*ret| is already non-NULL on entry
+ * then the result is written directly into |*ret|, otherwise a fresh |DH| is
+ * allocated. On successful exit, |*inp| is advanced past the DER structure. It
+ * returns the result or NULL on error. */
+OPENSSL_EXPORT DH *d2i_DHparams(DH **ret, const unsigned char **inp, long len);
+
+/* i2d_DHparams marshals |in| to an ASN.1, DER structure. If |outp| is not NULL
+ * then the result is written to |*outp| and |*outp| is advanced just past the
+ * output. It returns the number of bytes in the result, whether written or
+ * not, or a negative value on error. */
+OPENSSL_EXPORT int i2d_DHparams(const DH *in, unsigned char **outp);
+
+
+/* ex_data functions.
+ *
+ * See |ex_data.h| for details. */
+
+OPENSSL_EXPORT int DH_get_ex_new_index(long argl, void *argp,
+                                       CRYPTO_EX_unused *unused,
+                                       CRYPTO_EX_dup *dup_func,
+                                       CRYPTO_EX_free *free_func);
+OPENSSL_EXPORT int DH_set_ex_data(DH *d, int idx, void *arg);
+OPENSSL_EXPORT void *DH_get_ex_data(DH *d, int idx);
+
+
+struct dh_st {
+  BIGNUM *p;
+  BIGNUM *g;
+  BIGNUM *pub_key;  /* g^x mod p */
+  BIGNUM *priv_key; /* x */
+
+  /* priv_length contains the length, in bits, of the private value. If zero,
+   * the private value will be the same length as |p|. */
+  unsigned priv_length;
+
+  CRYPTO_MUTEX method_mont_p_lock;
+  BN_MONT_CTX *method_mont_p;
+
+  /* Place holders if we want to do X9.42 DH */
+  BIGNUM *q;
+  BIGNUM *j;
+  unsigned char *seed;
+  int seedlen;
+  BIGNUM *counter;
+
+  int flags;
+  CRYPTO_refcount_t references;
+  CRYPTO_EX_DATA ex_data;
+};
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#define DH_R_BAD_GENERATOR 100
+#define DH_R_INVALID_PUBKEY 101
+#define DH_R_MODULUS_TOO_LARGE 102
+#define DH_R_NO_PRIVATE_VALUE 103
+
+#endif  /* OPENSSL_HEADER_DH_H */

+ 258 - 0
app/src/main/jni/openssl/include/openssl/digest.h

@@ -0,0 +1,258 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_DIGEST_H
+#define OPENSSL_HEADER_DIGEST_H
+
+#include <openssl/base.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* Digest functions.
+ *
+ * An EVP_MD abstracts the details of a specific hash function allowing code to
+ * deal with the concept of a "hash function" without needing to know exactly
+ * which hash function it is. */
+
+
+/* Hash algorithms.
+ *
+ * The following functions return |EVP_MD| objects that implement the named hash
+ * function. */
+
+OPENSSL_EXPORT const EVP_MD *EVP_md4(void);
+OPENSSL_EXPORT const EVP_MD *EVP_md5(void);
+OPENSSL_EXPORT const EVP_MD *EVP_sha1(void);
+OPENSSL_EXPORT const EVP_MD *EVP_sha224(void);
+OPENSSL_EXPORT const EVP_MD *EVP_sha256(void);
+OPENSSL_EXPORT const EVP_MD *EVP_sha384(void);
+OPENSSL_EXPORT const EVP_MD *EVP_sha512(void);
+
+/* EVP_md5_sha1 is a TLS-specific |EVP_MD| which computes the concatenation of
+ * MD5 and SHA-1, as used in TLS 1.1 and below. */
+OPENSSL_EXPORT const EVP_MD *EVP_md5_sha1(void);
+
+/* EVP_get_digestbynid returns an |EVP_MD| for the given NID, or NULL if no
+ * such digest is known. */
+OPENSSL_EXPORT const EVP_MD *EVP_get_digestbynid(int nid);
+
+/* EVP_get_digestbyobj returns an |EVP_MD| for the given |ASN1_OBJECT|, or NULL
+ * if no such digest is known. */
+OPENSSL_EXPORT const EVP_MD *EVP_get_digestbyobj(const ASN1_OBJECT *obj);
+
+
+/* Digest contexts.
+ *
+ * An EVP_MD_CTX represents the state of a specific digest operation in
+ * progress. */
+
+/* EVP_MD_CTX_init initialises an, already allocated, |EVP_MD_CTX|. */
+OPENSSL_EXPORT void EVP_MD_CTX_init(EVP_MD_CTX *ctx);
+
+/* EVP_MD_CTX_create allocates and initialises a fresh |EVP_MD_CTX| and returns
+ * it, or NULL on allocation failure. */
+OPENSSL_EXPORT EVP_MD_CTX *EVP_MD_CTX_create(void);
+
+/* EVP_MD_CTX_cleanup frees any resources owned by |ctx| and resets it to a
+ * freshly initialised state. It does not free |ctx| itself. It returns one. */
+OPENSSL_EXPORT int EVP_MD_CTX_cleanup(EVP_MD_CTX *ctx);
+
+/* EVP_MD_CTX_destroy calls |EVP_MD_CTX_cleanup| and then frees |ctx| itself. */
+OPENSSL_EXPORT void EVP_MD_CTX_destroy(EVP_MD_CTX *ctx);
+
+/* EVP_MD_CTX_copy_ex sets |out|, which must already be initialised, to be a
+ * copy of |in|. It returns one on success and zero on error. */
+OPENSSL_EXPORT int EVP_MD_CTX_copy_ex(EVP_MD_CTX *out, const EVP_MD_CTX *in);
+
+
+/* Digest operations. */
+
+/* EVP_DigestInit_ex configures |ctx|, which must already have been
+ * initialised, for a fresh hashing operation using |type|. It returns one on
+ * success and zero otherwise. */
+OPENSSL_EXPORT int EVP_DigestInit_ex(EVP_MD_CTX *ctx, const EVP_MD *type,
+                                     ENGINE *engine);
+
+/* EVP_DigestInit acts like |EVP_DigestInit_ex| except that |ctx| is
+ * initialised before use. */
+OPENSSL_EXPORT int EVP_DigestInit(EVP_MD_CTX *ctx, const EVP_MD *type);
+
+/* EVP_DigestUpdate hashes |len| bytes from |data| into the hashing operation
+ * in |ctx|. It returns one. */
+OPENSSL_EXPORT int EVP_DigestUpdate(EVP_MD_CTX *ctx, const void *data,
+                                    size_t len);
+
+/* EVP_MAX_MD_SIZE is the largest digest size supported, in bytes.
+ * Functions that output a digest generally require the buffer have
+ * at least this much space. */
+#define EVP_MAX_MD_SIZE 64 /* SHA-512 is the longest so far. */
+
+/* EVP_DigestFinal_ex finishes the digest in |ctx| and writes the output to
+ * |md_out|. At most |EVP_MAX_MD_SIZE| bytes are written. If |out_size| is not
+ * NULL then |*out_size| is set to the number of bytes written. It returns one.
+ * After this call, the hash cannot be updated or finished again until
+ * |EVP_DigestInit_ex| is called to start another hashing operation. */
+OPENSSL_EXPORT int EVP_DigestFinal_ex(EVP_MD_CTX *ctx, uint8_t *md_out,
+                                      unsigned int *out_size);
+
+/* EVP_DigestFinal acts like |EVP_DigestFinal_ex| except that
+ * |EVP_MD_CTX_cleanup| is called on |ctx| before returning. */
+OPENSSL_EXPORT int EVP_DigestFinal(EVP_MD_CTX *ctx, uint8_t *md_out,
+                                   unsigned int *out_size);
+
+/* EVP_Digest performs a complete hashing operation in one call. It hashes
+ * |len| bytes from |data| and writes the digest to |md_out|. At most
+ * |EVP_MAX_MD_SIZE| bytes are written. If |out_size| is not NULL then
+ * |*out_size| is set to the number of bytes written. It returns one on success
+ * and zero otherwise. */
+OPENSSL_EXPORT int EVP_Digest(const void *data, size_t len, uint8_t *md_out,
+                              unsigned int *md_out_size, const EVP_MD *type,
+                              ENGINE *impl);
+
+
+/* Digest function accessors.
+ *
+ * These functions allow code to learn details about an abstract hash
+ * function. */
+
+/* EVP_MD_type returns a NID identifing |md|. (For example, |NID_sha256|.) */
+OPENSSL_EXPORT int EVP_MD_type(const EVP_MD *md);
+
+/* EVP_MD_flags returns the flags for |md|, which is a set of |EVP_MD_FLAG_*|
+ * values, ORed together. */
+OPENSSL_EXPORT uint32_t EVP_MD_flags(const EVP_MD *md);
+
+/* EVP_MD_size returns the digest size of |md|, in bytes. */
+OPENSSL_EXPORT size_t EVP_MD_size(const EVP_MD *md);
+
+/* EVP_MD_block_size returns the native block-size of |md|, in bytes. */
+OPENSSL_EXPORT size_t EVP_MD_block_size(const EVP_MD *md);
+
+/* EVP_MD_FLAG_PKEY_DIGEST indicates the the digest function is used with a
+ * specific public key in order to verify signatures. (For example,
+ * EVP_dss1.) */
+#define EVP_MD_FLAG_PKEY_DIGEST 1
+
+/* EVP_MD_FLAG_DIGALGID_ABSENT indicates that the parameter type in an X.509
+ * DigestAlgorithmIdentifier representing this digest function should be
+ * undefined rather than NULL. */
+#define EVP_MD_FLAG_DIGALGID_ABSENT 2
+
+
+/* Deprecated functions. */
+
+/* EVP_MD_CTX_copy sets |out|, which must /not/ be initialised, to be a copy of
+ * |in|. It returns one on success and zero on error. */
+OPENSSL_EXPORT int EVP_MD_CTX_copy(EVP_MD_CTX *out, const EVP_MD_CTX *in);
+
+/* EVP_add_digest does nothing and returns one. It exists only for
+ * compatibility with OpenSSL. */
+OPENSSL_EXPORT int EVP_add_digest(const EVP_MD *digest);
+
+/* EVP_get_digestbyname returns an |EVP_MD| given a human readable name in
+ * |name|, or NULL if the name is unknown. */
+OPENSSL_EXPORT const EVP_MD *EVP_get_digestbyname(const char *);
+
+
+/* Digest operation accessors. */
+
+/* EVP_MD_CTX_md returns the underlying digest function, or NULL if one has not
+ * been set. */
+OPENSSL_EXPORT const EVP_MD *EVP_MD_CTX_md(const EVP_MD_CTX *ctx);
+
+/* EVP_MD_CTX_size returns the digest size of |ctx|, in bytes. It
+ * will crash if a digest hasn't been set on |ctx|. */
+OPENSSL_EXPORT unsigned EVP_MD_CTX_size(const EVP_MD_CTX *ctx);
+
+/* EVP_MD_CTX_block_size returns the block size of the digest function used by
+ * |ctx|, in bytes. It will crash if a digest hasn't been set on |ctx|. */
+OPENSSL_EXPORT unsigned EVP_MD_CTX_block_size(const EVP_MD_CTX *ctx);
+
+/* EVP_MD_CTX_type returns a NID describing the digest function used by |ctx|.
+ * (For example, |NID_sha256|.) It will crash if a digest hasn't been set on
+ * |ctx|. */
+OPENSSL_EXPORT int EVP_MD_CTX_type(const EVP_MD_CTX *ctx);
+
+
+struct evp_md_pctx_ops;
+
+struct env_md_ctx_st {
+  /* digest is the underlying digest function, or NULL if not set. */
+  const EVP_MD *digest;
+  /* md_data points to a block of memory that contains the hash-specific
+   * context. */
+  void *md_data;
+
+  /* pctx is an opaque (at this layer) pointer to additional context that
+   * EVP_PKEY functions may store in this object. */
+  EVP_PKEY_CTX *pctx;
+
+  /* pctx_ops, if not NULL, points to a vtable that contains functions to
+   * manipulate |pctx|. */
+  const struct evp_md_pctx_ops *pctx_ops;
+} /* EVP_MD_CTX */;
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#define DIGEST_R_INPUT_NOT_INITIALIZED 100
+
+#endif  /* OPENSSL_HEADER_DIGEST_H */

+ 343 - 0
app/src/main/jni/openssl/include/openssl/dsa.h

@@ -0,0 +1,343 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.]
+ *
+ * The DSS routines are based on patches supplied by
+ * Steven Schoch <schoch@sheba.arc.nasa.gov>. */
+
+#ifndef OPENSSL_HEADER_DSA_H
+#define OPENSSL_HEADER_DSA_H
+
+#include <openssl/base.h>
+
+#include <openssl/engine.h>
+#include <openssl/ex_data.h>
+#include <openssl/thread.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* DSA contains functions for signing and verifing with the Digital Signature
+ * Algorithm. */
+
+
+/* Allocation and destruction. */
+
+/* DSA_new returns a new, empty DSA object or NULL on error. */
+OPENSSL_EXPORT DSA *DSA_new(void);
+
+/* DSA_free decrements the reference count of |dsa| and frees it if the
+ * reference count drops to zero. */
+OPENSSL_EXPORT void DSA_free(DSA *dsa);
+
+/* DSA_up_ref increments the reference count of |dsa|. */
+OPENSSL_EXPORT int DSA_up_ref(DSA *dsa);
+
+
+/* Parameter generation. */
+
+/* DSA_generate_parameters_ex generates a set of DSA parameters by following
+ * the procedure given in FIPS 186-4, appendix A.
+ * (http://nvlpubs.nist.gov/nistpubs/FIPS/NIST.FIPS.186-4.pdf)
+ *
+ * The larger prime will have a length of |bits| (e.g. 2048). The |seed| value
+ * allows others to generate and verify the same parameters and should be
+ * random input which is kept for reference. If |out_counter| or |out_h| are
+ * not NULL then the counter and h value used in the generation are written to
+ * them.
+ *
+ * The |cb| argument is passed to |BN_generate_prime_ex| and is thus called
+ * during the generation process in order to indicate progress. See the
+ * comments for that function for details. In addition to the calls made by
+ * |BN_generate_prime_ex|, |DSA_generate_parameters_ex| will call it with
+ * |event| equal to 2 and 3 at different stages of the process.
+ *
+ * It returns one on success and zero otherwise. */
+OPENSSL_EXPORT int DSA_generate_parameters_ex(DSA *dsa, unsigned bits,
+                                              const uint8_t *seed,
+                                              size_t seed_len, int *out_counter,
+                                              unsigned long *out_h,
+                                              BN_GENCB *cb);
+
+/* DSAparams_dup returns a freshly allocated |DSA| that contains a copy of the
+ * parameters from |dsa|. It returns NULL on error. */
+OPENSSL_EXPORT DSA *DSAparams_dup(const DSA *dsa);
+
+
+/* Key generation. */
+
+/* DSA_generate_key generates a public/private key pair in |dsa|, which must
+ * already have parameters setup. It returns one on success and zero on
+ * error. */
+OPENSSL_EXPORT int DSA_generate_key(DSA *dsa);
+
+
+/* Signatures. */
+
+/* DSA_SIG contains a DSA signature as a pair of integers. */
+typedef struct DSA_SIG_st {
+  BIGNUM *r, *s;
+} DSA_SIG;
+
+/* DSA_SIG_new returns a freshly allocated, DIG_SIG structure or NULL on error.
+ * Both |r| and |s| in the signature will be NULL. */
+OPENSSL_EXPORT DSA_SIG *DSA_SIG_new(void);
+
+/* DSA_SIG_free frees the contents of |sig| and then frees |sig| itself. */
+OPENSSL_EXPORT void DSA_SIG_free(DSA_SIG *sig);
+
+/* DSA_do_sign returns a signature of the hash in |digest| by the key in |dsa|
+ * and returns an allocated, DSA_SIG structure, or NULL on error. */
+OPENSSL_EXPORT DSA_SIG *DSA_do_sign(const uint8_t *digest, size_t digest_len,
+                                    DSA *dsa);
+
+/* DSA_do_verify verifies that |sig| is a valid signature, by the public key in
+ * |dsa|, of the hash in |digest|. It returns one if so, zero if invalid and -1
+ * on error.
+ *
+ * WARNING: do not use. This function returns -1 for error, 0 for invalid and 1
+ * for valid. However, this is dangerously different to the usual OpenSSL
+ * convention and could be a disaster if a user did |if (DSA_do_verify(...))|.
+ * Because of this, |DSA_check_signature| is a safer version of this.
+ *
+ * TODO(fork): deprecate. */
+OPENSSL_EXPORT int DSA_do_verify(const uint8_t *digest, size_t digest_len,
+                                 DSA_SIG *sig, const DSA *dsa);
+
+/* DSA_do_check_signature sets |*out_valid| to zero. Then it verifies that |sig|
+ * is a valid signature, by the public key in |dsa| of the hash in |digest|
+ * and, if so, it sets |*out_valid| to one.
+ *
+ * It returns one if it was able to verify the signature as valid or invalid,
+ * and zero on error. */
+OPENSSL_EXPORT int DSA_do_check_signature(int *out_valid, const uint8_t *digest,
+                                          size_t digest_len, DSA_SIG *sig,
+                                          const DSA *dsa);
+
+
+/* ASN.1 signatures.
+ *
+ * These functions also perform DSA signature operations, but deal with ASN.1
+ * encoded signatures as opposed to raw |BIGNUM|s. If you don't know what
+ * encoding a DSA signature is in, it's probably ASN.1. */
+
+/* DSA_sign signs |digest| with the key in |dsa| and writes the resulting
+ * signature, in ASN.1 form, to |out_sig| and the length of the signature to
+ * |*out_siglen|. There must be, at least, |DSA_size(dsa)| bytes of space in
+ * |out_sig|. It returns one on success and zero otherwise.
+ *
+ * (The |type| argument is ignored.) */
+OPENSSL_EXPORT int DSA_sign(int type, const uint8_t *digest, size_t digest_len,
+                            uint8_t *out_sig, unsigned int *out_siglen,
+                            DSA *dsa);
+
+/* DSA_verify verifies that |sig| is a valid, ASN.1 signature, by the public
+ * key in |dsa|, of the hash in |digest|. It returns one if so, zero if invalid
+ * and -1 on error.
+ *
+ * (The |type| argument is ignored.)
+ *
+ * WARNING: do not use. This function returns -1 for error, 0 for invalid and 1
+ * for valid. However, this is dangerously different to the usual OpenSSL
+ * convention and could be a disaster if a user did |if (DSA_do_verify(...))|.
+ * Because of this, |DSA_check_signature| is a safer version of this.
+ *
+ * TODO(fork): deprecate. */
+OPENSSL_EXPORT int DSA_verify(int type, const uint8_t *digest,
+                              size_t digest_len, const uint8_t *sig,
+                              size_t sig_len, const DSA *dsa);
+
+/* DSA_check_signature sets |*out_valid| to zero. Then it verifies that |sig|
+ * is a valid, ASN.1 signature, by the public key in |dsa|, of the hash in
+ * |digest|. If so, it sets |*out_valid| to one.
+ *
+ * It returns one if it was able to verify the signature as valid or invalid,
+ * and zero on error. */
+OPENSSL_EXPORT int DSA_check_signature(int *out_valid, const uint8_t *digest,
+                                       size_t digest_len, const uint8_t *sig,
+                                       size_t sig_len, const DSA *dsa);
+
+/* DSA_size returns the size, in bytes, of an ASN.1 encoded, DSA signature
+ * generated by |dsa|. Parameters must already have been setup in |dsa|. */
+OPENSSL_EXPORT int DSA_size(const DSA *dsa);
+
+
+/* ASN.1 encoding. */
+
+/* d2i_DSA_SIG parses an ASN.1, DER-encoded, DSA signature from |len| bytes at
+ * |*inp|. If |out_sig| is not NULL then, on exit, a pointer to the result is
+ * in |*out_sig|. If |*out_sig| is already non-NULL on entry then the result is
+ * written directly into |*out_sig|, otherwise a fresh |DSA_SIG| is allocated.
+ * On successful exit, |*inp| is advanced past the DER structure. It returns
+ * the result or NULL on error. */
+OPENSSL_EXPORT DSA_SIG *d2i_DSA_SIG(DSA_SIG **out_sig, const uint8_t **inp,
+                                    long len);
+
+/* i2d_DSA_SIG marshals |in| to an ASN.1, DER structure. If |outp| is not NULL
+ * then the result is written to |*outp| and |*outp| is advanced just past the
+ * output. It returns the number of bytes in the result, whether written or not,
+ * or a negative value on error. */
+OPENSSL_EXPORT int i2d_DSA_SIG(const DSA_SIG *in, uint8_t **outp);
+
+/* d2i_DSAPublicKey parses an ASN.1, DER-encoded, DSA public key from |len|
+ * bytes at |*inp|. If |out| is not NULL then, on exit, a pointer to the result
+ * is in |*out|. If |*out| is already non-NULL on entry then the result is
+ * written directly into |*out|, otherwise a fresh |DSA| is allocated. On
+ * successful exit, |*inp| is advanced past the DER structure. It returns the
+ * result or NULL on error. */
+OPENSSL_EXPORT DSA *d2i_DSAPublicKey(DSA **out, const uint8_t **inp, long len);
+
+/* i2d_DSAPublicKey marshals a public key from |in| to an ASN.1, DER structure.
+ * If |outp| is not NULL then the result is written to |*outp| and |*outp| is
+ * advanced just past the output. It returns the number of bytes in the result,
+ * whether written or not, or a negative value on error. */
+OPENSSL_EXPORT int i2d_DSAPublicKey(const DSA *in, unsigned char **outp);
+
+/* d2i_DSAPrivateKey parses an ASN.1, DER-encoded, DSA private key from |len|
+ * bytes at |*inp|. If |out| is not NULL then, on exit, a pointer to the result
+ * is in |*out|. If |*out| is already non-NULL on entry then the result is
+ * written directly into |*out|, otherwise a fresh |DSA| is allocated. On
+ * successful exit, |*inp| is advanced past the DER structure. It returns the
+ * result or NULL on error. */
+OPENSSL_EXPORT DSA *d2i_DSAPrivateKey(DSA **out, const uint8_t **inp, long len);
+
+/* i2d_DSAPrivateKey marshals a private key from |in| to an ASN.1, DER structure.
+ * If |outp| is not NULL then the result is written to |*outp| and |*outp| is
+ * advanced just past the output. It returns the number of bytes in the result,
+ * whether written or not, or a negative value on error. */
+OPENSSL_EXPORT int i2d_DSAPrivateKey(const DSA *in, unsigned char **outp);
+
+/* d2i_DSAparams parses ASN.1, DER-encoded, DSA parameters from |len| bytes at
+ * |*inp|. If |out| is not NULL then, on exit, a pointer to the result is in
+ * |*out|. If |*out| is already non-NULL on entry then the result is written
+ * directly into |*out|, otherwise a fresh |DSA| is allocated. On successful
+ * exit, |*inp| is advanced past the DER structure. It returns the result or
+ * NULL on error. */
+OPENSSL_EXPORT DSA *d2i_DSAparams(DSA **out, const uint8_t **inp, long len);
+
+/* i2d_DSAparams marshals DSA parameters from |in| to an ASN.1, DER structure.
+ * If |outp| is not NULL then the result is written to |*outp| and |*outp| is
+ * advanced just past the output. It returns the number of bytes in the result,
+ * whether written or not, or a negative value on error. */
+OPENSSL_EXPORT int i2d_DSAparams(const DSA *in, unsigned char **outp);
+
+
+/* Precomputation. */
+
+/* DSA_sign_setup precomputes the message independent part of the DSA signature
+ * and writes them to |*out_kinv| and |*out_r|. Returns one on success, zero on
+ * error.
+ *
+ * TODO(fork): decide what to do with this. Since making DSA* opaque there's no
+ * way for the user to install them. Also, it forces the DSA* not to be const
+ * when passing to the signing function. */
+OPENSSL_EXPORT int DSA_sign_setup(const DSA *dsa, BN_CTX *ctx,
+                                  BIGNUM **out_kinv, BIGNUM **out_r);
+
+
+/* Conversion. */
+
+/* DSA_dup_DH returns a |DH| constructed from the parameters of |dsa|. This is
+ * sometimes needed when Diffie-Hellman parameters are stored in the form of
+ * DSA parameters. It returns an allocated |DH| on success or NULL on error. */
+OPENSSL_EXPORT DH *DSA_dup_DH(const DSA *dsa);
+
+
+/* ex_data functions.
+ *
+ * See |ex_data.h| for details. */
+
+OPENSSL_EXPORT int DSA_get_ex_new_index(long argl, void *argp,
+                                        CRYPTO_EX_unused *unused,
+                                        CRYPTO_EX_dup *dup_func,
+                                        CRYPTO_EX_free *free_func);
+OPENSSL_EXPORT int DSA_set_ex_data(DSA *d, int idx, void *arg);
+OPENSSL_EXPORT void *DSA_get_ex_data(const DSA *d, int idx);
+
+
+struct dsa_st {
+  long version;
+  int write_params;
+  BIGNUM *p;
+  BIGNUM *q; /* == 20 */
+  BIGNUM *g;
+
+  BIGNUM *pub_key;  /* y public key */
+  BIGNUM *priv_key; /* x private key */
+
+  BIGNUM *kinv; /* Signing pre-calc */
+  BIGNUM *r;    /* Signing pre-calc */
+
+  int flags;
+  /* Normally used to cache montgomery values */
+  CRYPTO_MUTEX method_mont_p_lock;
+  BN_MONT_CTX *method_mont_p;
+  CRYPTO_refcount_t references;
+  CRYPTO_EX_DATA ex_data;
+};
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#define DSA_R_BAD_Q_VALUE 100
+#define DSA_R_MISSING_PARAMETERS 101
+#define DSA_R_MODULUS_TOO_LARGE 102
+#define DSA_R_NEED_NEW_SETUP_VALUES 103
+
+#endif  /* OPENSSL_HEADER_DSA_H */

+ 16 - 0
app/src/main/jni/openssl/include/openssl/dtls1.h

@@ -0,0 +1,16 @@
+/* Copyright (c) 2015, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+/* This header is provided in order to make compiling against code that expects
+   OpenSSL easier. */

+ 355 - 0
app/src/main/jni/openssl/include/openssl/ec.h

@@ -0,0 +1,355 @@
+/* Originally written by Bodo Moeller for the OpenSSL project.
+ * ====================================================================
+ * Copyright (c) 1998-2005 The OpenSSL Project.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. All advertising materials mentioning features or use of this
+ *    software must display the following acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
+ *
+ * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
+ *    endorse or promote products derived from this software without
+ *    prior written permission. For written permission, please contact
+ *    openssl-core@openssl.org.
+ *
+ * 5. Products derived from this software may not be called "OpenSSL"
+ *    nor may "OpenSSL" appear in their names without prior written
+ *    permission of the OpenSSL Project.
+ *
+ * 6. Redistributions of any form whatsoever must retain the following
+ *    acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
+ * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This product includes cryptographic software written by Eric Young
+ * (eay@cryptsoft.com).  This product includes software written by Tim
+ * Hudson (tjh@cryptsoft.com).
+ *
+ */
+/* ====================================================================
+ * Copyright 2002 Sun Microsystems, Inc. ALL RIGHTS RESERVED.
+ *
+ * Portions of the attached software ("Contribution") are developed by
+ * SUN MICROSYSTEMS, INC., and are contributed to the OpenSSL project.
+ *
+ * The Contribution is licensed pursuant to the OpenSSL open source
+ * license provided above.
+ *
+ * The elliptic curve binary polynomial software is originally written by
+ * Sheueling Chang Shantz and Douglas Stebila of Sun Microsystems
+ * Laboratories. */
+
+#ifndef OPENSSL_HEADER_EC_H
+#define OPENSSL_HEADER_EC_H
+
+#include <openssl/base.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* Low-level operations on elliptic curves. */
+
+
+typedef struct ec_group_st EC_GROUP;
+typedef struct ec_point_st EC_POINT;
+
+/** Enum for the point conversion form as defined in X9.62 (ECDSA)
+ *  for the encoding of a elliptic curve point (x,y) */
+typedef enum {
+	/** the point is encoded as z||x, where the octet z specifies 
+	 *  which solution of the quadratic equation y is  */
+	POINT_CONVERSION_COMPRESSED = 2,
+	/** the point is encoded as z||x||y, where z is the octet 0x04  */
+	POINT_CONVERSION_UNCOMPRESSED = 4
+} point_conversion_form_t;
+
+
+/* Elliptic curve groups. */
+
+/* EC_GROUP_new_by_curve_name returns a fresh EC_GROUP object for the elliptic
+ * curve specified by |nid|, or NULL on error.
+ *
+ * The supported NIDs are:
+ *   NID_secp224r1,
+ *   NID_X9_62_prime256v1,
+ *   NID_secp384r1,
+ *   NID_secp521r1 */
+OPENSSL_EXPORT EC_GROUP *EC_GROUP_new_by_curve_name(int nid);
+
+/* EC_GROUP_free frees |group| and the data that it points to. */
+OPENSSL_EXPORT void EC_GROUP_free(EC_GROUP *group);
+
+/* EC_GROUP_dup returns a fresh |EC_GROUP| which is equal to |a| or NULL on
+ * error. */
+OPENSSL_EXPORT EC_GROUP *EC_GROUP_dup(const EC_GROUP *a);
+
+/* EC_GROUP_cmp returns zero if |a| and |b| are the same group and non-zero
+ * otherwise. */
+OPENSSL_EXPORT int EC_GROUP_cmp(const EC_GROUP *a, const EC_GROUP *b,
+                                BN_CTX *ignored);
+
+/* EC_GROUP_get0_generator returns a pointer to the internal |EC_POINT| object
+ * in |group| that specifies the generator for the group. */
+OPENSSL_EXPORT const EC_POINT *EC_GROUP_get0_generator(const EC_GROUP *group);
+
+/* EC_GROUP_get0_order returns a pointer to the internal |BIGNUM| object in
+ * |group| that specifies the order of the group. */
+OPENSSL_EXPORT const BIGNUM *EC_GROUP_get0_order(const EC_GROUP *group);
+
+/* EC_GROUP_get_cofactor sets |*cofactor| to the cofactor of |group| using
+ * |ctx|, if it's not NULL. It returns one on success and zero otherwise. */
+OPENSSL_EXPORT int EC_GROUP_get_cofactor(const EC_GROUP *group,
+                                         BIGNUM *cofactor, BN_CTX *ctx);
+
+/* EC_GROUP_get_curve_GFp gets various parameters about a group. It sets
+ * |*out_p| to the order of the coordinate field and |*out_a| and |*out_b| to
+ * the parameters of the curve when expressed as y² = x³ + ax + b. Any of the
+ * output parameters can be NULL. It returns one on success and zero on
+ * error. */
+OPENSSL_EXPORT int EC_GROUP_get_curve_GFp(const EC_GROUP *group, BIGNUM *out_p,
+                                          BIGNUM *out_a, BIGNUM *out_b,
+                                          BN_CTX *ctx);
+
+/* EC_GROUP_get_curve_name returns a NID that identifies |group|. */
+OPENSSL_EXPORT int EC_GROUP_get_curve_name(const EC_GROUP *group);
+
+/* EC_GROUP_get_degree returns the number of bits needed to represent an
+ * element of the field underlying |group|. */
+OPENSSL_EXPORT unsigned EC_GROUP_get_degree(const EC_GROUP *group);
+
+
+/* Points on elliptic curves. */
+
+/* EC_POINT_new returns a fresh |EC_POINT| object in the given group, or NULL
+ * on error. */
+OPENSSL_EXPORT EC_POINT *EC_POINT_new(const EC_GROUP *group);
+
+/* EC_POINT_free frees |point| and the data that it points to. */
+OPENSSL_EXPORT void EC_POINT_free(EC_POINT *point);
+
+/* EC_POINT_clear_free clears the data that |point| points to, frees it and
+ * then frees |point| itself. */
+OPENSSL_EXPORT void EC_POINT_clear_free(EC_POINT *point);
+
+/* EC_POINT_copy sets |*dest| equal to |*src|. It returns one on success and
+ * zero otherwise. */
+OPENSSL_EXPORT int EC_POINT_copy(EC_POINT *dest, const EC_POINT *src);
+
+/* EC_POINT_dup returns a fresh |EC_POINT| that contains the same values as
+ * |src|, or NULL on error. */
+OPENSSL_EXPORT EC_POINT *EC_POINT_dup(const EC_POINT *src,
+                                      const EC_GROUP *group);
+
+/* EC_POINT_set_to_infinity sets |point| to be the "point at infinity" for the
+ * given group. */
+OPENSSL_EXPORT int EC_POINT_set_to_infinity(const EC_GROUP *group,
+                                            EC_POINT *point);
+
+/* EC_POINT_is_at_infinity returns one iff |point| is the point at infinity and
+ * zero otherwise. */
+OPENSSL_EXPORT int EC_POINT_is_at_infinity(const EC_GROUP *group,
+                                           const EC_POINT *point);
+
+/* EC_POINT_is_on_curve returns one if |point| is an element of |group| and
+ * zero otheriwse. If |ctx| is non-NULL, it may be used. */
+OPENSSL_EXPORT int EC_POINT_is_on_curve(const EC_GROUP *group,
+                                        const EC_POINT *point, BN_CTX *ctx);
+
+/* EC_POINT_cmp returns zero if |a| is equal to |b|, greater than zero is
+ * non-equal and -1 on error. If |ctx| is not NULL, it may be used. */
+OPENSSL_EXPORT int EC_POINT_cmp(const EC_GROUP *group, const EC_POINT *a,
+                                const EC_POINT *b, BN_CTX *ctx);
+
+/* EC_POINT_make_affine converts |point| to affine form, internally. It returns
+ * one on success and zero otherwise. If |ctx| is not NULL, it may be used. */
+OPENSSL_EXPORT int EC_POINT_make_affine(const EC_GROUP *group, EC_POINT *point,
+                                        BN_CTX *ctx);
+
+/* EC_POINTs_make_affine converts |num| points from |points| to affine form,
+ * internally. It returns one on success and zero otherwise. If |ctx| is not
+ * NULL, it may be used. */
+OPENSSL_EXPORT int EC_POINTs_make_affine(const EC_GROUP *group, size_t num,
+                                         EC_POINT *points[], BN_CTX *ctx);
+
+
+/* Point conversion. */
+
+/* EC_POINT_get_affine_coordinates_GFp sets |x| and |y| to the affine value of
+ * |point| using |ctx|, if it's not NULL. It returns one on success and zero
+ * otherwise. */
+OPENSSL_EXPORT int EC_POINT_get_affine_coordinates_GFp(const EC_GROUP *group,
+                                                       const EC_POINT *point,
+                                                       BIGNUM *x, BIGNUM *y,
+                                                       BN_CTX *ctx);
+
+/* EC_POINT_set_affine_coordinates_GFp sets the value of |p| to be (|x|, |y|).
+ * The |ctx| argument may be used if not NULL. It returns one on success or
+ * zero on error. Note that, unlike with OpenSSL, it's considered an error if
+ * the point is not on the curve. */
+OPENSSL_EXPORT int EC_POINT_set_affine_coordinates_GFp(const EC_GROUP *group,
+                                                       EC_POINT *point,
+                                                       const BIGNUM *x,
+                                                       const BIGNUM *y,
+                                                       BN_CTX *ctx);
+
+/* EC_POINT_point2oct serialises |point| into the X9.62 form given by |form|
+ * into, at most, |len| bytes at |buf|. It returns the number of bytes written
+ * or zero on error if |buf| is non-NULL, else the number of bytes needed. The
+ * |ctx| argument may be used if not NULL. */
+OPENSSL_EXPORT size_t EC_POINT_point2oct(const EC_GROUP *group,
+                                         const EC_POINT *point,
+                                         point_conversion_form_t form,
+                                         uint8_t *buf, size_t len, BN_CTX *ctx);
+
+/* EC_POINT_oct2point sets |point| from |len| bytes of X9.62 format
+ * serialisation in |buf|. It returns one on success and zero otherwise. The
+ * |ctx| argument may be used if not NULL. */
+OPENSSL_EXPORT int EC_POINT_oct2point(const EC_GROUP *group, EC_POINT *point,
+                                      const uint8_t *buf, size_t len,
+                                      BN_CTX *ctx);
+
+/* EC_POINT_set_compressed_coordinates_GFp sets |point| to equal the point with
+ * the given |x| coordinate and the y coordinate specified by |y_bit| (see
+ * X9.62). It returns one on success and zero otherwise. */
+OPENSSL_EXPORT int EC_POINT_set_compressed_coordinates_GFp(
+    const EC_GROUP *group, EC_POINT *point, const BIGNUM *x, int y_bit,
+    BN_CTX *ctx);
+
+
+/* Group operations. */
+
+/* EC_POINT_add sets |r| equal to |a| plus |b|. It returns one on success and
+ * zero otherwise. If |ctx| is not NULL, it may be used. */
+OPENSSL_EXPORT int EC_POINT_add(const EC_GROUP *group, EC_POINT *r,
+                                const EC_POINT *a, const EC_POINT *b,
+                                BN_CTX *ctx);
+
+/* EC_POINT_dbl sets |r| equal to |a| plus |a|. It returns one on success and
+ * zero otherwise. If |ctx| is not NULL, it may be used. */
+OPENSSL_EXPORT int EC_POINT_dbl(const EC_GROUP *group, EC_POINT *r,
+                                const EC_POINT *a, BN_CTX *ctx);
+
+/* EC_POINT_invert sets |a| equal to minus |a|. It returns one on success and zero
+ * otherwise. If |ctx| is not NULL, it may be used. */
+OPENSSL_EXPORT int EC_POINT_invert(const EC_GROUP *group, EC_POINT *a,
+                                   BN_CTX *ctx);
+
+/* EC_POINT_mul sets r = generator*n + q*m. It returns one on success and zero
+ * otherwise. If |ctx| is not NULL, it may be used. */
+OPENSSL_EXPORT int EC_POINT_mul(const EC_GROUP *group, EC_POINT *r,
+                                const BIGNUM *n, const EC_POINT *q,
+                                const BIGNUM *m, BN_CTX *ctx);
+
+
+/* Deprecated functions. */
+
+/* EC_GROUP_new_curve_GFp creates a new, arbitrary elliptic curve group based
+ * on the equation y² = x³ + a·x + b. It returns the new group or NULL on
+ * error.
+ *
+ * |EC_GROUP|s returned by this function will always compare as unequal via
+ * |EC_GROUP_cmp| (even to themselves). |EC_GROUP_get_curve_name| will always
+ * return |NID_undef|. */
+OPENSSL_EXPORT EC_GROUP *EC_GROUP_new_curve_GFp(const BIGNUM *p,
+                                                const BIGNUM *a,
+                                                const BIGNUM *b, BN_CTX *ctx);
+
+/* EC_GROUP_get_order sets |*order| to the order of |group|, if it's not
+ * NULL. It returns one on success and zero otherwise. |ctx| is ignored. Use
+ * |EC_GROUP_get0_order| instead. */
+OPENSSL_EXPORT int EC_GROUP_get_order(const EC_GROUP *group, BIGNUM *order,
+                                      BN_CTX *ctx);
+
+/* EC_GROUP_set_generator sets the generator for |group| to |generator|, which
+ * must have the given order and cofactor. This should only be used with
+ * |EC_GROUP| objects returned by |EC_GROUP_new_curve_GFp|. */
+OPENSSL_EXPORT int EC_GROUP_set_generator(EC_GROUP *group,
+                                          const EC_POINT *generator,
+                                          const BIGNUM *order,
+                                          const BIGNUM *cofactor);
+
+/* EC_GROUP_set_asn1_flag does nothing. */
+OPENSSL_EXPORT void EC_GROUP_set_asn1_flag(EC_GROUP *group, int flag);
+
+#define OPENSSL_EC_NAMED_CURVE 0
+
+typedef struct ec_method_st EC_METHOD;
+
+/* EC_GROUP_method_of returns NULL. */
+OPENSSL_EXPORT const EC_METHOD *EC_GROUP_method_of(const EC_GROUP *group);
+
+/* EC_METHOD_get_field_type returns NID_X9_62_prime_field. */
+OPENSSL_EXPORT int EC_METHOD_get_field_type(const EC_METHOD *meth);
+
+/* EC_GROUP_set_point_conversion_form aborts the process if |form| is not
+ * |POINT_CONVERSION_UNCOMPRESSED| and otherwise does nothing. */
+OPENSSL_EXPORT void EC_GROUP_set_point_conversion_form(
+    EC_GROUP *group, point_conversion_form_t form);
+
+
+/* Old code expects to get EC_KEY from ec.h. */
+#include <openssl/ec_key.h>
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#define EC_R_BUFFER_TOO_SMALL 100
+#define EC_R_COORDINATES_OUT_OF_RANGE 101
+#define EC_R_D2I_ECPKPARAMETERS_FAILURE 102
+#define EC_R_EC_GROUP_NEW_BY_NAME_FAILURE 103
+#define EC_R_GROUP2PKPARAMETERS_FAILURE 104
+#define EC_R_I2D_ECPKPARAMETERS_FAILURE 105
+#define EC_R_INCOMPATIBLE_OBJECTS 106
+#define EC_R_INVALID_COMPRESSED_POINT 107
+#define EC_R_INVALID_COMPRESSION_BIT 108
+#define EC_R_INVALID_ENCODING 109
+#define EC_R_INVALID_FIELD 110
+#define EC_R_INVALID_FORM 111
+#define EC_R_INVALID_GROUP_ORDER 112
+#define EC_R_INVALID_PRIVATE_KEY 113
+#define EC_R_MISSING_PARAMETERS 114
+#define EC_R_MISSING_PRIVATE_KEY 115
+#define EC_R_NON_NAMED_CURVE 116
+#define EC_R_NOT_INITIALIZED 117
+#define EC_R_PKPARAMETERS2GROUP_FAILURE 118
+#define EC_R_POINT_AT_INFINITY 119
+#define EC_R_POINT_IS_NOT_ON_CURVE 120
+#define EC_R_SLOT_FULL 121
+#define EC_R_UNDEFINED_GENERATOR 122
+#define EC_R_UNKNOWN_GROUP 123
+#define EC_R_UNKNOWN_ORDER 124
+#define EC_R_WRONG_ORDER 125
+#define EC_R_BIGNUM_OUT_OF_RANGE 126
+#define EC_R_WRONG_CURVE_PARAMETERS 127
+
+#endif  /* OPENSSL_HEADER_EC_H */

+ 280 - 0
app/src/main/jni/openssl/include/openssl/ec_key.h

@@ -0,0 +1,280 @@
+/* Originally written by Bodo Moeller for the OpenSSL project.
+ * ====================================================================
+ * Copyright (c) 1998-2005 The OpenSSL Project.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. All advertising materials mentioning features or use of this
+ *    software must display the following acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
+ *
+ * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
+ *    endorse or promote products derived from this software without
+ *    prior written permission. For written permission, please contact
+ *    openssl-core@openssl.org.
+ *
+ * 5. Products derived from this software may not be called "OpenSSL"
+ *    nor may "OpenSSL" appear in their names without prior written
+ *    permission of the OpenSSL Project.
+ *
+ * 6. Redistributions of any form whatsoever must retain the following
+ *    acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
+ * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This product includes cryptographic software written by Eric Young
+ * (eay@cryptsoft.com).  This product includes software written by Tim
+ * Hudson (tjh@cryptsoft.com).
+ *
+ */
+/* ====================================================================
+ * Copyright 2002 Sun Microsystems, Inc. ALL RIGHTS RESERVED.
+ *
+ * Portions of the attached software ("Contribution") are developed by
+ * SUN MICROSYSTEMS, INC., and are contributed to the OpenSSL project.
+ *
+ * The Contribution is licensed pursuant to the OpenSSL open source
+ * license provided above.
+ *
+ * The elliptic curve binary polynomial software is originally written by
+ * Sheueling Chang Shantz and Douglas Stebila of Sun Microsystems
+ * Laboratories. */
+
+#ifndef OPENSSL_HEADER_EC_KEY_H
+#define OPENSSL_HEADER_EC_KEY_H
+
+#include <openssl/base.h>
+
+#include <openssl/ec.h>
+#include <openssl/engine.h>
+#include <openssl/ex_data.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* ec_key.h contains functions that handle elliptic-curve points that are
+ * public/private keys. */
+
+
+/* EC key objects. */
+
+/* EC_KEY_new returns a fresh |EC_KEY| object or NULL on error. */
+OPENSSL_EXPORT EC_KEY *EC_KEY_new(void);
+
+/* EC_KEY_new_method acts the same as |EC_KEY_new|, but takes an explicit
+ * |ENGINE|. */
+OPENSSL_EXPORT EC_KEY *EC_KEY_new_method(const ENGINE *engine);
+
+/* EC_KEY_new_by_curve_name returns a fresh EC_KEY for group specified by |nid|
+ * or NULL on error. */
+OPENSSL_EXPORT EC_KEY *EC_KEY_new_by_curve_name(int nid);
+
+/* EC_KEY_free frees all the data owned by |key| and |key| itself. */
+OPENSSL_EXPORT void EC_KEY_free(EC_KEY *key);
+
+/* EC_KEY_copy sets |dst| equal to |src| and returns |dst| or NULL on error. */
+OPENSSL_EXPORT EC_KEY *EC_KEY_copy(EC_KEY *dst, const EC_KEY *src);
+
+/* EC_KEY_dup returns a fresh copy of |src| or NULL on error. */
+OPENSSL_EXPORT EC_KEY *EC_KEY_dup(const EC_KEY *src);
+
+/* EC_KEY_up_ref increases the reference count of |key|. It returns one on
+ * success and zero otherwise. */
+OPENSSL_EXPORT int EC_KEY_up_ref(EC_KEY *key);
+
+/* EC_KEY_is_opaque returns one if |key| is opaque and doesn't expose its key
+ * material. Otherwise it return zero. */
+OPENSSL_EXPORT int EC_KEY_is_opaque(const EC_KEY *key);
+
+/* EC_KEY_get0_group returns a pointer to the |EC_GROUP| object inside |key|. */
+OPENSSL_EXPORT const EC_GROUP *EC_KEY_get0_group(const EC_KEY *key);
+
+/* EC_KEY_set_group sets the |EC_GROUP| object that |key| will use to |group|.
+ * It returns one on success and zero otherwise. */
+OPENSSL_EXPORT int EC_KEY_set_group(EC_KEY *key, const EC_GROUP *group);
+
+/* EC_KEY_get0_private_key returns a pointer to the private key inside |key|. */
+OPENSSL_EXPORT const BIGNUM *EC_KEY_get0_private_key(const EC_KEY *key);
+
+/* EC_KEY_set_private_key sets the private key of |key| to |priv|. It returns
+ * one on success and zero otherwise. */
+OPENSSL_EXPORT int EC_KEY_set_private_key(EC_KEY *key, const BIGNUM *prv);
+
+/* EC_KEY_get0_public_key returns a pointer to the public key point inside
+ * |key|. */
+OPENSSL_EXPORT const EC_POINT *EC_KEY_get0_public_key(const EC_KEY *key);
+
+/* EC_KEY_set_public_key sets the public key of |key| to |pub|, by copying it.
+ * It returns one on success and zero otherwise. */
+OPENSSL_EXPORT int EC_KEY_set_public_key(EC_KEY *key, const EC_POINT *pub);
+
+#define EC_PKEY_NO_PARAMETERS 0x001
+#define EC_PKEY_NO_PUBKEY 0x002
+
+/* EC_KEY_get_enc_flags returns the encoding flags for |key|, which is a
+ * bitwise-OR of |EC_PKEY_*| values. */
+OPENSSL_EXPORT unsigned EC_KEY_get_enc_flags(const EC_KEY *key);
+
+/* EC_KEY_set_enc_flags sets the encoding flags for |key|, which is a
+ * bitwise-OR of |EC_PKEY_*| values. */
+OPENSSL_EXPORT void EC_KEY_set_enc_flags(EC_KEY *key, unsigned flags);
+
+/* EC_KEY_get_conv_form returns the conversation form that will be used by
+ * |key|. */
+OPENSSL_EXPORT point_conversion_form_t EC_KEY_get_conv_form(const EC_KEY *key);
+
+/* EC_KEY_set_conv_form sets the conversion form to be used by |key|. */
+OPENSSL_EXPORT void EC_KEY_set_conv_form(EC_KEY *key,
+                                         point_conversion_form_t cform);
+
+/* EC_KEY_check_key performs several checks on |key| (possibly including an
+ * expensive check that the public key is in the primary subgroup). It returns
+ * one if all checks pass and zero otherwise. If it returns zero then detail
+ * about the problem can be found on the error stack. */
+OPENSSL_EXPORT int EC_KEY_check_key(const EC_KEY *key);
+
+/* EC_KEY_set_public_key_affine_coordinates sets the public key in |key| to
+ * (|x|, |y|). It returns one on success and zero otherwise. */
+OPENSSL_EXPORT int EC_KEY_set_public_key_affine_coordinates(EC_KEY *key,
+                                                            BIGNUM *x,
+                                                            BIGNUM *y);
+
+
+/* Key generation. */
+
+/* EC_KEY_generate_key generates a random, private key, calculates the
+ * corresponding public key and stores both in |key|. It returns one on success
+ * or zero otherwise. */
+OPENSSL_EXPORT int EC_KEY_generate_key(EC_KEY *key);
+
+
+/* Serialisation. */
+
+/* d2i_ECPrivateKey parses an ASN.1, DER-encoded, private key from |len| bytes
+ * at |*inp|. If |out_key| is not NULL then, on exit, a pointer to the result
+ * is in |*out_key|. If |*out_key| is already non-NULL on entry then the result
+ * is written directly into |*out_key|, otherwise a fresh |EC_KEY| is
+ * allocated. On successful exit, |*inp| is advanced past the DER structure. It
+ * returns the result or NULL on error. */
+OPENSSL_EXPORT EC_KEY *d2i_ECPrivateKey(EC_KEY **out_key, const uint8_t **inp,
+                                        long len);
+
+/* i2d_ECPrivateKey marshals an EC private key from |key| to an ASN.1, DER
+ * structure. If |outp| is not NULL then the result is written to |*outp| and
+ * |*outp| is advanced just past the output. It returns the number of bytes in
+ * the result, whether written or not, or a negative value on error. */
+OPENSSL_EXPORT int i2d_ECPrivateKey(const EC_KEY *key, uint8_t **outp);
+
+/* d2i_ECParameters parses an ASN.1, DER-encoded, set of EC parameters from
+ * |len| bytes at |*inp|. If |out_key| is not NULL then, on exit, a pointer to
+ * the result is in |*out_key|. If |*out_key| is already non-NULL on entry then
+ * the result is written directly into |*out_key|, otherwise a fresh |EC_KEY|
+ * is allocated. On successful exit, |*inp| is advanced past the DER structure.
+ * It returns the result or NULL on error. */
+OPENSSL_EXPORT EC_KEY *d2i_ECParameters(EC_KEY **out_key, const uint8_t **inp,
+                                        long len);
+
+/* i2d_ECParameters marshals EC parameters from |key| to an ASN.1, DER
+ * structure. If |outp| is not NULL then the result is written to |*outp| and
+ * |*outp| is advanced just past the output. It returns the number of bytes in
+ * the result, whether written or not, or a negative value on error. */
+OPENSSL_EXPORT int i2d_ECParameters(const EC_KEY *key, uint8_t **outp);
+
+/* o2i_ECPublicKey parses an EC point from |len| bytes at |*inp| into
+ * |*out_key|. Note that this differs from the d2i format in that |*out_key|
+ * must be non-NULL with a group set. On successful exit, |*inp| is advanced by
+ * |len| bytes. It returns |*out_key| or NULL on error. */
+OPENSSL_EXPORT EC_KEY *o2i_ECPublicKey(EC_KEY **out_key, const uint8_t **inp,
+                                       long len);
+
+/* i2o_ECPublicKey marshals an EC point from |key|. If |outp| is not NULL then
+ * the result is written to |*outp| and |*outp| is advanced just past the
+ * output. It returns the number of bytes in the result, whether written or
+ * not, or a negative value on error. */
+OPENSSL_EXPORT int i2o_ECPublicKey(const EC_KEY *key, unsigned char **outp);
+
+
+/* ex_data functions.
+ *
+ * These functions are wrappers. See |ex_data.h| for details. */
+
+OPENSSL_EXPORT int EC_KEY_get_ex_new_index(long argl, void *argp,
+                                           CRYPTO_EX_unused *unused,
+                                           CRYPTO_EX_dup *dup_func,
+                                           CRYPTO_EX_free *free_func);
+OPENSSL_EXPORT int EC_KEY_set_ex_data(EC_KEY *r, int idx, void *arg);
+OPENSSL_EXPORT void *EC_KEY_get_ex_data(const EC_KEY *r, int idx);
+
+
+/* ECDSA method. */
+
+/* ECDSA_FLAG_OPAQUE specifies that this ECDSA_METHOD does not expose its key
+ * material. This may be set if, for instance, it is wrapping some other crypto
+ * API, like a platform key store. */
+#define ECDSA_FLAG_OPAQUE 1
+
+/* ecdsa_method_st is a structure of function pointers for implementing ECDSA.
+ * See engine.h. */
+struct ecdsa_method_st {
+  struct openssl_method_common_st common;
+
+  void *app_data;
+
+  int (*init)(EC_KEY *key);
+  int (*finish)(EC_KEY *key);
+
+  /* group_order_size returns the number of bytes needed to represent the order
+   * of the group. This is used to calculate the maximum size of an ECDSA
+   * signature in |ECDSA_size|. */
+  size_t (*group_order_size)(const EC_KEY *key);
+
+  /* sign matches the arguments and behaviour of |ECDSA_sign|. */
+  int (*sign)(const uint8_t *digest, size_t digest_len, uint8_t *sig,
+              unsigned int *sig_len, EC_KEY *eckey);
+
+  /* verify matches the arguments and behaviour of |ECDSA_verify|. */
+  int (*verify)(const uint8_t *digest, size_t digest_len, const uint8_t *sig,
+                size_t sig_len, EC_KEY *eckey);
+
+  int flags;
+};
+
+
+/* Deprecated functions. */
+
+/* EC_KEY_set_asn1_flag does nothing. */
+OPENSSL_EXPORT void EC_KEY_set_asn1_flag(EC_KEY *key, int flag);
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_EC_KEY_H */

+ 102 - 0
app/src/main/jni/openssl/include/openssl/ecdh.h

@@ -0,0 +1,102 @@
+/* ====================================================================
+ * Copyright 2002 Sun Microsystems, Inc. ALL RIGHTS RESERVED.
+ *
+ * The Elliptic Curve Public-Key Crypto Library (ECC Code) included
+ * herein is developed by SUN MICROSYSTEMS, INC., and is contributed
+ * to the OpenSSL project.
+ *
+ * The ECC Code is licensed pursuant to the OpenSSL open source
+ * license provided below.
+ *
+ * The ECDH software is originally written by Douglas Stebila of
+ * Sun Microsystems Laboratories.
+ *
+ */
+/* ====================================================================
+ * Copyright (c) 2000-2002 The OpenSSL Project.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. All advertising materials mentioning features or use of this
+ *    software must display the following acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
+ *
+ * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
+ *    endorse or promote products derived from this software without
+ *    prior written permission. For written permission, please contact
+ *    licensing@OpenSSL.org.
+ *
+ * 5. Products derived from this software may not be called "OpenSSL"
+ *    nor may "OpenSSL" appear in their names without prior written
+ *    permission of the OpenSSL Project.
+ *
+ * 6. Redistributions of any form whatsoever must retain the following
+ *    acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
+ * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This product includes cryptographic software written by Eric Young
+ * (eay@cryptsoft.com).  This product includes software written by Tim
+ * Hudson (tjh@cryptsoft.com). */
+
+#ifndef OPENSSL_HEADER_ECDH_H
+#define OPENSSL_HEADER_ECDH_H
+
+#include <openssl/base.h>
+
+#include <openssl/ec_key.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* Elliptic curve Diffie-Hellman. */
+
+
+/* ECDH_compute_key calculates the shared key between |pub_key| and |priv_key|.
+ * If |kdf| is not NULL, then it is called with the bytes of the shared key and
+ * the parameter |out|. When |kdf| returns, the value of |*outlen| becomes the
+ * return value. Otherwise, as many bytes of the shared key as will fit are
+ * copied directly to, at most, |outlen| bytes at |out|. It returns the number
+ * of bytes written to |out|, or -1 on error. */
+OPENSSL_EXPORT int ECDH_compute_key(void *out, size_t outlen,
+                                    const EC_POINT *pub_key, EC_KEY *priv_key,
+                                    void *(*kdf)(const void *in, size_t inlen,
+                                                 void *out, size_t *outlen));
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#define ECDH_R_KDF_FAILED 100
+#define ECDH_R_NO_PRIVATE_VALUE 101
+#define ECDH_R_POINT_ARITHMETIC_FAILURE 102
+
+#endif  /* OPENSSL_HEADER_ECDH_H */

+ 206 - 0
app/src/main/jni/openssl/include/openssl/ecdsa.h

@@ -0,0 +1,206 @@
+/* ====================================================================
+ * Copyright (c) 1998-2005 The OpenSSL Project.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. All advertising materials mentioning features or use of this
+ *    software must display the following acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
+ *
+ * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
+ *    endorse or promote products derived from this software without
+ *    prior written permission. For written permission, please contact
+ *    openssl-core@OpenSSL.org.
+ *
+ * 5. Products derived from this software may not be called "OpenSSL"
+ *    nor may "OpenSSL" appear in their names without prior written
+ *    permission of the OpenSSL Project.
+ *
+ * 6. Redistributions of any form whatsoever must retain the following
+ *    acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
+ * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This product includes cryptographic software written by Eric Young
+ * (eay@cryptsoft.com).  This product includes software written by Tim
+ * Hudson (tjh@cryptsoft.com). */
+
+#ifndef OPENSSL_HEADER_ECDSA_H
+#define OPENSSL_HEADER_ECDSA_H
+
+#include <openssl/base.h>
+
+#include <openssl/ec_key.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* ECDSA contains functions for signing and verifying with the Digital Signature
+ * Algorithm over elliptic curves. */
+
+
+/* Signing and verifing. */
+
+/* ECDSA_sign signs |digest_len| bytes from |digest| with |key| and writes the
+ * resulting signature to |sig|, which must have |ECDSA_size(key)| bytes of
+ * space. On successful exit, |*sig_len| is set to the actual number of bytes
+ * written. The |type| argument should be zero. It returns one on success and
+ * zero otherwise. */
+OPENSSL_EXPORT int ECDSA_sign(int type, const uint8_t *digest,
+                              size_t digest_len, uint8_t *sig,
+                              unsigned int *sig_len, EC_KEY *key);
+
+/* ECDSA_verify verifies that |sig_len| bytes from |sig| constitute a valid
+ * signature by |key| of |digest|. (The |type| argument should be zero.) It
+ * returns one on success or zero if the signature is invalid or an error
+ * occured. */
+OPENSSL_EXPORT int ECDSA_verify(int type, const uint8_t *digest,
+                                size_t digest_len, const uint8_t *sig,
+                                size_t sig_len, EC_KEY *key);
+
+/* ECDSA_size returns the maximum size of an ECDSA signature using |key|. It
+ * returns zero on error. */
+OPENSSL_EXPORT size_t ECDSA_size(const EC_KEY *key);
+
+
+/* Low-level signing and verification.
+ *
+ * Low-level functions handle signatures as |ECDSA_SIG| structures which allow
+ * the two values in an ECDSA signature to be handled separately. */
+
+struct ecdsa_sig_st {
+  BIGNUM *r;
+  BIGNUM *s;
+};
+
+/* ECDSA_SIG_new returns a fresh |ECDSA_SIG| structure or NULL on error. */
+OPENSSL_EXPORT ECDSA_SIG *ECDSA_SIG_new(void);
+
+/* ECDSA_SIG_free frees |sig| its member |BIGNUM|s. */
+OPENSSL_EXPORT void ECDSA_SIG_free(ECDSA_SIG *sig);
+
+/* ECDSA_do_sign signs |digest_len| bytes from |digest| with |key| and returns
+ * the resulting signature structure, or NULL on error. */
+OPENSSL_EXPORT ECDSA_SIG *ECDSA_do_sign(const uint8_t *digest,
+                                        size_t digest_len, EC_KEY *key);
+
+/* ECDSA_do_verify verifies that |sig| constitutes a valid signature by |key|
+ * of |digest|. It returns one on success or zero if the signature is invalid
+ * or on error. */
+OPENSSL_EXPORT int ECDSA_do_verify(const uint8_t *digest, size_t digest_len,
+                                   const ECDSA_SIG *sig, EC_KEY *key);
+
+
+/* Signing with precomputation.
+ *
+ * Parts of the ECDSA signature can be independent of the message to be signed
+ * thus it's possible to precompute them and reduce the signing latency.
+ *
+ * TODO(fork): remove support for this as it cannot support safe-randomness. */
+
+/* ECDSA_sign_setup precomputes parts of an ECDSA signing operation. It sets
+ * |*kinv| and |*rp| to the precomputed values and uses the |ctx| argument, if
+ * not NULL. It returns one on success and zero otherwise. */
+OPENSSL_EXPORT int ECDSA_sign_setup(EC_KEY *eckey, BN_CTX *ctx, BIGNUM **kinv,
+                                    BIGNUM **rp);
+
+/* ECDSA_do_sign_ex is the same as |ECDSA_do_sign| but takes precomputed values
+ * as generated by |ECDSA_sign_setup|. */
+OPENSSL_EXPORT ECDSA_SIG *ECDSA_do_sign_ex(const uint8_t *digest,
+                                           size_t digest_len,
+                                           const BIGNUM *kinv, const BIGNUM *rp,
+                                           EC_KEY *eckey);
+
+/* ECDSA_sign_ex is the same as |ECDSA_sign| but takes precomputed values as
+ * generated by |ECDSA_sign_setup|. */
+OPENSSL_EXPORT int ECDSA_sign_ex(int type, const uint8_t *digest,
+                                 size_t digest_len, uint8_t *sig,
+                                 unsigned int *sig_len, const BIGNUM *kinv,
+                                 const BIGNUM *rp, EC_KEY *eckey);
+
+
+/* ASN.1 functions. */
+
+/* ECDSA_SIG_parse parses a DER-encoded ECDSA-Sig-Value structure from |cbs| and
+ * advances |cbs|. It returns a newly-allocated |ECDSA_SIG| or NULL on error. */
+OPENSSL_EXPORT ECDSA_SIG *ECDSA_SIG_parse(CBS *cbs);
+
+/* ECDSA_SIG_from_bytes parses |in| as a DER-encoded ECDSA-Sig-Value structure.
+ * It returns a newly-allocated |ECDSA_SIG| structure or NULL on error. */
+OPENSSL_EXPORT ECDSA_SIG *ECDSA_SIG_from_bytes(const uint8_t *in,
+                                               size_t in_len);
+
+/* ECDSA_SIG_marshal marshals |sig| as a DER-encoded ECDSA-Sig-Value and appends
+ * the result to |cbb|. It returns one on success and zero on error. */
+OPENSSL_EXPORT int ECDSA_SIG_marshal(CBB *cbb, const ECDSA_SIG *sig);
+
+/* ECDSA_SIG_to_bytes marshals |sig| as a DER-encoded ECDSA-Sig-Value and, on
+ * success, sets |*out_bytes| to a newly allocated buffer containing the result
+ * and returns one. Otherwise, it returns zero. The result should be freed with
+ * |OPENSSL_free|. */
+OPENSSL_EXPORT int ECDSA_SIG_to_bytes(uint8_t **out_bytes, size_t *out_len,
+                                      const ECDSA_SIG *sig);
+
+/* ECDSA_SIG_max_len returns the maximum length of a DER-encoded ECDSA-Sig-Value
+ * structure for a group whose order is represented in |order_len| bytes, or
+ * zero on overflow. */
+OPENSSL_EXPORT size_t ECDSA_SIG_max_len(size_t order_len);
+
+
+/* Deprecated functions. */
+
+/* d2i_ECDSA_SIG parses an ASN.1, DER-encoded, signature from |len| bytes at
+ * |*inp|. If |out| is not NULL then, on exit, a pointer to the result is in
+ * |*out|. If |*out| is already non-NULL on entry then the result is written
+ * directly into |*out|, otherwise a fresh |ECDSA_SIG| is allocated. On
+ * successful exit, |*inp| is advanced past the DER structure. It returns the
+ * result or NULL on error. */
+OPENSSL_EXPORT ECDSA_SIG *d2i_ECDSA_SIG(ECDSA_SIG **out, const uint8_t **inp,
+                                        long len);
+
+/* i2d_ECDSA_SIG marshals a signature from |sig| to an ASN.1, DER
+ * structure. If |outp| is not NULL then the result is written to |*outp| and
+ * |*outp| is advanced just past the output. It returns the number of bytes in
+ * the result, whether written or not, or a negative value on error. */
+OPENSSL_EXPORT int i2d_ECDSA_SIG(const ECDSA_SIG *sig, uint8_t **outp);
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#define ECDSA_R_BAD_SIGNATURE 100
+#define ECDSA_R_MISSING_PARAMETERS 101
+#define ECDSA_R_NEED_NEW_SETUP_VALUES 102
+#define ECDSA_R_NOT_IMPLEMENTED 103
+#define ECDSA_R_RANDOM_NUMBER_GENERATION_FAILED 104
+#define ECDSA_R_ENCODE_ERROR 105
+
+#endif  /* OPENSSL_HEADER_ECDSA_H */

+ 98 - 0
app/src/main/jni/openssl/include/openssl/engine.h

@@ -0,0 +1,98 @@
+/* Copyright (c) 2014, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+#ifndef OPENSSL_HEADER_ENGINE_H
+#define OPENSSL_HEADER_ENGINE_H
+
+#include <openssl/base.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* Engines are collections of methods. Methods are tables of function pointers,
+ * defined for certain algorithms, that allow operations on those algorithms to
+ * be overridden via a callback. This can be used, for example, to implement an
+ * RSA* that forwards operations to a hardware module.
+ *
+ * Methods are reference counted but |ENGINE|s are not. When creating a method,
+ * you should zero the whole structure and fill in the function pointers that
+ * you wish before setting it on an |ENGINE|. Any functions pointers that
+ * are NULL indicate that the default behaviour should be used. */
+
+
+/* Allocation and destruction. */
+
+/* ENGINE_new returns an empty ENGINE that uses the default method for all
+ * algorithms. */
+OPENSSL_EXPORT ENGINE *ENGINE_new(void);
+
+/* ENGINE_free decrements the reference counts for all methods linked from
+ * |engine| and frees |engine| itself. */
+OPENSSL_EXPORT void ENGINE_free(ENGINE *engine);
+
+
+/* Method accessors.
+ *
+ * Method accessors take a method pointer and the size of the structure. The
+ * size allows for ABI compatibility in the case that the method structure is
+ * extended with extra elements at the end. Methods are always copied by the
+ * set functions.
+ *
+ * Set functions return one on success and zero on allocation failure. */
+
+OPENSSL_EXPORT int ENGINE_set_RSA_method(ENGINE *engine,
+                                         const RSA_METHOD *method,
+                                         size_t method_size);
+OPENSSL_EXPORT RSA_METHOD *ENGINE_get_RSA_method(const ENGINE *engine);
+
+OPENSSL_EXPORT int ENGINE_set_ECDSA_method(ENGINE *engine,
+                                           const ECDSA_METHOD *method,
+                                           size_t method_size);
+OPENSSL_EXPORT ECDSA_METHOD *ENGINE_get_ECDSA_method(const ENGINE *engine);
+
+
+/* Generic method functions.
+ *
+ * These functions take a void* type but actually operate on all method
+ * structures. */
+
+/* METHOD_ref increments the reference count of |method|. This is a no-op for
+ * now because all methods are currently static. */
+void METHOD_ref(void *method);
+
+/* METHOD_unref decrements the reference count of |method| and frees it if the
+ * reference count drops to zero. This is a no-op for now because all methods
+ * are currently static. */
+void METHOD_unref(void *method);
+
+
+/* Private functions. */
+
+/* openssl_method_common_st contains the common part of all method structures.
+ * This must be the first member of all method structures. */
+struct openssl_method_common_st {
+  int references;  /* dummy – not used. */
+  char is_static;
+};
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#define ENGINE_R_OPERATION_NOT_SUPPORTED 100
+
+#endif  /* OPENSSL_HEADER_ENGINE_H */

+ 487 - 0
app/src/main/jni/openssl/include/openssl/err.h

@@ -0,0 +1,487 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.]
+ */
+/* ====================================================================
+ * Copyright (c) 1998-2006 The OpenSSL Project.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. All advertising materials mentioning features or use of this
+ *    software must display the following acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
+ *
+ * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
+ *    endorse or promote products derived from this software without
+ *    prior written permission. For written permission, please contact
+ *    openssl-core@openssl.org.
+ *
+ * 5. Products derived from this software may not be called "OpenSSL"
+ *    nor may "OpenSSL" appear in their names without prior written
+ *    permission of the OpenSSL Project.
+ *
+ * 6. Redistributions of any form whatsoever must retain the following
+ *    acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
+ * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This product includes cryptographic software written by Eric Young
+ * (eay@cryptsoft.com).  This product includes software written by Tim
+ * Hudson (tjh@cryptsoft.com). */
+
+#ifndef OPENSSL_HEADER_ERR_H
+#define OPENSSL_HEADER_ERR_H
+
+#include <stdio.h>
+
+#include <openssl/base.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* Error queue handling functions.
+ *
+ * Errors in OpenSSL are generally signalled by the return value of a function.
+ * When a function fails it may add an entry to a per-thread error queue,
+ * which is managed by the functions in this header.
+ *
+ * Each error contains:
+ *   1) The library (i.e. ec, pem, rsa) which created it.
+ *   2) The file and line number of the call that added the error.
+ *   3) A pointer to some error specific data, which may be NULL.
+ *
+ * The library identifier and reason code are packed in a uint32_t and there
+ * exist various functions for unpacking it.
+ *
+ * The typical behaviour is that an error will occur deep in a call queue and
+ * that code will push an error onto the error queue. As the error queue
+ * unwinds, other functions will push their own errors. Thus, the "least
+ * recent" error is the most specific and the other errors will provide a
+ * backtrace of sorts. */
+
+
+/* Startup and shutdown. */
+
+/* ERR_load_BIO_strings does nothing.
+ *
+ * TODO(fork): remove. libjingle calls this. */
+OPENSSL_EXPORT void ERR_load_BIO_strings(void);
+
+/* ERR_load_ERR_strings does nothing. */
+OPENSSL_EXPORT void ERR_load_ERR_strings(void);
+
+/* ERR_load_crypto_strings does nothing. */
+OPENSSL_EXPORT void ERR_load_crypto_strings(void);
+
+/* ERR_free_strings does nothing. */
+OPENSSL_EXPORT void ERR_free_strings(void);
+
+
+/* Reading and formatting errors. */
+
+/* ERR_get_error gets the packed error code for the least recent error and
+ * removes that error from the queue. If there are no errors in the queue then
+ * it returns zero. */
+OPENSSL_EXPORT uint32_t ERR_get_error(void);
+
+/* ERR_get_error_line acts like |ERR_get_error|, except that the file and line
+ * number of the call that added the error are also returned. */
+OPENSSL_EXPORT uint32_t ERR_get_error_line(const char **file, int *line);
+
+/* ERR_get_error_line_data acts like |ERR_get_error_line|, but also returns the
+ * error-specific data pointer and flags. The flags are a bitwise-OR of
+ * |ERR_FLAG_*| values. The error-specific data is owned by the error queue
+ * and the pointer becomes invalid after the next call that affects the same
+ * thread's error queue. If |*flags| contains |ERR_FLAG_STRING| then |*data| is
+ * human-readable. */
+OPENSSL_EXPORT uint32_t ERR_get_error_line_data(const char **file, int *line,
+                                                const char **data, int *flags);
+
+/* The "peek" functions act like the |ERR_get_error| functions, above, but they
+ * do not remove the error from the queue. */
+OPENSSL_EXPORT uint32_t ERR_peek_error(void);
+OPENSSL_EXPORT uint32_t ERR_peek_error_line(const char **file, int *line);
+OPENSSL_EXPORT uint32_t ERR_peek_error_line_data(const char **file, int *line,
+                                                 const char **data, int *flags);
+
+/* The "peek last" functions act like the "peek" functions, above, except that
+ * they return the most recent error. */
+OPENSSL_EXPORT uint32_t ERR_peek_last_error(void);
+OPENSSL_EXPORT uint32_t ERR_peek_last_error_line(const char **file, int *line);
+OPENSSL_EXPORT uint32_t ERR_peek_last_error_line_data(const char **file,
+                                                      int *line,
+                                                      const char **data,
+                                                      int *flags);
+
+/* ERR_error_string generates a human-readable string representing
+ * |packed_error|, places it at |buf| (which must be at least
+ * ERR_ERROR_STRING_BUF_LEN bytes long) and returns |buf|. If |buf| is NULL,
+ * the error string is placed in a static buffer which is returned. (The static
+ * buffer may be overridden by concurrent calls in other threads so this form
+ * is deprecated.)
+ *
+ * The string will have the following format:
+ *
+ *   error:[error code]:[library name]:OPENSSL_internal:[reason string]
+ *
+ * error code is an 8 digit hexadecimal number; library name and reason string
+ * are ASCII text.
+ *
+ * TODO(fork): remove in favour of |ERR_error_string_n|. */
+OPENSSL_EXPORT char *ERR_error_string(uint32_t packed_error, char *buf);
+#define ERR_ERROR_STRING_BUF_LEN 256
+
+/* ERR_error_string_n is a variant of |ERR_error_string| that writes at most
+ * len characters (including the terminating NUL) and truncates the string if
+ * necessary. If |len| is greater than zero then |buf| is always NUL
+ * terminated. */
+OPENSSL_EXPORT void ERR_error_string_n(uint32_t packed_error, char *buf,
+                                       size_t len);
+
+/* ERR_lib_error_string returns a string representation of the library that
+ * generated |packed_error|. */
+OPENSSL_EXPORT const char *ERR_lib_error_string(uint32_t packed_error);
+
+/* ERR_reason_error_string returns a string representation of the reason for
+ * |packed_error|. */
+OPENSSL_EXPORT const char *ERR_reason_error_string(uint32_t packed_error);
+
+/* ERR_print_errors_callback_t is the type of a function used by
+ * |ERR_print_errors_cb|. It takes a pointer to a human readable string (and
+ * its length) that describes an entry in the error queue. The |ctx| argument
+ * is an opaque pointer given to |ERR_print_errors_cb|.
+ *
+ * It should return one on success or zero on error, which will stop the
+ * iteration over the error queue. */
+typedef int (*ERR_print_errors_callback_t)(const char *str, size_t len,
+                                           void *ctx);
+
+/* ERR_print_errors_cb calls |callback| with a string representation of each
+ * error in the current thread's error queue, from the least recent to the most
+ * recent error.
+ *
+ * The string will have the following format (which differs from
+ * |ERR_error_string|):
+ *
+ *   [thread id]:error:[error code]:[library name]:OPENSSL_internal:
+ *   [reason string]:[file]:[line number]:[optional string data]
+ *
+ * (All in one line.)
+ *
+ * The callback can return one to continue the iteration or zero to stop it.
+ * The |ctx| argument is an opaque value that is passed through to the
+ * callback. */
+OPENSSL_EXPORT void ERR_print_errors_cb(ERR_print_errors_callback_t callback,
+                                        void *ctx);
+
+/* ERR_print_errors_fp prints the current contents of the error stack to |file|
+ * using human readable strings where possible. */
+OPENSSL_EXPORT void ERR_print_errors_fp(FILE *file);
+
+
+/* Clearing errors. */
+
+/* ERR_clear_error clears the error queue for the current thread. */
+OPENSSL_EXPORT void ERR_clear_error(void);
+
+/* ERR_remove_thread_state clears the error queue for the current thread if
+ * |tid| is NULL. Otherwise it calls |assert(0)|, because it's no longer
+ * possible to delete the error queue for other threads.
+ *
+ * Error queues are thread-local data and are deleted automatically. You do not
+ * need to call this function. Use |ERR_clear_error|. */
+OPENSSL_EXPORT void ERR_remove_thread_state(const CRYPTO_THREADID *tid);
+
+
+/* Custom errors. */
+
+/* ERR_get_next_error_library returns a value suitable for passing as the
+ * |library| argument to |ERR_put_error|. This is intended for code that wishes
+ * to push its own, non-standard errors to the error queue. */
+OPENSSL_EXPORT int ERR_get_next_error_library(void);
+
+
+/* Deprecated functions. */
+
+/* ERR_remove_state calls |ERR_clear_error|. */
+OPENSSL_EXPORT void ERR_remove_state(unsigned long pid);
+
+/* ERR_func_error_string returns the string "OPENSSL_internal". */
+OPENSSL_EXPORT const char *ERR_func_error_string(uint32_t packed_error);
+
+
+/* Private functions. */
+
+/* ERR_clear_system_error clears the system's error value (i.e. errno). */
+OPENSSL_EXPORT void ERR_clear_system_error(void);
+
+/* OPENSSL_PUT_ERROR is used by OpenSSL code to add an error to the error
+ * queue. */
+#define OPENSSL_PUT_ERROR(library, reason) \
+  ERR_put_error(ERR_LIB_##library, 0, reason, __FILE__, __LINE__)
+
+/* OPENSSL_PUT_SYSTEM_ERROR is used by OpenSSL code to add an error from the
+ * operating system to the error queue.
+ * TODO(fork): include errno. */
+#define OPENSSL_PUT_SYSTEM_ERROR() \
+  ERR_put_error(ERR_LIB_SYS, 0, 0, __FILE__, __LINE__);
+
+/* ERR_put_error adds an error to the error queue, dropping the least recent
+ * error if neccessary for space reasons. */
+OPENSSL_EXPORT void ERR_put_error(int library, int unused, int reason,
+                                  const char *file, unsigned line);
+
+/* ERR_add_error_data takes a variable number (|count|) of const char*
+ * pointers, concatenates them and sets the result as the data on the most
+ * recent error. */
+OPENSSL_EXPORT void ERR_add_error_data(unsigned count, ...);
+
+/* ERR_add_error_dataf takes a printf-style format and arguments, and sets the
+ * result as the data on the most recent error. */
+OPENSSL_EXPORT void ERR_add_error_dataf(const char *format, ...);
+
+/* ERR_set_mark "marks" the most recent error for use with |ERR_pop_to_mark|.
+ * It returns one if an error was marked and zero if there are no errors. */
+OPENSSL_EXPORT int ERR_set_mark(void);
+
+/* ERR_pop_to_mark removes errors from the most recent to the least recent
+ * until (and not including) a "marked" error. It returns zero if no marked
+ * error was found (and thus all errors were removed) and one otherwise. Errors
+ * are marked using |ERR_set_mark|. */
+OPENSSL_EXPORT int ERR_pop_to_mark(void);
+
+struct err_error_st {
+  /* file contains the filename where the error occured. */
+  const char *file;
+  /* data contains optional data. It must be freed with |OPENSSL_free| if
+   * |flags&ERR_FLAG_MALLOCED|. */
+  char *data;
+  /* packed contains the error library and reason, as packed by ERR_PACK. */
+  uint32_t packed;
+  /* line contains the line number where the error occured. */
+  uint16_t line;
+  /* flags contains a bitwise-OR of ERR_FLAG_* values. */
+  uint8_t flags;
+};
+
+/* ERR_FLAG_STRING means that the |data| member is a NUL-terminated string that
+ * can be printed. */
+#define ERR_FLAG_STRING 1
+/* ERR_TXT_STRING is provided for compatibility with code that assumes that
+ * it's using OpenSSL. */
+#define ERR_TXT_STRING ERR_FLAG_STRING
+
+/* ERR_FLAG_PUBLIC_MASK is applied to the flags field before it is returned
+ * from functions like |ERR_get_error_line_data|. */
+#define ERR_FLAG_PUBLIC_MASK 0xf
+
+/* The following flag values are internal and are masked when flags are
+ * returned from functions like |ERR_get_error_line_data|. */
+
+/* ERR_FLAG_MALLOCED means the the |data| member must be freed when no longer
+ * needed. */
+#define ERR_FLAG_MALLOCED 16
+/* ERR_FLAG_MARK is used to indicate a reversion point in the queue. See
+ * |ERR_pop_to_mark|. */
+#define ERR_FLAG_MARK 32
+
+/* ERR_NUM_ERRORS is the limit of the number of errors in the queue. */
+#define ERR_NUM_ERRORS 16
+
+/* ERR_STATE contains the per-thread, error queue. */
+typedef struct err_state_st {
+  /* errors contains the ERR_NUM_ERRORS most recent errors, organised as a ring
+   * buffer. */
+  struct err_error_st errors[ERR_NUM_ERRORS];
+  /* top contains the index one past the most recent error. If |top| equals
+   * |bottom| then the queue is empty. */
+  unsigned top;
+  /* bottom contains the index of the last error in the queue. */
+  unsigned bottom;
+
+  /* to_free, if not NULL, contains a pointer owned by this structure that was
+   * previously a |data| pointer of one of the elements of |errors|. */
+  void *to_free;
+} ERR_STATE;
+
+enum {
+  ERR_LIB_NONE = 1,
+  ERR_LIB_SYS,
+  ERR_LIB_BN,
+  ERR_LIB_RSA,
+  ERR_LIB_DH,
+  ERR_LIB_EVP,
+  ERR_LIB_BUF,
+  ERR_LIB_OBJ,
+  ERR_LIB_PEM,
+  ERR_LIB_DSA,
+  ERR_LIB_X509,
+  ERR_LIB_ASN1,
+  ERR_LIB_CONF,
+  ERR_LIB_CRYPTO,
+  ERR_LIB_EC,
+  ERR_LIB_SSL,
+  ERR_LIB_BIO,
+  ERR_LIB_PKCS7,
+  ERR_LIB_PKCS8,
+  ERR_LIB_X509V3,
+  ERR_LIB_RAND,
+  ERR_LIB_ENGINE,
+  ERR_LIB_OCSP,
+  ERR_LIB_UI,
+  ERR_LIB_COMP,
+  ERR_LIB_ECDSA,
+  ERR_LIB_ECDH,
+  ERR_LIB_HMAC,
+  ERR_LIB_DIGEST,
+  ERR_LIB_CIPHER,
+  ERR_LIB_HKDF,
+  ERR_LIB_USER,
+  ERR_NUM_LIBS
+};
+
+#define ERR_R_SYS_LIB ERR_LIB_SYS
+#define ERR_R_BN_LIB ERR_LIB_BN
+#define ERR_R_RSA_LIB ERR_LIB_RSA
+#define ERR_R_DH_LIB ERR_LIB_DH
+#define ERR_R_EVP_LIB ERR_LIB_EVP
+#define ERR_R_BUF_LIB ERR_LIB_BUF
+#define ERR_R_OBJ_LIB ERR_LIB_OBJ
+#define ERR_R_PEM_LIB ERR_LIB_PEM
+#define ERR_R_DSA_LIB ERR_LIB_DSA
+#define ERR_R_X509_LIB ERR_LIB_X509
+#define ERR_R_ASN1_LIB ERR_LIB_ASN1
+#define ERR_R_CONF_LIB ERR_LIB_CONF
+#define ERR_R_CRYPTO_LIB ERR_LIB_CRYPTO
+#define ERR_R_EC_LIB ERR_LIB_EC
+#define ERR_R_SSL_LIB ERR_LIB_SSL
+#define ERR_R_BIO_LIB ERR_LIB_BIO
+#define ERR_R_PKCS7_LIB ERR_LIB_PKCS7
+#define ERR_R_PKCS8_LIB ERR_LIB_PKCS8
+#define ERR_R_X509V3_LIB ERR_LIB_X509V3
+#define ERR_R_RAND_LIB ERR_LIB_RAND
+#define ERR_R_DSO_LIB ERR_LIB_DSO
+#define ERR_R_ENGINE_LIB ERR_LIB_ENGINE
+#define ERR_R_OCSP_LIB ERR_LIB_OCSP
+#define ERR_R_UI_LIB ERR_LIB_UI
+#define ERR_R_COMP_LIB ERR_LIB_COMP
+#define ERR_R_ECDSA_LIB ERR_LIB_ECDSA
+#define ERR_R_ECDH_LIB ERR_LIB_ECDH
+#define ERR_R_STORE_LIB ERR_LIB_STORE
+#define ERR_R_FIPS_LIB ERR_LIB_FIPS
+#define ERR_R_CMS_LIB ERR_LIB_CMS
+#define ERR_R_TS_LIB ERR_LIB_TS
+#define ERR_R_HMAC_LIB ERR_LIB_HMAC
+#define ERR_R_JPAKE_LIB ERR_LIB_JPAKE
+#define ERR_R_USER_LIB ERR_LIB_USER
+#define ERR_R_DIGEST_LIB ERR_LIB_DIGEST
+#define ERR_R_CIPHER_LIB ERR_LIB_CIPHER
+#define ERR_R_HKDF_LIB ERR_LIB_HKDF
+
+/* Global reasons. */
+#define ERR_R_FATAL 64
+#define ERR_R_MALLOC_FAILURE (1 | ERR_R_FATAL)
+#define ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED (2 | ERR_R_FATAL)
+#define ERR_R_PASSED_NULL_PARAMETER (3 | ERR_R_FATAL)
+#define ERR_R_INTERNAL_ERROR (4 | ERR_R_FATAL)
+#define ERR_R_OVERFLOW (5 | ERR_R_FATAL)
+
+#define ERR_PACK(lib, reason)                                              \
+  (((((uint32_t)lib) & 0xff) << 24) | ((((uint32_t)reason) & 0xfff)))
+
+#define ERR_GET_LIB(packed_error) ((int)(((packed_error) >> 24) & 0xff))
+#define ERR_GET_FUNC(packed_error) 0
+#define ERR_GET_REASON(packed_error) ((int)((packed_error) & 0xfff))
+
+/* OPENSSL_DECLARE_ERROR_REASON is used by util/make_errors.h (which generates
+ * the error defines) to recognise that an additional reason value is needed.
+ * This is needed when the reason value is used outside of an
+ * |OPENSSL_PUT_ERROR| macro. The resulting define will be
+ * ${lib}_R_${reason}. */
+#define OPENSSL_DECLARE_ERROR_REASON(lib, reason)
+
+
+#if defined(__cplusplus)
+} /* extern C */
+#endif
+
+#endif /* OPENSSL_HEADER_ERR_H */

+ 750 - 0
app/src/main/jni/openssl/include/openssl/evp.h

@@ -0,0 +1,750 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_EVP_H
+#define OPENSSL_HEADER_EVP_H
+
+#include <openssl/base.h>
+
+#include <openssl/thread.h>
+
+/* OpenSSL included digest and cipher functions in this header so we include
+ * them for users that still expect that.
+ *
+ * TODO(fork): clean up callers so that they include what they use. */
+#include <openssl/aead.h>
+#include <openssl/base64.h>
+#include <openssl/cipher.h>
+#include <openssl/digest.h>
+#include <openssl/obj.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* EVP abstracts over public/private key algorithms. */
+
+
+/* Public key objects. */
+
+/* EVP_PKEY_new creates a new, empty public-key object and returns it or NULL
+ * on allocation failure. */
+OPENSSL_EXPORT EVP_PKEY *EVP_PKEY_new(void);
+
+/* EVP_PKEY_free frees all data referenced by |pkey| and then frees |pkey|
+ * itself. */
+OPENSSL_EXPORT void EVP_PKEY_free(EVP_PKEY *pkey);
+
+/* EVP_PKEY_up_ref increments the reference count of |pkey| and returns it. */
+OPENSSL_EXPORT EVP_PKEY *EVP_PKEY_up_ref(EVP_PKEY *pkey);
+
+/* EVP_PKEY_is_opaque returns one if |pkey| is opaque. Opaque keys are backed by
+ * custom implementations which do not expose key material and parameters. It is
+ * an error to attempt to duplicate, export, or compare an opaque key. */
+OPENSSL_EXPORT int EVP_PKEY_is_opaque(const EVP_PKEY *pkey);
+
+/* EVP_PKEY_supports_digest returns one if |pkey| supports digests of
+ * type |md|. This is intended for use with EVP_PKEYs backing custom
+ * implementations which can't sign all digests. */
+OPENSSL_EXPORT int EVP_PKEY_supports_digest(const EVP_PKEY *pkey,
+                                            const EVP_MD *md);
+
+/* EVP_PKEY_cmp compares |a| and |b| and returns one if they are equal, zero if
+ * not and a negative number on error.
+ *
+ * WARNING: this differs from the traditional return value of a "cmp"
+ * function. */
+OPENSSL_EXPORT int EVP_PKEY_cmp(const EVP_PKEY *a, const EVP_PKEY *b);
+
+/* EVP_PKEY_copy_parameters sets the parameters of |to| to equal the parameters
+ * of |from|. It returns one on success and zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_copy_parameters(EVP_PKEY *to, const EVP_PKEY *from);
+
+/* EVP_PKEY_missing_parameters returns one if |pkey| is missing needed
+ * parameters or zero if not, or if the algorithm doesn't take parameters. */
+OPENSSL_EXPORT int EVP_PKEY_missing_parameters(const EVP_PKEY *pkey);
+
+/* EVP_PKEY_size returns the maximum size, in bytes, of a signature signed by
+ * |pkey|. For an RSA key, this returns the number of bytes needed to represent
+ * the modulus. For an EC key, this returns the maximum size of a DER-encoded
+ * ECDSA signature. */
+OPENSSL_EXPORT int EVP_PKEY_size(const EVP_PKEY *pkey);
+
+/* EVP_PKEY_bits returns the "size", in bits, of |pkey|. For an RSA key, this
+ * returns the bit length of the modulus. For an EC key, this returns the bit
+ * length of the group order. */
+OPENSSL_EXPORT int EVP_PKEY_bits(EVP_PKEY *pkey);
+
+/* EVP_PKEY_id returns the type of |pkey|, which is one of the |EVP_PKEY_*|
+ * values. */
+OPENSSL_EXPORT int EVP_PKEY_id(const EVP_PKEY *pkey);
+
+/* EVP_PKEY_type returns a canonicalised form of |NID|. For example,
+ * |EVP_PKEY_RSA2| will be turned into |EVP_PKEY_RSA|. */
+OPENSSL_EXPORT int EVP_PKEY_type(int nid);
+
+
+/* Getting and setting concrete public key types.
+ *
+ * The following functions get and set the underlying public key in an
+ * |EVP_PKEY| object. The |set1| functions take an additional reference to the
+ * underlying key and return one on success or zero on error. The |assign|
+ * functions adopt the caller's reference. The |get1| functions return a fresh
+ * reference to the underlying object or NULL if |pkey| is not of the correct
+ * type. The |get0| functions behave the same but return a non-owning
+ * pointer. */
+
+OPENSSL_EXPORT int EVP_PKEY_set1_RSA(EVP_PKEY *pkey, RSA *key);
+OPENSSL_EXPORT int EVP_PKEY_assign_RSA(EVP_PKEY *pkey, RSA *key);
+OPENSSL_EXPORT RSA *EVP_PKEY_get0_RSA(EVP_PKEY *pkey);
+OPENSSL_EXPORT RSA *EVP_PKEY_get1_RSA(EVP_PKEY *pkey);
+
+OPENSSL_EXPORT int EVP_PKEY_set1_DSA(EVP_PKEY *pkey, DSA *key);
+OPENSSL_EXPORT int EVP_PKEY_assign_DSA(EVP_PKEY *pkey, DSA *key);
+OPENSSL_EXPORT DSA *EVP_PKEY_get0_DSA(EVP_PKEY *pkey);
+OPENSSL_EXPORT DSA *EVP_PKEY_get1_DSA(EVP_PKEY *pkey);
+
+OPENSSL_EXPORT int EVP_PKEY_set1_EC_KEY(EVP_PKEY *pkey, EC_KEY *key);
+OPENSSL_EXPORT int EVP_PKEY_assign_EC_KEY(EVP_PKEY *pkey, EC_KEY *key);
+OPENSSL_EXPORT EC_KEY *EVP_PKEY_get0_EC_KEY(EVP_PKEY *pkey);
+OPENSSL_EXPORT EC_KEY *EVP_PKEY_get1_EC_KEY(EVP_PKEY *pkey);
+
+#define EVP_PKEY_NONE NID_undef
+#define EVP_PKEY_RSA NID_rsaEncryption
+#define EVP_PKEY_RSA2 NID_rsa
+#define EVP_PKEY_DSA NID_dsa
+#define EVP_PKEY_EC NID_X9_62_id_ecPublicKey
+
+/* EVP_PKEY_assign sets the underlying key of |pkey| to |key|, which must be of
+ * the given type. The |type| argument should be one of the |EVP_PKEY_*|
+ * values. */
+OPENSSL_EXPORT int EVP_PKEY_assign(EVP_PKEY *pkey, int type, void *key);
+
+/* EVP_PKEY_set_type sets the type of |pkey| to |type|, which should be one of
+ * the |EVP_PKEY_*| values. It returns one if sucessful or zero otherwise. If
+ * |pkey| is NULL, it simply reports whether the type is known. */
+OPENSSL_EXPORT int EVP_PKEY_set_type(EVP_PKEY *pkey, int type);
+
+/* EVP_PKEY_cmp_parameters compares the parameters of |a| and |b|. It returns
+ * one if they match, zero if not, or a negative number of on error.
+ *
+ * WARNING: the return value differs from the usual return value convention. */
+OPENSSL_EXPORT int EVP_PKEY_cmp_parameters(const EVP_PKEY *a,
+                                           const EVP_PKEY *b);
+
+
+/* ASN.1 functions */
+
+/* d2i_PrivateKey parses an ASN.1, DER-encoded, private key from |len| bytes at
+ * |*inp|. If |out| is not NULL then, on exit, a pointer to the result is in
+ * |*out|. If |*out| is already non-NULL on entry then the result is written
+ * directly into |*out|, otherwise a fresh |EVP_PKEY| is allocated. On
+ * successful exit, |*inp| is advanced past the DER structure. It returns the
+ * result or NULL on error. */
+OPENSSL_EXPORT EVP_PKEY *d2i_PrivateKey(int type, EVP_PKEY **out,
+                                        const uint8_t **inp, long len);
+
+/* d2i_AutoPrivateKey acts the same as |d2i_PrivateKey|, but detects the type
+ * of the private key. */
+OPENSSL_EXPORT EVP_PKEY *d2i_AutoPrivateKey(EVP_PKEY **out, const uint8_t **inp,
+                                            long len);
+
+/* i2d_PrivateKey marshals a private key from |key| to an ASN.1, DER
+ * structure. If |outp| is not NULL then the result is written to |*outp| and
+ * |*outp| is advanced just past the output. It returns the number of bytes in
+ * the result, whether written or not, or a negative value on error. */
+OPENSSL_EXPORT int i2d_PrivateKey(const EVP_PKEY *key, uint8_t **outp);
+
+/* i2d_PublicKey marshals a public key from |key| to a type-specific format.
+ * If |outp| is not NULL then the result is written to |*outp| and
+ * |*outp| is advanced just past the output. It returns the number of bytes in
+ * the result, whether written or not, or a negative value on error.
+ *
+ * RSA keys are serialized as a DER-encoded RSAPublicKey (RFC 3447) structure.
+ * EC keys are serialized as an EC point per SEC 1. */
+OPENSSL_EXPORT int i2d_PublicKey(EVP_PKEY *key, uint8_t **outp);
+
+
+/* Signing */
+
+/* EVP_DigestSignInit sets up |ctx| for a signing operation with |type| and
+ * |pkey|. The |ctx| argument must have been initialised with
+ * |EVP_MD_CTX_init|. If |pctx| is not NULL, the |EVP_PKEY_CTX| of the signing
+ * operation will be written to |*pctx|; this can be used to set alternative
+ * signing options.
+ *
+ * It returns one on success, or zero on error. */
+OPENSSL_EXPORT int EVP_DigestSignInit(EVP_MD_CTX *ctx, EVP_PKEY_CTX **pctx,
+                                      const EVP_MD *type, ENGINE *e,
+                                      EVP_PKEY *pkey);
+
+/* EVP_DigestSignUpdate appends |len| bytes from |data| to the data which will
+ * be signed in |EVP_DigestSignFinal|. It returns one. */
+OPENSSL_EXPORT int EVP_DigestSignUpdate(EVP_MD_CTX *ctx, const void *data,
+                                        size_t len);
+
+/* EVP_DigestSignFinal signs the data that has been included by one or more
+ * calls to |EVP_DigestSignUpdate|. If |out_sig| is NULL then |*out_sig_len| is
+ * set to the maximum number of output bytes. Otherwise, on entry,
+ * |*out_sig_len| must contain the length of the |out_sig| buffer. If the call
+ * is successful, the signature is written to |out_sig| and |*out_sig_len| is
+ * set to its length.
+ *
+ * It returns one on success, or zero on error. */
+OPENSSL_EXPORT int EVP_DigestSignFinal(EVP_MD_CTX *ctx, uint8_t *out_sig,
+                                       size_t *out_sig_len);
+
+/* EVP_DigestSignAlgorithm encodes the signing parameters of |ctx| as an
+ * AlgorithmIdentifer and saves the result in |algor|.
+ *
+ * It returns one on success, or zero on error.
+ *
+ * TODO(davidben): This API should eventually lose the dependency on
+ * crypto/asn1/. */
+OPENSSL_EXPORT int EVP_DigestSignAlgorithm(EVP_MD_CTX *ctx, X509_ALGOR *algor);
+
+
+/* Verifying */
+
+/* EVP_DigestVerifyInit sets up |ctx| for a signature verification operation
+ * with |type| and |pkey|. The |ctx| argument must have been initialised with
+ * |EVP_MD_CTX_init|. If |pctx| is not NULL, the |EVP_PKEY_CTX| of the signing
+ * operation will be written to |*pctx|; this can be used to set alternative
+ * signing options.
+ *
+ * It returns one on success, or zero on error. */
+OPENSSL_EXPORT int EVP_DigestVerifyInit(EVP_MD_CTX *ctx, EVP_PKEY_CTX **pctx,
+                                        const EVP_MD *type, ENGINE *e,
+                                        EVP_PKEY *pkey);
+
+/* EVP_DigestVerifyInitFromAlgorithm sets up |ctx| for a signature verification
+ * operation with public key |pkey| and parameters from |algor|. The |ctx|
+ * argument must have been initialised with |EVP_MD_CTX_init|.
+ *
+ * It returns one on success, or zero on error.
+ *
+ * TODO(davidben): This API should eventually lose the dependency on
+ * crypto/asn1/. */
+OPENSSL_EXPORT int EVP_DigestVerifyInitFromAlgorithm(EVP_MD_CTX *ctx,
+                                                     X509_ALGOR *algor,
+                                                     EVP_PKEY *pkey);
+
+/* EVP_DigestVerifyUpdate appends |len| bytes from |data| to the data which
+ * will be verified by |EVP_DigestVerifyFinal|. It returns one. */
+OPENSSL_EXPORT int EVP_DigestVerifyUpdate(EVP_MD_CTX *ctx, const void *data,
+                                          size_t len);
+
+/* EVP_DigestVerifyFinal verifies that |sig_len| bytes of |sig| are a valid
+ * signature for the data that has been included by one or more calls to
+ * |EVP_DigestVerifyUpdate|. It returns one on success and zero otherwise. */
+OPENSSL_EXPORT int EVP_DigestVerifyFinal(EVP_MD_CTX *ctx, const uint8_t *sig,
+                                         size_t sig_len);
+
+
+/* Signing (old functions) */
+
+/* EVP_SignInit_ex configures |ctx|, which must already have been initialised,
+ * for a fresh signing operation using the hash function |type|. It returns one
+ * on success and zero otherwise.
+ *
+ * (In order to initialise |ctx|, either obtain it initialised with
+ * |EVP_MD_CTX_create|, or use |EVP_MD_CTX_init|.) */
+OPENSSL_EXPORT int EVP_SignInit_ex(EVP_MD_CTX *ctx, const EVP_MD *type,
+                                   ENGINE *impl);
+
+/* EVP_SignInit is a deprecated version of |EVP_SignInit_ex|.
+ *
+ * TODO(fork): remove. */
+OPENSSL_EXPORT int EVP_SignInit(EVP_MD_CTX *ctx, const EVP_MD *type);
+
+/* EVP_SignUpdate appends |len| bytes from |data| to the data which will be
+ * signed in |EVP_SignFinal|. */
+OPENSSL_EXPORT int EVP_SignUpdate(EVP_MD_CTX *ctx, const void *data,
+                                  size_t len);
+
+/* EVP_SignFinal signs the data that has been included by one or more calls to
+ * |EVP_SignUpdate|, using the key |pkey|, and writes it to |sig|. On entry,
+ * |sig| must point to at least |EVP_PKEY_size(pkey)| bytes of space. The
+ * actual size of the signature is written to |*out_sig_len|.
+ *
+ * It returns one on success and zero otherwise.
+ *
+ * It does not modify |ctx|, thus it's possible to continue to use |ctx| in
+ * order to sign a longer message. */
+OPENSSL_EXPORT int EVP_SignFinal(const EVP_MD_CTX *ctx, uint8_t *sig,
+                                 unsigned int *out_sig_len, EVP_PKEY *pkey);
+
+
+/* Verifying (old functions) */
+
+/* EVP_VerifyInit_ex configures |ctx|, which must already have been
+ * initialised, for a fresh signature verification operation using the hash
+ * function |type|. It returns one on success and zero otherwise.
+ *
+ * (In order to initialise |ctx|, either obtain it initialised with
+ * |EVP_MD_CTX_create|, or use |EVP_MD_CTX_init|.) */
+OPENSSL_EXPORT int EVP_VerifyInit_ex(EVP_MD_CTX *ctx, const EVP_MD *type,
+                                     ENGINE *impl);
+
+/* EVP_VerifyInit is a deprecated version of |EVP_VerifyInit_ex|.
+ *
+ * TODO(fork): remove. */
+OPENSSL_EXPORT int EVP_VerifyInit(EVP_MD_CTX *ctx, const EVP_MD *type);
+
+/* EVP_VerifyUpdate appends |len| bytes from |data| to the data which will be
+ * signed in |EVP_VerifyFinal|. */
+OPENSSL_EXPORT int EVP_VerifyUpdate(EVP_MD_CTX *ctx, const void *data,
+                                    size_t len);
+
+/* EVP_VerifyFinal verifies that |sig_len| bytes of |sig| are a valid
+ * signature, by |pkey|, for the data that has been included by one or more
+ * calls to |EVP_VerifyUpdate|.
+ *
+ * It returns one on success and zero otherwise.
+ *
+ * It does not modify |ctx|, thus it's possible to continue to use |ctx| in
+ * order to sign a longer message. */
+OPENSSL_EXPORT int EVP_VerifyFinal(EVP_MD_CTX *ctx, const uint8_t *sig,
+                                   size_t sig_len, EVP_PKEY *pkey);
+
+
+/* Printing */
+
+/* EVP_PKEY_print_public prints a textual representation of the public key in
+ * |pkey| to |out|. Returns one on success or zero otherwise. */
+OPENSSL_EXPORT int EVP_PKEY_print_public(BIO *out, const EVP_PKEY *pkey,
+                                         int indent, ASN1_PCTX *pctx);
+
+/* EVP_PKEY_print_private prints a textual representation of the private key in
+ * |pkey| to |out|. Returns one on success or zero otherwise. */
+OPENSSL_EXPORT int EVP_PKEY_print_private(BIO *out, const EVP_PKEY *pkey,
+                                          int indent, ASN1_PCTX *pctx);
+
+/* EVP_PKEY_print_params prints a textual representation of the parameters in
+ * |pkey| to |out|. Returns one on success or zero otherwise. */
+OPENSSL_EXPORT int EVP_PKEY_print_params(BIO *out, const EVP_PKEY *pkey,
+                                         int indent, ASN1_PCTX *pctx);
+
+
+/* Password stretching.
+ *
+ * Password stretching functions take a low-entropy password and apply a slow
+ * function that results in a key suitable for use in symmetric
+ * cryptography. */
+
+/* PKCS5_PBKDF2_HMAC computes |iterations| iterations of PBKDF2 of |password|
+ * and |salt|, using |digest|, and outputs |key_len| bytes to |out_key|. It
+ * returns one on success and zero on error. */
+OPENSSL_EXPORT int PKCS5_PBKDF2_HMAC(const char *password, size_t password_len,
+                                     const uint8_t *salt, size_t salt_len,
+                                     unsigned iterations, const EVP_MD *digest,
+                                     size_t key_len, uint8_t *out_key);
+
+/* PKCS5_PBKDF2_HMAC_SHA1 is the same as PKCS5_PBKDF2_HMAC, but with |digest|
+ * fixed to |EVP_sha1|. */
+OPENSSL_EXPORT int PKCS5_PBKDF2_HMAC_SHA1(const char *password,
+                                          size_t password_len, const uint8_t *salt,
+                                          size_t salt_len, unsigned iterations,
+                                          size_t key_len, uint8_t *out_key);
+
+
+/* Public key contexts.
+ *
+ * |EVP_PKEY_CTX| objects hold the context of an operation (e.g. signing or
+ * encrypting) that uses a public key. */
+
+/* EVP_PKEY_CTX_new allocates a fresh |EVP_PKEY_CTX| for use with |pkey|. It
+ * returns the context or NULL on error. */
+OPENSSL_EXPORT EVP_PKEY_CTX *EVP_PKEY_CTX_new(EVP_PKEY *pkey, ENGINE *e);
+
+/* EVP_PKEY_CTX_new_id allocates a fresh |EVP_PKEY_CTX| for a key of type |id|
+ * (e.g. |EVP_PKEY_HMAC|). This can be used for key generation where
+ * |EVP_PKEY_CTX_new| can't be used because there isn't an |EVP_PKEY| to pass
+ * it. It returns the context or NULL on error. */
+OPENSSL_EXPORT EVP_PKEY_CTX *EVP_PKEY_CTX_new_id(int id, ENGINE *e);
+
+/* EVP_PKEY_CTX_free frees |ctx| and the data it owns. */
+OPENSSL_EXPORT void EVP_PKEY_CTX_free(EVP_PKEY_CTX *ctx);
+
+/* EVP_PKEY_CTX_dup allocates a fresh |EVP_PKEY_CTX| and sets it equal to the
+ * state of |ctx|. It returns the fresh |EVP_PKEY_CTX| or NULL on error. */
+OPENSSL_EXPORT EVP_PKEY_CTX *EVP_PKEY_CTX_dup(EVP_PKEY_CTX *ctx);
+
+/* EVP_PKEY_CTX_get0_pkey returns the |EVP_PKEY| associated with |ctx|. */
+OPENSSL_EXPORT EVP_PKEY *EVP_PKEY_CTX_get0_pkey(EVP_PKEY_CTX *ctx);
+
+/* EVP_PKEY_CTX_set_app_data sets an opaque pointer on |ctx|. */
+OPENSSL_EXPORT void EVP_PKEY_CTX_set_app_data(EVP_PKEY_CTX *ctx, void *data);
+
+/* EVP_PKEY_CTX_get_app_data returns the opaque pointer from |ctx| that was
+ * previously set with |EVP_PKEY_CTX_set_app_data|, or NULL if none has been
+ * set. */
+OPENSSL_EXPORT void *EVP_PKEY_CTX_get_app_data(EVP_PKEY_CTX *ctx);
+
+/* EVP_PKEY_sign_init initialises an |EVP_PKEY_CTX| for a signing operation. It
+ * should be called before |EVP_PKEY_sign|.
+ *
+ * It returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_sign_init(EVP_PKEY_CTX *ctx);
+
+/* EVP_PKEY_sign signs |data_len| bytes from |data| using |ctx|. If |sig| is
+ * NULL, the maximum size of the signature is written to
+ * |out_sig_len|. Otherwise, |*sig_len| must contain the number of bytes of
+ * space available at |sig|. If sufficient, the signature will be written to
+ * |sig| and |*sig_len| updated with the true length.
+ *
+ * WARNING: Setting |sig| to NULL only gives the maximum size of the
+ * signature. The actual signature may be smaller.
+ *
+ * It returns one on success or zero on error. (Note: this differs from
+ * OpenSSL, which can also return negative values to indicate an error. ) */
+OPENSSL_EXPORT int EVP_PKEY_sign(EVP_PKEY_CTX *ctx, uint8_t *sig,
+                                 size_t *sig_len, const uint8_t *data,
+                                 size_t data_len);
+
+/* EVP_PKEY_verify_init initialises an |EVP_PKEY_CTX| for a signature
+ * verification operation. It should be called before |EVP_PKEY_verify|.
+ *
+ * It returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_verify_init(EVP_PKEY_CTX *ctx);
+
+/* EVP_PKEY_verify verifies that |sig_len| bytes from |sig| are a valid signature
+ * for |data|.
+ *
+ * It returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_verify(EVP_PKEY_CTX *ctx, const uint8_t *sig,
+                                   size_t sig_len, const uint8_t *data,
+                                   size_t data_len);
+
+/* EVP_PKEY_encrypt_init initialises an |EVP_PKEY_CTX| for an encryption
+ * operation. It should be called before |EVP_PKEY_encrypt|.
+ *
+ * It returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_encrypt_init(EVP_PKEY_CTX *ctx);
+
+/* EVP_PKEY_encrypt encrypts |in_len| bytes from |in|. If |out| is NULL, the
+ * maximum size of the ciphertext is written to |out_len|. Otherwise, |*out_len|
+ * must contain the number of bytes of space available at |out|. If sufficient,
+ * the ciphertext will be written to |out| and |*out_len| updated with the true
+ * length.
+ *
+ * WARNING: Setting |out| to NULL only gives the maximum size of the
+ * ciphertext. The actual ciphertext may be smaller.
+ *
+ * It returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_encrypt(EVP_PKEY_CTX *ctx, uint8_t *out,
+                                    size_t *out_len, const uint8_t *in,
+                                    size_t in_len);
+
+/* EVP_PKEY_decrypt_init initialises an |EVP_PKEY_CTX| for a decryption
+ * operation. It should be called before |EVP_PKEY_decrypt|.
+ *
+ * It returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_decrypt_init(EVP_PKEY_CTX *ctx);
+
+/* EVP_PKEY_decrypt decrypts |in_len| bytes from |in|. If |out| is NULL, the
+ * maximum size of the plaintext is written to |out_len|. Otherwise, |*out_len|
+ * must contain the number of bytes of space available at |out|. If sufficient,
+ * the ciphertext will be written to |out| and |*out_len| updated with the true
+ * length.
+ *
+ * WARNING: Setting |out| to NULL only gives the maximum size of the
+ * plaintext. The actual plaintext may be smaller.
+ *
+ * It returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_decrypt(EVP_PKEY_CTX *ctx, uint8_t *out,
+                                    size_t *out_len, const uint8_t *in,
+                                    size_t in_len);
+
+/* EVP_PKEY_derive_init initialises an |EVP_PKEY_CTX| for a key derivation
+ * operation. It should be called before |EVP_PKEY_derive_set_peer| and
+ * |EVP_PKEY_derive|.
+ *
+ * It returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_derive_init(EVP_PKEY_CTX *ctx);
+
+/* EVP_PKEY_derive_set_peer sets the peer's key to be used for key derivation
+ * by |ctx| to |peer|. It should be called after |EVP_PKEY_derive_init|. (For
+ * example, this is used to set the peer's key in (EC)DH.) It returns one on
+ * success and zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_derive_set_peer(EVP_PKEY_CTX *ctx, EVP_PKEY *peer);
+
+/* EVP_PKEY_derive derives a shared key between the two keys configured in
+ * |ctx|. If |key| is non-NULL then, on entry, |out_key_len| must contain the
+ * amount of space at |key|. If sufficient then the shared key will be written
+ * to |key| and |*out_key_len| will be set to the length. If |key| is NULL then
+ * |out_key_len| will be set to the maximum length.
+ *
+ * WARNING: Setting |out| to NULL only gives the maximum size of the key. The
+ * actual key may be smaller.
+ *
+ * It returns one on success and zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_derive(EVP_PKEY_CTX *ctx, uint8_t *key,
+                                   size_t *out_key_len);
+
+/* EVP_PKEY_keygen_init initialises an |EVP_PKEY_CTX| for a key generation
+ * operation. It should be called before |EVP_PKEY_keygen|.
+ *
+ * It returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_keygen_init(EVP_PKEY_CTX *ctx);
+
+/* EVP_PKEY_keygen performs a key generation operation using the values from
+ * |ctx| and sets |*ppkey| to a fresh |EVP_PKEY| containing the resulting key.
+ * It returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_keygen(EVP_PKEY_CTX *ctx, EVP_PKEY **ppkey);
+
+
+/* Generic control functions. */
+
+/* EVP_PKEY_CTX_set_signature_md sets |md| as the digest to be used in a
+ * signature operation. It returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_CTX_set_signature_md(EVP_PKEY_CTX *ctx,
+                                                 const EVP_MD *md);
+
+/* EVP_PKEY_CTX_get_signature_md sets |*out_md| to the digest to be used in a
+ * signature operation. It returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_CTX_get_signature_md(EVP_PKEY_CTX *ctx,
+                                                 const EVP_MD **out_md);
+
+
+/* RSA specific control functions. */
+
+/* EVP_PKEY_CTX_set_rsa_padding sets the padding type to use. It should be one
+ * of the |RSA_*_PADDING| values. Returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_CTX_set_rsa_padding(EVP_PKEY_CTX *ctx, int padding);
+
+/* EVP_PKEY_CTX_get_rsa_padding sets |*out_padding| to the current padding
+ * value, which is one of the |RSA_*_PADDING| values. Returns one on success or
+ * zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_CTX_get_rsa_padding(EVP_PKEY_CTX *ctx,
+                                                int *out_padding);
+
+/* EVP_PKEY_CTX_set_rsa_pss_saltlen sets the length of the salt in a PSS-padded
+ * signature. A value of -1 cause the salt to be the same length as the digest
+ * in the signature. A value of -2 causes the salt to be the maximum length
+ * that will fit. Otherwise the value gives the size of the salt in bytes.
+ *
+ * Returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_CTX_set_rsa_pss_saltlen(EVP_PKEY_CTX *ctx,
+                                                    int salt_len);
+
+/* EVP_PKEY_CTX_get_rsa_pss_saltlen sets |*out_salt_len| to the salt length of
+ * a PSS-padded signature. See the documentation for
+ * |EVP_PKEY_CTX_set_rsa_pss_saltlen| for details of the special values that it
+ * can take.
+ *
+ * Returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_CTX_get_rsa_pss_saltlen(EVP_PKEY_CTX *ctx,
+                                                    int *out_salt_len);
+
+/* EVP_PKEY_CTX_set_rsa_keygen_bits sets the size of the desired RSA modulus,
+ * in bits, for key generation. Returns one on success or zero on
+ * error. */
+OPENSSL_EXPORT int EVP_PKEY_CTX_set_rsa_keygen_bits(EVP_PKEY_CTX *ctx,
+                                                    int bits);
+
+/* EVP_PKEY_CTX_set_rsa_keygen_pubexp sets |e| as the public exponent for key
+ * generation. Returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_CTX_set_rsa_keygen_pubexp(EVP_PKEY_CTX *ctx,
+                                                      BIGNUM *e);
+
+/* EVP_PKEY_CTX_set_rsa_oaep_md sets |md| as the digest used in OAEP padding.
+ * Returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_CTX_set_rsa_oaep_md(EVP_PKEY_CTX *ctx,
+                                                const EVP_MD *md);
+
+/* EVP_PKEY_CTX_get_rsa_oaep_md sets |*out_md| to the digest function used in
+ * OAEP padding. Returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_CTX_get_rsa_oaep_md(EVP_PKEY_CTX *ctx,
+                                                const EVP_MD **out_md);
+
+/* EVP_PKEY_CTX_set_rsa_mgf1_md sets |md| as the digest used in MGF1. Returns
+ * one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_CTX_set_rsa_mgf1_md(EVP_PKEY_CTX *ctx,
+                                                const EVP_MD *md);
+
+/* EVP_PKEY_CTX_get_rsa_mgf1_md sets |*out_md| to the digest function used in
+ * MGF1. Returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_CTX_get_rsa_mgf1_md(EVP_PKEY_CTX *ctx,
+                                                const EVP_MD **out_md);
+
+/* EVP_PKEY_CTX_set0_rsa_oaep_label sets |label_len| bytes from |label| as the
+ * label used in OAEP. DANGER: On success, this call takes ownership of |label|
+ * and will call |OPENSSL_free| on it when |ctx| is destroyed.
+ *
+ * Returns one on success or zero on error. */
+OPENSSL_EXPORT int EVP_PKEY_CTX_set0_rsa_oaep_label(EVP_PKEY_CTX *ctx,
+                                                    const uint8_t *label,
+                                                    size_t label_len);
+
+/* EVP_PKEY_CTX_get0_rsa_oaep_label sets |*out_label| to point to the internal
+ * buffer containing the OAEP label (which may be NULL) and returns the length
+ * of the label or a negative value on error.
+ *
+ * WARNING: the return value differs from the usual return value convention. */
+OPENSSL_EXPORT int EVP_PKEY_CTX_get0_rsa_oaep_label(EVP_PKEY_CTX *ctx,
+                                                    const uint8_t **out_label);
+
+
+/* Deprecated functions. */
+
+/* EVP_PKEY_DH is defined for compatibility, but it is impossible to create an
+ * |EVP_PKEY| of that type. */
+#define EVP_PKEY_DH NID_dhKeyAgreement
+
+/* OpenSSL_add_all_algorithms does nothing. */
+OPENSSL_EXPORT void OpenSSL_add_all_algorithms(void);
+
+/* OpenSSL_add_all_ciphers does nothing. */
+OPENSSL_EXPORT void OpenSSL_add_all_ciphers(void);
+
+/* OpenSSL_add_all_digests does nothing. */
+OPENSSL_EXPORT void OpenSSL_add_all_digests(void);
+
+/* EVP_cleanup does nothing. */
+OPENSSL_EXPORT void EVP_cleanup(void);
+
+
+/* Private functions */
+
+/* EVP_PKEY_asn1_find returns the ASN.1 method table for the given |nid|, which
+ * should be one of the |EVP_PKEY_*| values. It returns NULL if |nid| is
+ * unknown. */
+OPENSSL_EXPORT const EVP_PKEY_ASN1_METHOD *EVP_PKEY_asn1_find(ENGINE **pengine,
+                                                              int nid);
+
+/* EVP_PKEY_asn1_find_str returns an |EVP_PKEY_ASN1_METHOD| by matching values
+ * of the |len| bytes at |name|. For example, if name equals "EC" then it will
+ * return an ECC method. The |pengine| argument is ignored.
+ *
+ * TODO(fork): move to PEM? */
+OPENSSL_EXPORT const EVP_PKEY_ASN1_METHOD *EVP_PKEY_asn1_find_str(
+    ENGINE **pengine, const char *name, size_t len);
+
+struct evp_pkey_st {
+  CRYPTO_refcount_t references;
+
+  /* type contains one of the EVP_PKEY_* values or NID_undef and determines
+   * which element (if any) of the |pkey| union is valid. */
+  int type;
+
+  union {
+    char *ptr;
+    RSA *rsa;
+    DSA *dsa;
+    DH *dh;
+    EC_KEY *ec;
+  } pkey;
+
+  /* ameth contains a pointer to a method table that contains many ASN.1
+   * methods for the key type. */
+  const EVP_PKEY_ASN1_METHOD *ameth;
+} /* EVP_PKEY */;
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#define EVP_R_BUFFER_TOO_SMALL 100
+#define EVP_R_COMMAND_NOT_SUPPORTED 101
+#define EVP_R_DIFFERENT_KEY_TYPES 104
+#define EVP_R_DIFFERENT_PARAMETERS 105
+#define EVP_R_EXPECTING_AN_EC_KEY_KEY 107
+#define EVP_R_EXPECTING_A_DH_KEY 109
+#define EVP_R_EXPECTING_A_DSA_KEY 110
+#define EVP_R_ILLEGAL_OR_UNSUPPORTED_PADDING_MODE 111
+#define EVP_R_INVALID_CURVE 112
+#define EVP_R_INVALID_DIGEST_LENGTH 113
+#define EVP_R_INVALID_DIGEST_TYPE 114
+#define EVP_R_INVALID_KEYBITS 115
+#define EVP_R_INVALID_MGF1_MD 116
+#define EVP_R_INVALID_PADDING_MODE 118
+#define EVP_R_INVALID_PSS_PARAMETERS 119
+#define EVP_R_INVALID_SALT_LENGTH 121
+#define EVP_R_INVALID_TRAILER 122
+#define EVP_R_KEYS_NOT_SET 123
+#define EVP_R_MISSING_PARAMETERS 124
+#define EVP_R_NO_DEFAULT_DIGEST 125
+#define EVP_R_NO_KEY_SET 126
+#define EVP_R_NO_MDC2_SUPPORT 127
+#define EVP_R_NO_NID_FOR_CURVE 128
+#define EVP_R_NO_OPERATION_SET 129
+#define EVP_R_NO_PARAMETERS_SET 130
+#define EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE 131
+#define EVP_R_OPERATON_NOT_INITIALIZED 132
+#define EVP_R_UNKNOWN_DIGEST 133
+#define EVP_R_UNKNOWN_MASK_DIGEST 134
+#define EVP_R_UNSUPPORTED_ALGORITHM 138
+#define EVP_R_UNSUPPORTED_MASK_ALGORITHM 139
+#define EVP_R_UNSUPPORTED_MASK_PARAMETER 140
+#define EVP_R_EXPECTING_AN_RSA_KEY 141
+#define EVP_R_INVALID_OPERATION 142
+#define EVP_R_DECODE_ERROR 143
+#define EVP_R_INVALID_PSS_SALTLEN 144
+#define EVP_R_UNKNOWN_PUBLIC_KEY_TYPE 145
+#define EVP_R_CONTEXT_NOT_INITIALISED 146
+#define EVP_R_DIGEST_AND_KEY_TYPE_NOT_SUPPORTED 147
+#define EVP_R_WRONG_PUBLIC_KEY_TYPE 148
+#define EVP_R_UNKNOWN_SIGNATURE_ALGORITHM 149
+#define EVP_R_UNKNOWN_MESSAGE_DIGEST_ALGORITHM 150
+#define EVP_R_BN_DECODE_ERROR 151
+#define EVP_R_PARAMETER_ENCODING_ERROR 152
+#define EVP_R_UNSUPPORTED_PUBLIC_KEY_TYPE 153
+#define EVP_R_UNSUPPORTED_SIGNATURE_TYPE 154
+
+#endif  /* OPENSSL_HEADER_EVP_H */

+ 213 - 0
app/src/main/jni/openssl/include/openssl/ex_data.h

@@ -0,0 +1,213 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.]
+ */
+/* ====================================================================
+ * Copyright (c) 1998-2001 The OpenSSL Project.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. All advertising materials mentioning features or use of this
+ *    software must display the following acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
+ *
+ * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
+ *    endorse or promote products derived from this software without
+ *    prior written permission. For written permission, please contact
+ *    openssl-core@openssl.org.
+ *
+ * 5. Products derived from this software may not be called "OpenSSL"
+ *    nor may "OpenSSL" appear in their names without prior written
+ *    permission of the OpenSSL Project.
+ *
+ * 6. Redistributions of any form whatsoever must retain the following
+ *    acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit (http://www.openssl.org/)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
+ * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This product includes cryptographic software written by Eric Young
+ * (eay@cryptsoft.com).  This product includes software written by Tim
+ * Hudson (tjh@cryptsoft.com). */
+
+#ifndef OPENSSL_HEADER_EX_DATA_H
+#define OPENSSL_HEADER_EX_DATA_H
+
+#include <openssl/base.h>
+
+#include <openssl/stack.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* ex_data is a mechanism for associating arbitrary extra data with objects.
+ * For each type of object that supports ex_data, different users can be
+ * assigned indexes in which to store their data. Each index has callback
+ * functions that are called when an object of that type is freed or
+ * duplicated. */
+
+
+typedef struct crypto_ex_data_st CRYPTO_EX_DATA;
+
+
+/* Type-specific functions.
+ *
+ * Each type that supports ex_data provides three functions: */
+
+#if 0 /* Sample */
+
+/* TYPE_get_ex_new_index allocates a new index for |TYPE|. See the
+ * descriptions of the callback typedefs for details of when they are
+ * called. Any of the callback arguments may be NULL. The |argl| and |argp|
+ * arguments are opaque values that are passed to the callbacks. It returns the
+ * new index or a negative number on error.
+ *
+ * TODO(fork): this should follow the standard calling convention. */
+OPENSSL_EXPORT int TYPE_get_ex_new_index(long argl, void *argp,
+                                         CRYPTO_EX_unused *unused,
+                                         CRYPTO_EX_dup *dup_func,
+                                         CRYPTO_EX_free *free_func);
+
+/* TYPE_set_ex_data sets an extra data pointer on |t|. The |index| argument
+ * should have been returned from a previous call to |TYPE_get_ex_new_index|. */
+OPENSSL_EXPORT int TYPE_set_ex_data(TYPE *t, int index, void *arg);
+
+/* TYPE_get_ex_data returns an extra data pointer for |t|, or NULL if no such
+ * pointer exists. The |index| argument should have been returned from a
+ * previous call to |TYPE_get_ex_new_index|. */
+OPENSSL_EXPORT void *TYPE_get_ex_data(const TYPE *t, int index);
+
+#endif /* Sample */
+
+
+/* Callback types. */
+
+/* CRYPTO_EX_free is a callback function that is called when an object of the
+ * class with extra data pointers is being destroyed. For example, if this
+ * callback has been passed to |SSL_get_ex_new_index| then it may be called each
+ * time an |SSL*| is destroyed.
+ *
+ * The callback is passed the new object (i.e. the |SSL*|) in |parent|. The
+ * arguments |argl| and |argp| contain opaque values that were given to
+ * |CRYPTO_get_ex_new_index|. The callback should return one on success, but
+ * the value is ignored.
+ *
+ * This callback may be called with a NULL value for |ptr| if |parent| has no
+ * value set for this index. However, the callbacks may also be skipped entirely
+ * if no extra data pointers are set on |parent| at all. */
+typedef void CRYPTO_EX_free(void *parent, void *ptr, CRYPTO_EX_DATA *ad,
+                            int index, long argl, void *argp);
+
+/* CRYPTO_EX_dup is a callback function that is called when an object of the
+ * class is being copied and thus the ex_data linked to it also needs to be
+ * copied. On entry, |*from_d| points to the data for this index from the
+ * original object. When the callback returns, |*from_d| will be set as the
+ * data for this index in |to|.
+ *
+ * This callback may be called with a NULL value for |*from_d| if |from| has no
+ * value set for this index. However, the callbacks may also be skipped entirely
+ * if no extra data pointers are set on |from| at all. */
+typedef int CRYPTO_EX_dup(CRYPTO_EX_DATA *to, const CRYPTO_EX_DATA *from,
+                          void **from_d, int index, long argl, void *argp);
+
+
+/* Deprecated functions. */
+
+/* CRYPTO_cleanup_all_ex_data does nothing. */
+OPENSSL_EXPORT void CRYPTO_cleanup_all_ex_data(void);
+
+
+/* Private structures. */
+
+/* CRYPTO_EX_unused is a placeholder for an unused callback. It is aliased to
+ * int to ensure non-NULL callers fail to compile rather than fail silently. */
+typedef int CRYPTO_EX_unused;
+
+struct crypto_ex_data_st {
+  STACK_OF(void) *sk;
+};
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_EX_DATA_H */

+ 44 - 0
app/src/main/jni/openssl/include/openssl/hkdf.h

@@ -0,0 +1,44 @@
+/* Copyright (c) 2014, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+#ifndef OPENSSL_HEADER_HKDF_H
+#define OPENSSL_HEADER_HKDF_H
+
+#include <openssl/base.h>
+
+#ifdef  __cplusplus
+extern "C" {
+#endif
+
+
+/* Computes HKDF (as specified by RFC 5869) of initial keying material |secret|
+ * with |salt| and |info| using |digest|, and outputs |out_len| bytes to
+ * |out_key|. It returns one on success and zero on error.
+ *
+ * HKDF is an Extract-and-Expand algorithm. It does not do any key stretching,
+ * and as such, is not suited to be used alone to generate a key from a
+ * password. */
+OPENSSL_EXPORT int HKDF(uint8_t *out_key, size_t out_len, const EVP_MD *digest,
+                        const uint8_t *secret, size_t secret_len,
+                        const uint8_t *salt, size_t salt_len,
+                        const uint8_t *info, size_t info_len);
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#define HKDF_R_OUTPUT_TOO_LARGE 100
+
+#endif  /* OPENSSL_HEADER_HKDF_H */

+ 160 - 0
app/src/main/jni/openssl/include/openssl/hmac.h

@@ -0,0 +1,160 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_HMAC_H
+#define OPENSSL_HEADER_HMAC_H
+
+#include <openssl/base.h>
+
+#include <openssl/digest.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* HMAC contains functions for constructing PRFs from Merkle–Damgård hash
+ * functions using HMAC. */
+
+
+/* One-shot operation. */
+
+/* HMAC calculates the HMAC of |data_len| bytes of |data|, using the given key
+ * and hash function, and writes the result to |out|. On entry, |out| must
+ * contain |EVP_MAX_MD_SIZE| bytes of space. The actual length of the result is
+ * written to |*out_len|. It returns |out| or NULL on error. */
+OPENSSL_EXPORT uint8_t *HMAC(const EVP_MD *evp_md, const void *key,
+                             size_t key_len, const uint8_t *data,
+                             size_t data_len, uint8_t *out,
+                             unsigned int *out_len);
+
+
+/* Incremental operation. */
+
+/* HMAC_CTX_init initialises |ctx| for use in an HMAC operation. It's assumed
+ * that HMAC_CTX objects will be allocated on the stack thus no allocation
+ * function is provided. If needed, allocate |sizeof(HMAC_CTX)| and call
+ * |HMAC_CTX_init| on it. */
+OPENSSL_EXPORT void HMAC_CTX_init(HMAC_CTX *ctx);
+
+/* HMAC_CTX_cleanup frees data owned by |ctx|. */
+OPENSSL_EXPORT void HMAC_CTX_cleanup(HMAC_CTX *ctx);
+
+/* HMAC_Init_ex sets up an initialised |HMAC_CTX| to use |md| as the hash
+ * function and |key| as the key. For a non-initial call, |md| may be NULL, in
+ * which case the previous hash function will be used. If the hash function has
+ * not changed and |key| is NULL, |ctx| reuses the previous key. It returns one
+ * on success or zero otherwise.
+ *
+ * WARNING: NULL and empty keys are ambiguous on non-initial calls. Passing NULL
+ * |key| but repeating the previous |md| reuses the previous key rather than the
+ * empty key. */
+OPENSSL_EXPORT int HMAC_Init_ex(HMAC_CTX *ctx, const void *key, size_t key_len,
+                                const EVP_MD *md, ENGINE *impl);
+
+/* HMAC_Update hashes |data_len| bytes from |data| into the current HMAC
+ * operation in |ctx|. It returns one. */
+OPENSSL_EXPORT int HMAC_Update(HMAC_CTX *ctx, const uint8_t *data,
+                               size_t data_len);
+
+/* HMAC_Final completes the HMAC operation in |ctx| and writes the result to
+ * |out| and the sets |*out_len| to the length of the result. On entry, |out|
+ * must contain at least |EVP_MAX_MD_SIZE| bytes of space. It returns one on
+ * success or zero on error. */
+OPENSSL_EXPORT int HMAC_Final(HMAC_CTX *ctx, uint8_t *out,
+                              unsigned int *out_len);
+
+
+/* Utility functions. */
+
+/* HMAC_size returns the size, in bytes, of the HMAC that will be produced by
+ * |ctx|. On entry, |ctx| must have been setup with |HMAC_Init_ex|. */
+OPENSSL_EXPORT size_t HMAC_size(const HMAC_CTX *ctx);
+
+/* HMAC_CTX_copy_ex sets |dest| equal to |src|. On entry, |dest| must have been
+ * initialised by calling |HMAC_CTX_init|. It returns one on success and zero
+ * on error. */
+OPENSSL_EXPORT int HMAC_CTX_copy_ex(HMAC_CTX *dest, const HMAC_CTX *src);
+
+
+/* Deprecated functions. */
+
+OPENSSL_EXPORT int HMAC_Init(HMAC_CTX *ctx, const void *key, int key_len,
+                             const EVP_MD *md);
+
+/* HMAC_CTX_copy calls |HMAC_CTX_init| on |dest| and then sets it equal to
+ * |src|. On entry, |dest| must /not/ be initialised for an operation with
+ * |HMAC_Init_ex|. It returns one on success and zero on error. */
+OPENSSL_EXPORT int HMAC_CTX_copy(HMAC_CTX *dest, const HMAC_CTX *src);
+
+
+/* Private functions */
+
+#define HMAC_MAX_MD_CBLOCK 128 /* largest known is SHA512 */
+
+struct hmac_ctx_st {
+  const EVP_MD *md;
+  EVP_MD_CTX md_ctx;
+  EVP_MD_CTX i_ctx;
+  EVP_MD_CTX o_ctx;
+} /* HMAC_CTX */;
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_HMAC_H */

+ 192 - 0
app/src/main/jni/openssl/include/openssl/lhash.h

@@ -0,0 +1,192 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_LHASH_H
+#define OPENSSL_HEADER_LHASH_H
+
+#include <openssl/base.h>
+#include <openssl/type_check.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* lhash is a traditional, chaining hash table that automatically expands and
+ * contracts as needed. One should not use the lh_* functions directly, rather
+ * use the type-safe macro wrappers:
+ *
+ * A hash table of a specific type of object has type |LHASH_OF(type)|. This
+ * can be defined (once) with |DEFINE_LHASH_OF(type)| and declared where needed
+ * with |DECLARE_LHASH_OF(type)|. For example:
+ *
+ *   struct foo {
+ *     int bar;
+ *   };
+ *
+ *   DEFINE_LHASH_OF(struct foo);
+ *
+ * Although note that the hash table will contain /pointers/ to |foo|.
+ *
+ * A macro will be defined for each of the lh_* functions below. For
+ * LHASH_OF(foo), the macros would be lh_foo_new, lh_foo_num_items etc. */
+
+
+#define LHASH_OF(type) struct lhash_st_##type
+
+#define DEFINE_LHASH_OF(type) LHASH_OF(type) { int dummy; }
+
+#define DECLARE_LHASH_OF(type) LHASH_OF(type);
+
+/* The make_macros.sh script in this directory parses the following lines and
+ * generates the lhash_macros.h file that contains macros for the following
+ * types of stacks:
+ *
+ * LHASH_OF:ASN1_OBJECT
+ * LHASH_OF:CONF_VALUE
+ * LHASH_OF:SSL_SESSION */
+
+#define IN_LHASH_H
+#include <openssl/lhash_macros.h>
+#undef IN_LHASH_H
+
+
+/* lhash_item_st is an element of a hash chain. It points to the opaque data
+ * for this element and to the next item in the chain. The linked-list is NULL
+ * terminated. */
+typedef struct lhash_item_st {
+  void *data;
+  struct lhash_item_st *next;
+  /* hash contains the cached, hash value of |data|. */
+  uint32_t hash;
+} LHASH_ITEM;
+
+/* lhash_cmp_func is a comparison function that returns a value equal, or not
+ * equal, to zero depending on whether |*a| is equal, or not equal to |*b|,
+ * respectively. Note the difference between this and |stack_cmp_func| in that
+ * this takes pointers to the objects directly. */
+typedef int (*lhash_cmp_func)(const void *a, const void *b);
+
+/* lhash_hash_func is a function that maps an object to a uniformly distributed
+ * uint32_t. */
+typedef uint32_t (*lhash_hash_func)(const void *a);
+
+typedef struct lhash_st {
+  /* num_items contains the total number of items in the hash table. */
+  size_t num_items;
+  /* buckets is an array of |num_buckets| pointers. Each points to the head of
+   * a chain of LHASH_ITEM objects that have the same hash value, mod
+   * |num_buckets|. */
+  LHASH_ITEM **buckets;
+  /* num_buckets contains the length of |buckets|. This value is always >=
+   * kMinNumBuckets. */
+  size_t num_buckets;
+  /* callback_depth contains the current depth of |lh_doall| or |lh_doall_arg|
+   * calls. If non-zero then this suppresses resizing of the |buckets| array,
+   * which would otherwise disrupt the iteration. */
+  unsigned callback_depth;
+
+  lhash_cmp_func comp;
+  lhash_hash_func hash;
+} _LHASH;
+
+/* lh_new returns a new, empty hash table or NULL on error. If |comp| is NULL,
+ * |strcmp| will be used. If |hash| is NULL, a generic hash function will be
+ * used. */
+OPENSSL_EXPORT _LHASH *lh_new(lhash_hash_func hash, lhash_cmp_func comp);
+
+/* lh_free frees the hash table itself but none of the elements. See
+ * |lh_doall|. */
+OPENSSL_EXPORT void lh_free(_LHASH *lh);
+
+/* lh_num_items returns the number of items in |lh|. */
+OPENSSL_EXPORT size_t lh_num_items(const _LHASH *lh);
+
+/* lh_retrieve finds an element equal to |data| in the hash table and returns
+ * it. If no such element exists, it returns NULL. */
+OPENSSL_EXPORT void *lh_retrieve(const _LHASH *lh, const void *data);
+
+/* lh_insert inserts |data| into the hash table. If an existing element is
+ * equal to |data| (with respect to the comparison function) then |*old_data|
+ * will be set to that value and it will be replaced. Otherwise, or in the
+ * event of an error, |*old_data| will be set to NULL. It returns one on
+ * success or zero in the case of an allocation error. */
+OPENSSL_EXPORT int lh_insert(_LHASH *lh, void **old_data, void *data);
+
+/* lh_delete removes an element equal to |data| from the hash table and returns
+ * it. If no such element is found, it returns NULL. */
+OPENSSL_EXPORT void *lh_delete(_LHASH *lh, const void *data);
+
+/* lh_doall calls |func| on each element of the hash table.
+ * TODO(fork): rename this */
+OPENSSL_EXPORT void lh_doall(_LHASH *lh, void (*func)(void *));
+
+/* lh_doall_arg calls |func| on each element of the hash table and also passes
+ * |arg| as the second argument.
+ * TODO(fork): rename this */
+OPENSSL_EXPORT void lh_doall_arg(_LHASH *lh, void (*func)(void *, void *),
+                                 void *arg);
+
+/* lh_strhash is the default hash function which processes NUL-terminated
+ * strings. */
+OPENSSL_EXPORT uint32_t lh_strhash(const char *c);
+
+
+#if defined(__cplusplus)
+} /* extern C */
+#endif
+
+#endif /* OPENSSL_HEADER_LHASH_H */

+ 132 - 0
app/src/main/jni/openssl/include/openssl/lhash_macros.h

@@ -0,0 +1,132 @@
+/* Copyright (c) 2014, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+#if !defined(IN_LHASH_H)
+#error "Don't include this file directly. Include lhash.h"
+#endif
+
+/* ASN1_OBJECT */
+#define lh_ASN1_OBJECT_new(hash, comp)                                        \
+  ((LHASH_OF(ASN1_OBJECT) *)lh_new(                                           \
+      CHECKED_CAST(lhash_hash_func, uint32_t (*)(const ASN1_OBJECT *), hash), \
+      CHECKED_CAST(lhash_cmp_func,                                            \
+                   int (*)(const ASN1_OBJECT *a, const ASN1_OBJECT *b),       \
+                   comp)))
+
+#define lh_ASN1_OBJECT_free(lh) \
+  lh_free(CHECKED_CAST(_LHASH *, LHASH_OF(ASN1_OBJECT) *, lh));
+
+#define lh_ASN1_OBJECT_num_items(lh) \
+  lh_num_items(CHECKED_CAST(_LHASH *, LHASH_OF(ASN1_OBJECT) *, lh))
+
+#define lh_ASN1_OBJECT_retrieve(lh, data)                  \
+  ((ASN1_OBJECT *)lh_retrieve(                             \
+      CHECKED_CAST(_LHASH *, LHASH_OF(ASN1_OBJECT) *, lh), \
+      CHECKED_CAST(void *, ASN1_OBJECT *, data)))
+
+#define lh_ASN1_OBJECT_insert(lh, old_data, data)                \
+  lh_insert(CHECKED_CAST(_LHASH *, LHASH_OF(ASN1_OBJECT) *, lh), \
+            CHECKED_CAST(void **, ASN1_OBJECT **, old_data),     \
+            CHECKED_CAST(void *, ASN1_OBJECT *, data))
+
+#define lh_ASN1_OBJECT_delete(lh, data)                    \
+  ((ASN1_OBJECT *)lh_delete(                               \
+      CHECKED_CAST(_LHASH *, LHASH_OF(ASN1_OBJECT) *, lh), \
+      CHECKED_CAST(void *, ASN1_OBJECT *, data)))
+
+#define lh_ASN1_OBJECT_doall(lh, func)                          \
+  lh_doall(CHECKED_CAST(_LHASH *, LHASH_OF(ASN1_OBJECT) *, lh), \
+           CHECKED_CAST(void (*)(void *), void (*)(ASN1_OBJECT *), func));
+
+#define lh_ASN1_OBJECT_doall_arg(lh, func, arg)                     \
+  lh_doall_arg(CHECKED_CAST(_LHASH *, LHASH_OF(ASN1_OBJECT) *, lh), \
+               CHECKED_CAST(void (*)(void *, void *),               \
+                            void (*)(ASN1_OBJECT *, void *), func), \
+               arg);
+
+/* CONF_VALUE */
+#define lh_CONF_VALUE_new(hash, comp)                                        \
+  ((LHASH_OF(CONF_VALUE) *)lh_new(                                           \
+      CHECKED_CAST(lhash_hash_func, uint32_t (*)(const CONF_VALUE *), hash), \
+      CHECKED_CAST(lhash_cmp_func,                                           \
+                   int (*)(const CONF_VALUE *a, const CONF_VALUE *b), comp)))
+
+#define lh_CONF_VALUE_free(lh) \
+  lh_free(CHECKED_CAST(_LHASH *, LHASH_OF(CONF_VALUE) *, lh));
+
+#define lh_CONF_VALUE_num_items(lh) \
+  lh_num_items(CHECKED_CAST(_LHASH *, LHASH_OF(CONF_VALUE) *, lh))
+
+#define lh_CONF_VALUE_retrieve(lh, data)                  \
+  ((CONF_VALUE *)lh_retrieve(                             \
+      CHECKED_CAST(_LHASH *, LHASH_OF(CONF_VALUE) *, lh), \
+      CHECKED_CAST(void *, CONF_VALUE *, data)))
+
+#define lh_CONF_VALUE_insert(lh, old_data, data)                \
+  lh_insert(CHECKED_CAST(_LHASH *, LHASH_OF(CONF_VALUE) *, lh), \
+            CHECKED_CAST(void **, CONF_VALUE **, old_data),     \
+            CHECKED_CAST(void *, CONF_VALUE *, data))
+
+#define lh_CONF_VALUE_delete(lh, data)                                         \
+  ((CONF_VALUE *)lh_delete(CHECKED_CAST(_LHASH *, LHASH_OF(CONF_VALUE) *, lh), \
+                           CHECKED_CAST(void *, CONF_VALUE *, data)))
+
+#define lh_CONF_VALUE_doall(lh, func)                          \
+  lh_doall(CHECKED_CAST(_LHASH *, LHASH_OF(CONF_VALUE) *, lh), \
+           CHECKED_CAST(void (*)(void *), void (*)(CONF_VALUE *), func));
+
+#define lh_CONF_VALUE_doall_arg(lh, func, arg)                     \
+  lh_doall_arg(CHECKED_CAST(_LHASH *, LHASH_OF(CONF_VALUE) *, lh), \
+               CHECKED_CAST(void (*)(void *, void *),              \
+                            void (*)(CONF_VALUE *, void *), func), \
+               arg);
+
+/* SSL_SESSION */
+#define lh_SSL_SESSION_new(hash, comp)                                        \
+  ((LHASH_OF(SSL_SESSION) *)lh_new(                                           \
+      CHECKED_CAST(lhash_hash_func, uint32_t (*)(const SSL_SESSION *), hash), \
+      CHECKED_CAST(lhash_cmp_func,                                            \
+                   int (*)(const SSL_SESSION *a, const SSL_SESSION *b),       \
+                   comp)))
+
+#define lh_SSL_SESSION_free(lh) \
+  lh_free(CHECKED_CAST(_LHASH *, LHASH_OF(SSL_SESSION) *, lh));
+
+#define lh_SSL_SESSION_num_items(lh) \
+  lh_num_items(CHECKED_CAST(_LHASH *, LHASH_OF(SSL_SESSION) *, lh))
+
+#define lh_SSL_SESSION_retrieve(lh, data)                  \
+  ((SSL_SESSION *)lh_retrieve(                             \
+      CHECKED_CAST(_LHASH *, LHASH_OF(SSL_SESSION) *, lh), \
+      CHECKED_CAST(void *, SSL_SESSION *, data)))
+
+#define lh_SSL_SESSION_insert(lh, old_data, data)                \
+  lh_insert(CHECKED_CAST(_LHASH *, LHASH_OF(SSL_SESSION) *, lh), \
+            CHECKED_CAST(void **, SSL_SESSION **, old_data),     \
+            CHECKED_CAST(void *, SSL_SESSION *, data))
+
+#define lh_SSL_SESSION_delete(lh, data)                    \
+  ((SSL_SESSION *)lh_delete(                               \
+      CHECKED_CAST(_LHASH *, LHASH_OF(SSL_SESSION) *, lh), \
+      CHECKED_CAST(void *, SSL_SESSION *, data)))
+
+#define lh_SSL_SESSION_doall(lh, func)                          \
+  lh_doall(CHECKED_CAST(_LHASH *, LHASH_OF(SSL_SESSION) *, lh), \
+           CHECKED_CAST(void (*)(void *), void (*)(SSL_SESSION *), func));
+
+#define lh_SSL_SESSION_doall_arg(lh, func, arg)                     \
+  lh_doall_arg(CHECKED_CAST(_LHASH *, LHASH_OF(SSL_SESSION) *, lh), \
+               CHECKED_CAST(void (*)(void *, void *),               \
+                            void (*)(SSL_SESSION *, void *), func), \
+               arg);

+ 102 - 0
app/src/main/jni/openssl/include/openssl/md4.h

@@ -0,0 +1,102 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_MD4_H
+#define OPENSSL_HEADER_MD4_H
+
+#include <openssl/base.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* MD4. */
+
+/* MD4_CBLOCK is the block size of MD4. */
+#define MD4_CBLOCK 64
+
+/* MD4_DIGEST_LENGTH is the length of an MD4 digest. */
+#define MD4_DIGEST_LENGTH 16
+
+/* MD4_Init initialises |md4| and returns one. */
+OPENSSL_EXPORT int MD4_Init(MD4_CTX *md4);
+
+/* MD4_Update adds |len| bytes from |data| to |md4| and returns one. */
+OPENSSL_EXPORT int MD4_Update(MD4_CTX *md4, const void *data, size_t len);
+
+/* MD4_Final adds the final padding to |md4| and writes the resulting digest to
+ * |md|, which must have at least |MD4_DIGEST_LENGTH| bytes of space. It
+ * returns one. */
+OPENSSL_EXPORT int MD4_Final(uint8_t *md, MD4_CTX *md4);
+
+/* MD4_Transform is a low-level function that performs a single, MD4 block
+ * transformation using the state from |md4| and 64 bytes from |block|. */
+OPENSSL_EXPORT void MD4_Transform(MD4_CTX *md4, const uint8_t *block);
+
+struct md4_state_st {
+  uint32_t h[4];
+  uint32_t Nl, Nh;
+  uint8_t data[MD4_CBLOCK];
+  unsigned num;
+};
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_MD4_H */

+ 107 - 0
app/src/main/jni/openssl/include/openssl/md5.h

@@ -0,0 +1,107 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_MD5_H
+#define OPENSSL_HEADER_MD5_H
+
+#include <openssl/base.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* MD5. */
+
+
+/* MD5_CBLOCK is the block size of MD5. */
+#define MD5_CBLOCK 64
+
+/* MD5_DIGEST_LENGTH is the length of an MD5 digest. */
+#define MD5_DIGEST_LENGTH 16
+
+/* MD5_Init initialises |md5| and returns one. */
+OPENSSL_EXPORT int MD5_Init(MD5_CTX *md5);
+
+/* MD5_Update adds |len| bytes from |data| to |md5| and returns one. */
+OPENSSL_EXPORT int MD5_Update(MD5_CTX *md5, const void *data, size_t len);
+
+/* MD5_Final adds the final padding to |md5| and writes the resulting digest to
+ * |md|, which must have at least |MD5_DIGEST_LENGTH| bytes of space. It
+ * returns one. */
+OPENSSL_EXPORT int MD5_Final(uint8_t *md, MD5_CTX *md5);
+
+/* MD5 writes the digest of |len| bytes from |data| to |out| and returns |out|.
+ * There must be at least |MD5_DIGEST_LENGTH| bytes of space in |out|. */
+OPENSSL_EXPORT uint8_t *MD5(const uint8_t *data, size_t len, uint8_t *out);
+
+/* MD5_Transform is a low-level function that performs a single, MD5 block
+ * transformation using the state from |md5| and 64 bytes from |block|. */
+OPENSSL_EXPORT void MD5_Transform(MD5_CTX *md5, const uint8_t *block);
+
+struct md5_state_st {
+  uint32_t h[4];
+  uint32_t Nl, Nh;
+  uint8_t data[MD5_CBLOCK];
+  unsigned num;
+};
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_MD5_H */

+ 140 - 0
app/src/main/jni/openssl/include/openssl/mem.h

@@ -0,0 +1,140 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_MEM_H
+#define OPENSSL_HEADER_MEM_H
+
+#include <openssl/base.h>
+
+#include <stdlib.h>
+#include <stdarg.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* Memory and string functions, see also buf.h.
+ *
+ * OpenSSL has, historically, had a complex set of malloc debugging options.
+ * However, that was written in a time before Valgrind and ASAN. Since we now
+ * have those tools, the OpenSSL allocation functions are simply macros around
+ * the standard memory functions. */
+
+
+#define OPENSSL_malloc malloc
+#define OPENSSL_realloc realloc
+#define OPENSSL_free free
+
+/* OPENSSL_realloc_clean acts like |realloc|, but clears the previous memory
+ * buffer.  Because this is implemented as a wrapper around |malloc|, it needs
+ * to be given the size of the buffer pointed to by |ptr|. */
+void *OPENSSL_realloc_clean(void *ptr, size_t old_size, size_t new_size);
+
+/* OPENSSL_cleanse zeros out |len| bytes of memory at |ptr|. This is similar to
+ * |memset_s| from C11. */
+OPENSSL_EXPORT void OPENSSL_cleanse(void *ptr, size_t len);
+
+/* CRYPTO_memcmp returns zero iff the |len| bytes at |a| and |b| are equal. It
+ * takes an amount of time dependent on |len|, but independent of the contents
+ * of |a| and |b|. Unlike memcmp, it cannot be used to put elements into a
+ * defined order as the return value when a != b is undefined, other than to be
+ * non-zero. */
+OPENSSL_EXPORT int CRYPTO_memcmp(const void *a, const void *b, size_t len);
+
+/* OPENSSL_hash32 implements the 32 bit, FNV-1a hash. */
+OPENSSL_EXPORT uint32_t OPENSSL_hash32(const void *ptr, size_t len);
+
+/* OPENSSL_strdup has the same behaviour as strdup(3). */
+OPENSSL_EXPORT char *OPENSSL_strdup(const char *s);
+
+/* OPENSSL_strnlen has the same behaviour as strnlen(3). */
+OPENSSL_EXPORT size_t OPENSSL_strnlen(const char *s, size_t len);
+
+/* OPENSSL_strcasecmp has the same behaviour as strcasecmp(3). */
+OPENSSL_EXPORT int OPENSSL_strcasecmp(const char *a, const char *b);
+
+/* OPENSSL_strncasecmp has the same behaviour as strncasecmp(3). */
+OPENSSL_EXPORT int OPENSSL_strncasecmp(const char *a, const char *b, size_t n);
+
+/* DECIMAL_SIZE returns an upper bound for the length of the decimal
+ * representation of the given type. */
+#define DECIMAL_SIZE(type)	((sizeof(type)*8+2)/3+1)
+
+/* Printf functions.
+ *
+ * These functions are either OpenSSL wrappers for standard functions (i.e.
+ * |BIO_snprintf| and |BIO_vsnprintf|) which don't exist in C89, or are
+ * versions of printf functions that output to a BIO rather than a FILE. */
+#ifdef __GNUC__
+#define __bio_h__attr__ __attribute__
+#else
+#define __bio_h__attr__(x)
+#endif
+OPENSSL_EXPORT int BIO_snprintf(char *buf, size_t n, const char *format, ...)
+    __bio_h__attr__((__format__(__printf__, 3, 4)));
+
+OPENSSL_EXPORT int BIO_vsnprintf(char *buf, size_t n, const char *format,
+                                 va_list args)
+    __bio_h__attr__((__format__(__printf__, 3, 0)));
+#undef __bio_h__attr__
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_MEM_H */

+ 198 - 0
app/src/main/jni/openssl/include/openssl/obj.h

@@ -0,0 +1,198 @@
+/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_OBJ_H
+#define OPENSSL_HEADER_OBJ_H
+
+#include <openssl/base.h>
+
+#include <openssl/bytestring.h>
+#include <openssl/obj_mac.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* The objects library deals with the registration and indexing of ASN.1 object
+ * identifiers. These values are often written as a dotted sequence of numbers,
+ * e.g. 1.2.840.113549.1.9.16.3.9.
+ *
+ * Internally, OpenSSL likes to deal with these values by numbering them with
+ * numbers called "nids". OpenSSL has a large, built-in database of common
+ * object identifiers and also has both short and long names for them.
+ *
+ * This library provides functions for translating between object identifiers,
+ * nids, short names and long names.
+ *
+ * The nid values should not be used outside of a single process: they are not
+ * stable identifiers. */
+
+
+/* Basic operations. */
+
+/* OBJ_dup returns a duplicate copy of |obj| or NULL on allocation failure. */
+OPENSSL_EXPORT ASN1_OBJECT *OBJ_dup(const ASN1_OBJECT *obj);
+
+/* OBJ_cmp returns a value less than, equal to or greater than zero if |a| is
+ * less than, equal to or greater than |b|, respectively. */
+OPENSSL_EXPORT int OBJ_cmp(const ASN1_OBJECT *a, const ASN1_OBJECT *b);
+
+
+/* Looking up nids. */
+
+/* OBJ_obj2nid returns the nid corresponding to |obj|, or |NID_undef| if no
+ * such object is known. */
+OPENSSL_EXPORT int OBJ_obj2nid(const ASN1_OBJECT *obj);
+
+/* OBJ_cbs2nid returns the nid corresponding to the DER data in |cbs|, or
+ * |NID_undef| if no such object is known. */
+OPENSSL_EXPORT int OBJ_cbs2nid(const CBS *cbs);
+
+/* OBJ_sn2nid returns the nid corresponding to |short_name|, or |NID_undef| if
+ * no such short name is known. */
+OPENSSL_EXPORT int OBJ_sn2nid(const char *short_name);
+
+/* OBJ_ln2nid returns the nid corresponding to |long_name|, or |NID_undef| if
+ * no such long name is known. */
+OPENSSL_EXPORT int OBJ_ln2nid(const char *long_name);
+
+/* OBJ_txt2nid returns the nid corresponding to |s|, which may be a short name,
+ * long name, or an ASCII string containing a dotted sequence of numbers. It
+ * returns the nid or NID_undef if unknown. */
+OPENSSL_EXPORT int OBJ_txt2nid(const char *s);
+
+
+/* Getting information about nids. */
+
+/* OBJ_nid2obj returns the ASN1_OBJECT corresponding to |nid|, or NULL if |nid|
+ * is unknown. */
+OPENSSL_EXPORT const ASN1_OBJECT *OBJ_nid2obj(int nid);
+
+/* OBJ_nid2sn returns the short name for |nid|, or NULL if |nid| is unknown. */
+OPENSSL_EXPORT const char *OBJ_nid2sn(int nid);
+
+/* OBJ_nid2ln returns the long name for |nid|, or NULL if |nid| is unknown. */
+OPENSSL_EXPORT const char *OBJ_nid2ln(int nid);
+
+/* OBJ_nid2cbb writes |nid| as an ASN.1 OBJECT IDENTIFIER to |out|. It returns
+ * one on success or zero otherwise. */
+OPENSSL_EXPORT int OBJ_nid2cbb(CBB *out, int nid);
+
+
+/* Dealing with textual representations of object identifiers. */
+
+/* OBJ_txt2obj returns an ASN1_OBJECT for the textual respresentation in |s|.
+ * If |dont_search_names| is zero, then |s| will be matched against the long
+ * and short names of a known objects to find a match. Otherwise |s| must
+ * contain an ASCII string with a dotted sequence of numbers. The resulting
+ * object need not be previously known. It returns a freshly allocated
+ * |ASN1_OBJECT| or NULL on error. */
+OPENSSL_EXPORT ASN1_OBJECT *OBJ_txt2obj(const char *s, int dont_search_names);
+
+/* OBJ_obj2txt converts |obj| to a textual representation. If
+ * |dont_return_name| is zero then |obj| will be matched against known objects
+ * and the long (preferably) or short name will be used if found. Otherwise
+ * |obj| will be converted into a dotted sequence of integers. If |out| is not
+ * NULL, then at most |out_len| bytes of the textual form will be written
+ * there. If |out_len| is at least one, then string written to |out| will
+ * always be NUL terminated. It returns the number of characters that could
+ * have been written, not including the final NUL, or -1 on error. */
+OPENSSL_EXPORT int OBJ_obj2txt(char *out, int out_len, const ASN1_OBJECT *obj,
+                               int dont_return_name);
+
+
+/* Adding objects at runtime. */
+
+/* OBJ_create adds a known object and returns the nid of the new object, or
+ * NID_undef on error. */
+OPENSSL_EXPORT int OBJ_create(const char *oid, const char *short_name,
+                              const char *long_name);
+
+
+/* Handling signature algorithm identifiers.
+ *
+ * Some NIDs (e.g. sha256WithRSAEncryption) specify both a digest algorithm and
+ * a public key algorithm. The following functions map between pairs of digest
+ * and public-key algorithms and the NIDs that specify their combination.
+ *
+ * Sometimes the combination NID leaves the digest unspecified (e.g.
+ * rsassaPss). In these cases, the digest NID is |NID_undef|. */
+
+/* OBJ_find_sigid_algs finds the digest and public-key NIDs that correspond to
+ * the signing algorithm |sign_nid|. If successful, it sets |*out_digest_nid|
+ * and |*out_pkey_nid| and returns one. Otherwise it returns zero. Any of
+ * |out_digest_nid| or |out_pkey_nid| can be NULL if the caller doesn't need
+ * that output value. */
+OPENSSL_EXPORT int OBJ_find_sigid_algs(int sign_nid, int *out_digest_nid,
+                                       int *out_pkey_nid);
+
+/* OBJ_find_sigid_by_algs finds the signature NID that corresponds to the
+ * combination of |digest_nid| and |pkey_nid|. If success, it sets
+ * |*out_sign_nid| and returns one. Otherwise it returns zero. The
+ * |out_sign_nid| argument can be NULL if the caller only wishes to learn
+ * whether the combination is valid. */
+OPENSSL_EXPORT int OBJ_find_sigid_by_algs(int *out_sign_nid, int digest_nid,
+                                          int pkey_nid);
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#define OBJ_R_UNKNOWN_NID 100
+
+#endif  /* OPENSSL_HEADER_OBJ_H */

File diff suppressed because it is too large
+ 4144 - 0
app/src/main/jni/openssl/include/openssl/obj_mac.h


+ 18 - 0
app/src/main/jni/openssl/include/openssl/objects.h

@@ -0,0 +1,18 @@
+/* Copyright (c) 2014, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+/* This header is provided in order to make compiling against code that expects
+   OpenSSL easier. */
+
+#include "obj.h"

+ 60 - 0
app/src/main/jni/openssl/include/openssl/opensslconf.h

@@ -0,0 +1,60 @@
+/* Copyright (c) 2014, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+/* This header is provided in order to make compiling against code that expects
+   OpenSSL easier. */
+
+#ifndef OPENSSL_HEADER_OPENSSLCONF_H
+#define OPENSSL_HEADER_OPENSSLCONF_H
+
+
+#define OPENSSL_NO_BF
+#define OPENSSL_NO_BUF_FREELISTS
+#define OPENSSL_NO_CAMELLIA
+#define OPENSSL_NO_CAPIENG
+#define OPENSSL_NO_CAST
+#define OPENSSL_NO_CMS
+#define OPENSSL_NO_COMP
+#define OPENSSL_NO_DANE
+#define OPENSSL_NO_DEPRECATED
+#define OPENSSL_NO_DYNAMIC_ENGINE
+#define OPENSSL_NO_EC_NISTP_64_GCC_128
+#define OPENSSL_NO_EC2M
+#define OPENSSL_NO_ENGINE
+#define OPENSSL_NO_GMP
+#define OPENSSL_NO_GOST
+#define OPENSSL_NO_HEARTBEATS
+#define OPENSSL_NO_HW
+#define OPENSSL_NO_IDEA
+#define OPENSSL_NO_JPAKE
+#define OPENSSL_NO_KRB5
+#define OPENSSL_NO_MD2
+#define OPENSSL_NO_MDC2
+#define OPENSSL_NO_OCB
+#define OPENSSL_NO_OCSP
+#define OPENSSL_NO_RC2
+#define OPENSSL_NO_RC5
+#define OPENSSL_NO_RFC3779
+#define OPENSSL_NO_RIPEMD
+#define OPENSSL_NO_RMD160
+#define OPENSSL_NO_SCTP
+#define OPENSSL_NO_SEED
+#define OPENSSL_NO_SRP
+#define OPENSSL_NO_SSL2
+#define OPENSSL_NO_STATIC_ENGINE
+#define OPENSSL_NO_STORE
+#define OPENSSL_NO_WHIRLPOOL
+
+
+#endif  /* OPENSSL_HEADER_OPENSSLCONF_H */

+ 18 - 0
app/src/main/jni/openssl/include/openssl/opensslv.h

@@ -0,0 +1,18 @@
+/* Copyright (c) 2014, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+/* This header is provided in order to make compiling against code that expects
+   OpenSSL easier. */
+
+#include "crypto.h"

+ 18 - 0
app/src/main/jni/openssl/include/openssl/ossl_typ.h

@@ -0,0 +1,18 @@
+/* Copyright (c) 2014, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+/* This header is provided in order to make compiling against code that expects
+   OpenSSL easier. */
+
+#include "base.h"

+ 517 - 0
app/src/main/jni/openssl/include/openssl/pem.h

@@ -0,0 +1,517 @@
+/* Copyright (C) 1995-1997 Eric Young (eay@cryptsoft.com)
+ * All rights reserved.
+ *
+ * This package is an SSL implementation written
+ * by Eric Young (eay@cryptsoft.com).
+ * The implementation was written so as to conform with Netscapes SSL.
+ *
+ * This library is free for commercial and non-commercial use as long as
+ * the following conditions are aheared to.  The following conditions
+ * apply to all code found in this distribution, be it the RC4, RSA,
+ * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
+ * included with this distribution is covered by the same copyright terms
+ * except that the holder is Tim Hudson (tjh@cryptsoft.com).
+ *
+ * Copyright remains Eric Young's, and as such any Copyright notices in
+ * the code are not to be removed.
+ * If this package is used in a product, Eric Young should be given attribution
+ * as the author of the parts of the library used.
+ * This can be in the form of a textual message at program startup or
+ * in documentation (online or textual) provided with the package.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *    "This product includes cryptographic software written by
+ *     Eric Young (eay@cryptsoft.com)"
+ *    The word 'cryptographic' can be left out if the rouines from the library
+ *    being used are not cryptographic related :-).
+ * 4. If you include any Windows specific code (or a derivative thereof) from
+ *    the apps directory (application code) you must include an acknowledgement:
+ *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * The licence and distribution terms for any publically available version or
+ * derivative of this code cannot be changed.  i.e. this code cannot simply be
+ * copied and put under another distribution licence
+ * [including the GNU Public Licence.] */
+
+#ifndef OPENSSL_HEADER_PEM_H
+#define OPENSSL_HEADER_PEM_H
+
+#include <openssl/base64.h>
+#include <openssl/bio.h>
+#include <openssl/cipher.h>
+#include <openssl/digest.h>
+#include <openssl/evp.h>
+#include <openssl/stack.h>
+#include <openssl/x509.h>
+
+#ifdef  __cplusplus
+extern "C" {
+#endif
+
+
+#define PEM_BUFSIZE		1024
+
+#define PEM_OBJ_UNDEF		0
+#define PEM_OBJ_X509		1
+#define PEM_OBJ_X509_REQ	2
+#define PEM_OBJ_CRL		3
+#define PEM_OBJ_SSL_SESSION	4
+#define PEM_OBJ_PRIV_KEY	10
+#define PEM_OBJ_PRIV_RSA	11
+#define PEM_OBJ_PRIV_DSA	12
+#define PEM_OBJ_PRIV_DH		13
+#define PEM_OBJ_PUB_RSA		14
+#define PEM_OBJ_PUB_DSA		15
+#define PEM_OBJ_PUB_DH		16
+#define PEM_OBJ_DHPARAMS	17
+#define PEM_OBJ_DSAPARAMS	18
+#define PEM_OBJ_PRIV_RSA_PUBLIC	19
+#define PEM_OBJ_PRIV_ECDSA	20
+#define PEM_OBJ_PUB_ECDSA	21
+#define PEM_OBJ_ECPARAMETERS	22
+
+#define PEM_ERROR		30
+#define PEM_DEK_DES_CBC         40
+#define PEM_DEK_IDEA_CBC        45
+#define PEM_DEK_DES_EDE         50
+#define PEM_DEK_DES_ECB         60
+#define PEM_DEK_RSA             70
+#define PEM_DEK_RSA_MD2         80
+#define PEM_DEK_RSA_MD5         90
+
+#define PEM_MD_MD2		NID_md2
+#define PEM_MD_MD5		NID_md5
+#define PEM_MD_SHA		NID_sha
+#define PEM_MD_MD2_RSA		NID_md2WithRSAEncryption
+#define PEM_MD_MD5_RSA		NID_md5WithRSAEncryption
+#define PEM_MD_SHA_RSA		NID_sha1WithRSAEncryption
+
+#define PEM_STRING_X509_OLD	"X509 CERTIFICATE"
+#define PEM_STRING_X509		"CERTIFICATE"
+#define PEM_STRING_X509_PAIR	"CERTIFICATE PAIR"
+#define PEM_STRING_X509_TRUSTED	"TRUSTED CERTIFICATE"
+#define PEM_STRING_X509_REQ_OLD	"NEW CERTIFICATE REQUEST"
+#define PEM_STRING_X509_REQ	"CERTIFICATE REQUEST"
+#define PEM_STRING_X509_CRL	"X509 CRL"
+#define PEM_STRING_EVP_PKEY	"ANY PRIVATE KEY"
+#define PEM_STRING_PUBLIC	"PUBLIC KEY"
+#define PEM_STRING_RSA		"RSA PRIVATE KEY"
+#define PEM_STRING_RSA_PUBLIC	"RSA PUBLIC KEY"
+#define PEM_STRING_DSA		"DSA PRIVATE KEY"
+#define PEM_STRING_DSA_PUBLIC	"DSA PUBLIC KEY"
+#define PEM_STRING_PKCS7	"PKCS7"
+#define PEM_STRING_PKCS7_SIGNED	"PKCS #7 SIGNED DATA"
+#define PEM_STRING_PKCS8	"ENCRYPTED PRIVATE KEY"
+#define PEM_STRING_PKCS8INF	"PRIVATE KEY"
+#define PEM_STRING_DHPARAMS	"DH PARAMETERS"
+#define PEM_STRING_SSL_SESSION	"SSL SESSION PARAMETERS"
+#define PEM_STRING_DSAPARAMS	"DSA PARAMETERS"
+#define PEM_STRING_ECDSA_PUBLIC "ECDSA PUBLIC KEY"
+#define PEM_STRING_ECPRIVATEKEY	"EC PRIVATE KEY"
+#define PEM_STRING_PARAMETERS	"PARAMETERS"
+#define PEM_STRING_CMS		"CMS"
+
+  /* Note that this structure is initialised by PEM_SealInit and cleaned up
+     by PEM_SealFinal (at least for now) */
+typedef struct PEM_Encode_Seal_st
+	{
+	EVP_ENCODE_CTX encode;
+	EVP_MD_CTX md;
+	EVP_CIPHER_CTX cipher;
+	} PEM_ENCODE_SEAL_CTX;
+
+/* enc_type is one off */
+#define PEM_TYPE_ENCRYPTED      10
+#define PEM_TYPE_MIC_ONLY       20
+#define PEM_TYPE_MIC_CLEAR      30
+#define PEM_TYPE_CLEAR		40
+
+typedef struct pem_recip_st
+	{
+	char *name;
+	X509_NAME *dn;
+
+	int cipher;
+	int key_enc;
+	/*	char iv[8]; unused and wrong size */
+	} PEM_USER;
+
+typedef struct pem_ctx_st
+	{
+	int type;		/* what type of object */
+
+	struct	{
+		int version;	
+		int mode;		
+		} proc_type;
+
+	char *domain;
+
+	struct	{
+		int cipher;
+	/* unused, and wrong size
+	   unsigned char iv[8]; */
+		} DEK_info;
+		
+	PEM_USER *originator;
+
+	int num_recipient;
+	PEM_USER **recipient;
+
+	EVP_MD *md;		/* signature type */
+
+	int md_enc;		/* is the md encrypted or not? */
+	int md_len;		/* length of md_data */
+	char *md_data;		/* message digest, could be pkey encrypted */
+
+	EVP_CIPHER *dec;	/* date encryption cipher */
+	int key_len;		/* key length */
+	unsigned char *key;	/* key */
+	/* unused, and wrong size
+	   unsigned char iv[8]; */
+
+	
+	int  data_enc;		/* is the data encrypted */
+	int data_len;
+	unsigned char *data;
+	} PEM_CTX;
+
+/* These macros make the PEM_read/PEM_write functions easier to maintain and
+ * write. Now they are all implemented with either:
+ * IMPLEMENT_PEM_rw(...) or IMPLEMENT_PEM_rw_cb(...)
+ */
+
+#ifdef OPENSSL_NO_FP_API
+
+#define IMPLEMENT_PEM_read_fp(name, type, str, asn1) /**/
+#define IMPLEMENT_PEM_write_fp(name, type, str, asn1) /**/
+#define IMPLEMENT_PEM_write_fp_const(name, type, str, asn1) /**/
+#define IMPLEMENT_PEM_write_cb_fp(name, type, str, asn1) /**/
+#define IMPLEMENT_PEM_write_cb_fp_const(name, type, str, asn1) /**/
+
+#else
+
+#define IMPLEMENT_PEM_read_fp(name, type, str, asn1) \
+OPENSSL_EXPORT type *PEM_read_##name(FILE *fp, type **x, pem_password_cb *cb, void *u)\
+{ \
+return PEM_ASN1_read((d2i_of_void *)d2i_##asn1, str,fp,(void **)x,cb,u); \
+} 
+
+#define IMPLEMENT_PEM_write_fp(name, type, str, asn1) \
+OPENSSL_EXPORT int PEM_write_##name(FILE *fp, type *x) \
+{ \
+return PEM_ASN1_write((i2d_of_void *)i2d_##asn1,str,fp,x,NULL,NULL,0,NULL,NULL); \
+}
+
+#define IMPLEMENT_PEM_write_fp_const(name, type, str, asn1) \
+OPENSSL_EXPORT int PEM_write_##name(FILE *fp, const type *x) \
+{ \
+return PEM_ASN1_write((i2d_of_void *)i2d_##asn1,str,fp,(void *)x,NULL,NULL,0,NULL,NULL); \
+}
+
+#define IMPLEMENT_PEM_write_cb_fp(name, type, str, asn1) \
+OPENSSL_EXPORT int PEM_write_##name(FILE *fp, type *x, const EVP_CIPHER *enc, \
+	     unsigned char *kstr, int klen, pem_password_cb *cb, \
+		  void *u) \
+	{ \
+	return PEM_ASN1_write((i2d_of_void *)i2d_##asn1,str,fp,x,enc,kstr,klen,cb,u); \
+	}
+
+#define IMPLEMENT_PEM_write_cb_fp_const(name, type, str, asn1) \
+OPENSSL_EXPORT int PEM_write_##name(FILE *fp, type *x, const EVP_CIPHER *enc, \
+	     unsigned char *kstr, int klen, pem_password_cb *cb, \
+		  void *u) \
+	{ \
+	return PEM_ASN1_write((i2d_of_void *)i2d_##asn1,str,fp,x,enc,kstr,klen,cb,u); \
+	}
+
+#endif
+
+#define IMPLEMENT_PEM_read_bio(name, type, str, asn1) \
+OPENSSL_EXPORT type *PEM_read_bio_##name(BIO *bp, type **x, pem_password_cb *cb, void *u)\
+{ \
+return PEM_ASN1_read_bio((d2i_of_void *)d2i_##asn1, str,bp,(void **)x,cb,u); \
+}
+
+#define IMPLEMENT_PEM_write_bio(name, type, str, asn1) \
+OPENSSL_EXPORT int PEM_write_bio_##name(BIO *bp, type *x) \
+{ \
+return PEM_ASN1_write_bio((i2d_of_void *)i2d_##asn1,str,bp,x,NULL,NULL,0,NULL,NULL); \
+}
+
+#define IMPLEMENT_PEM_write_bio_const(name, type, str, asn1) \
+OPENSSL_EXPORT int PEM_write_bio_##name(BIO *bp, const type *x) \
+{ \
+return PEM_ASN1_write_bio((i2d_of_void *)i2d_##asn1,str,bp,(void *)x,NULL,NULL,0,NULL,NULL); \
+}
+
+#define IMPLEMENT_PEM_write_cb_bio(name, type, str, asn1) \
+OPENSSL_EXPORT int PEM_write_bio_##name(BIO *bp, type *x, const EVP_CIPHER *enc, \
+	     unsigned char *kstr, int klen, pem_password_cb *cb, void *u) \
+	{ \
+	return PEM_ASN1_write_bio((i2d_of_void *)i2d_##asn1,str,bp,x,enc,kstr,klen,cb,u); \
+	}
+
+#define IMPLEMENT_PEM_write_cb_bio_const(name, type, str, asn1) \
+OPENSSL_EXPORT int PEM_write_bio_##name(BIO *bp, type *x, const EVP_CIPHER *enc, \
+	     unsigned char *kstr, int klen, pem_password_cb *cb, void *u) \
+	{ \
+	return PEM_ASN1_write_bio((i2d_of_void *)i2d_##asn1,str,bp,(void *)x,enc,kstr,klen,cb,u); \
+	}
+
+#define IMPLEMENT_PEM_write(name, type, str, asn1) \
+	IMPLEMENT_PEM_write_bio(name, type, str, asn1) \
+	IMPLEMENT_PEM_write_fp(name, type, str, asn1) 
+
+#define IMPLEMENT_PEM_write_const(name, type, str, asn1) \
+	IMPLEMENT_PEM_write_bio_const(name, type, str, asn1) \
+	IMPLEMENT_PEM_write_fp_const(name, type, str, asn1) 
+
+#define IMPLEMENT_PEM_write_cb(name, type, str, asn1) \
+	IMPLEMENT_PEM_write_cb_bio(name, type, str, asn1) \
+	IMPLEMENT_PEM_write_cb_fp(name, type, str, asn1) 
+
+#define IMPLEMENT_PEM_write_cb_const(name, type, str, asn1) \
+	IMPLEMENT_PEM_write_cb_bio_const(name, type, str, asn1) \
+	IMPLEMENT_PEM_write_cb_fp_const(name, type, str, asn1) 
+
+#define IMPLEMENT_PEM_read(name, type, str, asn1) \
+	IMPLEMENT_PEM_read_bio(name, type, str, asn1) \
+	IMPLEMENT_PEM_read_fp(name, type, str, asn1) 
+
+#define IMPLEMENT_PEM_rw(name, type, str, asn1) \
+	IMPLEMENT_PEM_read(name, type, str, asn1) \
+	IMPLEMENT_PEM_write(name, type, str, asn1)
+
+#define IMPLEMENT_PEM_rw_const(name, type, str, asn1) \
+	IMPLEMENT_PEM_read(name, type, str, asn1) \
+	IMPLEMENT_PEM_write_const(name, type, str, asn1)
+
+#define IMPLEMENT_PEM_rw_cb(name, type, str, asn1) \
+	IMPLEMENT_PEM_read(name, type, str, asn1) \
+	IMPLEMENT_PEM_write_cb(name, type, str, asn1)
+
+/* These are the same except they are for the declarations */
+
+#if defined(OPENSSL_NO_FP_API)
+
+#define DECLARE_PEM_read_fp(name, type) /**/
+#define DECLARE_PEM_write_fp(name, type) /**/
+#define DECLARE_PEM_write_cb_fp(name, type) /**/
+
+#else
+
+#define DECLARE_PEM_read_fp(name, type) \
+	OPENSSL_EXPORT type *PEM_read_##name(FILE *fp, type **x, pem_password_cb *cb, void *u);
+
+#define DECLARE_PEM_write_fp(name, type) \
+	OPENSSL_EXPORT int PEM_write_##name(FILE *fp, type *x);
+
+#define DECLARE_PEM_write_fp_const(name, type) \
+	OPENSSL_EXPORT int PEM_write_##name(FILE *fp, const type *x);
+
+#define DECLARE_PEM_write_cb_fp(name, type) \
+	OPENSSL_EXPORT int PEM_write_##name(FILE *fp, type *x, const EVP_CIPHER *enc, \
+	     unsigned char *kstr, int klen, pem_password_cb *cb, void *u);
+
+#endif
+
+#define DECLARE_PEM_read_bio(name, type) \
+	OPENSSL_EXPORT type *PEM_read_bio_##name(BIO *bp, type **x, pem_password_cb *cb, void *u);
+
+#define DECLARE_PEM_write_bio(name, type) \
+	OPENSSL_EXPORT int PEM_write_bio_##name(BIO *bp, type *x);
+
+#define DECLARE_PEM_write_bio_const(name, type) \
+	OPENSSL_EXPORT int PEM_write_bio_##name(BIO *bp, const type *x);
+
+#define DECLARE_PEM_write_cb_bio(name, type) \
+	OPENSSL_EXPORT int PEM_write_bio_##name(BIO *bp, type *x, const EVP_CIPHER *enc, \
+	     unsigned char *kstr, int klen, pem_password_cb *cb, void *u);
+
+
+#define DECLARE_PEM_write(name, type) \
+	DECLARE_PEM_write_bio(name, type) \
+	DECLARE_PEM_write_fp(name, type) 
+
+#define DECLARE_PEM_write_const(name, type) \
+	DECLARE_PEM_write_bio_const(name, type) \
+	DECLARE_PEM_write_fp_const(name, type)
+
+#define DECLARE_PEM_write_cb(name, type) \
+	DECLARE_PEM_write_cb_bio(name, type) \
+	DECLARE_PEM_write_cb_fp(name, type) 
+
+#define DECLARE_PEM_read(name, type) \
+	DECLARE_PEM_read_bio(name, type) \
+	DECLARE_PEM_read_fp(name, type)
+
+#define DECLARE_PEM_rw(name, type) \
+	DECLARE_PEM_read(name, type) \
+	DECLARE_PEM_write(name, type)
+
+#define DECLARE_PEM_rw_const(name, type) \
+	DECLARE_PEM_read(name, type) \
+	DECLARE_PEM_write_const(name, type)
+
+#define DECLARE_PEM_rw_cb(name, type) \
+	DECLARE_PEM_read(name, type) \
+	DECLARE_PEM_write_cb(name, type)
+
+/* "userdata": new with OpenSSL 0.9.4 */
+typedef int pem_password_cb(char *buf, int size, int rwflag, void *userdata);
+
+OPENSSL_EXPORT int	PEM_get_EVP_CIPHER_INFO(char *header, EVP_CIPHER_INFO *cipher);
+OPENSSL_EXPORT int	PEM_do_header (EVP_CIPHER_INFO *cipher, unsigned char *data,long *len, pem_password_cb *callback,void *u);
+
+OPENSSL_EXPORT int	PEM_read_bio(BIO *bp, char **name, char **header, unsigned char **data,long *len);
+OPENSSL_EXPORT int	PEM_write_bio(BIO *bp,const char *name, const char *hdr, const unsigned char *data, long len);
+OPENSSL_EXPORT int PEM_bytes_read_bio(unsigned char **pdata, long *plen, char **pnm, const char *name, BIO *bp, pem_password_cb *cb, void *u);
+OPENSSL_EXPORT void *	PEM_ASN1_read_bio(d2i_of_void *d2i, const char *name, BIO *bp, void **x, pem_password_cb *cb, void *u);
+OPENSSL_EXPORT int	PEM_ASN1_write_bio(i2d_of_void *i2d,const char *name,BIO *bp, void *x, const EVP_CIPHER *enc,unsigned char *kstr,int klen, pem_password_cb *cb, void *u);
+
+OPENSSL_EXPORT STACK_OF(X509_INFO) *	PEM_X509_INFO_read_bio(BIO *bp, STACK_OF(X509_INFO) *sk, pem_password_cb *cb, void *u);
+OPENSSL_EXPORT int	PEM_X509_INFO_write_bio(BIO *bp,X509_INFO *xi, EVP_CIPHER *enc, unsigned char *kstr, int klen, pem_password_cb *cd, void *u);
+
+OPENSSL_EXPORT int	PEM_read(FILE *fp, char **name, char **header, unsigned char **data,long *len);
+OPENSSL_EXPORT int	PEM_write(FILE *fp, const char *name, const char *hdr, const unsigned char *data, long len);
+OPENSSL_EXPORT void *  PEM_ASN1_read(d2i_of_void *d2i, const char *name, FILE *fp, void **x, pem_password_cb *cb, void *u);
+OPENSSL_EXPORT int	PEM_ASN1_write(i2d_of_void *i2d,const char *name,FILE *fp, void *x,const EVP_CIPHER *enc,unsigned char *kstr, int klen,pem_password_cb *callback, void *u);
+OPENSSL_EXPORT STACK_OF(X509_INFO) *	PEM_X509_INFO_read(FILE *fp, STACK_OF(X509_INFO) *sk, pem_password_cb *cb, void *u);
+
+OPENSSL_EXPORT int	PEM_SealInit(PEM_ENCODE_SEAL_CTX *ctx, EVP_CIPHER *type, EVP_MD *md_type, unsigned char **ek, int *ekl, unsigned char *iv, EVP_PKEY **pubk, int npubk);
+OPENSSL_EXPORT void	PEM_SealUpdate(PEM_ENCODE_SEAL_CTX *ctx, unsigned char *out, int *outl, unsigned char *in, int inl);
+OPENSSL_EXPORT int	PEM_SealFinal(PEM_ENCODE_SEAL_CTX *ctx, unsigned char *sig,int *sigl, unsigned char *out, int *outl, EVP_PKEY *priv);
+
+OPENSSL_EXPORT void    PEM_SignInit(EVP_MD_CTX *ctx, EVP_MD *type);
+OPENSSL_EXPORT void    PEM_SignUpdate(EVP_MD_CTX *ctx,unsigned char *d,unsigned int cnt);
+OPENSSL_EXPORT int	PEM_SignFinal(EVP_MD_CTX *ctx, unsigned char *sigret, unsigned int *siglen, EVP_PKEY *pkey);
+
+/* PEM_def_callback treats |userdata| as a string and copies it into |buf|,
+ * assuming its |size| is sufficient. Returns the length of the string, or 0
+ * if there is not enough room. If either |buf| or |userdata| is NULL, 0 is
+ * returned. Note that this is different from OpenSSL, which prompts for a
+ * password. */
+OPENSSL_EXPORT int	PEM_def_callback(char *buf, int size, int rwflag, void *userdata);
+OPENSSL_EXPORT void	PEM_proc_type(char *buf, int type);
+OPENSSL_EXPORT void	PEM_dek_info(char *buf, const char *type, int len, char *str);
+
+
+DECLARE_PEM_rw(X509, X509)
+
+DECLARE_PEM_rw(X509_AUX, X509)
+
+DECLARE_PEM_rw(X509_CERT_PAIR, X509_CERT_PAIR)
+
+DECLARE_PEM_rw(X509_REQ, X509_REQ)
+DECLARE_PEM_write(X509_REQ_NEW, X509_REQ)
+
+DECLARE_PEM_rw(X509_CRL, X509_CRL)
+
+/* DECLARE_PEM_rw(PKCS7, PKCS7) */
+
+DECLARE_PEM_rw(NETSCAPE_CERT_SEQUENCE, NETSCAPE_CERT_SEQUENCE)
+
+DECLARE_PEM_rw(PKCS8, X509_SIG)
+
+DECLARE_PEM_rw(PKCS8_PRIV_KEY_INFO, PKCS8_PRIV_KEY_INFO)
+
+DECLARE_PEM_rw_cb(RSAPrivateKey, RSA)
+
+DECLARE_PEM_rw_const(RSAPublicKey, RSA)
+DECLARE_PEM_rw(RSA_PUBKEY, RSA)
+
+#ifndef OPENSSL_NO_DSA
+
+DECLARE_PEM_rw_cb(DSAPrivateKey, DSA)
+
+DECLARE_PEM_rw(DSA_PUBKEY, DSA)
+
+DECLARE_PEM_rw_const(DSAparams, DSA)
+
+#endif
+
+DECLARE_PEM_rw_cb(ECPrivateKey, EC_KEY)
+DECLARE_PEM_rw(EC_PUBKEY, EC_KEY)
+
+
+DECLARE_PEM_rw_const(DHparams, DH)
+
+
+DECLARE_PEM_rw_cb(PrivateKey, EVP_PKEY)
+
+DECLARE_PEM_rw(PUBKEY, EVP_PKEY)
+
+OPENSSL_EXPORT int PEM_write_bio_PKCS8PrivateKey_nid(BIO *bp, EVP_PKEY *x, int nid, char *kstr, int klen, pem_password_cb *cb, void *u);
+OPENSSL_EXPORT int PEM_write_bio_PKCS8PrivateKey(BIO *, EVP_PKEY *, const EVP_CIPHER *, char *, int, pem_password_cb *, void *);
+OPENSSL_EXPORT int i2d_PKCS8PrivateKey_bio(BIO *bp, EVP_PKEY *x, const EVP_CIPHER *enc, char *kstr, int klen, pem_password_cb *cb, void *u);
+OPENSSL_EXPORT int i2d_PKCS8PrivateKey_nid_bio(BIO *bp, EVP_PKEY *x, int nid, char *kstr, int klen, pem_password_cb *cb, void *u);
+OPENSSL_EXPORT EVP_PKEY *d2i_PKCS8PrivateKey_bio(BIO *bp, EVP_PKEY **x, pem_password_cb *cb, void *u);
+
+OPENSSL_EXPORT int i2d_PKCS8PrivateKey_fp(FILE *fp, EVP_PKEY *x, const EVP_CIPHER *enc, char *kstr, int klen, pem_password_cb *cb, void *u);
+OPENSSL_EXPORT int i2d_PKCS8PrivateKey_nid_fp(FILE *fp, EVP_PKEY *x, int nid, char *kstr, int klen, pem_password_cb *cb, void *u);
+OPENSSL_EXPORT int PEM_write_PKCS8PrivateKey_nid(FILE *fp, EVP_PKEY *x, int nid, char *kstr, int klen, pem_password_cb *cb, void *u);
+
+OPENSSL_EXPORT EVP_PKEY *d2i_PKCS8PrivateKey_fp(FILE *fp, EVP_PKEY **x, pem_password_cb *cb, void *u);
+
+OPENSSL_EXPORT int PEM_write_PKCS8PrivateKey(FILE *fp,EVP_PKEY *x,const EVP_CIPHER *enc, char *kstr,int klen, pem_password_cb *cd, void *u);
+
+OPENSSL_EXPORT EVP_PKEY *PEM_read_bio_Parameters(BIO *bp, EVP_PKEY **x);
+OPENSSL_EXPORT int PEM_write_bio_Parameters(BIO *bp, EVP_PKEY *x);
+
+
+OPENSSL_EXPORT EVP_PKEY *b2i_PrivateKey(const unsigned char **in, long length);
+OPENSSL_EXPORT EVP_PKEY *b2i_PublicKey(const unsigned char **in, long length);
+OPENSSL_EXPORT EVP_PKEY *b2i_PrivateKey_bio(BIO *in);
+OPENSSL_EXPORT EVP_PKEY *b2i_PublicKey_bio(BIO *in);
+OPENSSL_EXPORT int i2b_PrivateKey_bio(BIO *out, EVP_PKEY *pk);
+OPENSSL_EXPORT int i2b_PublicKey_bio(BIO *out, EVP_PKEY *pk);
+OPENSSL_EXPORT EVP_PKEY *b2i_PVK_bio(BIO *in, pem_password_cb *cb, void *u);
+OPENSSL_EXPORT int i2b_PVK_bio(BIO *out, EVP_PKEY *pk, int enclevel, pem_password_cb *cb, void *u);
+
+
+void ERR_load_PEM_strings(void);
+
+
+#ifdef  __cplusplus
+}
+#endif
+
+#define PEM_R_BAD_BASE64_DECODE 100
+#define PEM_R_BAD_DECRYPT 101
+#define PEM_R_BAD_END_LINE 102
+#define PEM_R_BAD_IV_CHARS 103
+#define PEM_R_BAD_PASSWORD_READ 104
+#define PEM_R_CIPHER_IS_NULL 105
+#define PEM_R_ERROR_CONVERTING_PRIVATE_KEY 106
+#define PEM_R_NOT_DEK_INFO 107
+#define PEM_R_NOT_ENCRYPTED 108
+#define PEM_R_NOT_PROC_TYPE 109
+#define PEM_R_NO_START_LINE 110
+#define PEM_R_READ_KEY 111
+#define PEM_R_SHORT_HEADER 112
+#define PEM_R_UNSUPPORTED_CIPHER 113
+#define PEM_R_UNSUPPORTED_ENCRYPTION 114
+
+#endif  /* OPENSSL_HEADER_PEM_H */

+ 18 - 0
app/src/main/jni/openssl/include/openssl/pkcs12.h

@@ -0,0 +1,18 @@
+/* Copyright (c) 2014, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+/* This header is provided in order to make compiling against code that expects
+   OpenSSL easier. */
+
+#include "pkcs8.h"

+ 16 - 0
app/src/main/jni/openssl/include/openssl/pkcs7.h

@@ -0,0 +1,16 @@
+/* Copyright (c) 2014, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+/* This header is provided in order to make compiling against code that expects
+   OpenSSL easier. */

+ 220 - 0
app/src/main/jni/openssl/include/openssl/pkcs8.h

@@ -0,0 +1,220 @@
+/* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
+ * project 1999.
+ */
+/* ====================================================================
+ * Copyright (c) 1999 The OpenSSL Project.  All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * 3. All advertising materials mentioning features or use of this
+ *    software must display the following acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
+ *
+ * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
+ *    endorse or promote products derived from this software without
+ *    prior written permission. For written permission, please contact
+ *    licensing@OpenSSL.org.
+ *
+ * 5. Products derived from this software may not be called "OpenSSL"
+ *    nor may "OpenSSL" appear in their names without prior written
+ *    permission of the OpenSSL Project.
+ *
+ * 6. Redistributions of any form whatsoever must retain the following
+ *    acknowledgment:
+ *    "This product includes software developed by the OpenSSL Project
+ *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
+ * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
+ * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
+ * OF THE POSSIBILITY OF SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This product includes cryptographic software written by Eric Young
+ * (eay@cryptsoft.com).  This product includes software written by Tim
+ * Hudson (tjh@cryptsoft.com). */
+
+
+#ifndef OPENSSL_HEADER_PKCS8_H
+#define OPENSSL_HEADER_PKCS8_H
+
+#include <openssl/base.h>
+#include <openssl/x509.h>
+
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+
+/* PKCS8_encrypt_pbe serializes and encrypts a PKCS8_PRIV_KEY_INFO with PBES1 or
+ * PBES2 as defined in PKCS #5. Only pbeWithSHAAnd128BitRC4,
+ * pbeWithSHAAnd3-KeyTripleDES-CBC and pbeWithSHA1And40BitRC2, defined in PKCS
+ * #12, and PBES2, are supported.  PBES2 is selected by setting |cipher| and
+ * passing -1 for |pbe_nid|.  Otherwise, PBES1 is used and |cipher| is ignored.
+ *
+ * The |pass_raw_len| bytes pointed to by |pass_raw| are used as the password.
+ * Note that any conversions from the password as supplied in a text string
+ * (such as those specified in B.1 of PKCS #12) must be performed by the caller.
+ *
+ * If |salt| is NULL, a random salt of |salt_len| bytes is generated. If
+ * |salt_len| is zero, a default salt length is used instead.
+ *
+ * The resulting structure is stored in an X509_SIG which must be freed by the
+ * caller.
+ *
+ * TODO(davidben): Really? An X509_SIG? OpenSSL probably did that because it has
+ * the same structure as EncryptedPrivateKeyInfo. */
+OPENSSL_EXPORT X509_SIG *PKCS8_encrypt_pbe(int pbe_nid,
+                                           const EVP_CIPHER *cipher,
+                                           const uint8_t *pass_raw,
+                                           size_t pass_raw_len,
+                                           uint8_t *salt, size_t salt_len,
+                                           int iterations,
+                                           PKCS8_PRIV_KEY_INFO *p8inf);
+
+/* PKCS8_decrypt_pbe decrypts and decodes a PKCS8_PRIV_KEY_INFO with PBES1 or
+ * PBES2 as defined in PKCS #5. Only pbeWithSHAAnd128BitRC4,
+ * pbeWithSHAAnd3-KeyTripleDES-CBC and pbeWithSHA1And40BitRC2, and PBES2,
+ * defined in PKCS #12, are supported.
+ *
+ * The |pass_raw_len| bytes pointed to by |pass_raw| are used as the password.
+ * Note that any conversions from the password as supplied in a text string
+ * (such as those specified in B.1 of PKCS #12) must be performed by the caller.
+ *
+ * The resulting structure must be freed by the caller. */
+OPENSSL_EXPORT PKCS8_PRIV_KEY_INFO *PKCS8_decrypt_pbe(X509_SIG *pkcs8,
+                                                      const uint8_t *pass_raw,
+                                                      size_t pass_raw_len);
+
+/* PKCS12_get_key_and_certs parses a PKCS#12 structure from |in|, authenticates
+ * and decrypts it using |password|, sets |*out_key| to the included private
+ * key and appends the included certificates to |out_certs|. It returns one on
+ * success and zero on error. The caller takes ownership of the outputs. */
+OPENSSL_EXPORT int PKCS12_get_key_and_certs(EVP_PKEY **out_key,
+                                            STACK_OF(X509) *out_certs,
+                                            CBS *in, const char *password);
+
+
+/* Deprecated functions. */
+
+/* PKCS8_encrypt calls |PKCS8_encrypt_pbe| after (in the PKCS#12 case) treating
+ * |pass| as an ASCII string, appending U+0000, and converting to UCS-2. (So the
+ * empty password encodes as two NUL bytes.) In the PBES2 case, the password is
+ * unchanged.  */
+OPENSSL_EXPORT X509_SIG *PKCS8_encrypt(int pbe_nid, const EVP_CIPHER *cipher,
+                                       const char *pass, int pass_len,
+                                       uint8_t *salt, size_t salt_len,
+                                       int iterations,
+                                       PKCS8_PRIV_KEY_INFO *p8inf);
+
+/* PKCS8_decrypt calls PKCS8_decrypt_pbe after (in the PKCS#12 case) treating
+ * |pass| as an ASCII string, appending U+0000, and converting to UCS-2. (So the
+ *  empty password encodes as two NUL bytes.) In the PBES2 case, the password is
+ * unchanged. */
+OPENSSL_EXPORT PKCS8_PRIV_KEY_INFO *PKCS8_decrypt(X509_SIG *pkcs8,
+                                                  const char *pass,
+                                                  int pass_len);
+
+/* PKCS12_PBE_add does nothing. It exists for compatibility with OpenSSL. */
+OPENSSL_EXPORT void PKCS12_PBE_add(void);
+
+/* d2i_PKCS12 is a dummy function that copies |*ber_bytes| into a
+ * |PKCS12| structure. The |out_p12| argument must be NULL. On exit,
+ * |*ber_bytes| will be advanced by |ber_len|. It returns a fresh |PKCS12|
+ * structure or NULL on error.
+ *
+ * Note: unlike other d2i functions, |d2i_PKCS12| will always consume |ber_len|
+ * bytes.*/
+OPENSSL_EXPORT PKCS12 *d2i_PKCS12(PKCS12 **out_p12, const uint8_t **ber_bytes,
+                                  size_t ber_len);
+
+/* d2i_PKCS12_bio acts like |d2i_PKCS12| but reads from a |BIO|. */
+OPENSSL_EXPORT PKCS12* d2i_PKCS12_bio(BIO *bio, PKCS12 **out_p12);
+
+/* d2i_PKCS12_fp acts like |d2i_PKCS12| but reads from a |FILE|. */
+OPENSSL_EXPORT PKCS12* d2i_PKCS12_fp(FILE *fp, PKCS12 **out_p12);
+
+/* PKCS12_parse calls |PKCS12_get_key_and_certs| on the ASN.1 data stored in
+ * |p12|. The |out_pkey| and |out_cert| arguments must not be NULL and, on
+ * successful exit, the private key and first certificate will be stored in
+ * them. The |out_ca_certs| argument may be NULL but, if not, then any extra
+ * certificates will be appended to |*out_ca_certs|. If |*out_ca_certs| is NULL
+ * then it will be set to a freshly allocated stack containing the extra certs.
+ *
+ * It returns one on success and zero on error. */
+OPENSSL_EXPORT int PKCS12_parse(const PKCS12 *p12, const char *password,
+                                EVP_PKEY **out_pkey, X509 **out_cert,
+                                STACK_OF(X509) **out_ca_certs);
+
+/* PKCS12_verify_mac returns one if |password| is a valid password for |p12|
+ * and zero otherwise. Since |PKCS12_parse| doesn't take a length parameter,
+ * it's not actually possible to use a non-NUL-terminated password to actually
+ * get anything from a |PKCS12|. Thus |password| and |password_len| may be
+ * |NULL| and zero, respectively, or else |password_len| may be -1, or else
+ * |password[password_len]| must be zero and no other NUL bytes may appear in
+ * |password|. If the |password_len| checks fail, zero is returned
+ * immediately. */
+OPENSSL_EXPORT int PKCS12_verify_mac(const PKCS12 *p12, const char *password,
+                                     int password_len);
+
+/* PKCS12_free frees |p12| and its contents. */
+OPENSSL_EXPORT void PKCS12_free(PKCS12 *p12);
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#define PKCS8_R_BAD_PKCS12_DATA 100
+#define PKCS8_R_BAD_PKCS12_VERSION 101
+#define PKCS8_R_CIPHER_HAS_NO_OBJECT_IDENTIFIER 102
+#define PKCS8_R_CRYPT_ERROR 103
+#define PKCS8_R_DECODE_ERROR 104
+#define PKCS8_R_ENCODE_ERROR 105
+#define PKCS8_R_ENCRYPT_ERROR 106
+#define PKCS8_R_ERROR_SETTING_CIPHER_PARAMS 107
+#define PKCS8_R_INCORRECT_PASSWORD 108
+#define PKCS8_R_KEYGEN_FAILURE 109
+#define PKCS8_R_KEY_GEN_ERROR 110
+#define PKCS8_R_METHOD_NOT_SUPPORTED 111
+#define PKCS8_R_MISSING_MAC 112
+#define PKCS8_R_MULTIPLE_PRIVATE_KEYS_IN_PKCS12 113
+#define PKCS8_R_PKCS12_PUBLIC_KEY_INTEGRITY_NOT_SUPPORTED 114
+#define PKCS8_R_PKCS12_TOO_DEEPLY_NESTED 115
+#define PKCS8_R_PRIVATE_KEY_DECODE_ERROR 116
+#define PKCS8_R_PRIVATE_KEY_ENCODE_ERROR 117
+#define PKCS8_R_TOO_LONG 118
+#define PKCS8_R_UNKNOWN_ALGORITHM 119
+#define PKCS8_R_UNKNOWN_CIPHER 120
+#define PKCS8_R_UNKNOWN_CIPHER_ALGORITHM 121
+#define PKCS8_R_UNKNOWN_DIGEST 122
+#define PKCS8_R_UNKNOWN_HASH 123
+#define PKCS8_R_UNSUPPORTED_PRIVATE_KEY_ALGORITHM 124
+#define PKCS8_R_UNSUPPORTED_KEYLENGTH 125
+#define PKCS8_R_UNSUPPORTED_SALT_TYPE 126
+#define PKCS8_R_UNSUPPORTED_CIPHER 127
+#define PKCS8_R_UNSUPPORTED_KEY_DERIVATION_FUNCTION 128
+#define PKCS8_R_BAD_ITERATION_COUNT 129
+#define PKCS8_R_UNSUPPORTED_PRF 130
+
+#endif  /* OPENSSL_HEADER_PKCS8_H */

+ 51 - 0
app/src/main/jni/openssl/include/openssl/poly1305.h

@@ -0,0 +1,51 @@
+/* Copyright (c) 2014, Google Inc.
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
+
+#ifndef OPENSSL_HEADER_POLY1305_H
+#define OPENSSL_HEADER_POLY1305_H
+
+#include <openssl/base.h>
+
+#ifdef  __cplusplus
+extern "C" {
+#endif
+
+
+typedef uint8_t poly1305_state[512];
+
+/* CRYPTO_poly1305_init sets up |state| so that it can be used to calculate an
+ * authentication tag with the one-time key |key|. Note that |key| is a
+ * one-time key and therefore there is no `reset' method because that would
+ * enable several messages to be authenticated with the same key. */
+OPENSSL_EXPORT void CRYPTO_poly1305_init(poly1305_state* state,
+                                         const uint8_t key[32]);
+
+/* CRYPTO_poly1305_update processes |in_len| bytes from |in|. It can be called
+ * zero or more times after poly1305_init. */
+OPENSSL_EXPORT void CRYPTO_poly1305_update(poly1305_state* state,
+                                           const uint8_t* in,
+                                           size_t in_len);
+
+/* CRYPTO_poly1305_finish completes the poly1305 calculation and writes a 16
+ * byte authentication tag to |mac|. The |mac| address must be 16-byte
+ * aligned. */
+OPENSSL_EXPORT void CRYPTO_poly1305_finish(poly1305_state* state,
+                                           uint8_t mac[16]);
+
+
+#if defined(__cplusplus)
+}  /* extern C */
+#endif
+
+#endif  /* OPENSSL_HEADER_POLY1305_H */

+ 0 - 0
app/src/main/jni/openssl/include/openssl/pqueue.h


Some files were not shown because too many files changed in this diff