[optimize] merge network write
This commit is contained in:
@@ -278,15 +278,15 @@ class AbyssStream private constructor(
|
|||||||
private fun sendPlaintextChunk(plaintext: ByteArray) {
|
private fun sendPlaintextChunk(plaintext: ByteArray) {
|
||||||
if (closed) throw IllegalStateException("AbyssStream closed")
|
if (closed) throw IllegalStateException("AbyssStream closed")
|
||||||
|
|
||||||
val ciphertextAndTag: ByteArray
|
|
||||||
val nonce = ByteArray(NONCE_LEN)
|
val nonce = ByteArray(NONCE_LEN)
|
||||||
|
val ciphertextAndTag: ByteArray
|
||||||
val counterValue: Long
|
val counterValue: Long
|
||||||
synchronized(sendLock) {
|
synchronized(sendLock) {
|
||||||
counterValue = sendCounter.getAndIncrement()
|
counterValue = sendCounter.getAndIncrement()
|
||||||
}
|
}
|
||||||
|
|
||||||
System.arraycopy(sendSalt, 0, nonce, 0, NONCE_SALT_LEN)
|
System.arraycopy(sendSalt, 0, nonce, 0, NONCE_SALT_LEN)
|
||||||
val bb = ByteBuffer.wrap(nonce, NONCE_SALT_LEN, 8)
|
ByteBuffer.wrap(nonce, NONCE_SALT_LEN, 8).putLong(counterValue)
|
||||||
bb.putLong(counterValue)
|
|
||||||
|
|
||||||
try {
|
try {
|
||||||
ciphertextAndTag = aeadEncrypt(nonce, plaintext)
|
ciphertextAndTag = aeadEncrypt(nonce, plaintext)
|
||||||
@@ -295,17 +295,22 @@ class AbyssStream private constructor(
|
|||||||
}
|
}
|
||||||
|
|
||||||
val payloadLen = ciphertextAndTag.size
|
val payloadLen = ciphertextAndTag.size
|
||||||
val header = ByteBuffer.allocate(4).putInt(payloadLen).array()
|
// header + ciphertextAndTag 一次性合并
|
||||||
|
val packet = ByteBuffer.allocate(4 + payloadLen)
|
||||||
|
.putInt(payloadLen)
|
||||||
|
.put(ciphertextAndTag)
|
||||||
|
.array()
|
||||||
|
|
||||||
try {
|
try {
|
||||||
synchronized(output) {
|
synchronized(output) {
|
||||||
output.write(header)
|
output.write(packet)
|
||||||
if (payloadLen > 0) output.write(ciphertextAndTag)
|
|
||||||
output.flush()
|
output.flush()
|
||||||
}
|
}
|
||||||
} finally {
|
} finally {
|
||||||
// clear sensitive
|
// clear sensitive
|
||||||
ciphertextAndTag.fill(0)
|
ciphertextAndTag.fill(0)
|
||||||
plaintext.fill(0)
|
plaintext.fill(0)
|
||||||
|
packet.fill(0)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
package com.acitelight.aether.service
|
package com.acitelight.aether.service
|
||||||
|
|
||||||
|
|
||||||
|
import android.util.Log
|
||||||
import com.acitelight.aether.service.AuthManager.db64
|
import com.acitelight.aether.service.AuthManager.db64
|
||||||
import kotlinx.coroutines.*
|
import kotlinx.coroutines.*
|
||||||
import kotlinx.coroutines.flow.first
|
import kotlinx.coroutines.flow.first
|
||||||
@@ -102,7 +103,9 @@ class AbyssTunnelProxy @Inject constructor(
|
|||||||
val read = localIn.read(buffer)
|
val read = localIn.read(buffer)
|
||||||
if (read <= 0)
|
if (read <= 0)
|
||||||
break
|
break
|
||||||
|
Log.i("Delay Analyze", "Read $read Bytes from HttpClient")
|
||||||
abyss.write(buffer, 0, read)
|
abyss.write(buffer, 0, read)
|
||||||
|
Log.i("Delay Analyze", "Wrote $read Bytes to Remote Abyss")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -113,7 +116,9 @@ class AbyssTunnelProxy @Inject constructor(
|
|||||||
val n = abyss.read(buffer, 0, buffer.size)
|
val n = abyss.read(buffer, 0, buffer.size)
|
||||||
if (n <= 0)
|
if (n <= 0)
|
||||||
break
|
break
|
||||||
|
Log.i("Delay Analyze", "Read $n Bytes from Remote Abyss")
|
||||||
localOut.write(buffer, 0, n)
|
localOut.write(buffer, 0, n)
|
||||||
|
Log.i("Delay Analyze", "Wrote $n Bytes to HttpClient")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -224,6 +224,11 @@ object ApiClient {
|
|||||||
}
|
}
|
||||||
|
|
||||||
api = createRetrofit().create(ApiInterface::class.java)
|
api = createRetrofit().create(ApiInterface::class.java)
|
||||||
|
|
||||||
|
Log.i("Delay Analyze", "Start Abyss Hello")
|
||||||
|
val h = api!!.hello()
|
||||||
|
Log.i("Delay Analyze", "Abyss Hello: ${h.string()}")
|
||||||
|
|
||||||
return base
|
return base
|
||||||
} catch (e: Exception) {
|
} catch (e: Exception) {
|
||||||
api = null
|
api = null
|
||||||
|
|||||||
@@ -4,12 +4,14 @@ import com.acitelight.aether.model.BookMark
|
|||||||
import com.acitelight.aether.model.ChallengeResponse
|
import com.acitelight.aether.model.ChallengeResponse
|
||||||
import com.acitelight.aether.model.ComicResponse
|
import com.acitelight.aether.model.ComicResponse
|
||||||
import com.acitelight.aether.model.VideoResponse
|
import com.acitelight.aether.model.VideoResponse
|
||||||
|
import okhttp3.Response
|
||||||
import okhttp3.ResponseBody
|
import okhttp3.ResponseBody
|
||||||
import retrofit2.http.Body
|
import retrofit2.http.Body
|
||||||
import retrofit2.http.GET
|
import retrofit2.http.GET
|
||||||
import retrofit2.http.POST
|
import retrofit2.http.POST
|
||||||
import retrofit2.http.Path
|
import retrofit2.http.Path
|
||||||
import retrofit2.http.Query
|
import retrofit2.http.Query
|
||||||
|
import retrofit2.http.Streaming
|
||||||
|
|
||||||
interface ApiInterface {
|
interface ApiInterface {
|
||||||
@GET("api/video")
|
@GET("api/video")
|
||||||
@@ -56,4 +58,7 @@ interface ApiInterface {
|
|||||||
@Path("user") user: String,
|
@Path("user") user: String,
|
||||||
@Body challengeResponse: ChallengeResponse
|
@Body challengeResponse: ChallengeResponse
|
||||||
): ResponseBody
|
): ResponseBody
|
||||||
|
|
||||||
|
@GET("api/abyss")
|
||||||
|
suspend fun hello(): ResponseBody
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,5 +1,6 @@
|
|||||||
package com.acitelight.aether.view
|
package com.acitelight.aether.view
|
||||||
|
|
||||||
|
import android.util.Log
|
||||||
import android.widget.Toast
|
import android.widget.Toast
|
||||||
import androidx.compose.foundation.layout.Arrangement
|
import androidx.compose.foundation.layout.Arrangement
|
||||||
import androidx.compose.foundation.layout.Column
|
import androidx.compose.foundation.layout.Column
|
||||||
@@ -36,8 +37,13 @@ import androidx.compose.ui.text.input.KeyboardType
|
|||||||
import androidx.compose.ui.unit.dp
|
import androidx.compose.ui.unit.dp
|
||||||
import androidx.compose.ui.unit.sp
|
import androidx.compose.ui.unit.sp
|
||||||
import androidx.hilt.navigation.compose.hiltViewModel
|
import androidx.hilt.navigation.compose.hiltViewModel
|
||||||
|
import androidx.lifecycle.viewModelScope
|
||||||
import androidx.lifecycle.viewmodel.compose.viewModel
|
import androidx.lifecycle.viewmodel.compose.viewModel
|
||||||
|
import com.acitelight.aether.service.ApiClient.api
|
||||||
import com.acitelight.aether.viewModel.MeScreenViewModel
|
import com.acitelight.aether.viewModel.MeScreenViewModel
|
||||||
|
import kotlinx.coroutines.Dispatchers
|
||||||
|
import kotlinx.coroutines.launch
|
||||||
|
import kotlinx.coroutines.withContext
|
||||||
|
|
||||||
@Composable
|
@Composable
|
||||||
fun MeScreen(meScreenViewModel: MeScreenViewModel = hiltViewModel()) {
|
fun MeScreen(meScreenViewModel: MeScreenViewModel = hiltViewModel()) {
|
||||||
@@ -189,13 +195,28 @@ fun MeScreen(meScreenViewModel: MeScreenViewModel = hiltViewModel()) {
|
|||||||
Spacer(modifier = Modifier.height(24.dp))
|
Spacer(modifier = Modifier.height(24.dp))
|
||||||
|
|
||||||
// Save Button
|
// Save Button
|
||||||
Button(
|
Row{
|
||||||
onClick = {
|
Button(
|
||||||
meScreenViewModel.updateServer(url, cert, context)
|
onClick = {
|
||||||
},
|
meScreenViewModel.updateServer(url, cert, context)
|
||||||
modifier = Modifier.fillMaxWidth()
|
},
|
||||||
) {
|
modifier = Modifier.fillMaxWidth(0.5f)
|
||||||
Text("Save")
|
) {
|
||||||
|
Text("Save")
|
||||||
|
}
|
||||||
|
|
||||||
|
Button(
|
||||||
|
onClick = {
|
||||||
|
meScreenViewModel.viewModelScope.launch {
|
||||||
|
Log.i("Delay Analyze", "Start Abyss Hello")
|
||||||
|
val h = api!!.hello()
|
||||||
|
Log.i("Delay Analyze", "Abyss Hello: ${h.string()}")
|
||||||
|
}
|
||||||
|
},
|
||||||
|
modifier = Modifier.fillMaxWidth(0.5f)
|
||||||
|
) {
|
||||||
|
Text("Ping")
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user