Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
C
com.ccwangluo.accelerator
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
sheteng
com.ccwangluo.accelerator
Commits
93084f0e
Commit
93084f0e
authored
Dec 06, 2015
by
Mygod
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Ask for ROOT only when it's needed
parent
ac98caa4
Changes
13
Hide whitespace changes
Inline
Side-by-side
Showing
13 changed files
with
82 additions
and
112 deletions
+82
-112
src/main/res/values-zh/strings.xml
src/main/res/values-zh/strings.xml
+6
-3
src/main/res/values/strings.xml
src/main/res/values/strings.xml
+6
-3
src/main/res/xml/pref_all.xml
src/main/res/xml/pref_all.xml
+6
-4
src/main/scala/com/github/shadowsocks/AppManager.scala
src/main/scala/com/github/shadowsocks/AppManager.scala
+1
-3
src/main/scala/com/github/shadowsocks/Shadowsocks.scala
src/main/scala/com/github/shadowsocks/Shadowsocks.scala
+17
-26
src/main/scala/com/github/shadowsocks/ShadowsocksApplication.scala
...scala/com/github/shadowsocks/ShadowsocksApplication.scala
+2
-3
src/main/scala/com/github/shadowsocks/ShadowsocksNatService.scala
.../scala/com/github/shadowsocks/ShadowsocksNatService.scala
+10
-10
src/main/scala/com/github/shadowsocks/ShadowsocksSettings.scala
...in/scala/com/github/shadowsocks/ShadowsocksSettings.scala
+7
-10
src/main/scala/com/github/shadowsocks/ShadowsocksVpnService.scala
.../scala/com/github/shadowsocks/ShadowsocksVpnService.scala
+2
-4
src/main/scala/com/github/shadowsocks/package.scala
src/main/scala/com/github/shadowsocks/package.scala
+13
-0
src/main/scala/com/github/shadowsocks/preferences/NatSwitchPreference.scala
.../github/shadowsocks/preferences/NatSwitchPreference.scala
+0
-27
src/main/scala/com/github/shadowsocks/utils/Console.scala
src/main/scala/com/github/shadowsocks/utils/Console.scala
+4
-10
src/main/scala/com/github/shadowsocks/utils/Utils.scala
src/main/scala/com/github/shadowsocks/utils/Utils.scala
+8
-9
No files found.
src/main/res/values-zh/strings.xml
View file @
93084f0e
...
...
@@ -34,6 +34,8 @@
<string
name=
"auto_connect_summary"
>
随系统启动后台服务
</string>
<string
name=
"forward_success"
>
后台服务已开始运行。
</string>
<string
name=
"service_failed"
>
无法连接远程服务器
</string>
<string
name=
"nat_no_root"
>
NAT 模式需要 ROOT 权限
</string>
<string
name=
"switch_to_vpn"
>
切换到 VPN 模式
</string>
<string
name=
"stop"
>
停止服务
</string>
<string
name=
"stopping"
>
正在关闭……
</string>
<string
name=
"vpn_error"
>
后台服务启动失败:%s
</string>
...
...
@@ -52,14 +54,15 @@
<string
name=
"about"
>
关于
</string>
<string
name=
"about_title"
>
影梭(shadowsocks)%s
</string>
<string
name=
"flush_dnscache"
>
刷新 DNS 缓存
</string>
<string
name=
"flush_dnscache_summary_disabled"
>
需要 ROOT 权限
</string>
<string
name=
"flush_dnscache_summary"
>
只需在 NAT 模式下使用
</string>
<string
name=
"flush_dnscache_summary_root"
>
只需在 NAT 模式下使用,需要 ROOT 权限
</string>
<string
name=
"flush_dnscache_no_root"
>
在没有 ROOT 权限的情况下无法刷新 DNS 缓存
</string>
<string
name=
"flushing"
>
刷新中……
</string>
<string
name=
"qrcode"
>
二维码
</string>
<string
name=
"add_profile"
>
添加配置文件
</string>
<string
name=
"nat"
>
NAT 模式 (仅限调试)
</string>
<string
name=
"nat_summary"
>
从 VPN 模式切换为 NAT 模式
</string>
<string
name=
"nat_summary_no_root"
>
NAT 模式已禁用,需要 ROOT 权限
</string>
<string
name=
"nat_summary"
>
从 VPN 模式切换为 NAT 模式,需要 ROOT 权限
</string>
<string
name=
"udp_dns"
>
UDP 转发
</string>
<string
name=
"udp_dns_summary"
>
由远程服务器转发 UDP 协议的数据包
</string>
...
...
src/main/res/values/strings.xml
View file @
93084f0e
...
...
@@ -10,8 +10,7 @@
<string
name=
"profile"
>
Profile
</string>
<string
name=
"profile_summary"
>
Switch to another profile or add new profiles
</string>
<string
name=
"nat"
>
NAT mode (deprecated)
</string>
<string
name=
"nat_summary"
>
Use NAT mode instead of VPN mode
</string>
<string
name=
"nat_summary_no_root"
>
NAT mode is disabled without root
</string>
<string
name=
"nat_summary"
>
Use NAT mode instead of VPN mode. Requires ROOT permission.
</string>
<string
name=
"stat"
>
Network Traffic
</string>
<string
name=
"stat_summary"
>
Sent: \t\t\t\t\t%3$s\t↑\t%1$s/s\nReceived: \t%4$s\t↓\t%2$s/s
</string>
<string
name=
"stat_profiles"
>
\n%1$s↑\t%2$s↓
</string>
...
...
@@ -61,6 +60,8 @@
<!-- notification category -->
<string
name=
"forward_success"
>
Shadowsocks started.
</string>
<string
name=
"service_failed"
>
Failed to connect the remote server
</string>
<string
name=
"nat_no_root"
>
NAT mode requires ROOT permission
</string>
<string
name=
"switch_to_vpn"
>
Switch to VPN mode
</string>
<string
name=
"stop"
>
Stop the service
</string>
<string
name=
"stopping"
>
Shutting down…
</string>
<string
name=
"vpn_error"
>
%s
</string>
...
...
@@ -84,7 +85,9 @@
<string
name=
"about_title"
>
Shadowsocks %s
</string>
<string
name=
"qrcode"
>
QR Code
</string>
<string
name=
"flush_dnscache"
>
Flush DNS cache
</string>
<string
name=
"flush_dnscache_summary_disabled"
>
Requires ROOT permission
</string>
<string
name=
"flush_dnscache_summary"
>
Only useful in NAT mode
</string>
<string
name=
"flush_dnscache_summary_root"
>
Only useful in NAT mode. Requires ROOT permission.
</string>
<string
name=
"flush_dnscache_no_root"
>
Flush DNS cache cannot proceed without ROOT permission
</string>
<string
name=
"flushing"
>
Flushing
</string>
<string
name=
"add_profile"
>
Add Profile
</string>
<string
name=
"action_export"
>
Export to Clipboard
</string>
...
...
src/main/res/xml/pref_all.xml
View file @
93084f0e
...
...
@@ -83,12 +83,14 @@
android:summary=
"@string/auto_connect_summary"
android:title=
"@string/auto_connect"
/>
<
com.github.shadowsocks.preferences.Nat
SwitchPreference
android:key=
"isNAT"
android:title=
"@string/nat"
android:summary=
"@string/nat_summary"
/>
<SwitchPreference
android:key=
"isNAT"
android:title=
"@string/nat"
android:summary=
"@string/nat_summary"
/>
<Preference
android:key=
"recovery"
android:title=
"@string/recovery"
android:summary=
"@string/recovery_summary"
/>
<Preference
android:key=
"flush_dnscache"
android:title=
"@string/flush_dnscache"
/>
<Preference
android:key=
"flush_dnscache"
android:title=
"@string/flush_dnscache"
android:summary=
"@string/flush_dnscache_summary_root"
/>
<Preference
android:key=
"about"
android:title=
"@string/about"
/>
</PreferenceCategory>
...
...
src/main/scala/com/github/shadowsocks/AppManager.scala
View file @
93084f0e
...
...
@@ -58,8 +58,6 @@ import com.github.shadowsocks.utils.{Key, Utils}
import
scala.collection.JavaConversions._
import
scala.collection.mutable
import
scala.concurrent.ExecutionContext.Implicits.global
import
scala.concurrent.Future
import
scala.language.implicitConversions
object
AppManager
{
...
...
@@ -249,7 +247,7 @@ class AppManager extends AppCompatActivity with OnCheckedChangeListener with OnC
}
def
loadAppsAsync
()
{
Future
{
Throwable
Future
{
while
(!
appsLoading
)
loadApps
()
appsLoading
=
false
handler
.
post
(()
=>
{
...
...
src/main/scala/com/github/shadowsocks/Shadowsocks.scala
View file @
93084f0e
...
...
@@ -65,8 +65,6 @@ import com.github.shadowsocks.utils._
import
com.google.android.gms.ads.
{
AdRequest
,
AdSize
,
AdView
}
import
scala.collection.mutable.ArrayBuffer
import
scala.concurrent.ExecutionContext.Implicits.global
import
scala.concurrent.Future
object
Typefaces
{
def
get
(
c
:
Context
,
assetPath
:
String
)
:
Typeface
=
{
...
...
@@ -182,8 +180,13 @@ class Shadowsocks
handler
.
postDelayed
(()
=>
fabProgressCircle
.
hide
(),
1000
)
fab
.
setEnabled
(
true
)
changeSwitch
(
checked
=
false
)
if
(
m
!=
null
)
Snackbar
.
make
(
findViewById
(
android
.
R
.
id
.
content
),
getString
(
R
.
string
.
vpn_error
).
formatLocal
(
Locale
.
ENGLISH
,
m
),
Snackbar
.
LENGTH_LONG
).
show
if
(
m
!=
null
)
{
val
snackbar
=
Snackbar
.
make
(
findViewById
(
android
.
R
.
id
.
content
),
getString
(
R
.
string
.
vpn_error
).
formatLocal
(
Locale
.
ENGLISH
,
m
),
Snackbar
.
LENGTH_LONG
)
if
(
m
==
getString
(
R
.
string
.
nat_no_root
))
snackbar
.
setAction
(
R
.
string
.
switch_to_vpn
,
(
_
=>
preferences
.
natSwitch
.
setChecked
(
false
))
:
View.OnClickListener
)
snackbar
.
show
}
setPreferenceEnabled
(
enabled
=
true
)
case
State
.
STOPPING
=>
fab
.
setBackgroundTintList
(
greyTint
)
...
...
@@ -317,10 +320,10 @@ class Shadowsocks
cmd
.
append
(
"chmod 666 %s%s-vpn.pid"
.
formatLocal
(
Locale
.
ENGLISH
,
Path
.
BASE
,
task
))
}
if
(!
ShadowsocksApplication
.
isVpnEnabled
)
{
Console
.
runRootCommand
(
cmd
.
toArray
)
}
else
{
if
(
ShadowsocksApplication
.
isVpnEnabled
)
{
Console
.
runCommand
(
cmd
.
toArray
)
}
else
{
Console
.
runRootCommand
(
cmd
.
toArray
)
}
cmd
.
clear
()
...
...
@@ -341,8 +344,7 @@ class Shadowsocks
cmd
.
append
(
"rm -f %s%s-vpn.pid"
.
formatLocal
(
Locale
.
ENGLISH
,
Path
.
BASE
,
task
))
cmd
.
append
(
"rm -f %s%s-vpn.conf"
.
formatLocal
(
Locale
.
ENGLISH
,
Path
.
BASE
,
task
))
}
Console
.
runCommand
(
cmd
.
toArray
)
if
(!
ShadowsocksApplication
.
isVpnEnabled
)
{
if
(
ShadowsocksApplication
.
isVpnEnabled
)
Console
.
runCommand
(
cmd
.
toArray
)
else
{
Console
.
runRootCommand
(
cmd
.
toArray
)
Console
.
runRootCommand
(
Utils
.
getIptables
+
" -t nat -F OUTPUT"
)
}
...
...
@@ -361,7 +363,7 @@ class Shadowsocks
}
def
prepareStartService
()
{
Future
{
Throwable
Future
{
if
(
ShadowsocksApplication
.
isVpnEnabled
)
{
val
intent
=
VpnService
.
prepare
(
this
)
if
(
intent
!=
null
)
{
...
...
@@ -534,18 +536,6 @@ class Shadowsocks
handler
.
removeCallbacksAndMessages
(
null
)
}
def
copyToSystem
()
{
val
ab
=
new
ArrayBuffer
[
String
]
ab
.
append
(
"mount -o rw,remount -t yaffs2 /dev/block/mtdblock3 /system"
)
for
(
executable
<-
Shadowsocks
.
EXECUTABLES
)
{
ab
.
append
(
"cp %s%s /system/bin/"
.
formatLocal
(
Locale
.
ENGLISH
,
Path
.
BASE
,
executable
))
ab
.
append
(
"chmod 755 /system/bin/"
+
executable
)
ab
.
append
(
"chown root:shell /system/bin/"
+
executable
)
}
ab
.
append
(
"mount -o ro,remount -t yaffs2 /dev/block/mtdblock3 /system"
)
Console
.
runRootCommand
(
ab
.
toArray
)
}
def
install
()
{
copyAssets
(
System
.
getABI
)
...
...
@@ -565,7 +555,7 @@ class Shadowsocks
def
recovery
()
{
serviceStop
()
val
h
=
showProgress
(
R
.
string
.
recovering
)
Future
{
Throwable
Future
{
reset
()
h
.
sendEmptyMessage
(
0
)
}
...
...
@@ -573,8 +563,9 @@ class Shadowsocks
def
flushDnsCache
()
{
val
h
=
showProgress
(
R
.
string
.
flushing
)
Future
{
Utils
.
toggleAirplaneMode
(
getBaseContext
)
ThrowableFuture
{
if
(!
Utils
.
toggleAirplaneMode
(
getBaseContext
))
h
.
post
(()
=>
Snackbar
.
make
(
findViewById
(
android
.
R
.
id
.
content
),
R
.
string
.
flush_dnscache_no_root
,
Snackbar
.
LENGTH_LONG
).
show
)
h
.
sendEmptyMessage
(
0
)
}
}
...
...
@@ -595,7 +586,7 @@ class Shadowsocks
def
checkText
(
key
:
String
)
:
Boolean
=
{
val
text
=
ShadowsocksApplication
.
settings
.
getString
(
key
,
""
)
if
(
text
!=
null
&&
text
.
length
>
0
)
return
true
Snackbar
.
make
(
findViewById
(
android
.
R
.
id
.
content
),
getString
(
R
.
string
.
proxy_empty
)
,
Snackbar
.
LENGTH_LONG
).
show
Snackbar
.
make
(
findViewById
(
android
.
R
.
id
.
content
),
R
.
string
.
proxy_empty
,
Snackbar
.
LENGTH_LONG
).
show
false
}
...
...
src/main/scala/com/github/shadowsocks/ShadowsocksApplication.scala
View file @
93084f0e
...
...
@@ -46,7 +46,7 @@ import android.app.Application
import
android.content.pm.PackageManager
import
android.preference.PreferenceManager
import
com.github.shadowsocks.database.
{
DBHelper
,
ProfileManager
}
import
com.github.shadowsocks.utils.
{
Console
,
Key
,
Utils
}
import
com.github.shadowsocks.utils.
{
Key
,
Utils
}
import
com.google.android.gms.analytics.
{
GoogleAnalytics
,
HitBuilders
}
import
com.google.android.gms.common.api.ResultCallback
import
com.google.android.gms.tagmanager.
{
ContainerHolder
,
TagManager
}
...
...
@@ -60,8 +60,7 @@ object ShadowsocksApplication {
lazy
val
settings
=
PreferenceManager
.
getDefaultSharedPreferences
(
instance
)
lazy
val
profileManager
=
new
ProfileManager
(
settings
,
dbHelper
)
val
isRoot
=
Console
.
isRoot
def
isVpnEnabled
=
!(
isRoot
&&
settings
.
getBoolean
(
Key
.
isNAT
,
!
Utils
.
isLollipopOrAbove
))
def
isVpnEnabled
=
!
settings
.
getBoolean
(
Key
.
isNAT
,
false
)
def
getVersionName
=
try
{
instance
.
getPackageManager
.
getPackageInfo
(
instance
.
getPackageName
,
0
).
versionName
...
...
src/main/scala/com/github/shadowsocks/ShadowsocksNatService.scala
View file @
93084f0e
...
...
@@ -55,8 +55,6 @@ import com.github.shadowsocks.utils._
import
scala.collection.JavaConversions._
import
scala.collection.mutable.ArrayBuffer
import
scala.concurrent.ExecutionContext.Implicits.global
import
scala.concurrent.Future
class
ShadowsocksNatService
extends
BaseService
{
...
...
@@ -144,7 +142,7 @@ class ShadowsocksNatService extends BaseService {
})
Console
.
runRootCommand
(
cmdBuf
.
toArray
)
}
else
{
Console
.
runRootCommand
(
Array
(
"ndc resolver flushdefaultif"
,
"ndc resolver flushif wlan0"
)
)
Console
.
runRootCommand
(
"ndc resolver flushdefaultif"
,
"ndc resolver flushif wlan0"
)
}
}
...
...
@@ -384,12 +382,17 @@ class ShadowsocksNatService extends BaseService {
}
}
}
Console
.
runRootCommand
(
init_sb
.
toArray
)
Console
.
runRootCommand
(
http_sb
.
toArray
)
Console
.
runRootCommand
((
init_sb
++
http_sb
).
toArray
)
}
override
def
startRunner
(
config
:
Config
)
{
changeState
(
State
.
CONNECTING
)
if
(!
Console
.
isRoot
)
{
changeState
(
State
.
STOPPED
,
getString
(
R
.
string
.
nat_no_root
))
return
}
super
.
startRunner
(
config
)
// register close receiver
...
...
@@ -404,10 +407,7 @@ class ShadowsocksNatService extends BaseService {
ShadowsocksApplication
.
track
(
TAG
,
"start"
)
changeState
(
State
.
CONNECTING
)
Future
{
ThrowableFuture
{
if
(
config
.
proxy
==
"198.199.101.152"
)
{
val
holder
=
ShadowsocksApplication
.
containerHolder
try
{
...
...
@@ -465,7 +465,7 @@ class ShadowsocksNatService extends BaseService {
closeReceiver
=
null
}
notification
.
destroy
()
if
(
notification
!=
null
)
notification
.
destroy
()
ShadowsocksApplication
.
track
(
TAG
,
"stop"
)
...
...
src/main/scala/com/github/shadowsocks/ShadowsocksSettings.scala
View file @
93084f0e
...
...
@@ -14,6 +14,7 @@ import com.github.shadowsocks.utils.Key
// TODO: Move related logic here
class
ShadowsocksSettings
extends
PreferenceFragment
with
OnSharedPreferenceChangeListener
{
private
lazy
val
activity
=
getActivity
.
asInstanceOf
[
Shadowsocks
]
lazy
val
natSwitch
=
findPreference
(
Key
.
isNAT
).
asInstanceOf
[
SwitchPreference
]
private
var
isProxyApps
:
SwitchPreference
=
_
...
...
@@ -35,10 +36,8 @@ class ShadowsocksSettings extends PreferenceFragment with OnSharedPreferenceChan
})
val
flush
=
findPreference
(
"flush_dnscache"
)
if
(
Build
.
VERSION
.
SDK_INT
>=
17
&&
!
ShadowsocksApplication
.
isRoot
)
{
flush
.
setEnabled
(
false
)
flush
.
setSummary
(
R
.
string
.
flush_dnscache_summary_disabled
)
}
else
flush
.
setOnPreferenceClickListener
((
preference
:
Preference
)
=>
{
if
(
Build
.
VERSION
.
SDK_INT
<
17
)
flush
.
setSummary
(
R
.
string
.
flush_dnscache_summary
)
flush
.
setOnPreferenceClickListener
(
_
=>
{
ShadowsocksApplication
.
track
(
Shadowsocks
.
TAG
,
"flush_dnscache"
)
activity
.
flushDnsCache
()
true
...
...
@@ -73,12 +72,10 @@ class ShadowsocksSettings extends PreferenceFragment with OnSharedPreferenceChan
}
def
onSharedPreferenceChanged
(
sharedPreferences
:
SharedPreferences
,
key
:
String
)
=
key
match
{
case
Key
.
isNAT
=>
if
(
ShadowsocksApplication
.
isRoot
&&
activity
!=
null
)
{
activity
.
handler
.
post
(()
=>
{
activity
.
deattachService
activity
.
attachService
})
}
case
Key
.
isNAT
=>
activity
.
handler
.
post
(()
=>
{
activity
.
deattachService
activity
.
attachService
})
case
_
=>
}
}
src/main/scala/com/github/shadowsocks/ShadowsocksVpnService.scala
View file @
93084f0e
...
...
@@ -55,8 +55,6 @@ import org.apache.commons.net.util.SubnetUtils
import
scala.collection.JavaConversions._
import
scala.collection.mutable.ArrayBuffer
import
scala.concurrent.ExecutionContext.Implicits.global
import
scala.concurrent.Future
class
ShadowsocksVpnService
extends
VpnService
with
BaseService
{
val
TAG
=
"ShadowsocksVpnService"
...
...
@@ -122,7 +120,7 @@ class ShadowsocksVpnService extends VpnService with BaseService {
vpnThread
=
null
}
notification
.
destroy
()
if
(
notification
!=
null
)
notification
.
destroy
()
// channge the state
changeState
(
State
.
STOPPING
)
...
...
@@ -213,7 +211,7 @@ class ShadowsocksVpnService extends VpnService with BaseService {
changeState
(
State
.
CONNECTING
)
Future
{
Throwable
Future
{
if
(
config
.
proxy
==
"198.199.101.152"
)
{
val
holder
=
ShadowsocksApplication
.
containerHolder
try
{
...
...
src/main/scala/com/github/shadowsocks/package.scala
0 → 100644
View file @
93084f0e
package
com.github
import
scala.concurrent.ExecutionContext.Implicits.global
import
scala.concurrent.Future
/**
* @author Mygod
*/
package
object
shadowsocks
{
def
ThrowableFuture
[
T
](
f
:
=>
T
)
=
Future
(
f
)
onFailure
{
case
e
:
Throwable
=>
e
.
printStackTrace
()
}
}
src/main/scala/com/github/shadowsocks/preferences/NatSwitchPreference.scala
deleted
100644 → 0
View file @
ac98caa4
package
com.github.shadowsocks.preferences
import
android.content.Context
import
android.content.res.TypedArray
import
android.preference.SwitchPreference
import
android.util.AttributeSet
import
com.github.shadowsocks.
{
R
,
ShadowsocksApplication
}
/**
* TODO: No animations?
* @author Mygod
*/
final
class
NatSwitchPreference
(
context
:
Context
,
attrs
:
AttributeSet
)
extends
SwitchPreference
(
context
,
attrs
)
{
private
var
disabled
=
false
override
def
isEnabled
=
super
.
isEnabled
&&
!
disabled
override
def
setEnabled
(
b
:
Boolean
)
=
super
.
setEnabled
(
b
&&
!
disabled
)
if
(!
ShadowsocksApplication
.
isRoot
)
{
disabled
=
true
setEnabled
(
false
)
setSummary
(
R
.
string
.
nat_summary_no_root
)
}
override
def
onGetDefaultValue
(
a
:
TypedArray
,
index
:
Int
)
=
(!
ShadowsocksApplication
.
isVpnEnabled
).
asInstanceOf
[
AnyRef
]
}
src/main/scala/com/github/shadowsocks/utils/Console.scala
View file @
93084f0e
...
...
@@ -75,17 +75,11 @@ object Console {
shell
.
close
()
}
def
runRootCommand
(
command
:
String
)
:
String
=
runRootCommand
(
Array
(
command
))
def
runRootCommand
(
command
:
String
,
context
:
String
)
:
String
=
runRootCommand
(
Array
(
command
),
context
)
def
runRootCommand
(
commands
:
Array
[
String
])
:
String
=
runRootCommand
(
commands
,
"u:r:init_shell:s0"
)
def
runRootCommand
(
commands
:
Array
[
String
],
context
:
String
)
:
String
=
{
if
(!
isRoot
)
{
return
null
}
val
shell
=
openRootShell
(
context
)
def
runRootCommand
(
commands
:
String*
)
:
String
=
runRootCommand
(
commands
.
toArray
)
def
runRootCommand
(
commands
:
Array
[
String
])
:
String
=
{
val
shell
=
openRootShell
(
"u:r:init_shell:s0"
)
val
sb
=
new
StringBuilder
shell
.
addCommand
(
commands
,
0
,
((
commandCode
:
Int
,
exitCode
:
Int
,
output
:
util.List
[
String
]
)
=>
{
shell
.
addCommand
(
commands
,
0
,
((
_
,
exitCode
,
output
)
=>
{
if
(
exitCode
<
0
)
{
shell
.
close
()
}
else
{
...
...
src/main/scala/com/github/shadowsocks/utils/Utils.scala
View file @
93084f0e
...
...
@@ -140,12 +140,14 @@ object Utils {
}
// Blocked > 3 seconds
def
toggleAirplaneMode
(
context
:
Context
)
{
if
(
ShadowsocksApplication
.
isRoot
)
{
Console
.
runRootCommand
(
Array
(
"ndc resolver flushdefaultif"
,
"ndc resolver flushif wlan0"
))
def
toggleAirplaneMode
(
context
:
Context
)
=
{
if
(
Console
.
isRoot
)
{
Console
.
runRootCommand
(
"ndc resolver flushdefaultif"
,
"ndc resolver flushif wlan0"
)
true
}
else
if
(
Build
.
VERSION
.
SDK_INT
<
17
)
{
toggleBelowApiLevel17
(
context
)
}
true
}
else
false
}
//noinspection ScalaDeprecation
...
...
@@ -305,8 +307,7 @@ object Utils {
var
compatible
:
Boolean
=
false
var
version
:
Boolean
=
false
val
command
=
Array
(
iptables
+
" --version"
,
iptables
+
" -L -t nat -n"
)
val
lines
=
Console
.
runRootCommand
(
command
)
val
lines
=
Console
.
runRootCommand
(
iptables
+
" --version"
,
iptables
+
" -L -t nat -n"
)
if
(
lines
==
null
)
return
if
(
lines
.
contains
(
"OUTPUT"
))
{
...
...
@@ -384,9 +385,7 @@ object Utils {
hasRedirectSupport
=
1
val
command
=
Utils
.
getIptables
+
" -t nat -A OUTPUT -p udp --dport 54 -j REDIRECT --to 8154"
val
lines
=
Console
.
runRootCommand
(
command
)
Console
.
runRootCommand
(
command
.
replace
(
"-A"
,
"-D"
))
val
lines
=
Console
.
runRootCommand
(
command
,
command
.
replace
(
"-A"
,
"-D"
))
if
(
lines
==
null
)
return
if
(
lines
.
contains
(
"No chain/target/match"
))
{
hasRedirectSupport
=
0
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment