Commit f6841848 authored by Max Lv's avatar Max Lv

chnroute works perfectly without root on lollipop

parent 52cb1506
...@@ -46,7 +46,6 @@ import java.util.{Timer, TimerTask} ...@@ -46,7 +46,6 @@ import java.util.{Timer, TimerTask}
import android.app.{Notification, NotificationManager, PendingIntent, Service} import android.app.{Notification, NotificationManager, PendingIntent, Service}
import android.content._ import android.content._
import android.content.pm.{PackageInfo, PackageManager} import android.content.pm.{PackageInfo, PackageManager}
import android.graphics.Color
import android.net.TrafficStats import android.net.TrafficStats
import android.os._ import android.os._
import android.support.v4.app.NotificationCompat import android.support.v4.app.NotificationCompat
......
...@@ -75,12 +75,28 @@ class ShadowsocksVpnService extends VpnService with BaseService { ...@@ -75,12 +75,28 @@ class ShadowsocksVpnService extends VpnService with BaseService {
private lazy val application = getApplication.asInstanceOf[ShadowsocksApplication] private lazy val application = getApplication.asInstanceOf[ShadowsocksApplication]
def isACLEnabled: Boolean = {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
true
} else {
false
}
}
def isByass(net: SubnetUtils): Boolean = { def isByass(net: SubnetUtils): Boolean = {
val info = net.getInfo val info = net.getInfo
info.isInRange(config.proxy) info.isInRange(config.proxy)
} }
def startShadowsocksDaemon() { def startShadowsocksDaemon() {
if (isACLEnabled && config.isGFWList) {
val chn_list: Array[String] = getResources.getStringArray(R.array.chn_list_full)
ConfigUtils.printToFile(new File(Path.BASE + "chn.acl"))(p => {
chn_list.foreach(item => p.println(item))
})
}
val cmd = new ArrayBuffer[String] val cmd = new ArrayBuffer[String]
cmd += ("ss-local" , "-u" cmd += ("ss-local" , "-u"
, "-b" , "127.0.0.1" , "-b" , "127.0.0.1"
...@@ -90,13 +106,34 @@ class ShadowsocksVpnService extends VpnService with BaseService { ...@@ -90,13 +106,34 @@ class ShadowsocksVpnService extends VpnService with BaseService {
, "-k" , config.sitekey , "-k" , config.sitekey
, "-m" , config.encMethod , "-m" , config.encMethod
, "-f" , Path.BASE + "ss-local.pid") , "-f" , Path.BASE + "ss-local.pid")
if (config.isGFWList && isACLEnabled) {
cmd += "--acl"
cmd += (Path.BASE + "chn.acl")
}
if (BuildConfig.DEBUG) Log.d(TAG, cmd.mkString(" ")) if (BuildConfig.DEBUG) Log.d(TAG, cmd.mkString(" "))
Core.sslocal(cmd.toArray) Core.sslocal(cmd.toArray)
} }
def startDnsTunnel() = {
val cmd = new ArrayBuffer[String]
cmd += ("ss-tunnel"
, "-b" , "127.0.0.1"
, "-l" , "8163"
, "-L" , "8.8.8.8:53"
, "-s" , config.proxy
, "-p" , config.remotePort.toString
, "-k" , config.sitekey
, "-m" , config.encMethod
, "-f" , Path.BASE + "ss-tunnel.pid")
if (BuildConfig.DEBUG) Log.d(TAG, cmd.mkString(" "))
Core.sstunnel(cmd.toArray)
}
def startDnsDaemon() { def startDnsDaemon() {
val conf = { val conf = {
ConfigUtils.PDNSD.format("0.0.0.0") ConfigUtils.PDNSD_LOCAL.format("0.0.0.0", 8163)
} }
ConfigUtils.printToFile(new File(Path.BASE + "pdnsd.conf"))(p => { ConfigUtils.printToFile(new File(Path.BASE + "pdnsd.conf"))(p => {
p.println(conf) p.println(conf)
...@@ -144,15 +181,17 @@ class ShadowsocksVpnService extends VpnService with BaseService { ...@@ -144,15 +181,17 @@ class ShadowsocksVpnService extends VpnService with BaseService {
} }
} }
if (!config.isBypassApps) { if (config.isBypassApps) {
builder.addAllowedApplication(this.getPackageName) builder.addDisallowedApplication(this.getPackageName)
} }
} else {
builder.addDisallowedApplication(this.getPackageName)
} }
} }
if (InetAddressUtils.isIPv6Address(config.proxy)) { if (InetAddressUtils.isIPv6Address(config.proxy)) {
builder.addRoute("0.0.0.0", 0) builder.addRoute("0.0.0.0", 0)
} else if (config.isGFWList) { } else if (!isACLEnabled && config.isGFWList) {
val gfwList = { val gfwList = {
if (Build.VERSION.SDK_INT == Build.VERSION_CODES.KITKAT) { if (Build.VERSION.SDK_INT == Build.VERSION_CODES.KITKAT) {
getResources.getStringArray(R.array.simple_list) getResources.getStringArray(R.array.simple_list)
...@@ -168,24 +207,28 @@ class ShadowsocksVpnService extends VpnService with BaseService { ...@@ -168,24 +207,28 @@ class ShadowsocksVpnService extends VpnService with BaseService {
} }
}) })
} else { } else {
for (i <- 1 to 223) { if (isACLEnabled) {
if (i != 26 && i != 127) { builder.addRoute("0.0.0.0", 0)
val addr = i.toString + ".0.0.0" } else {
val cidr = addr + "/8" for (i <- 1 to 223) {
val net = new SubnetUtils(cidr) if (i != 26 && i != 127) {
val addr = i.toString + ".0.0.0"
if (!isByass(net)) { val cidr = addr + "/8"
if (!InetAddress.getByName(addr).isSiteLocalAddress) { val net = new SubnetUtils(cidr)
builder.addRoute(addr, 8)
} if (!isByass(net)) {
} else { if (!InetAddress.getByName(addr).isSiteLocalAddress) {
for (j <- 0 to 255) { builder.addRoute(addr, 8)
val subAddr = i.toString + "." + j.toString + ".0.0" }
val subCidr = subAddr + "/16" } else {
val subNet = new SubnetUtils(subCidr) for (j <- 0 to 255) {
if (!isByass(subNet)) { val subAddr = i.toString + "." + j.toString + ".0.0"
if (!InetAddress.getByName(subAddr).isSiteLocalAddress) { val subCidr = subAddr + "/16"
builder.addRoute(subAddr, 16) val subNet = new SubnetUtils(subCidr)
if (!isByass(subNet)) {
if (!InetAddress.getByName(subAddr).isSiteLocalAddress) {
builder.addRoute(subAddr, 16)
}
} }
} }
} }
...@@ -236,7 +279,10 @@ class ShadowsocksVpnService extends VpnService with BaseService { ...@@ -236,7 +279,10 @@ class ShadowsocksVpnService extends VpnService with BaseService {
def handleConnection: Boolean = { def handleConnection: Boolean = {
startVpn() startVpn()
startShadowsocksDaemon() startShadowsocksDaemon()
if (!config.isUdpDns) startDnsDaemon() if (!config.isUdpDns) {
startDnsDaemon()
startDnsTunnel()
}
true true
} }
...@@ -264,13 +310,15 @@ class ShadowsocksVpnService extends VpnService with BaseService { ...@@ -264,13 +310,15 @@ class ShadowsocksVpnService extends VpnService with BaseService {
} }
def killProcesses() { def killProcesses() {
val ab = new ArrayBuffer[String] for (task <- Array("ss-local", "ss-tunnel", "tun2socks", "pdnsd")) {
try {
ab.append("kill -9 `cat " + Path.BASE + "ss-local.pid`") val pid = scala.io.Source.fromFile(Path.BASE + task + ".pid").mkString.trim.toInt
ab.append("kill -9 `cat " + Path.BASE + "tun2socks.pid`") Process.killProcess(pid)
ab.append("kill -15 `cat " + Path.BASE + "pdnsd.pid`") Log.d(TAG, "kill pid: " + pid)
} catch {
Console.runCommand(ab.toArray) case e: Throwable => Log.e(TAG, "unable to kill " + task, e)
}
}
} }
override def startRunner(c: Config) { override def startRunner(c: Config) {
......
...@@ -92,6 +92,38 @@ object ConfigUtils { ...@@ -92,6 +92,38 @@ object ConfigUtils {
|} |}
""".stripMargin """.stripMargin
val PDNSD_LOCAL =
"""
|global {
| perm_cache = 2048;
| cache_dir = "/data/data/com.github.shadowsocks";
| server_ip = %s;
| server_port = 8153;
| query_method = tcp_only;
| run_ipv4 = on;
| min_ttl = 15m;
| max_ttl = 1w;
| timeout = 10;
| daemon = on;
| pid_file = "/data/data/com.github.shadowsocks/pdnsd.pid";
|}
|
|server {
| label = "local";
| ip = 127.0.0.1;
| port = %d;
| timeout = 5;
|}
|
|rr {
| name=localhost;
| reverse=on;
| a=127.0.0.1;
| owner=localhost;
| soa=localhost,root.localhost,42,86400,900,86400,86400;
|}
""".stripMargin
val PDNSD_BYPASS = val PDNSD_BYPASS =
""" """
|global { |global {
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment