summaryrefslogtreecommitdiff
path: root/ipscrambling
diff options
context:
space:
mode:
Diffstat (limited to 'ipscrambling')
-rw-r--r--ipscrambling/README.md2
-rw-r--r--ipscrambling/build.gradle4
-rw-r--r--ipscrambling/dependencies.gradle61
-rw-r--r--ipscrambling/exportdependencies/publish.gradle6
-rw-r--r--ipscrambling/exportdependencies/update_dependencies.md4
-rw-r--r--ipscrambling/src/main/java/foundation/e/advancedprivacy/ipscrambler/KoinModule.kt2
-rw-r--r--ipscrambling/src/main/java/foundation/e/advancedprivacy/ipscrambler/OrbotServiceSupervisor.kt (renamed from ipscrambling/src/main/java/foundation/e/advancedprivacy/ipscrambler/IpScramblerModule.kt)132
7 files changed, 107 insertions, 104 deletions
diff --git a/ipscrambling/README.md b/ipscrambling/README.md
index 777b6a1..be51828 100644
--- a/ipscrambling/README.md
+++ b/ipscrambling/README.md
@@ -22,7 +22,7 @@ This will put compiled AAR and pom file exposing their dependencies in the local
repository (usually in ~/.m2/repository).
-To push release on gitlab
+To push release on gitlab (you will need a valid gitLabPrivateToken in ~/.gradle/gradle.properties)
./gradlew --console=verbose publish
diff --git a/ipscrambling/build.gradle b/ipscrambling/build.gradle
index 39efce7..29fed4f 100644
--- a/ipscrambling/build.gradle
+++ b/ipscrambling/build.gradle
@@ -50,7 +50,9 @@ dependencies {
libs.bundles.koin,
libs.bundles.kotlin.android.coroutines,
libs.androidx.localbroadcast,
+ libs.pcap4j,
+ libs.timber
)
implementation libs.e.orbotservice
- //implementation project(':ipscrambling:orbotservice')
+ implementation project(':core')
}
diff --git a/ipscrambling/dependencies.gradle b/ipscrambling/dependencies.gradle
index 412bf9a..31b6b78 100644
--- a/ipscrambling/dependencies.gradle
+++ b/ipscrambling/dependencies.gradle
@@ -1,5 +1,5 @@
ext {
- versions = [
+ orbotversions = [
android_material : "1.4.0",
android_shell : "1.0.0",
android_snowfall : "1.2.1",
@@ -26,36 +26,37 @@ ext {
tor_android : "0.4.7.10",
pcap_core : "1.8.2",
pcap_factory : "1.8.2",
- orbot_service : libs.versions.orbotservice,
+ orbot_service : "orbot-16.6.3-2", //libs.versions.orbotservice,
+ orbot_service_dependencies : "orbot-16.6.3-1",
]
- libs = [
- android_material : "com.google.android.material:material:$versions.android_material",
- android_shell : "com.jaredrummler:android-shell:$versions.android_shell",
- android_snowfall : "com.github.jetradarmobile:android-snowfall:$versions.android_snowfall",
- android_volley : "com.android.volley:volley:$versions.android_volley",
- androidx_appcompat : "androidx.appcompat:appcompat:$versions.androidx_appcompat",
- androidx_constraint : "androidx.constraintlayout:constraintlayout:$versions.androidx_constraint",
- androidx_coordinator : "androidx.coordinatorlayout:coordinatorlayout:$versions.androidx_coordinator",
- androidx_core : "androidx.core:core:$versions.androidx_core",
- androidx_leanback_core : "androidx.leanback:leanback:$versions.androidx_leanback",
- androidx_leanback_paging : "androidx.leanback:leanback-paging:$versions.androidx_leanback_paging",
- androidx_leanback_preferences : "androidx.leanback:leanback-preference:$versions.androidx_leanback",
- androidx_leanback_tab : "androidx.leanback:leanback-tab:$versions.androidx_leanback_tab",
- androidx_localbroadcast : "androidx.localbroadcastmanager:localbroadcastmanager:$versions.androidx_localbroadcast",
- androidx_multidex : "androidx.multidex:multidex:$versions.androidx_multidex",
- androidx_palette : "androidx.palette:palette:$versions.androidx_palette",
- androidx_recyclerview : "androidx.recyclerview:recyclerview:$versions.androidx_recyclerview",
- apl_appintro : "com.github.apl-devs:appintro:$versions.apl_appintro",
- bclogic_pulsator : "pl.bclogic:pulsator4droid:$versions.bclogic_pulsator",
- fastlane_screengrab : "tools.fastlane:screengrab:$versions.fastlane_screengrab",
- guardian_geoip : "foundation.e:geoip:$versions.orbot_service",
- guardian_jsocks : "com.gitlab.guardianproject:jsocksandroid:$versions.guardian_jsocks",
- guardian_jtorctl : "info.guardianproject:jtorctl:$versions.guardian_jtorctl",
- ipt_proxy : "foundation.e:OrbotIPtProxy:$versions.orbot_service",
- portmapper : "com.offbynull.portmapper:portmapper:$versions.portmapper",
- tor_android : "foundation.e:tor-android:$versions.orbot_service",
- pcap_core : "org.pcap4j:pcap4j-core:$versions.pcap_core",
- pcap_factory : "org.pcap4j:pcap4j-packetfactory-static:$versions.pcap_factory"
+ orbotlibs = [
+ android_material : "com.google.android.material:material:$orbotversions.android_material",
+ android_shell : "com.jaredrummler:android-shell:$orbotversions.android_shell",
+ android_snowfall : "com.github.jetradarmobile:android-snowfall:$orbotversions.android_snowfall",
+ android_volley : "com.android.volley:volley:$orbotversions.android_volley",
+ androidx_appcompat : "androidx.appcompat:appcompat:$orbotversions.androidx_appcompat",
+ androidx_constraint : "androidx.constraintlayout:constraintlayout:$orbotversions.androidx_constraint",
+ androidx_coordinator : "androidx.coordinatorlayout:coordinatorlayout:$orbotversions.androidx_coordinator",
+ androidx_core : "androidx.core:core:$orbotversions.androidx_core",
+ androidx_leanback_core : "androidx.leanback:leanback:$orbotversions.androidx_leanback",
+ androidx_leanback_paging : "androidx.leanback:leanback-paging:$orbotversions.androidx_leanback_paging",
+ androidx_leanback_preferences : "androidx.leanback:leanback-preference:$orbotversions.androidx_leanback",
+ androidx_leanback_tab : "androidx.leanback:leanback-tab:$orbotversions.androidx_leanback_tab",
+ androidx_localbroadcast : "androidx.localbroadcastmanager:localbroadcastmanager:$orbotversions.androidx_localbroadcast",
+ androidx_multidex : "androidx.multidex:multidex:$orbotversions.androidx_multidex",
+ androidx_palette : "androidx.palette:palette:$orbotversions.androidx_palette",
+ androidx_recyclerview : "androidx.recyclerview:recyclerview:$orbotversions.androidx_recyclerview",
+ apl_appintro : "com.github.apl-devs:appintro:$orbotversions.apl_appintro",
+ bclogic_pulsator : "pl.bclogic:pulsator4droid:$orbotversions.bclogic_pulsator",
+ fastlane_screengrab : "tools.fastlane:screengrab:$orbotversions.fastlane_screengrab",
+ guardian_geoip : "foundation.e:geoip:$orbotversions.orbot_service_dependencies",
+ guardian_jsocks : "com.gitlab.guardianproject:jsocksandroid:$orbotversions.guardian_jsocks",
+ guardian_jtorctl : "info.guardianproject:jtorctl:$orbotversions.guardian_jtorctl",
+ ipt_proxy : "foundation.e:OrbotIPtProxy:$orbotversions.orbot_service_dependencies",
+ portmapper : "com.offbynull.portmapper:portmapper:$orbotversions.portmapper",
+ tor_android : "foundation.e:tor-android:$orbotversions.orbot_service_dependencies",
+ pcap_core : "org.pcap4j:pcap4j-core:$orbotversions.pcap_core",
+ pcap_factory : "org.pcap4j:pcap4j-packetfactory-static:$orbotversions.pcap_factory"
]
}
diff --git a/ipscrambling/exportdependencies/publish.gradle b/ipscrambling/exportdependencies/publish.gradle
index 657ce22..3ff0f91 100644
--- a/ipscrambling/exportdependencies/publish.gradle
+++ b/ipscrambling/exportdependencies/publish.gradle
@@ -5,7 +5,7 @@ publishing {
maven(MavenPublication) {
groupId 'foundation.e'
artifactId 'orbotservice'
- version versions.orbot_service
+ version orbotversions.orbot_service
artifact "$buildDir/outputs/aar/orbotservice-release.aar"
pom.withXml {
@@ -25,7 +25,7 @@ publishing {
def ciApiV4Url = System.getenv("CI_API_V4_URL")
if (ciJobToken != null) {
maven {
- url "${ciApiV4Url}/projects/1063/packages/maven"
+ url "${ciApiV4Url}/projects/900/packages/maven"
credentials(HttpHeaderCredentials) {
name = 'Job-Token'
value = ciJobToken
@@ -36,7 +36,7 @@ publishing {
}
} else {
maven {
- url "https://gitlab.e.foundation/api/v4/projects/1063/packages/maven"
+ url "https://gitlab.e.foundation/api/v4/projects/900/packages/maven"
credentials(HttpHeaderCredentials) {
name = "Private-Token"
value = gitLabPrivateToken
diff --git a/ipscrambling/exportdependencies/update_dependencies.md b/ipscrambling/exportdependencies/update_dependencies.md
index 32ef58d..faf11f3 100644
--- a/ipscrambling/exportdependencies/update_dependencies.md
+++ b/ipscrambling/exportdependencies/update_dependencies.md
@@ -17,7 +17,7 @@ mvn install:install-file \
mvn deploy:deploy-file \
-DrepositoryId=gitlab-e-maven \
--Durl=https://gitlab.e.foundation/api/v4/projects/1063/packages/maven \
+-Durl=https://gitlab.e.foundation/api/v4/projects/900/packages/maven \
-DartifactId=[ARTIFACTID] \
-Dpackaging=aar \
-Dfile=[PATH]
@@ -37,7 +37,7 @@ step 4 :
mvn deploy:deploy-file \
-DrepositoryId=gitlab-e-maven \
--Durl=https://gitlab.e.foundation/api/v4/projects/1063/packages/maven \
+-Durl=https://gitlab.e.foundation/api/v4/projects/900/packages/maven \
-DartifactId=tor-android \
-Dpackaging=aar \
-Dfile="../../orbot/libs/tor-android-binary-release.aar
diff --git a/ipscrambling/src/main/java/foundation/e/advancedprivacy/ipscrambler/KoinModule.kt b/ipscrambling/src/main/java/foundation/e/advancedprivacy/ipscrambler/KoinModule.kt
index bfb9b32..79aeb05 100644
--- a/ipscrambling/src/main/java/foundation/e/advancedprivacy/ipscrambler/KoinModule.kt
+++ b/ipscrambling/src/main/java/foundation/e/advancedprivacy/ipscrambler/KoinModule.kt
@@ -21,5 +21,5 @@ import org.koin.core.module.dsl.singleOf
import org.koin.dsl.module
val ipScramblerModule = module {
- singleOf(::IpScramblerModule)
+ singleOf(::OrbotServiceSupervisor)
}
diff --git a/ipscrambling/src/main/java/foundation/e/advancedprivacy/ipscrambler/IpScramblerModule.kt b/ipscrambling/src/main/java/foundation/e/advancedprivacy/ipscrambler/OrbotServiceSupervisor.kt
index d1f01a0..8813948 100644
--- a/ipscrambling/src/main/java/foundation/e/advancedprivacy/ipscrambler/IpScramblerModule.kt
+++ b/ipscrambling/src/main/java/foundation/e/advancedprivacy/ipscrambler/OrbotServiceSupervisor.kt
@@ -1,4 +1,5 @@
/*
+ * Copyright (C) 2023 MURENA SAS
* Copyright (C) 2021 E FOUNDATION
*
* This program is free software: you can redistribute it and/or modify
@@ -27,28 +28,37 @@ import android.os.Bundle
import android.os.Handler
import android.os.Looper
import android.os.Message
-import android.util.Log
import androidx.localbroadcastmanager.content.LocalBroadcastManager
+import foundation.e.advancedprivacy.domain.entities.FeatureServiceState
+import kotlinx.coroutines.CoroutineScope
+import kotlinx.coroutines.Dispatchers
+import kotlinx.coroutines.delay
+import kotlinx.coroutines.flow.MutableStateFlow
+import kotlinx.coroutines.flow.StateFlow
+import kotlinx.coroutines.flow.update
+import kotlinx.coroutines.launch
+import kotlinx.coroutines.withContext
+import org.pcap4j.packet.DnsPacket
import org.torproject.android.service.OrbotConstants
import org.torproject.android.service.OrbotConstants.ACTION_STOP_FOREGROUND_TASK
import org.torproject.android.service.OrbotService
import org.torproject.android.service.util.Prefs
+import timber.log.Timber
import java.security.InvalidParameterException
+import java.util.function.Function
@SuppressLint("CommitPrefEdits")
-class IpScramblerModule(private val context: Context) {
- interface Listener {
- fun onStatusChanged(newStatus: Status)
- fun log(message: String)
- fun onTrafficUpdate(upload: Long, download: Long, read: Long, write: Long)
- }
+class OrbotServiceSupervisor(
+ private val context: Context,
+ private val coroutineScope: CoroutineScope,
+) {
+ private val _state = MutableStateFlow(FeatureServiceState.OFF)
+ val state: StateFlow<FeatureServiceState> = _state
enum class Status {
OFF, ON, STARTING, STOPPING, START_DISABLED
}
companion object {
- const val TAG = "IpScramblerModule"
-
private val EXIT_COUNTRY_CODES = setOf("DE", "AT", "SE", "CH", "IS", "CA", "US", "ES", "FR", "BG", "PL", "AU", "BR", "CZ", "DK", "FI", "GB", "HU", "NL", "JP", "RO", "RU", "SG", "SK")
// Key where exit country is stored by orbot service.
@@ -58,7 +68,6 @@ class IpScramblerModule(private val context: Context) {
}
private var currentStatus: Status? = null
- private val listeners = mutableSetOf<Listener>()
private val localBroadcastReceiver: BroadcastReceiver = object : BroadcastReceiver() {
override fun onReceive(context: Context, intent: Intent) {
@@ -70,7 +79,7 @@ class IpScramblerModule(private val context: Context) {
currentStatus = newStatus
}
} catch (e: Exception) {
- Log.e(TAG, "Can't parse Orbot service status.")
+ Timber.e("Can't parse Orbot service status.")
}
return
}
@@ -87,18 +96,6 @@ class IpScramblerModule(private val context: Context) {
val action = msg.obj as? String ?: return
val data = msg.data
when (action) {
- OrbotConstants.LOCAL_ACTION_LOG ->
- data.getString(OrbotConstants.LOCAL_EXTRA_LOG)?.let { newLog(it) }
-
- OrbotConstants.LOCAL_ACTION_BANDWIDTH -> {
- trafficUpdate(
- data.getLong("up", 0),
- data.getLong("down", 0),
- data.getLong("written", 0),
- data.getLong("read", 0)
- )
- }
-
OrbotConstants.LOCAL_ACTION_PORTS -> {
httpProxyPort = data.getInt(OrbotService.EXTRA_HTTP_PROXY_PORT, -1)
socksProxyPort = data.getInt(OrbotService.EXTRA_SOCKS_PROXY_PORT, -1)
@@ -110,9 +107,11 @@ class IpScramblerModule(private val context: Context) {
val newStatus = Status.valueOf(it)
updateStatus(newStatus, force = true)
} catch (e: Exception) {
- Log.e(TAG, "Can't parse Orbot service status.")
+ Timber.e("Can't parse Orbot service status.")
}
}
+ OrbotConstants.LOCAL_ACTION_LOG,
+ OrbotConstants.LOCAL_ACTION_BANDWIDTH -> {} // Unused in Advanced Privacy
}
super.handleMessage(msg)
}
@@ -150,9 +149,24 @@ class IpScramblerModule(private val context: Context) {
private fun updateStatus(status: Status, force: Boolean = false) {
if (force || status != currentStatus) {
- currentStatus = status
- listeners.forEach {
- it.onStatusChanged(status)
+ val newState = when (status) {
+ Status.OFF -> FeatureServiceState.OFF
+ Status.ON -> FeatureServiceState.ON
+ Status.STARTING -> FeatureServiceState.STARTING
+ Status.STOPPING,
+ Status.START_DISABLED -> FeatureServiceState.STOPPING
+ }
+
+ coroutineScope.launch(Dispatchers.IO) {
+ _state.update { currentState ->
+ if (newState == FeatureServiceState.OFF &&
+ currentState == FeatureServiceState.STOPPING
+ ) {
+ // Wait for orbot to relax before allowing user to reactivate it.
+ delay(1000)
+ }
+ newState
+ }
}
}
}
@@ -165,14 +179,6 @@ class IpScramblerModule(private val context: Context) {
return currentStatus != Status.OFF
}
- private fun newLog(message: String) {
- listeners.forEach { it.log(message) }
- }
-
- private fun trafficUpdate(upload: Long, download: Long, read: Long, write: Long) {
- listeners.forEach { it.onTrafficUpdate(upload, download, read, write) }
- }
-
private fun sendIntentToService(action: String, extra: Bundle? = null) {
val intent = Intent(context, OrbotService::class.java)
intent.action = action
@@ -203,27 +209,29 @@ class IpScramblerModule(private val context: Context) {
}
@SuppressLint("ApplySharedPref")
- private fun setExitCountryCode(countryCode: String) {
- val countryParam = when {
- countryCode.isEmpty() -> ""
- countryCode in EXIT_COUNTRY_CODES -> "{$countryCode}"
- else -> throw InvalidParameterException(
- "Only these countries are available: ${EXIT_COUNTRY_CODES.joinToString { ", " } }"
- )
- }
+ suspend fun setExitCountryCode(countryCode: String) {
+ withContext(Dispatchers.IO) {
+ val countryParam = when {
+ countryCode.isEmpty() -> ""
+ countryCode in EXIT_COUNTRY_CODES -> "{$countryCode}"
+ else -> throw InvalidParameterException(
+ "Only these countries are available: ${EXIT_COUNTRY_CODES.joinToString { ", " }}"
+ )
+ }
- if (isServiceRunning()) {
- val extra = Bundle()
- extra.putString("exit", countryParam)
- sendIntentToService(OrbotConstants.CMD_SET_EXIT, extra)
- } else {
- Prefs.getSharedPrefs(context)
- .edit().putString(PREFS_KEY_EXIT_NODES, countryParam)
- .commit()
+ if (isServiceRunning()) {
+ val extra = Bundle()
+ extra.putString("exit", countryParam)
+ sendIntentToService(OrbotConstants.CMD_SET_EXIT, extra)
+ } else {
+ Prefs.getSharedPrefs(context)
+ .edit().putString(PREFS_KEY_EXIT_NODES, countryParam)
+ .commit()
+ }
}
}
- private fun getExitCountryCode(): String {
+ fun getExitCountryCode(): String {
val raw = Prefs.getExitNodes()
return if (raw.isEmpty()) raw else raw.slice(1..2)
}
@@ -232,6 +240,10 @@ class IpScramblerModule(private val context: Context) {
return VpnService.prepare(context)
}
+ fun setDNSFilter(shouldBlock: Function<DnsPacket?, DnsPacket?>?) {
+ OrbotService.shouldBlock = shouldBlock
+ }
+
fun start(enableNotification: Boolean) {
Prefs.enableNotification(enableNotification)
Prefs.putUseVpn(true)
@@ -242,6 +254,8 @@ class IpScramblerModule(private val context: Context) {
}
fun stop() {
+ if (!isServiceRunning()) return
+
updateStatus(Status.STOPPING)
Prefs.putUseVpn(false)
@@ -280,10 +294,6 @@ class IpScramblerModule(private val context: Context) {
get() = getTorifiedApps()
set(value) = saveTorifiedApps(value)
- var exitCountry: String
- get() = getExitCountryCode()
- set(value) = setExitCountryCode(value)
-
fun getAvailablesLocations(): Set<String> = EXIT_COUNTRY_CODES
var httpProxyPort: Int = -1
@@ -292,16 +302,6 @@ class IpScramblerModule(private val context: Context) {
var socksProxyPort: Int = -1
private set
- fun addListener(listener: Listener) {
- listeners.add(listener)
- }
- fun removeListener(listener: Listener) {
- listeners.remove(listener)
- }
- fun clearListeners() {
- listeners.clear()
- }
-
fun onCleared() {
LocalBroadcastManager.getInstance(context).unregisterReceiver(localBroadcastReceiver)
}