Skip to content
GitLab
Projects
Groups
Snippets
Help
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Sign in / Register
Toggle navigation
Open sidebar
deBeauvoir
sentinel-android
Commits
86c2cfdc
Verified
Commit
86c2cfdc
authored
Aug 19, 2020
by
Sarath
⚔
Browse files
new tor service
parent
23f3db4e
Changes
30
Expand all
Hide whitespace changes
Inline
Side-by-side
Showing
20 changed files
with
2946 additions
and
90 deletions
+2946
-90
torservice/.gitignore
torservice/.gitignore
+1
-0
torservice/build.gradle
torservice/build.gradle
+78
-0
torservice/consumer-rules.pro
torservice/consumer-rules.pro
+0
-0
torservice/proguard-rules.pro
torservice/proguard-rules.pro
+21
-0
torservice/src/main/AndroidManifest.xml
torservice/src/main/AndroidManifest.xml
+1
-2
torservice/src/main/java/com/invertedx/torservice/ConnectionChangeReceiver.java
...va/com/invertedx/torservice/ConnectionChangeReceiver.java
+2
-1
torservice/src/main/java/com/invertedx/torservice/NetworkManager.java
...rc/main/java/com/invertedx/torservice/NetworkManager.java
+1
-3
torservice/src/main/java/com/invertedx/torservice/TorEventHandler.java
...c/main/java/com/invertedx/torservice/TorEventHandler.java
+267
-0
torservice/src/main/java/com/invertedx/torservice/TorPrefernceConstants.java
.../java/com/invertedx/torservice/TorPrefernceConstants.java
+41
-0
torservice/src/main/java/com/invertedx/torservice/TorProxyManager.java
...c/main/java/com/invertedx/torservice/TorProxyManager.java
+1546
-0
torservice/src/main/java/com/invertedx/torservice/TorServiceConstants.java
...in/java/com/invertedx/torservice/TorServiceConstants.java
+42
-0
torservice/src/main/java/com/invertedx/torservice/util/CustomNativeLoader.java
...ava/com/invertedx/torservice/util/CustomNativeLoader.java
+128
-0
torservice/src/main/java/com/invertedx/torservice/util/CustomShell.java
.../main/java/com/invertedx/torservice/util/CustomShell.java
+80
-0
torservice/src/main/java/com/invertedx/torservice/util/CustomTorResourceInstaller.java
...invertedx/torservice/util/CustomTorResourceInstaller.java
+67
-68
torservice/src/main/java/com/invertedx/torservice/util/ExternalIPFetcher.java
...java/com/invertedx/torservice/util/ExternalIPFetcher.java
+96
-0
torservice/src/main/java/com/invertedx/torservice/util/NativeLoader.java
...main/java/com/invertedx/torservice/util/NativeLoader.java
+25
-16
torservice/src/main/java/com/invertedx/torservice/util/PortForwarder.java
...ain/java/com/invertedx/torservice/util/PortForwarder.java
+80
-0
torservice/src/main/java/com/invertedx/torservice/util/Prefs.java
...ce/src/main/java/com/invertedx/torservice/util/Prefs.java
+123
-0
torservice/src/main/java/com/invertedx/torservice/util/TCPSourceApp.java
...main/java/com/invertedx/torservice/util/TCPSourceApp.java
+315
-0
torservice/src/main/java/com/invertedx/torservice/util/TorServiceUtils.java
...n/java/com/invertedx/torservice/util/TorServiceUtils.java
+32
-0
No files found.
tor/.gitignore
→
tor
service
/.gitignore
View file @
86c2cfdc
/build
/.idea
*.iml
\ No newline at end of file
torservice/build.gradle
0 → 100644
View file @
86c2cfdc
apply
plugin:
'com.android.library'
apply
plugin:
'kotlin-android'
apply
plugin:
'kotlin-android-extensions'
android
{
compileSdkVersion
29
buildToolsVersion
"29.0.3"
sourceSets
{
main
{
jniLibs
.
srcDirs
=
[
'./src/main/libs'
]
}
}
compileOptions
{
sourceCompatibility
1.8
targetCompatibility
1.8
}
defaultConfig
{
minSdkVersion
21
targetSdkVersion
29
versionCode
1
versionName
"1.0"
testInstrumentationRunner
"androidx.test.runner.AndroidJUnitRunner"
consumerProguardFiles
'consumer-rules.pro'
}
buildTypes
{
release
{
minifyEnabled
false
proguardFiles
getDefaultProguardFile
(
'proguard-android-optimize.txt'
),
'proguard-rules.pro'
}
}
aaptOptions
{
cruncherEnabled
=
false
}
lintOptions
{
abortOnError
false
}
packagingOptions
{
exclude
'assets/arm/obfs4proxy'
//this is redundant
}
}
dependencies
{
implementation
fileTree
(
dir:
'libs'
,
include:
[
'*.jar'
])
implementation
"org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"
implementation
'androidx.appcompat:appcompat:1.1.0'
implementation
'androidx.core:core-ktx:1.2.0'
testImplementation
'junit:junit:4.13'
androidTestImplementation
'androidx.test.ext:junit:1.1.1'
androidTestImplementation
'androidx.test.espresso:espresso-core:3.2.0'
implementation
'io.reactivex.rxjava2:rxandroid:2.1.0'
implementation
'androidx.legacy:legacy-support-v4:1.0.0'
implementation
'org.torproject:tor-android-binary:0.4.2.5'
implementation
'info.pluggabletransports.aptds:apt-dispatch-library:1.0.9'
implementation
'info.pluggabletransports.aptds:apt-meek-obfs4-legacy:1.0.9'
implementation
'info.pluggabletransports.aptds:jsocksAndroid:1.0.4'
implementation
'org.torproject:tor-android-binary:0.4.2.7a'
implementation
'com.jaredrummler:android-shell:1.0.0'
implementation
fileTree
(
dir:
'libs'
,
include:
[
'.so'
])
testImplementation
'junit:junit:4.13'
implementation
(
'com.offbynull.portmapper:portmapper:2.0.5'
){
transitive
=
true
}
implementation
'org.briarproject:jtorctl:0.3'
}
torservice/consumer-rules.pro
0 → 100644
View file @
86c2cfdc
torservice/proguard-rules.pro
0 → 100644
View file @
86c2cfdc
# Add project specific ProGuard rules here.
#
You
can
control
the
set
of
applied
configuration
files
using
the
#
proguardFiles
setting
in
build
.
gradle
.
#
#
For
more
details
,
see
#
http
://
developer
.
android
.
com
/
guide
/
developing
/
tools
/
proguard
.
html
#
If
your
project
uses
WebView
with
JS
,
uncomment
the
following
#
and
specify
the
fully
qualified
class
name
to
the
JavaScript
interface
#
class
:
#-
keepclassmembers
class
fqcn
.
of
.
javascript
.
interface
.
for
.
webview
{
#
public
*
;
#
}
#
Uncomment
this
to
preserve
the
line
number
information
for
#
debugging
stack
traces
.
#-
keepattributes
SourceFile
,
LineNumberTable
#
If
you
keep
the
line
number
information
,
uncomment
this
to
#
hide
the
original
source
file
name
.
#-
renamesourcefileattribute
SourceFile
tor/src/main/AndroidManifest.xml
→
tor
service
/src/main/AndroidManifest.xml
View file @
86c2cfdc
<manifest
xmlns:android=
"http://schemas.android.com/apk/res/android"
package=
"com.
msopentech.thali.toronionproxy.android"
>
package=
"com.
invertedx.torservice"
>
<uses-permission
android:name=
"android.permission.ACCESS_NETWORK_STATE"
/>
<uses-permission
android:name=
"android.permission.ACCESS_WIFI_STATE"
/>
<uses-permission
android:name=
"android.permission.INTERNET"
/>
</manifest>
tor/src/main/java/com/
msopentech/thali/android/toronionproxy
/ConnectionChangeReceiver.java
→
tor
service
/src/main/java/com/
invertedx/torservice
/ConnectionChangeReceiver.java
View file @
86c2cfdc
package
com.msopentech.thali.android.toronionproxy
;
package
com.invertedx.torservice
;
import
android.content.BroadcastReceiver
;
import
android.content.Context
;
...
...
tor/src/main/java/com/
msopentech/thali/android/toronionproxy
/NetworkManager.java
→
tor
service
/src/main/java/com/
invertedx/torservice
/NetworkManager.java
View file @
86c2cfdc
package
com.msopentech.thali.android.toronionproxy
;
import
java.util.concurrent.TimeUnit
;
package
com.invertedx.torservice
;
import
io.reactivex.Observable
;
import
io.reactivex.Observer
;
...
...
torservice/src/main/java/com/invertedx/torservice/TorEventHandler.java
0 → 100644
View file @
86c2cfdc
package
com.invertedx.torservice
;
import
android.text.TextUtils
;
import
android.util.Log
;
import
com.invertedx.torservice.util.Prefs
;
import
net.freehaven.tor.control.EventHandler
;
import
org.jetbrains.annotations.NotNull
;
import
java.text.NumberFormat
;
import
java.util.HashMap
;
import
java.util.Iterator
;
import
java.util.List
;
import
java.util.Locale
;
import
java.util.StringTokenizer
;
/**
* Created by n8fr8 on 9/25/16.
*/
public
class
TorEventHandler
implements
EventHandler
,
TorServiceConstants
{
private
TorProxyManager
torProxyManager
;
private
long
lastRead
=
-
1
;
private
long
lastWritten
=
-
1
;
private
long
mTotalTrafficWritten
=
0
;
private
long
mTotalTrafficRead
=
0
;
private
NumberFormat
mNumberFormat
=
null
;
private
HashMap
<
String
,
Node
>
hmBuiltNodes
=
new
HashMap
<
String
,
Node
>();
public
class
Node
{
public
String
status
;
public
String
id
;
public
String
name
;
public
String
ipAddress
;
public
String
country
;
public
String
organization
;
public
boolean
isFetchingInfo
=
false
;
}
public
HashMap
<
String
,
Node
>
getNodes
()
{
return
hmBuiltNodes
;
}
public
TorEventHandler
(
TorProxyManager
receiver
)
{
torProxyManager
=
receiver
;
mNumberFormat
=
NumberFormat
.
getInstance
(
Locale
.
getDefault
());
//localized numbers!
}
@Override
public
void
newDescriptors
(
List
<
String
>
orList
)
{
Iterator
<
String
>
iterator
=
orList
.
iterator
();
StringBuilder
stringBuilder
=
new
StringBuilder
();
while
(
iterator
.
hasNext
())
{
stringBuilder
.
append
(
iterator
.
next
());
}
}
@Override
public
void
orConnStatus
(
String
status
,
String
orName
)
{
StringBuilder
sb
=
new
StringBuilder
();
sb
.
append
(
"orConnStatus ("
);
sb
.
append
(
parseNodeName
(
orName
));
sb
.
append
(
"): "
);
sb
.
append
(
status
);
torProxyManager
.
debug
(
sb
.
toString
());
}
@Override
public
void
streamStatus
(
String
status
,
String
streamID
,
String
target
)
{
StringBuilder
sb
=
new
StringBuilder
();
sb
.
append
(
"StreamStatus ("
);
sb
.
append
((
streamID
));
sb
.
append
(
"): "
);
sb
.
append
(
status
);
torProxyManager
.
setCircuitStatus
(
sb
.
toString
());
}
@Override
public
void
message
(
String
severity
,
String
msg
)
{
torProxyManager
.
setCircuitStatus
(
severity
+
": "
+
msg
);
}
@Override
public
void
unrecognized
(
String
type
,
String
msg
)
{
torProxyManager
.
setCircuitStatus
(
msg
);
torProxyManager
.
logNotice
(
msg
);
}
@Override
public
void
bandwidthUsed
(
long
read
,
long
written
)
{
if
(
read
!=
lastRead
||
written
!=
lastWritten
)
{
StringBuilder
sb
=
new
StringBuilder
();
sb
.
append
(
formatCount
(
read
));
sb
.
append
(
" \u2193"
);
sb
.
append
(
" / "
);
sb
.
append
(
formatCount
(
written
));
sb
.
append
(
" \u2191"
);
torProxyManager
.
bandWidthUpdate
(
sb
.
toString
(),
read
,
written
);
mTotalTrafficWritten
+=
written
;
mTotalTrafficRead
+=
read
;
}
lastWritten
=
written
;
lastRead
=
read
;
torProxyManager
.
bandwidthUsed
(
read
,
written
);
}
private
String
formatCount
(
long
count
)
{
// Converts the supplied argument into a string.
// Under 2Mb, returns "xxx.xKb"
// Over 2Mb, returns "xxx.xxMb"
if
(
mNumberFormat
!=
null
)
if
(
count
<
1
e6
)
return
mNumberFormat
.
format
(
Math
.
round
((
float
)
((
int
)
(
count
*
10
/
1024
))
/
10
))
+
"kbps"
;
else
return
mNumberFormat
.
format
(
Math
.
round
((
float
)
((
int
)
(
count
*
100
/
1024
/
1024
))
/
100
))
+
"mbps"
;
else
return
""
;
//return count+" kB";
}
public
void
circuitStatus
(
String
status
,
String
circID
,
String
path
)
{
/* once the first circuit is complete, then announce that Orbot is on*/
if
(
torProxyManager
.
getCurrentStatus
()
==
TorProxyManager
.
ConnectionStatus
.
CONNECTING
&&
TextUtils
.
equals
(
status
,
"BUILT"
))
{
torProxyManager
.
setStatus
(
TorProxyManager
.
ConnectionStatus
.
CONNECTED
);
torProxyManager
.
sendLogs
(
"Connected to the Tor network"
);
}
String
msg
=
"CircuitStatus: "
+
circID
+
" "
+
status
;
//String purpose = info.get("PURPOSE");
//if(purpose != null) msg += ", purpose: " + purpose;
//String hsState = info.get("HS_STATE");
//if(hsState != null) msg += ", state: " + hsState;
//String rendQuery = info.get("REND_QUERY");
//if(rendQuery != null) msg += ", service: " + rendQuery;
if
(!
path
.
isEmpty
())
msg
+=
", path: "
+
shortenPath
(
path
);
torProxyManager
.
setCircuitStatus
(
msg
);
// LOG.info(msg);
if
(
Prefs
.
viewCircuitStatus
())
{
StringBuilder
sb
=
new
StringBuilder
();
sb
.
append
(
"Circuit ("
);
sb
.
append
((
circID
));
sb
.
append
(
") "
);
sb
.
append
(
status
);
sb
.
append
(
": "
);
StringTokenizer
st
=
new
StringTokenizer
(
path
,
","
);
Node
node
=
null
;
boolean
isFirstNode
=
true
;
int
nodeCount
=
st
.
countTokens
();
while
(
st
.
hasMoreTokens
())
{
String
nodePath
=
st
.
nextToken
();
String
nodeId
=
null
,
nodeName
=
null
;
String
[]
nodeParts
;
if
(
nodePath
.
contains
(
"="
))
nodeParts
=
nodePath
.
split
(
"="
);
else
nodeParts
=
nodePath
.
split
(
"~"
);
if
(
nodeParts
.
length
==
1
)
{
nodeId
=
nodeParts
[
0
].
substring
(
1
);
if
(
node
!=
null
)
{
nodeName
=
node
.
id
;
}
}
else
if
(
nodeParts
.
length
==
2
)
{
nodeId
=
nodeParts
[
0
].
substring
(
1
);
nodeName
=
nodeParts
[
1
];
}
if
(
nodeId
==
null
)
continue
;
node
=
hmBuiltNodes
.
get
(
nodeId
);
if
(
node
==
null
)
{
node
=
new
Node
();
node
.
id
=
nodeId
;
node
.
name
=
nodeName
;
}
node
.
status
=
status
;
sb
.
append
(
node
.
name
);
if
(!
TextUtils
.
isEmpty
(
node
.
ipAddress
))
sb
.
append
(
"("
).
append
(
node
.
ipAddress
).
append
(
")"
);
if
(
st
.
hasMoreTokens
())
sb
.
append
(
" > "
);
// torProxyManager.setCircuitStatus(status);
if
(
status
.
equals
(
"EXTENDED"
))
{
if
(
isFirstNode
)
{
hmBuiltNodes
.
put
(
node
.
id
,
node
);
if
(
node
.
ipAddress
==
null
&&
(!
node
.
isFetchingInfo
)
&&
Prefs
.
useDebugLogging
())
{
node
.
isFetchingInfo
=
true
;
// torProxyManager.exec(new ExternalIPFetcher(torProxyManager, node, OrbotService.mPortHTTP));
}
isFirstNode
=
false
;
}
}
else
if
(
status
.
equals
(
"BUILT"
))
{
torProxyManager
.
logNotice
(
sb
.
toString
());
// torProxyManager.setCircuitStatus(hmBuiltNodes.toString());
}
else
if
(
status
.
equals
(
"CLOSED"
))
{
torProxyManager
.
logNotice
(
sb
.
toString
());
hmBuiltNodes
.
remove
(
node
.
id
);
}
}
}
}
private
String
parseNodeName
(
String
node
)
{
if
(
node
.
indexOf
(
'='
)
!=
-
1
)
{
return
(
node
.
substring
(
node
.
indexOf
(
"="
)
+
1
));
}
else
if
(
node
.
indexOf
(
'~'
)
!=
-
1
)
{
return
(
node
.
substring
(
node
.
indexOf
(
"~"
)
+
1
));
}
else
return
node
;
}
@NotNull
private
String
shortenPath
(
String
id
)
{
StringBuilder
s
=
new
StringBuilder
();
if
(
s
.
length
()
>
0
)
s
.
append
(
','
);
s
.
append
(
id
.
substring
(
1
,
7
));
return
s
.
toString
();
}
}
torservice/src/main/java/com/invertedx/torservice/TorPrefernceConstants.java
0 → 100644
View file @
86c2cfdc
/* Copyright (c) 2009, Nathan Freitas, Orbot/The Guardian Project - http://openideals.com/guardian */
/* See LICENSE for licensing information */
package
com.invertedx.torservice
;
public
interface
TorPrefernceConstants
{
String
TAG
=
"TorServiceManager"
;
String
PREF_OR
=
"pref_or"
;
String
PREF_OR_PORT
=
"pref_or_port"
;
String
PREF_OR_NICKNAME
=
"pref_or_nickname"
;
String
DIRECTORY_TOR_BINARY
=
"app_torfiles"
;
String
PREF_REACHABLE_ADDRESSES
=
"pref_reachable_addresses"
;
String
PREF_REACHABLE_ADDRESSES_PORTS
=
"pref_reachable_addresses_ports"
;
String
PREF_DISABLE_NETWORK
=
"pref_disable_network"
;
String
PREF_TOR_SHARED_PREFS
=
"tor_preferences"
;
String
PREF_SOCKS
=
"pref_socks"
;
String
PREF_HTTP
=
"pref_http"
;
String
PREF_ISOLATE_DEST
=
"pref_isolate_dest"
;
String
PREF_CONNECTION_PADDING
=
"pref_connection_padding"
;
String
PREF_REDUCED_CONNECTION_PADDING
=
"pref_reduced_connection_padding"
;
String
PREF_CIRCUIT_PADDING
=
"pref_circuit_padding"
;
String
PREF_REDUCED_CIRCUIT_PADDING
=
"pref_reduced_circuit_padding"
;
String
PREF_PREFER_IPV6
=
"pref_prefer_ipv6"
;
String
PREF_DISABLE_IPV4
=
"pref_disable_ipv4"
;
String
APP_TOR_KEY
=
"_app_tor"
;
String
APP_DATA_KEY
=
"_app_data"
;
String
APP_WIFI_KEY
=
"_app_wifi"
;
}
torservice/src/main/java/com/invertedx/torservice/TorProxyManager.java
0 → 100644
View file @
86c2cfdc
This diff is collapsed.
Click to expand it.
torservice/src/main/java/com/invertedx/torservice/TorServiceConstants.java
0 → 100644
View file @
86c2cfdc
/* Copyright (c) 2009, Nathan Freitas, Orbot / The Guardian Project - http://openideals.com/guardian */
/* See LICENSE for licensing information */
package
com.invertedx.torservice
;
import
android.content.Intent
;
public
interface
TorServiceConstants
{
String
DIRECTORY_TOR_DATA
=
"data"
;
String
TOR_CONTROL_PORT_FILE
=
"control.txt"
;
String
TOR_PID_FILE
=
"torpid"
;
//torrc (tor config file)
String
TORRC_ASSET_KEY
=
"torrc"
;
String
TOR_CONTROL_COOKIE
=
"control_auth_cookie"
;
//geoip data file asset key
String
GEOIP_ASSET_KEY
=
"geoip"
;
String
GEOIP6_ASSET_KEY
=
"geoip6"
;
String
IP_LOCALHOST
=
"127.0.0.1"
;
int
TOR_TRANSPROXY_PORT_DEFAULT
=
9040
;
// int TOR_DNS_PORT_DEFAULT = 5400;
// String HTTP_PROXY_PORT_DEFAULT = "8118"; // like Privoxy!
String
SOCKS_PROXY_PORT_DEFAULT
=
"auto"
;
String
PREF_BINARY_TOR_VERSION_INSTALLED
=
"BINARY_TOR_VERSION_INSTALLED"
;
//obfsproxy
String
OBFSCLIENT_ASSET_KEY
=
"obfs4proxy"
;
String
HIDDEN_SERVICES_DIR
=
"hidden_services"
;
}
torservice/src/main/java/com/invertedx/torservice/util/CustomNativeLoader.java
0 → 100644
View file @
86c2cfdc
package
com.invertedx.torservice.util
;
import
android.content.Context
;
import
android.content.pm.ApplicationInfo
;
import
android.os.Build
;
import
android.util.Log
;
import
java.io.File
;
import
java.io.FileOutputStream
;
import
java.io.InputStream
;
import
java.io.OutputStream
;
import
java.util.zip.ZipEntry
;
import
java.util.zip.ZipFile
;
public
class
CustomNativeLoader
{
private
final
static
String
TAG
=
"CNL"
;
private
static
boolean
loadFromZip
(
Context
context
,
String
libname
,
File
destLocalFile
,
String
arch
)
{
ZipFile
zipFile
=
null
;
InputStream
stream
=
null
;
try
{
zipFile
=
new
ZipFile
(
context
.
getApplicationInfo
().
sourceDir
);
ZipEntry
entry
=
zipFile
.
getEntry
(
"lib/"
+
arch
+
"/"
+
libname
+
".so"
);
if
(
entry
==
null
)
{
entry
=
zipFile
.
getEntry
(
"jni/"
+
arch
+
"/"
+
libname
+
".so"
);
if
(
entry
==
null
)
throw
new
Exception
(
"Unable to find file in apk:"
+
"lib/"
+
arch
+
"/"
+
libname
);
}
//how we wrap this in another stream because the native .so is zipped itself
stream
=
zipFile
.
getInputStream
(
entry
);
OutputStream
out
=
new
FileOutputStream
(
destLocalFile
);
byte
[]
buf
=
new
byte
[
4096
];
int
len
;
while
((
len
=
stream
.
read
(
buf
))
>
0
)
{
Thread
.
yield
();
out
.
write
(
buf
,
0
,
len
);
}
out
.
close
();
destLocalFile
.
setReadable
(
true
,
false
);
destLocalFile
.
setExecutable
(
true
,
false
);
destLocalFile
.
setWritable
(
true
);
return
true
;
}
catch
(
Exception
e
)
{
Log
.
e
(
TAG
,
e
.
getMessage
());
}
finally
{
if
(
stream
!=
null
)
{
try
{
stream
.
close
();
}
catch
(
Exception
e
)
{
Log
.
e
(
TAG
,
e
.
getMessage
());
}
}
if
(
zipFile
!=
null
)
{
try
{
zipFile
.
close
();
}
catch
(
Exception
e
)
{
Log
.
e
(
TAG
,
e
.
getMessage
());
}
}
}
return
false
;
}
public
static
File
loadNativeBinary
(
Context
context
,
String
libname
,
File
destLocalFile
)
{
try
{
File
fileNativeBin
=
new
File
(
getNativeLibraryDir
(
context
),
libname
+
".so"
);
if
(!
fileNativeBin
.
exists
())
fileNativeBin
=
new
File
(
getNativeLibraryDir
(
context
),
"lib"
+
libname
+
".so"
);
if
(
fileNativeBin
.
exists
())
{
if
(
fileNativeBin
.
canExecute
())
return
fileNativeBin
;
else
{
setExecutable
(
fileNativeBin
);
if
(
fileNativeBin
.
canExecute
())
return
fileNativeBin
;