diff --git a/res/values/strings.xml b/res/values/strings.xml
index 091debb908455858a91f2c53e5dc3c84cc18a317..00b712781d1cf1a76434acfc6d7d9a6f43e8a336 100644
--- a/res/values/strings.xml
+++ b/res/values/strings.xml
@@ -61,6 +61,8 @@
Preliminary update preparation
Low battery
The battery level is too low, you need at least %1$d%% of the battery to continue, %2$d%% if charging.
+ Free up space
+ The update cannot be completed because there is insufficient free space; at least %1$s of free space is required. Please clear your internal storage before proceeding.
Reboot
diff --git a/src/org/lineageos/updater/UpdatesActivity.java b/src/org/lineageos/updater/UpdatesActivity.java
index 173452f08973c7347a566620f5407604daccf8eb..9f6a4e552647c8e42ccd2377c27c87a9d575291e 100644
--- a/src/org/lineageos/updater/UpdatesActivity.java
+++ b/src/org/lineageos/updater/UpdatesActivity.java
@@ -23,9 +23,9 @@ import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
-import android.content.res.Configuration;
import android.content.ServiceConnection;
import android.content.SharedPreferences;
+import android.content.res.Configuration;
import android.icu.text.DateFormat;
import android.net.Uri;
import android.os.Build;
diff --git a/src/org/lineageos/updater/UpdatesListAdapter.java b/src/org/lineageos/updater/UpdatesListAdapter.java
index 4566b88a0a5f33c6f8095e18534b99b7d2be67cd..04ad0028a463caf9793a2005b3ea517b9d7c1057 100644
--- a/src/org/lineageos/updater/UpdatesListAdapter.java
+++ b/src/org/lineageos/updater/UpdatesListAdapter.java
@@ -15,12 +15,10 @@
*/
package org.lineageos.updater;
-import android.app.Activity;
import android.content.Intent;
import android.content.IntentFilter;
import android.content.SharedPreferences;
import android.content.res.Resources;
-import android.net.Uri;
import android.os.BatteryManager;
import android.os.PowerManager;
import android.text.SpannableString;
@@ -40,8 +38,6 @@ import android.widget.LinearLayout;
import android.widget.ProgressBar;
import android.widget.TextView;
-import androidx.activity.result.ActivityResultLauncher;
-import androidx.activity.result.contract.ActivityResultContracts;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AlertDialog;
import androidx.appcompat.view.ContextThemeWrapper;
@@ -55,7 +51,6 @@ import com.google.android.material.snackbar.Snackbar;
import org.lineageos.updater.controller.UpdaterController;
import org.lineageos.updater.controller.UpdaterService;
-import org.lineageos.updater.misc.BuildInfoUtils;
import org.lineageos.updater.misc.Constants;
import org.lineageos.updater.misc.StringGenerator;
import org.lineageos.updater.misc.Utils;
@@ -454,8 +449,8 @@ public class UpdatesListAdapter extends RecyclerView.Adapter= neededSpace;
+ if (!hasFreeSpace) {
+ String message = resources.getString(R.string.dialog_free_space_low_message_pct,
+ Utils.getFileSize(neededSpace));
+ return new AlertDialog.Builder(mActivity)
+ .setTitle(R.string.dialog_free_space_low_title)
+ .setMessage(message)
+ .setPositiveButton(android.R.string.ok, null);
+ }
+
String buildDate = StringGenerator.getDateLocalizedUTC(mActivity,
DateFormat.MEDIUM, update.getTimestamp());
String buildInfoText = mActivity.getString(R.string.list_build_version_date_e,
diff --git a/src/org/lineageos/updater/controller/UpdateInstaller.java b/src/org/lineageos/updater/controller/UpdateInstaller.java
index b111f9f33275d3810f6bd6a5f890f9d131591823..720d13ec5a5d45c17fb38b927ddbec20ff6f9326 100644
--- a/src/org/lineageos/updater/controller/UpdateInstaller.java
+++ b/src/org/lineageos/updater/controller/UpdateInstaller.java
@@ -31,8 +31,8 @@ import org.lineageos.updater.model.UpdateStatus;
import java.io.File;
import java.io.IOException;
-import java.nio.file.attribute.PosixFilePermission;
import java.nio.file.Files;
+import java.nio.file.attribute.PosixFilePermission;
import java.util.HashSet;
import java.util.Set;
diff --git a/src/org/lineageos/updater/controller/UpdaterService.java b/src/org/lineageos/updater/controller/UpdaterService.java
index b71a4f686c7f765bdb566820c3ded1a9fbd21110..bf0139008208fd8316ded0101a0918d6cf4ab44e 100644
--- a/src/org/lineageos/updater/controller/UpdaterService.java
+++ b/src/org/lineageos/updater/controller/UpdaterService.java
@@ -41,7 +41,6 @@ import androidx.preference.PreferenceManager;
import org.lineageos.updater.R;
import org.lineageos.updater.UpdaterReceiver;
import org.lineageos.updater.UpdatesActivity;
-import org.lineageos.updater.misc.BuildInfoUtils;
import org.lineageos.updater.misc.Constants;
import org.lineageos.updater.misc.StringGenerator;
import org.lineageos.updater.misc.Utils;
diff --git a/src/org/lineageos/updater/download/HttpURLConnectionClient.java b/src/org/lineageos/updater/download/HttpURLConnectionClient.java
index df6283b5cb8bdc40f043a4d459c04a98e3f6619a..606bef16ccf08c3667eaea8bb5882966977953b3 100644
--- a/src/org/lineageos/updater/download/HttpURLConnectionClient.java
+++ b/src/org/lineageos/updater/download/HttpURLConnectionClient.java
@@ -17,9 +17,10 @@ package org.lineageos.updater.download;
import android.os.SystemClock;
import android.os.SystemProperties;
-
import android.util.Log;
+import org.lineageos.updater.misc.Constants;
+
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
@@ -34,8 +35,6 @@ import java.util.PriorityQueue;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
-import org.lineageos.updater.misc.Constants;
-
public class HttpURLConnectionClient implements DownloadClient {
private final static String TAG = "HttpURLConnectionClient";
diff --git a/src/org/lineageos/updater/misc/Utils.java b/src/org/lineageos/updater/misc/Utils.java
index 0a614ac7621f5118dd14555904d6d97a0ca1ffbf..7758b8ab2ecfbb0e426ea2bdb4d415a8712125a7 100644
--- a/src/org/lineageos/updater/misc/Utils.java
+++ b/src/org/lineageos/updater/misc/Utils.java
@@ -20,7 +20,6 @@ import static android.os.SystemUpdateManager.KEY_STATUS;
import static android.os.SystemUpdateManager.KEY_TITLE;
import static android.os.SystemUpdateManager.STATUS_IDLE;
import static android.os.SystemUpdateManager.STATUS_WAITING_DOWNLOAD;
-import static android.os.SystemUpdateManager.STATUS_UNKNOWN;
import android.app.AlarmManager;
import android.content.ClipData;
@@ -35,7 +34,9 @@ import android.net.Network;
import android.net.NetworkCapabilities;
import android.net.Uri;
import android.os.Bundle;
+import android.os.Environment;
import android.os.PersistableBundle;
+import android.os.StatFs;
import android.os.SystemProperties;
import android.os.SystemUpdateManager;
import android.os.storage.StorageManager;
@@ -59,15 +60,14 @@ import java.io.BufferedReader;
import java.io.File;
import java.io.FileReader;
import java.io.IOException;
+import java.text.DecimalFormat;
import java.util.ArrayList;
import java.util.Enumeration;
-import java.util.HashSet;
import java.util.List;
import java.util.Locale;
-import java.util.Set;
+import java.util.regex.Pattern;
import java.util.zip.ZipEntry;
import java.util.zip.ZipFile;
-import java.util.regex.Pattern;
public class Utils {
@@ -159,6 +159,20 @@ public class Utils {
return new int[]{ major, minor };
}
+ public static long availableFreeSpace() {
+ StatFs stats = new StatFs(Environment.getDataDirectory().getAbsolutePath());
+ return stats.getAvailableBlocksLong() * stats.getBlockSizeLong();
+ }
+
+ // https://stackoverflow.com/a/28527441
+ public static String getFileSize(long size) {
+ if (size <= 0)
+ return "0";
+ final String[] units = new String[] { "B", "KB", "MB", "GB", "TB" };
+ int digitGroups = (int) (Math.log10(size) / Math.log10(1024));
+ return new DecimalFormat("#,##0.#").format(size / Math.pow(1024, digitGroups)) + " " + units[digitGroups];
+ }
+
public static boolean canInstall(UpdateBaseInfo update) {
return (SystemProperties.getBoolean(Constants.PROP_UPDATER_ALLOW_DOWNGRADING, false) ||
update.getTimestamp() > SystemProperties.getLong(Constants.PROP_BUILD_DATE, 0));