Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 0 additions & 18 deletions app/src/main/java/org/fptn/vpn/enums/HandlerMessageTypes.java

This file was deleted.

15 changes: 3 additions & 12 deletions app/src/main/java/org/fptn/vpn/services/CustomVpnConnection.java
Original file line number Diff line number Diff line change
Expand Up @@ -11,16 +11,13 @@
import android.net.IpPrefix;
import android.net.VpnService;
import android.os.Build;
import android.os.Message;
import android.os.ParcelFileDescriptor;
import android.util.Log;

import org.fptn.vpn.database.model.FptnServerDto;
import org.fptn.vpn.enums.BypassCensorshipMethod;
import org.fptn.vpn.enums.ConnectionState;
import org.fptn.vpn.enums.HandlerMessageTypes;
import org.fptn.vpn.enums.NetworkType;
import org.fptn.vpn.enums.TLSHandshakeObfuscation;
import org.fptn.vpn.services.websocket.WebSocketAlreadyShutdownException;
import org.fptn.vpn.services.websocket.WebSocketClientWrapper;
import org.fptn.vpn.utils.DataRateCalculator;
Expand All @@ -47,7 +44,6 @@

import inet.ipaddr.IPAddress;
import inet.ipaddr.IPAddressString;
import kotlin.Triple;
import lombok.Getter;
import lombok.Setter;

Expand Down Expand Up @@ -314,20 +310,15 @@ private void cancelReconnectTask() {
}

private void sendExceptionToService(PVNClientException exception) {
service.getHandler().sendMessage(Message.obtain(service.getHandler(), HandlerMessageTypes.ERROR.getValue(), connectionId, 0, exception));
service.sendExceptionToService(exception);
}

private void sendSpeedInfoAndDurationToService(String downloadSpeed, String uploadSpeed, long duration) {
service.getHandler().sendMessage(
Message.obtain(service.getHandler(), HandlerMessageTypes.SPEED_INFO.getValue(), connectionId, 0,
new Triple<>(downloadSpeed, uploadSpeed, duration))
);
service.updateSpeedInfo(downloadSpeed, uploadSpeed, duration);
}

private void sendConnectionStateToService(ConnectionState connectionState) {
service.getHandler().sendMessage(
Message.obtain(service.getHandler(), HandlerMessageTypes.CONNECTION_STATE.getValue(), connectionId, reconnectCount.get(), connectionState)
);
service.updateConnectionState(connectionState, reconnectCount.get());
}

private boolean isTunInterfaceValid(ParcelFileDescriptor vpnInterface) {
Expand Down
95 changes: 23 additions & 72 deletions app/src/main/java/org/fptn/vpn/services/CustomVpnService.java
Original file line number Diff line number Diff line change
Expand Up @@ -20,9 +20,7 @@
import android.net.VpnService;
import android.os.Binder;
import android.os.Build;
import android.os.Handler;
import android.os.IBinder;
import android.os.Message;
import android.os.PowerManager;
import android.os.SystemClock;
import android.service.quicksettings.TileService;
Expand All @@ -37,7 +35,6 @@
import org.fptn.vpn.database.model.FptnServerDto;
import org.fptn.vpn.enums.BypassCensorshipMethod;
import org.fptn.vpn.enums.ConnectionState;
import org.fptn.vpn.enums.HandlerMessageTypes;
import org.fptn.vpn.enums.NetworkType;
import org.fptn.vpn.repository.FptnServerRepository;
import org.fptn.vpn.services.tile.FptnTileService;
Expand All @@ -49,7 +46,6 @@
import org.fptn.vpn.vpnclient.exception.ErrorCode;
import org.fptn.vpn.vpnclient.exception.PVNClientException;

import java.util.Arrays;
import java.util.List;
import java.util.Objects;
import java.util.Optional;
Expand All @@ -62,7 +58,7 @@
import kotlin.Triple;
import lombok.Getter;

public class CustomVpnService extends VpnService implements Handler.Callback {
public class CustomVpnService extends VpnService {
private static final String TAG = CustomVpnService.class.getSimpleName();

public static final String ACTION_CONNECT = "CustomVpnService:CONNECT";
Expand All @@ -75,10 +71,6 @@ public class CustomVpnService extends VpnService implements Handler.Callback {
public static final String ACTION_RESET_ALARM = "CustomVpnService:ACTION_RESET_ALARM";
public static final int ONE_MINUTE = 60_000;

//Handler - queue of events from another threads, that need to process in this thread
@Getter
private Handler handler;

private final AtomicReference<CustomVpnConnection> activeConnection = new AtomicReference<>();

private final AtomicInteger nextConnectionId = new AtomicInteger(1);
Expand Down Expand Up @@ -117,6 +109,28 @@ public static void bindService(Context context, ServiceConnection connection) {
context.bindService(intent, connection, BIND_AUTO_CREATE);
}

public void updateSpeedInfo(String downloadSpeed, String uploadSpeed, long duration) {
if (serviceStateMutableLiveData.getValue().getConnectionState() == ConnectionState.CONNECTED) {
updateNotificationWithMessage(
String.format("%s %s", getString(R.string.connected_to), getActionConnectServerInfo()),
String.format(getString(R.string.download_upload_speed_pattern), downloadSpeed, uploadSpeed)
);

speedAndDurationMutableLiveData.postValue(new Triple<>(downloadSpeed, uploadSpeed, duration));
}
}

public void sendExceptionToService(PVNClientException exception) {
disconnect(exception);
if (Objects.equals(exception.errorCode, ErrorCode.RECONNECTING_FAILED)) {
showReconnectionFailedNotification();
}
}

public void updateConnectionState(ConnectionState connectionState, int reconnectionCount) {
switchState(connectionState, reconnectionCount);
}

public class LocalBinder extends Binder {
public CustomVpnService getService() {
return CustomVpnService.this;
Expand Down Expand Up @@ -160,10 +174,6 @@ public synchronized static void startToDisconnect(Context context) {
@Override
public void onCreate() {
Log.i(TAG, "CustomVpnService.onCreate() Thread.Id: " + Thread.currentThread().getId());
// The handler is only used to show messages.
if (handler == null) {
handler = new Handler(this);
}
// pending intent for open MainActivity on tap
launchMainActivityPendingIntent = PendingIntent.getActivity(this, 0,
new Intent(this, HomeActivity.class),
Expand Down Expand Up @@ -419,49 +429,6 @@ private void setConnectionState(ConnectionState connectionState, PVNClientExcept
.build());
}

@Override
public boolean handleMessage(@NonNull Message message) {
Log.d(TAG, "handleMessage: " + message);

/* Check connectionId in message to exclude false positive change state UI on dead connection */
int connectionId = message.arg1;
if (Optional.ofNullable(activeConnection.get()).map(CustomVpnConnection::getConnectionId).orElse(-1) == connectionId) {
HandlerMessageTypes type = Arrays.stream(HandlerMessageTypes.values()).filter(t -> t.getValue() == message.what).findFirst().orElse(HandlerMessageTypes.UNKNOWN);
switch (type) {
case SPEED_INFO:
if (serviceStateMutableLiveData.getValue().getConnectionState() == ConnectionState.CONNECTED) {
Triple<String, String, Long> speedAndDuration = (Triple<String, String, Long>) message.obj;
String downloadSpeed = speedAndDuration.getFirst();
String uploadSpeed = speedAndDuration.getSecond();

updateNotificationWithMessage(
String.format("%s %s", getString(R.string.connected_to), getActionConnectServerInfo()),
String.format(getString(R.string.download_upload_speed_pattern), downloadSpeed, uploadSpeed)
);

speedAndDurationMutableLiveData.postValue(speedAndDuration);
}
break;
case CONNECTION_STATE:
ConnectionState connectionState = (ConnectionState) message.obj;
int reconnectionCount = message.arg2;

switchState(connectionState, reconnectionCount);
break;
case ERROR:
PVNClientException exception = (PVNClientException) message.obj;
disconnect(exception);
if (Objects.equals(exception.errorCode, ErrorCode.RECONNECTING_FAILED)) {
showReconnectionFailedNotification();
}
break;
default:
Log.e(TAG, "unexpected message: " + message);
}
}
return true;
}

private void connect(FptnServerDto fptnServerDto, String sniHostname) {
// Moving VPNService to foreground to give it higher priority in system
startForegroundWithNotification(getString(R.string.connecting_to) + fptnServerDto.getServerInfo());
Expand Down Expand Up @@ -594,22 +561,6 @@ private void startForegroundWithNotification(String title) {
}
}

// private void startForegroundWithNotification(String title) {
// if (!isNotificationAllowed) {
// return;
// }
//
// NotificationUtils.configureNotificationChannel(this);
// Notification notification = createNotification(title, "");
//
// if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.UPSIDE_DOWN_CAKE) {
// startForeground(Constants.MAIN_CONNECTED_NOTIFICATION_ID, notification,
// ServiceInfo.FOREGROUND_SERVICE_TYPE_CONNECTED_DEVICE);
// } else {
// startForeground(Constants.MAIN_CONNECTED_NOTIFICATION_ID, notification);
// }
// }

private void updateNotificationWithMessage(String title, String message) {
if (!isNotificationAllowed) {
return;
Expand Down
Loading