diff --git a/core/schemas/com.github.shadowsocks.database.PrivateDatabase/29.json b/core/schemas/com.github.shadowsocks.database.PrivateDatabase/29.json
index 5a695600e7..8251c64540 100644
--- a/core/schemas/com.github.shadowsocks.database.PrivateDatabase/29.json
+++ b/core/schemas/com.github.shadowsocks.database.PrivateDatabase/29.json
@@ -2,11 +2,11 @@
"formatVersion": 1,
"database": {
"version": 29,
- "identityHash": "5b5c55a1277c63e14416316f9198ed43",
+ "identityHash": "edf35c5851b4cb55bb5dbbf278199450",
"entities": [
{
"tableName": "Profile",
- "createSql": "CREATE TABLE IF NOT EXISTS `${TABLE_NAME}` (`id` INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL, `name` TEXT, `host` TEXT NOT NULL, `remotePort` INTEGER NOT NULL, `password` TEXT NOT NULL, `method` TEXT NOT NULL, `route` TEXT NOT NULL, `remoteDns` TEXT NOT NULL, `proxyApps` INTEGER NOT NULL, `bypass` INTEGER NOT NULL, `udpdns` INTEGER NOT NULL, `ipv6` INTEGER NOT NULL, `metered` INTEGER NOT NULL, `individual` TEXT NOT NULL, `plugin` TEXT, `udpFallback` INTEGER, `subscription` INTEGER NOT NULL, `tx` INTEGER NOT NULL, `rx` INTEGER NOT NULL, `userOrder` INTEGER NOT NULL)",
+ "createSql": "CREATE TABLE IF NOT EXISTS `${TABLE_NAME}` (`id` INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL, `name` TEXT, `host` TEXT NOT NULL, `remotePort` INTEGER NOT NULL, `password` TEXT NOT NULL, `method` TEXT NOT NULL, `route` TEXT NOT NULL, `remoteDns` TEXT NOT NULL, `proxyApps` INTEGER NOT NULL, `bypass` INTEGER NOT NULL, `udpdns` INTEGER NOT NULL, `ipv6` INTEGER NOT NULL, `metered` INTEGER NOT NULL, `individual` TEXT NOT NULL, `plugin` TEXT, `udpFallback` INTEGER, `optimizeBuffers` INTEGER NOT NULL, `subscription` INTEGER NOT NULL, `tx` INTEGER NOT NULL, `rx` INTEGER NOT NULL, `userOrder` INTEGER NOT NULL)",
"fields": [
{
"fieldPath": "id",
@@ -104,6 +104,12 @@
"affinity": "INTEGER",
"notNull": false
},
+ {
+ "fieldPath": "optimizeBuffers",
+ "columnName": "optimizeBuffers",
+ "affinity": "INTEGER",
+ "notNull": true
+ },
{
"fieldPath": "subscription",
"columnName": "subscription",
@@ -130,10 +136,10 @@
}
],
"primaryKey": {
+ "autoGenerate": true,
"columnNames": [
"id"
- ],
- "autoGenerate": true
+ ]
},
"indices": [],
"foreignKeys": []
@@ -162,10 +168,10 @@
}
],
"primaryKey": {
+ "autoGenerate": false,
"columnNames": [
"key"
- ],
- "autoGenerate": false
+ ]
},
"indices": [],
"foreignKeys": []
@@ -174,7 +180,7 @@
"views": [],
"setupQueries": [
"CREATE TABLE IF NOT EXISTS room_master_table (id INTEGER PRIMARY KEY,identity_hash TEXT)",
- "INSERT OR REPLACE INTO room_master_table (id,identity_hash) VALUES(42, '5b5c55a1277c63e14416316f9198ed43')"
+ "INSERT OR REPLACE INTO room_master_table (id,identity_hash) VALUES(42, 'edf35c5851b4cb55bb5dbbf278199450')"
]
}
}
\ No newline at end of file
diff --git a/core/src/main/java/com/github/shadowsocks/bg/ProxyInstance.kt b/core/src/main/java/com/github/shadowsocks/bg/ProxyInstance.kt
index 05f834707b..ceff44109a 100644
--- a/core/src/main/java/com/github/shadowsocks/bg/ProxyInstance.kt
+++ b/core/src/main/java/com/github/shadowsocks/bg/ProxyInstance.kt
@@ -117,10 +117,22 @@ class ProxyInstance(val profile: Profile, private val route: String = profile.ro
val cmd = arrayListOf(
File((service as Context).applicationInfo.nativeLibraryDir, Executable.SS_LOCAL).absolutePath,
"--stat-path", stat.absolutePath,
- "-c", configFile.absolutePath,
+ "-c", configFile.absolutePath
)
- if (service.isVpnService) cmd += "--vpn"
+ if (profile.optimizeBuffers) {
+ cmd += "--inbound-send-buffer-size 16384"
+ cmd += "--inbound-recv-buffer-size 16384"
+
+ if (profile.plugin?.isNotBlank() == true) {
+ cmd += "--outbound-send-buffer-size 16384"
+ cmd += "--outbound-recv-buffer-size 16384"
+ }
+ }
+
+ if (service.isVpnService) {
+ cmd += "--vpn"
+ }
if (route != Acl.ALL) {
cmd += "--acl"
diff --git a/core/src/main/java/com/github/shadowsocks/database/Profile.kt b/core/src/main/java/com/github/shadowsocks/database/Profile.kt
index bae60e1066..d1f95a1836 100644
--- a/core/src/main/java/com/github/shadowsocks/database/Profile.kt
+++ b/core/src/main/java/com/github/shadowsocks/database/Profile.kt
@@ -70,6 +70,7 @@ data class Profile(
var individual: String = "",
var plugin: String? = null,
var udpFallback: Long? = null,
+ var optimizeBuffers: Boolean = true,
// managed fields
var subscription: SubscriptionStatus = SubscriptionStatus.UserConfigured,
@@ -355,6 +356,7 @@ data class Profile(
DataStore.individual = individual
DataStore.plugin = plugin ?: ""
DataStore.udpFallback = udpFallback
+ DataStore.optimizeBuffers = optimizeBuffers
DataStore.privateStore.remove(Key.dirty)
}
@@ -378,5 +380,6 @@ data class Profile(
individual = DataStore.individual
plugin = DataStore.plugin
udpFallback = DataStore.udpFallback
+ optimizeBuffers = DataStore.optimizeBuffers
}
}
diff --git a/core/src/main/java/com/github/shadowsocks/preference/DataStore.kt b/core/src/main/java/com/github/shadowsocks/preference/DataStore.kt
index a523681f74..c6fd940c5c 100644
--- a/core/src/main/java/com/github/shadowsocks/preference/DataStore.kt
+++ b/core/src/main/java/com/github/shadowsocks/preference/DataStore.kt
@@ -104,6 +104,9 @@ object DataStore : OnPreferenceDataStoreChangeListener {
var udpFallback: Long?
get() = privateStore.getLong(Key.udpFallback)
set(value) = privateStore.putLong(Key.udpFallback, value)
+ var optimizeBuffers: Boolean
+ get() = privateStore.getBoolean(Key.optimizeBuffers) ?: true
+ set(value) = privateStore.putBoolean(Key.optimizeBuffers, value)
var dirty: Boolean
get() = privateStore.getBoolean(Key.dirty) ?: false
set(value) = privateStore.putBoolean(Key.dirty, value)
diff --git a/core/src/main/java/com/github/shadowsocks/utils/Constants.kt b/core/src/main/java/com/github/shadowsocks/utils/Constants.kt
index 52b6de20ec..b48f54bbd8 100644
--- a/core/src/main/java/com/github/shadowsocks/utils/Constants.kt
+++ b/core/src/main/java/com/github/shadowsocks/utils/Constants.kt
@@ -61,6 +61,7 @@ object Key {
const val plugin = "plugin"
const val pluginConfigure = "plugin.configure"
const val udpFallback = "udpFallback"
+ const val optimizeBuffers = "optimizeBuffers";
const val dirty = "profileDirty"
diff --git a/core/src/main/res/values-ar/strings.xml b/core/src/main/res/values-ar/strings.xml
index 32c3815094..414dce3b2b 100644
--- a/core/src/main/res/values-ar/strings.xml
+++ b/core/src/main/res/values-ar/strings.xml
@@ -34,4 +34,6 @@
"المنفذ"
"كلمة المرور"
"طريقة التشفير"
+ حسِن مخازن الذاكرة ل TCP
+ يعالج مشكلة نفاذ الوقت اثناء الرفع نتيجة تضخم مخازن الذاكرة
\ No newline at end of file
diff --git a/core/src/main/res/values-de/strings.xml b/core/src/main/res/values-de/strings.xml
index 8794f90a91..eeedbdeede 100644
--- a/core/src/main/res/values-de/strings.xml
+++ b/core/src/main/res/values-de/strings.xml
@@ -39,6 +39,7 @@ Empfangen: \t%4$s\t↓\t%2$s"
"Verschlüsselungsmethode"
+ TCP-Puffer optimieren
"IPv6-Route"
"Leite IPv6-Traffic zu Remote um"
"GFW-Liste"
@@ -49,6 +50,7 @@ Empfangen: \t%4$s\t↓\t%2$s"
"Aktiviere um ausgewählte Apps zu umgehen"
"Automatisch verbinden"
"Starte Shadowsocks bei Systemstart/nach App-Update automatisch, falls es zuvor aktiv war"
+ Upload-Zeitüberschreitung (Bufferbloat) beheben
"Umschalten benötigt eventuell ROOT-Zugriff"
"Nicht unterstützte Kernel-Version: %s < 3.7.1"
"Sende DNS über UDP"
diff --git a/core/src/main/res/values-es/strings.xml b/core/src/main/res/values-es/strings.xml
index 63d8ee9a04..54911d6cd5 100644
--- a/core/src/main/res/values-es/strings.xml
+++ b/core/src/main/res/values-es/strings.xml
@@ -40,6 +40,7 @@ Recibido: \t%4$s\t↓\t%2$s"
"Método de Cifrado"
+ Optimizar buffers TCP
"Ruta IPv6"
"Redireccionar tráfico IPv6 a ruta"
"Ruta"
@@ -54,6 +55,7 @@ Recibido: \t%4$s\t↓\t%2$s"
"Activar Shadowsocks al iniciar"
+ Corregir el error de tiempo de espera de carga debido a bufferbloat
"Versión del Núcleo sin soporte: %s < 3.7.1"
"Enviar DNS sobre UDP"
diff --git a/core/src/main/res/values-fa/strings.xml b/core/src/main/res/values-fa/strings.xml
index c38d4c7b58..eb027af4d4 100644
--- a/core/src/main/res/values-fa/strings.xml
+++ b/core/src/main/res/values-fa/strings.xml
@@ -41,6 +41,7 @@
"روش رمزگذاری"
+ بهینهسازی بافرهای TCP
"مسیر IPv6"
"ترافیک IPv6 را به سرور هدایت کن"
"مسیر"
@@ -52,6 +53,7 @@
"این گزینه را فعال کنید تا اپلیکیشنهای انتخاب شده از VPN استفاده نکنند"
"وصلشدن اتوماتیک"
"فعالشدن شدوساکس لحظه روشنشدن گوشی بروزرسانی شود اگر از قبل درحال اجرا بوده است"
+ رفع مشکل تایم اوت آپلود به دلیل بافرهای بزرگ
"تغییر وضعیت ممکن است به مجوز ROOT نیاز داشته باشد"
"نسخه هسته پشتیبانی نشده: %s <3.7.1"
"ارسال DNS از طریق UDP"
diff --git a/core/src/main/res/values-fr/strings.xml b/core/src/main/res/values-fr/strings.xml
index 18c1724d31..f7e91a86f3 100644
--- a/core/src/main/res/values-fr/strings.xml
+++ b/core/src/main/res/values-fr/strings.xml
@@ -40,6 +40,7 @@ Reçu : \t\t\t%4$s\t↓\t%2$s"
"Méthode d'Encryption"
+ Optimiser les tampons TCP
"Route IPv6"
"Rediriger le trafic IPv6 vers le serveur distant"
"Route"
@@ -57,6 +58,7 @@ Reçu : \t\t\t%4$s\t↓\t%2$s"
"Activer Shadowsocks au démarrage"
+ Résoudre le problème de délai d\'envoi lié au bufferbloat
"Activer nécessite la permission ROOT"
"Version du noyau non supportée : %s <3.7.1"
diff --git a/core/src/main/res/values-ja/strings.xml b/core/src/main/res/values-ja/strings.xml
index 5bd153c1bf..39bd5ab3fc 100644
--- a/core/src/main/res/values-ja/strings.xml
+++ b/core/src/main/res/values-ja/strings.xml
@@ -42,6 +42,7 @@
"暗号化方式"
+ TCP バッファを最適化
"IPv6 プロキシ"
"リモートサーバーに IPv6 パケットを転送"
"プロキシ方式"
@@ -59,6 +60,7 @@
"システム起動時にバックグラウンドで本サービスを開始"
+ バッファブロートによるアップロード遅延を解消する
"使用するには ROOT 権限が必要"
"ご利用のカーネルバージョンはサポートしておりません:%s < 3.7.1"
diff --git a/core/src/main/res/values-ko/strings.xml b/core/src/main/res/values-ko/strings.xml
index 5081943e40..22222f9890 100644
--- a/core/src/main/res/values-ko/strings.xml
+++ b/core/src/main/res/values-ko/strings.xml
@@ -39,6 +39,7 @@
"암호화 방법"
+ TCP 버퍼 최적화
"IPv6 라우팅"
"IPv6 트래픽도 원격으로 리다이렉트 합니다"
"라우팅 대상"
@@ -58,6 +59,7 @@
"장치가 켜질 때 Shadowsocks를 자동으로 활성화합니다"
+ 업로드 버퍼 크기 초과로 인한 시간 초과 해결
"루트 권한이 필요합니다"
"지원하지 않는 버전의 커널입니다: %s < 3.7.1"
diff --git a/core/src/main/res/values-ru/strings.xml b/core/src/main/res/values-ru/strings.xml
index e601fa3013..48ba925d7e 100644
--- a/core/src/main/res/values-ru/strings.xml
+++ b/core/src/main/res/values-ru/strings.xml
@@ -40,6 +40,7 @@
"Метод шифрования"
+ Оптимизировать буферы TCP
"Маршрутизация IPv6"
"Перенаправлять трафик IPv6 на удалённый сервер"
"Маршрут"
@@ -52,6 +53,7 @@
"Включите эту функцию для работы выбранных приложений в обход прокси"
"Автоподключение"
"Запускать Shadowsocks при включении/после обновления приложения, если оно было запущено до этого"
+ Устранить таймаут загрузки из-за переполнения буфера
"Переключение может запрашивать Root (права суперпользователя)"
"Неподдерживаемая версия ядра: %s < 3.7.1"
"Посылать DNS-запросы через UDP"
diff --git a/core/src/main/res/values-tr/strings.xml b/core/src/main/res/values-tr/strings.xml
index 63a0c99c10..d817df7671 100644
--- a/core/src/main/res/values-tr/strings.xml
+++ b/core/src/main/res/values-tr/strings.xml
@@ -37,6 +37,7 @@
"Uzaktan Port"
"Şifre"
"Şifreleme Methodu"
+ TCP Arabelleklerini Optimize Edin
"IPv6 trafiğini remote'a yönlendir"
"Rota"
"GFW Listesi"
@@ -53,6 +54,8 @@
"Shadowsocks'ı cihazı başlatırken aç"
+ Aşırı boyutlu arabelleklerden kaynaklanan yükleme zaman aşımını düzeltin.
+
"Açıp kapamak için ROOT yetkisi gerekiyor"
"Desteklenmeyen kernel sürümü: %s < 3.7.1"
diff --git a/core/src/main/res/values-uk/strings.xml b/core/src/main/res/values-uk/strings.xml
index 921e508512..910e02ab09 100644
--- a/core/src/main/res/values-uk/strings.xml
+++ b/core/src/main/res/values-uk/strings.xml
@@ -80,6 +80,7 @@
"Використовувати поточний профіль"
+ Виправити таймаут завантаження через завеликі буфери
"Надіслано:"
"Отримано:"
@@ -92,6 +93,7 @@
"Власні правила"
"Додати правило…"
"Редагувати правило"
+ Оптимізувати буфери TCP
"Всі"
"Оминати локальні мережі"
"Оминати Китай"
diff --git a/core/src/main/res/values-zh-rCN/strings.xml b/core/src/main/res/values-zh-rCN/strings.xml
index a42055ecdb..1174a6744b 100644
--- a/core/src/main/res/values-zh-rCN/strings.xml
+++ b/core/src/main/res/values-zh-rCN/strings.xml
@@ -40,6 +40,7 @@
"加密方式"
+ 优化 TCP 缓冲区
"IPv6 路由"
"转发 IPv6 流量到远程服务器"
"路由"
@@ -51,6 +52,7 @@
"绕过选择的应用"
"自动连接"
"系统启动或应用更新后自动恢复运行"
+ 解决因缓冲区过大导致的上传超时问题
"切换可能需要 ROOT 权限"
"不支持的内核版本: %s < 3.7.1"
"使用 UDP DNS"
diff --git a/core/src/main/res/values-zh-rTW/strings.xml b/core/src/main/res/values-zh-rTW/strings.xml
index 76b5fa6a54..a728c4c707 100644
--- a/core/src/main/res/values-zh-rTW/strings.xml
+++ b/core/src/main/res/values-zh-rTW/strings.xml
@@ -41,6 +41,7 @@
"加密方法"
+ 最佳化 TCP 緩衝區
"IPv6 路由"
"向遠端重新導向 IPv6 流量"
"路由"
@@ -58,6 +59,7 @@
"在裝置啟動時啟用 Shadowsocks"
+ 修正因緩衝區過大導致上傳逾時的問題
"切換需要 ROOT 權限"
"不支援的核心版本:%s < 3.7.1"
diff --git a/core/src/main/res/values/strings.xml b/core/src/main/res/values/strings.xml
index 04ed7d9d67..8fb5180a50 100644
--- a/core/src/main/res/values/strings.xml
+++ b/core/src/main/res/values/strings.xml
@@ -32,6 +32,8 @@
Remote Port
Password
Encrypt Method
+ Optimize TCP Buffers
+ Fix upload timeout (bufferbloat)
IPv6 Route
diff --git a/mobile/src/main/java/com/github/shadowsocks/ProfileConfigFragment.kt b/mobile/src/main/java/com/github/shadowsocks/ProfileConfigFragment.kt
index 8ca2d21c4d..f238097ec1 100644
--- a/mobile/src/main/java/com/github/shadowsocks/ProfileConfigFragment.kt
+++ b/mobile/src/main/java/com/github/shadowsocks/ProfileConfigFragment.kt
@@ -79,6 +79,7 @@ class ProfileConfigFragment : PreferenceFragmentCompat(),
private lateinit var pluginConfiguration: PluginConfiguration
private lateinit var receiver: BroadcastReceiver
private lateinit var udpFallback: Preference
+ private lateinit var optimizeBuffers: SwitchPreference
private fun makeDirt() {
DataStore.dirty = true
@@ -115,6 +116,8 @@ class ProfileConfigFragment : PreferenceFragmentCompat(),
pluginConfiguration = PluginConfiguration(DataStore.plugin)
initPlugins()
udpFallback = findPreference(Key.udpFallback)!!
+ optimizeBuffers = findPreference(Key.optimizeBuffers)!!
+ optimizeBuffers.isChecked = DataStore.optimizeBuffers
DataStore.privateStore.registerChangeListener(this)
val profile = ProfileManager.getProfile(profileId) ?: Profile()
diff --git a/mobile/src/main/res/xml/pref_profile.xml b/mobile/src/main/res/xml/pref_profile.xml
index 5db0dd19a3..64f2891d83 100644
--- a/mobile/src/main/res/xml/pref_profile.xml
+++ b/mobile/src/main/res/xml/pref_profile.xml
@@ -65,8 +65,11 @@
app:key="remoteDns"
app:icon="@drawable/ic_action_dns"
app:title="@string/remote_dns"
- app:useSimpleSummaryProvider="true"/>
-
+ app:useSimpleSummaryProvider="true" />
+