From 1b5cfae20a43bb482cce7b8cd8230fe767181f0f Mon Sep 17 00:00:00 2001 From: woesss Date: Thu, 28 Dec 2023 18:17:52 +0300 Subject: [PATCH] Fixed reading descriptor with empty value --- .../playsoftware/j2meloader/util/IOUtils.java | 22 ++--- .../woesss/j2me/installer/AppInstaller.java | 13 +-- .../java/ru/woesss/j2me/jar/Descriptor.java | 90 ++++++------------- 3 files changed, 38 insertions(+), 87 deletions(-) diff --git a/app/src/main/java/ru/playsoftware/j2meloader/util/IOUtils.java b/app/src/main/java/ru/playsoftware/j2meloader/util/IOUtils.java index b04da20e..793a938d 100644 --- a/app/src/main/java/ru/playsoftware/j2meloader/util/IOUtils.java +++ b/app/src/main/java/ru/playsoftware/j2meloader/util/IOUtils.java @@ -1,5 +1,6 @@ /* * Copyright 2020 Nikita Shakarun + * Copyright 2023 Yury Kharchenko * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -16,30 +17,19 @@ package ru.playsoftware.j2meloader.util; -import java.io.ByteArrayOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; -public class IOUtils { - - private static final int BUFFER_SIZE = 16384; +import kotlin.io.ByteStreamsKt; +import kotlin.io.ConstantsKt; +public class IOUtils { public static byte[] toByteArray(InputStream stream) throws IOException { - ByteArrayOutputStream outputStream = new ByteArrayOutputStream(); - byte[] buf = new byte[BUFFER_SIZE]; - int len; - while ((len = stream.read(buf)) != -1) { - outputStream.write(buf, 0, len); - } - return outputStream.toByteArray(); + return ByteStreamsKt.readBytes(stream); } public static void copy(InputStream input, OutputStream output) throws IOException { - byte[] buf = new byte[BUFFER_SIZE]; - int len; - while ((len = input.read(buf)) != -1) { - output.write(buf, 0, len); - } + ByteStreamsKt.copyTo(input, output, ConstantsKt.DEFAULT_BUFFER_SIZE); } } diff --git a/app/src/main/java/ru/woesss/j2me/installer/AppInstaller.java b/app/src/main/java/ru/woesss/j2me/installer/AppInstaller.java index ac048a70..8b295fed 100644 --- a/app/src/main/java/ru/woesss/j2me/installer/AppInstaller.java +++ b/app/src/main/java/ru/woesss/j2me/installer/AppInstaller.java @@ -22,11 +22,9 @@ import com.android.dx.command.dexer.Main; -import ru.woesss.util.zip.ZipFile; import net.lingala.zip4j.io.inputstream.ZipInputStream; import net.lingala.zip4j.model.FileHeader; -import java.io.ByteArrayOutputStream; import java.io.DataInputStream; import java.io.File; import java.io.FileInputStream; @@ -48,8 +46,10 @@ import ru.playsoftware.j2meloader.config.Config; import ru.playsoftware.j2meloader.util.ConverterException; import ru.playsoftware.j2meloader.util.FileUtils; +import ru.playsoftware.j2meloader.util.IOUtils; import ru.playsoftware.j2meloader.util.ZipUtils; import ru.woesss.j2me.jar.Descriptor; +import ru.woesss.util.zip.ZipFile; public class AppInstaller { private static final String TAG = AppInstaller.class.getSimpleName(); @@ -340,13 +340,8 @@ private Descriptor loadManifest(File jar) throws IOException { throw new IOException("JAR not have " + JarFile.MANIFEST_NAME); } try (ZipInputStream is = zip.getInputStream(manifest)) { - ByteArrayOutputStream baos = new ByteArrayOutputStream(20480); - byte[] buf = new byte[4096]; - int read; - while ((read = is.read(buf)) != -1) { - baos.write(buf, 0, read); - } - return new Descriptor(baos.toString(), false); + String text = new String(IOUtils.toByteArray(is)); + return new Descriptor(text, false); } } } diff --git a/app/src/main/java/ru/woesss/j2me/jar/Descriptor.java b/app/src/main/java/ru/woesss/j2me/jar/Descriptor.java index 357b7d4d..223bc131 100644 --- a/app/src/main/java/ru/woesss/j2me/jar/Descriptor.java +++ b/app/src/main/java/ru/woesss/j2me/jar/Descriptor.java @@ -1,5 +1,5 @@ /* - * Copyright 2020 Yury Kharchenko + * Copyright 2020-2023 Yury Kharchenko * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -17,27 +17,22 @@ package ru.woesss.j2me.jar; import android.content.Context; -import android.net.Uri; import android.text.SpannableStringBuilder; -import android.util.Log; -import java.io.EOFException; +import androidx.annotation.Nullable; + import java.io.File; -import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.IOException; -import java.io.InputStream; import java.io.OutputStream; import java.text.DecimalFormat; import java.util.HashMap; import java.util.Map; -import androidx.annotation.Nullable; import ru.playsoftware.j2meloader.R; +import ru.playsoftware.j2meloader.util.FileUtils; public class Descriptor { - private static final String TAG = Descriptor.class.getName(); - private static final char UNICODE_BOM = '\uFEFF'; private static final String MANIFEST_VERSION = "Manifest-Version"; // required in JAD and Manifest @@ -74,7 +69,11 @@ public class Descriptor { public Descriptor(String source, boolean isJad) throws IOException { this.isJad = isJad; - init(source); + try { + parse(source); + } catch (Exception e) { + throw new DescriptorException("Bad descriptor: \n" + source, e); + } if (isJad) { verifyJadAttrs(); } @@ -83,26 +82,7 @@ public Descriptor(String source, boolean isJad) throws IOException { } public Descriptor(File file, boolean isJad) throws IOException { - this.isJad = isJad; - byte[] buf; - try (InputStream inputStream = new FileInputStream(file)) { - int count = inputStream.available(); - buf = new byte[count]; - int n = 0; - while (n < buf.length) { - int read = inputStream.read(buf, n, buf.length - n); - if (read < 0) { - throw new EOFException(); - } - n += read; - } - } - init(new String(buf)); - if (isJad) { - verifyJadAttrs(); - } - verify(); - + this(FileUtils.getText(file.getPath()), isJad); } public int compareVersion(String version) { @@ -170,15 +150,6 @@ public final Map getAttrs() { return attributes; } - private void init(String source) throws DescriptorException { - try { - parse(source); - } catch (Exception e) { - Log.e(TAG, source); - throw new DescriptorException("Bad descriptor", e); - } - } - private void parse(String source) { String[] lines = source.split("[\\n\\r]+"); int length = lines.length; @@ -186,39 +157,34 @@ private void parse(String source) { throw new IllegalArgumentException("Descriptor source is empty"); } String line0 = lines[0]; - if (line0.charAt(0) == UNICODE_BOM) + if (line0.length() > 0 && line0.charAt(0) == UNICODE_BOM) lines[0] = line0.substring(1); Map attrs = attributes; final StringBuilder sb = new StringBuilder("1.0"); String key = MANIFEST_VERSION; for (String line : lines) { - if (line.trim().isEmpty()) { - continue; - } int colon = line.indexOf(':'); if (colon == -1) { - if (line.charAt(0) == ' ') sb.append(line, 1, line.length()); - else sb.append(line); + if (line.isEmpty()) { + continue; + } + if (line.charAt(0) == ' ') { + sb.append(line, 1, line.length()); + } else { + sb.append(line); + } } else { attrs.put(key, sb.toString().trim()); sb.setLength(0); - key = line.substring(0, colon++).trim(); - if (line.charAt(colon) == ' ') - colon++; - sb.append(line, colon, line.length()); + key = line.substring(0, colon).trim(); + if (line.length() > ++colon) { + sb.append(line, colon, line.length()); + } } } attrs.put(key, sb.toString().trim()); } - private String getFileLocation(String jarURL) { - Uri jarUri = Uri.parse(jarURL); - if ("http".equalsIgnoreCase(jarUri.getScheme()) || "https".equalsIgnoreCase(jarUri.getScheme())) { - return "Интернет"; - } - return "Файл"; - } - public String getName() { return attributes.get(MIDLET_NAME); } @@ -279,12 +245,12 @@ public String getJarUrl() { @Override public boolean equals(@Nullable Object obj) { - if (this == obj) + if (this == obj) { return true; - if (!(obj instanceof Descriptor)) - return false; - Descriptor o = (Descriptor) obj; - return getName().equals(o.getName()) && getVendor().equals(o.getVendor()); + } else if (obj instanceof Descriptor o) { + return getName().equals(o.getName()) && getVendor().equals(o.getVendor()); + } + return false; } public SpannableStringBuilder getInfo(Context c) {