diff --git a/app/build.gradle b/app/build.gradle index b7b5db6..32faffc 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -10,8 +10,8 @@ android { applicationId "com.vectras.vm" minSdk minApi targetSdk targetApi - versionCode 35 - versionName "3.3.1" + versionCode 36 + versionName "3.3.2" testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner" multiDexEnabled true } diff --git a/app/src/main/java/com/termux/app/BackgroundJob.java b/app/src/main/java/com/termux/app/BackgroundJob.java index cd7f7d1..00d5340 100644 --- a/app/src/main/java/com/termux/app/BackgroundJob.java +++ b/app/src/main/java/com/termux/app/BackgroundJob.java @@ -152,7 +152,7 @@ public final class BackgroundJob { environment.add("LANG=en_US.UTF-8"); //environment.add("PATH=" + TermuxService.PREFIX_PATH + "/bin"); environment.add("PWD=" + cwd); - environment.add("TMPDIR=" + TermuxService.PREFIX_PATH + "/tmp"); + environment.add("TMPDIR=/tmp"); environment.add("BOOTCLASSPATH=" + System.getenv("BOOTCLASSPATH")); environment.add("ANDROID_ROOT=" + System.getenv("ANDROID_ROOT")); environment.add("ANDROID_DATA=" + System.getenv("ANDROID_DATA")); diff --git a/app/src/main/java/com/vectras/vm/RomInfo.java b/app/src/main/java/com/vectras/vm/RomInfo.java index 7885422..dfead87 100644 --- a/app/src/main/java/com/vectras/vm/RomInfo.java +++ b/app/src/main/java/com/vectras/vm/RomInfo.java @@ -50,6 +50,15 @@ public class RomInfo extends AppCompatActivity { private String currentViews = "0"; private boolean isAnBuiID = false; private String contentID = ""; + private String token = ""; + private String urlToGetInfo = ""; + private RequestNetwork net; + private RequestNetwork.RequestListener _net_request_listener; + private boolean retryUpdateView = true; + private boolean retrySendLike; + private boolean hasRetriedView; + private boolean hasRetriedLike; + private boolean waitingForUpdateLike; @Override protected void onCreate(Bundle savedInstanceState) { @@ -296,8 +305,8 @@ public class RomInfo extends AppCompatActivity { binding.btnLike.setOnClickListener(v -> sendLikeUpdate(contentID)); if (!contentID.isEmpty()) { - RequestNetwork net = new RequestNetwork(this); - RequestNetwork.RequestListener _net_request_listener = new RequestNetwork.RequestListener() { + net = new RequestNetwork(this); + _net_request_listener = new RequestNetwork.RequestListener() { @SuppressLint("SetTextI18n") @Override public void onResponse(String tag, String response, HashMap responseHeaders) { @@ -308,6 +317,8 @@ public class RomInfo extends AppCompatActivity { }.getType() ); + if (map.containsKey("token")) token = Objects.requireNonNull(map.get("token")).toString(); + binding.btnLike.setVisibility(View.VISIBLE); String likeContent = getString(R.string.like); boolean isLiked = MainSettingsManager.getLikes(RomInfo.this).contains("," + getIntent().getStringExtra("id")); @@ -336,6 +347,8 @@ public class RomInfo extends AppCompatActivity { } binding.tvViews.setText(viewsContent); + if (retryUpdateView) sendViewUpdate(contentID); + if (retrySendLike) sendLikeUpdate(contentID); } else { binding.lnAllViews.setVisibility(View.GONE); binding.btnLike.setVisibility(View.GONE); @@ -351,7 +364,7 @@ public class RomInfo extends AppCompatActivity { } }; - String urlToGetInfo = "https://go.anbui.ovh/egg/contentinfo?id=" + contentID + (isAnBuiID ? "" : "&app=vectrasvm"); + urlToGetInfo = "https://go.anbui.ovh/egg/contentinfo?id=" + contentID + (isAnBuiID ? "" : "&app=vectrasvm"); net.startRequestNetwork(RequestNetworkController.GET,urlToGetInfo,"contentinfo", _net_request_listener); Log.i(TAG, "urlToGetInfo: " + urlToGetInfo); @@ -360,6 +373,9 @@ public class RomInfo extends AppCompatActivity { } private void sendLikeUpdate(String id) { + if (waitingForUpdateLike) return; + waitingForUpdateLike = true; + String addlikecount; if (MainSettingsManager.getLikes(this).contains("," + id)) { @@ -377,7 +393,8 @@ public class RomInfo extends AppCompatActivity { String json = "{" + "\"id\":\"" + id + "\"," + "\"addcount\":" + addlikecount - + (isAnBuiID ? "" : ",\"app\":\"vectrasvm\"") + + (isAnBuiID ? "" : ",\"app\":\"vectrasvm\",") + + "\"token\":" + "\"" + token + "\"" + "}"; RequestBody body = RequestBody.create( @@ -393,11 +410,26 @@ public class RomInfo extends AppCompatActivity { client.newCall(request).enqueue(new Callback() { @Override public void onFailure(@NonNull Call call, @NonNull IOException e) { + waitingForUpdateLike = false; Log.e(TAG, "sendLikeUpdate: ", e); } @Override public void onResponse(@NonNull Call call, @NonNull Response response) throws IOException { + int statusCode = response.code(); + + if (statusCode == 403 && !hasRetriedLike) { + retrySendLike = true; + hasRetriedLike = true; + waitingForUpdateLike = false; + net.startRequestNetwork(RequestNetworkController.GET, urlToGetInfo,"contentinfo", _net_request_listener); + return; + } + + retrySendLike = false; + hasRetriedLike = false; + waitingForUpdateLike = false; + if (response.isSuccessful()) { String resBody = response.body().string(); if (!resBody.isEmpty()) { @@ -433,7 +465,8 @@ public class RomInfo extends AppCompatActivity { String json = "{" + "\"id\":\"" + id + "\"" - + (isAnBuiID ? "" : ",\"app\":\"vectrasvm\"") + + (isAnBuiID ? "" : ",\"app\":\"vectrasvm\",") + + "\"token\":" + "\"" + token + "\"" + "}"; RequestBody body = RequestBody.create( @@ -454,6 +487,18 @@ public class RomInfo extends AppCompatActivity { @Override public void onResponse(@NonNull Call call, @NonNull Response response) throws IOException { + int statusCode = response.code(); + + if (statusCode == 403 && !hasRetriedView) { + retryUpdateView = true; + hasRetriedView = true; + net.startRequestNetwork(RequestNetworkController.GET, urlToGetInfo,"contentinfo", _net_request_listener); + return; + } + + retryUpdateView = false; + hasRetriedView = false; + if (response.isSuccessful()) { String resBody = response.body().string(); if (!resBody.isEmpty()) { diff --git a/app/src/main/java/com/vectras/vm/VMManager.java b/app/src/main/java/com/vectras/vm/VMManager.java index f3f30f8..edef36c 100644 --- a/app/src/main/java/com/vectras/vm/VMManager.java +++ b/app/src/main/java/com/vectras/vm/VMManager.java @@ -678,15 +678,13 @@ public class VMManager { } public static boolean isthiscommandsafe(@NonNull String _command, Context _context) { - //xterm -e bash -c ' - String result = _command.replaceFirst("(?i)^\\s*xterm\\s+-e\\s+bash\\s+-c\\s*'", ""); - Log.d("VMManager.isthiscommandsafe", result); + Log.d("VMManager.isthiscommandsafe", _command); - if (result.startsWith("qemu")) { - if (!result.contains("&")) { - if (!result.contains("\n")) { - if (!result.contains(";")) { - if (!result.contains("|")) { + if (_command.startsWith("qemu")) { + if (!_command.contains("&")) { + if (!_command.contains("\n")) { + if (!_command.contains(";")) { + if (!_command.contains("|")) { return true; } else { latestUnsafeCommandReason = _context.getString(R.string.command_are_not_allowed_to_contain_vertical_bars); diff --git a/app/src/main/java/com/vectras/vm/home/core/HomeStartVM.java b/app/src/main/java/com/vectras/vm/home/core/HomeStartVM.java index ff6e339..593b689 100644 --- a/app/src/main/java/com/vectras/vm/home/core/HomeStartVM.java +++ b/app/src/main/java/com/vectras/vm/home/core/HomeStartVM.java @@ -46,6 +46,7 @@ public class HomeStartVM { public static String pendingVMID = ""; public static String pendingThumbnailFile = ""; public static boolean isLaunchFromPending = false; + public static String runCommandFormat = "export TMPDIR=/tmp && mkdir -p $TMPDIR/pulse && export XDG_RUNTIME_DIR=/tmp && pulseaudio --start --exit-idle-time=-1 > /dev/null 2>&1 && %s"; public static void startNow( Activity activity, @@ -62,10 +63,11 @@ public class HomeStartVM { } else { if (MainSettingsManager.getVmUi(activity).equals("X11")) { pendingVMName = vmName; - pendingEnv = "xterm -e bash -c '" + env + "'"; + pendingEnv = env; pendingVMID = vmID; pendingThumbnailFile = thumbnailFile; DisplaySystem.launch(activity); + runCommandFormat = String.format(runCommandFormat, "xterm -e bash -c '%s'"); return; } } @@ -164,11 +166,14 @@ public class HomeStartVM { VMManager.isQemuStopedWithError = false; + String finalCommand = String.format(runCommandFormat, env); + Log.i(TAG, finalCommand); + if (ServiceUtils.isServiceRunning(activity, MainService.class)) { - MainService.startCommand(env, activity); + MainService.startCommand(finalCommand, activity); } else { Intent serviceIntent = new Intent(activity, MainService.class); - MainService.env = env; + MainService.env = finalCommand; MainService.CHANNEL_ID = vmName; MainService.activity = activity; if (SDK_INT >= Build.VERSION_CODES.O) { @@ -222,11 +227,13 @@ public class HomeStartVM { Log.d("HomeStartVM", i + ": " + params[i]); } + setDefault(); } public static void startPending(Activity activity) { isLaunchFromPending = true; startNow(activity, pendingVMName, pendingEnv, pendingVMID, pendingThumbnailFile); + setDefault(); } public static void showProgressDialog(Activity activity, String _content, String thumbnailFile) { @@ -265,4 +272,8 @@ public class HomeStartVM { progressDialog.show(); } + + public static void setDefault() { + runCommandFormat = "export TMPDIR=/tmp && mkdir -p $TMPDIR/pulse && export XDG_RUNTIME_DIR=/tmp && pulseaudio --start --exit-idle-time=-1 > /dev/null 2>&1 && %s"; + } } diff --git a/app/src/main/java/com/vectras/vm/setupwizard/SetupWizardActivity.java b/app/src/main/java/com/vectras/vm/setupwizard/SetupWizardActivity.java index 44cf852..f0c4e54 100644 --- a/app/src/main/java/com/vectras/vm/setupwizard/SetupWizardActivity.java +++ b/app/src/main/java/com/vectras/vm/setupwizard/SetupWizardActivity.java @@ -54,12 +54,8 @@ import com.vectras.vm.utils.PermissionUtils; import java.io.BufferedReader; import java.io.BufferedWriter; import java.io.File; -import java.io.FileInputStream; -import java.io.FileNotFoundException; -import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStreamReader; -import java.io.OutputStream; import java.io.OutputStreamWriter; import java.util.ArrayList; import java.util.HashMap; @@ -86,6 +82,7 @@ public class SetupWizardActivity extends AppCompatActivity { private boolean isServerError = false; private boolean isManualMode = false; private boolean isAllowCheckPermissions = false; + String tarPath; @Override protected void onCreate(Bundle savedInstanceState) { @@ -201,8 +198,6 @@ public class SetupWizardActivity extends AppCompatActivity { checkpermissions(); } - String tarPath; - // Function to append text and automatically scroll to bottom @SuppressLint("SetTextI18n") private void appendTextAndScroll(String textToAdd) { @@ -284,6 +279,8 @@ public class SetupWizardActivity extends AppCompatActivity { cmd += " echo \"Just a sec...\";" + " apk add qemu-audio-sdl pulseaudio;" + + " echo export TMPDIR=/tmp >> /etc/profile;" + + " mkdir -p $TMPDIR/pulse;" + " echo export PULSE_SERVER=127.0.0.1 >> /etc/profile;" + " mkdir -p ~/.vnc && echo -e \"555555\\n555555\" | vncpasswd -f > ~/.vnc/passwd && chmod 0600 ~/.vnc/passwd;" + " echo \"installation successful! xssFjnj58Id\""; @@ -300,14 +297,8 @@ public class SetupWizardActivity extends AppCompatActivity { isFirstLaunch = true; SetupFeatureCore.checkabi(this); - File tarGZ = new File(tarPath); - if (tarGZ.exists()) { - isManualMode = true; - startSetup(); - } else { - if (binding.linearsimplesetupui.getVisibility() == View.GONE) { - showAdvancedSetupDialog(); - } + if (binding.linearsimplesetupui.getVisibility() == View.GONE) { + showAdvancedSetupDialog(); } } @@ -354,54 +345,19 @@ public class SetupWizardActivity extends AppCompatActivity { private final ActivityResultLauncher bootstrapFilePicker = registerForActivityResult(new ActivityResultContracts.GetContent(), uri -> { if (uri != null) { - File selectedFilePath = new File(getPath(uri)); String abi = Build.SUPPORTED_ABIS[0]; - if (selectedFilePath.toString().endsWith(abi + ".tar.gz")) { + if (FileUtils.getFileNameFromUri(this, uri).endsWith(abi + ".tar.gz")) { simpleSetupUIControler(1); new Thread(() -> { - FileInputStream File = null; try { - File = (FileInputStream) getContentResolver().openInputStream(uri); - } catch (FileNotFoundException e) { + setTextStatus(getString(R.string.copying_file)); + FileUtils.copyFileFromUri(this, uri, tarPath); runOnUiThread(() -> { - DialogUtils.oneDialog(this, - getString(R.string.oops), - getString(R.string.the_file_could_not_be_processed_content), - getResources().getString(R.string.ok), - true, - R.drawable.warning_48px, - true, - null, - () -> { - if (binding.linearsimplesetupui.getVisibility() == View.GONE) { - showAdvancedSetupDialog(); - } - }); - simpleSetupUIControler(0); + isManualMode = true; + startSetup(); + MainSettingsManager.setsetUpWithManualSetupBefore(SetupWizardActivity.this, true); }); - } - try { - try { - try (OutputStream out = new FileOutputStream(tarPath)) { - // Transfer bytes from in to out - byte[] buf = new byte[1024]; - int len; - while (true) { - assert File != null; - if (!((len = File.read(buf)) > 0)) break; - out.write(buf, 0, len); - } - } - } finally { - runOnUiThread(() -> { - isManualMode = true; - startSetup(); - MainSettingsManager.setsetUpWithManualSetupBefore(SetupWizardActivity.this, true); - }); - assert File != null; - File.close(); - } - } catch (IOException e) { + } catch (Exception e) { runOnUiThread(() -> { DialogUtils.oneDialog(this, getString(R.string.oops), @@ -422,8 +378,8 @@ public class SetupWizardActivity extends AppCompatActivity { }).start(); } else { DialogUtils.oneDialog(this, - "Invalid file", - "Please select vectras-vm-" + abi + ".tar.gz file.", + getString(R.string.invalid_file), + getString(R.string.please_select) + " vectras-vm-" + abi + ".tar.gz.", getResources().getString(R.string.ok), true, R.drawable.warning_48px, diff --git a/app/src/main/java/com/vectras/vm/utils/DialogUtils.java b/app/src/main/java/com/vectras/vm/utils/DialogUtils.java index d19784a..8e23c0d 100644 --- a/app/src/main/java/com/vectras/vm/utils/DialogUtils.java +++ b/app/src/main/java/com/vectras/vm/utils/DialogUtils.java @@ -11,6 +11,7 @@ import android.net.Uri; import android.os.Build; import android.text.Html; import android.text.Spannable; +import android.text.SpannableString; import android.text.method.LinkMovementMethod; import android.text.util.Linkify; import android.view.LayoutInflater; @@ -52,7 +53,9 @@ public class DialogUtils { title.setText(_title); if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) { - Spannable sp = (Spannable) Html.fromHtml(_message, Html.FROM_HTML_MODE_LEGACY); + Spannable sp = (Spannable) (isHTML(_message) ? + Html.fromHtml(_message, Html.FROM_HTML_MODE_LEGACY) : + new SpannableString(_message)); Linkify.addLinks(sp, Linkify.ALL); content.setText(sp); content.setMovementMethod(LinkMovementMethod.getInstance()); @@ -110,7 +113,9 @@ public class DialogUtils { title.setText(_title); if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) { - Spannable sp = (Spannable) Html.fromHtml(_message, Html.FROM_HTML_MODE_LEGACY); + Spannable sp = (Spannable) (isHTML(_message) ? + Html.fromHtml(_message, Html.FROM_HTML_MODE_LEGACY) : + new SpannableString(_message)); Linkify.addLinks(sp, Linkify.ALL); content.setText(sp); content.setMovementMethod(LinkMovementMethod.getInstance()); @@ -169,7 +174,9 @@ public class DialogUtils { title.setText(_title); if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) { - Spannable sp = (Spannable) Html.fromHtml(_message, Html.FROM_HTML_MODE_LEGACY); + Spannable sp = (Spannable) (isHTML(_message) ? + Html.fromHtml(_message, Html.FROM_HTML_MODE_LEGACY) : + new SpannableString(_message)); Linkify.addLinks(sp, Linkify.ALL); content.setText(sp); content.setMovementMethod(LinkMovementMethod.getInstance()); @@ -269,4 +276,8 @@ public class DialogUtils { ); } } + + public static boolean isHTML(String content) { + return content.contains("<") && content.contains(""); + } } diff --git a/app/src/main/java/com/vectras/vterm/Terminal.java b/app/src/main/java/com/vectras/vterm/Terminal.java index c16f763..0daeb49 100644 --- a/app/src/main/java/com/vectras/vterm/Terminal.java +++ b/app/src/main/java/com/vectras/vterm/Terminal.java @@ -105,7 +105,7 @@ public class Terminal { processBuilder.environment().put("HOME", "/root"); processBuilder.environment().put("USER", user); processBuilder.environment().put("TERM", "xterm-256color"); - processBuilder.environment().put("TMPDIR", tmpDir.getAbsolutePath()); + processBuilder.environment().put("TMPDIR", "/tmp"); processBuilder.environment().put("SHELL", "/bin/sh"); processBuilder.environment().put("DISPLAY", DISPLAY); processBuilder.environment().put("PULSE_SERVER", "127.0.0.1"); @@ -199,7 +199,7 @@ public class Terminal { //processBuilder.environment().put("PATH", "/bin:/usr/bin:/sbin:/usr/sbin"); //processBuilder.environment().put("LD_LIBRARY_PATH", TermuxService.PREFIX_PATH + "/lib"); processBuilder.environment().put("TERM", "xterm-256color"); - processBuilder.environment().put("TMPDIR", tmpDir.getAbsolutePath()); + processBuilder.environment().put("TMPDIR", "/tmp"); processBuilder.environment().put("SHELL", "/bin/sh"); processBuilder.environment().put("DISPLAY", DISPLAY); processBuilder.environment().put("PULSE_SERVER", "127.0.0.1"); @@ -303,7 +303,7 @@ public class Terminal { processBuilder.environment().put("HOME", "/root"); processBuilder.environment().put("USER", user); processBuilder.environment().put("TERM", "xterm-256color"); - processBuilder.environment().put("TMPDIR", tmpDir.getAbsolutePath()); + processBuilder.environment().put("TMPDIR", "/tmp"); processBuilder.environment().put("SHELL", "/bin/sh"); processBuilder.environment().put("DISPLAY", DISPLAY); processBuilder.environment().put("PULSE_SERVER", "127.0.0.1"); @@ -381,7 +381,7 @@ public class Terminal { processBuilder.environment().put("HOME", "/root"); processBuilder.environment().put("USER", user); processBuilder.environment().put("TERM", "xterm-256color"); - processBuilder.environment().put("TMPDIR", tmpDir.getAbsolutePath()); + processBuilder.environment().put("TMPDIR", "/tmp"); processBuilder.environment().put("SHELL", "/bin/sh"); processBuilder.environment().put("DISPLAY", DISPLAY); processBuilder.environment().put("PULSE_SERVER", "127.0.0.1"); @@ -499,7 +499,7 @@ public class Terminal { processBuilder.environment().put("HOME", "/root"); processBuilder.environment().put("USER", user); processBuilder.environment().put("TERM", "xterm-256color"); - processBuilder.environment().put("TMPDIR", tmpDir.getAbsolutePath()); + processBuilder.environment().put("TMPDIR", "/tmp"); processBuilder.environment().put("SHELL", "/bin/sh"); processBuilder.environment().put("DISPLAY", DISPLAY); processBuilder.environment().put("PULSE_SERVER", "127.0.0.1"); diff --git a/app/src/main/java/com/vectras/vterm/TerminalBottomSheetDialog.java b/app/src/main/java/com/vectras/vterm/TerminalBottomSheetDialog.java index 2f5e8bd..b9cbe4c 100644 --- a/app/src/main/java/com/vectras/vterm/TerminalBottomSheetDialog.java +++ b/app/src/main/java/com/vectras/vterm/TerminalBottomSheetDialog.java @@ -170,7 +170,7 @@ public class TerminalBottomSheetDialog { //processBuilder.environment().put("PATH", "/bin:/usr/bin:/sbin:/usr/sbin"); //processBuilder.environment().put("LD_LIBRARY_PATH", TermuxService.PREFIX_PATH + "/lib"); processBuilder.environment().put("TERM", "xterm-256color"); - processBuilder.environment().put("TMPDIR", tmpDir.getAbsolutePath()); + processBuilder.environment().put("TMPDIR", "/tmp"); processBuilder.environment().put("SHELL", "/bin/sh"); processBuilder.environment().put("DISPLAY", ":0"); processBuilder.environment().put("PULSE_SERVER", "127.0.0.1"); diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index c462daa..f0b0498 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -3,7 +3,7 @@ Vectras VM - 3.3.1 + 3.3.2 Stable Home Logger @@ -608,6 +608,7 @@ An error occurred while installing system files. Copying file… CD-ROM (iso file only) + Invalid file diff --git a/web/data/UpdateConfig.json b/web/data/UpdateConfig.json index da22646..095d10a 100644 --- a/web/data/UpdateConfig.json +++ b/web/data/UpdateConfig.json @@ -5,11 +5,11 @@ "url": "https://github.com/AnBui2004/Vectras-VM-Emu-Android/releases/tag/3.3.0", "Message": "

3.3.0

New Qemu 9.2.2 with 3dfx! And bugs fixed.", "cancellable": true, - "versionCodeBeta":"35", - "versionNameBeta":"3.3.1", - "versionNameBetas":"3.0.0,3.1.0,3.2.1,3.2.2,3.2.3,3.2.4,3.2.5,3.2.6,3.2.7,3.2.8,3.2.9,3.2.10,3.3.0,3.3.1", + "versionCodeBeta":"36", + "versionNameBeta":"3.3.2", + "versionNameBetas":"3.0.0,3.1.0,3.2.1,3.2.2,3.2.3,3.2.4,3.2.5,3.2.6,3.2.7,3.2.8,3.2.9,3.2.10,3.3.1,3.3.2", "sizeBeta": "60 MB", "urlBeta": "https://github.com/AnBui2004/Vectras-VM-Emu-Android/releases", - "MessageBeta": "

3.3.1

Bugs fixed.", + "MessageBeta": "

3.3.2

Bugs fixed.", "cancellableBeta": true }