From 085a2db92a366532d9967912ffd8410f9803c88e Mon Sep 17 00:00:00 2001 From: undownding Date: Mon, 11 Oct 2021 12:45:08 +0800 Subject: [PATCH 01/11] GPT creator --- .../github/mjdev/libaums/partition/gpt/GPT.kt | 48 +++++++++++++++++++ .../mjdev/libaums/partition/gpt/GPTCreator.kt | 11 +++++ 2 files changed, 59 insertions(+) create mode 100644 libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt create mode 100644 libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPTCreator.kt diff --git a/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt new file mode 100644 index 00000000..2dd60b0f --- /dev/null +++ b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt @@ -0,0 +1,48 @@ +package com.github.mjdev.libaums.partition.gpt + +import com.github.mjdev.libaums.driver.BlockDeviceDriver +import com.github.mjdev.libaums.partition.PartitionTable +import com.github.mjdev.libaums.partition.PartitionTableEntry +import java.io.IOException +import java.nio.ByteBuffer +import java.util.ArrayList + +class GPT private constructor(): PartitionTable { + + // See also https://zh.wikipedia.org/wiki/GUID%E7%A3%81%E7%A2%9F%E5%88%86%E5%89%B2%E8%A1% + + private val partitions = ArrayList() + + override val size: Int get() = partitions.size * 128 + override val partitionTableEntries: List + get() = partitions + + companion object { + + const val EFI_PART = "EFI_PART" + + @Throws(IOException::class) + fun read(blockDevice: BlockDeviceDriver): GPT? { + val result = GPT() + val buffer = ByteBuffer.allocate(Math.max(128, blockDevice.blockSize)) + blockDevice.read(512, buffer) // LBA 0 + + if (String(buffer.array(), 0x00, 8) == EFI_PART) { + blockDevice.read(1024L + (result.partitions.size * 128), buffer) + while (buffer[0].toInt() != 0) { + val offset = 1024 + (result.partitions.size * 128) + val entry = PartitionTableEntry(0, + buffer.getInt(offset + 32), buffer.getInt(offset + 40)) + + result.partitions.add(entry) + blockDevice.read(offset + 128L, buffer) + } + } else { + throw IOException("not a valid GPT") + } + + return result + } + } + +} \ No newline at end of file diff --git a/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPTCreator.kt b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPTCreator.kt new file mode 100644 index 00000000..cbde0459 --- /dev/null +++ b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPTCreator.kt @@ -0,0 +1,11 @@ +package com.github.mjdev.libaums.partition.gpt + +import com.github.mjdev.libaums.driver.BlockDeviceDriver +import com.github.mjdev.libaums.partition.PartitionTable +import com.github.mjdev.libaums.partition.PartitionTableFactory +import java.nio.ByteBuffer + +class GPTCreator: PartitionTableFactory.PartitionTableCreator { + override fun read(blockDevice: BlockDeviceDriver): PartitionTable? = GPT.read(blockDevice) + +} \ No newline at end of file From 45ac92aff549a6523614e5b3d33b33de8c0aab1d Mon Sep 17 00:00:00 2001 From: undownding Date: Mon, 11 Oct 2021 12:48:35 +0800 Subject: [PATCH 02/11] adjust MBR and GPT --- .../github/mjdev/libaums/partition/gpt/GPTCreator.kt | 1 - .../libaums/partition/mbr/MasterBootRecordCreator.kt | 11 +++++++++-- 2 files changed, 9 insertions(+), 3 deletions(-) diff --git a/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPTCreator.kt b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPTCreator.kt index cbde0459..fbb2263a 100644 --- a/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPTCreator.kt +++ b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPTCreator.kt @@ -7,5 +7,4 @@ import java.nio.ByteBuffer class GPTCreator: PartitionTableFactory.PartitionTableCreator { override fun read(blockDevice: BlockDeviceDriver): PartitionTable? = GPT.read(blockDevice) - } \ No newline at end of file diff --git a/libaums/src/main/java/com/github/mjdev/libaums/partition/mbr/MasterBootRecordCreator.kt b/libaums/src/main/java/com/github/mjdev/libaums/partition/mbr/MasterBootRecordCreator.kt index 181ce17e..aff9cc26 100644 --- a/libaums/src/main/java/com/github/mjdev/libaums/partition/mbr/MasterBootRecordCreator.kt +++ b/libaums/src/main/java/com/github/mjdev/libaums/partition/mbr/MasterBootRecordCreator.kt @@ -3,6 +3,8 @@ package com.github.mjdev.libaums.partition.mbr import com.github.mjdev.libaums.driver.BlockDeviceDriver import com.github.mjdev.libaums.partition.PartitionTable import com.github.mjdev.libaums.partition.PartitionTableFactory +import com.github.mjdev.libaums.partition.gpt.GPT +import com.github.mjdev.libaums.partition.gpt.GPTCreator import java.io.IOException import java.nio.ByteBuffer @@ -14,7 +16,12 @@ class MasterBootRecordCreator : PartitionTableFactory.PartitionTableCreator { @Throws(IOException::class) override fun read(blockDevice: BlockDeviceDriver): PartitionTable? { val buffer = ByteBuffer.allocate(Math.max(512, blockDevice.blockSize)) - blockDevice.read(0, buffer) - return MasterBootRecord.read(buffer) + blockDevice.read(512, buffer) + return if (String(buffer.array(), 0x00, 8) == GPT.EFI_PART) { + GPTCreator().read(blockDevice) + } else { + blockDevice.read(0, buffer) + MasterBootRecord.read(buffer) + } } } From c9a372599c7f675a8f6d431c9cb238a76148ca14 Mon Sep 17 00:00:00 2001 From: Magnus Date: Fri, 10 Mar 2023 19:17:02 +0100 Subject: [PATCH 03/11] Fix imports --- .../java/com/github/mjdev/libaums/partition/gpt/GPT.kt | 6 +++--- .../com/github/mjdev/libaums/partition/gpt/GPTCreator.kt | 8 ++++---- 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt index 2dd60b0f..8657e284 100644 --- a/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt +++ b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt @@ -1,8 +1,8 @@ package com.github.mjdev.libaums.partition.gpt -import com.github.mjdev.libaums.driver.BlockDeviceDriver -import com.github.mjdev.libaums.partition.PartitionTable -import com.github.mjdev.libaums.partition.PartitionTableEntry +import me.jahnen.libaums.core.driver.BlockDeviceDriver +import me.jahnen.libaums.core.partition.PartitionTable +import me.jahnen.libaums.core.partition.PartitionTableEntry import java.io.IOException import java.nio.ByteBuffer import java.util.ArrayList diff --git a/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPTCreator.kt b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPTCreator.kt index fbb2263a..a9ec41b2 100644 --- a/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPTCreator.kt +++ b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPTCreator.kt @@ -1,9 +1,9 @@ package com.github.mjdev.libaums.partition.gpt -import com.github.mjdev.libaums.driver.BlockDeviceDriver -import com.github.mjdev.libaums.partition.PartitionTable -import com.github.mjdev.libaums.partition.PartitionTableFactory -import java.nio.ByteBuffer +import me.jahnen.libaums.core.driver.BlockDeviceDriver +import me.jahnen.libaums.core.partition.PartitionTable +import me.jahnen.libaums.core.partition.PartitionTableFactory + class GPTCreator: PartitionTableFactory.PartitionTableCreator { override fun read(blockDevice: BlockDeviceDriver): PartitionTable? = GPT.read(blockDevice) From 10b2dd832d0fda54438ac2930d4b5d898299dcfd Mon Sep 17 00:00:00 2001 From: Magnus Date: Fri, 10 Mar 2023 19:20:11 +0100 Subject: [PATCH 04/11] include GPT in creation workflow for partition tables --- .../src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt | 2 +- .../me/jahnen/libaums/core/partition/PartitionTableFactory.kt | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt index 8657e284..8d103f70 100644 --- a/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt +++ b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt @@ -38,7 +38,7 @@ class GPT private constructor(): PartitionTable { blockDevice.read(offset + 128L, buffer) } } else { - throw IOException("not a valid GPT") + return null } return result diff --git a/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableFactory.kt b/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableFactory.kt index 8632deca..ee9da6d6 100644 --- a/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableFactory.kt +++ b/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableFactory.kt @@ -17,6 +17,7 @@ package me.jahnen.libaums.core.partition +import com.github.mjdev.libaums.partition.gpt.GPTCreator import me.jahnen.libaums.core.driver.BlockDeviceDriver import me.jahnen.libaums.core.partition.fs.FileSystemPartitionTableCreator import me.jahnen.libaums.core.partition.mbr.MasterBootRecordCreator @@ -41,6 +42,7 @@ object PartitionTableFactory { init { registerPartitionTable(FileSystemPartitionTableCreator()) + registerPartitionTable(GPTCreator()) registerPartitionTable(MasterBootRecordCreator()) } From af62accdab2fbc8cef65a8a8b42b76b8af1e6c1d Mon Sep 17 00:00:00 2001 From: Magnus Date: Fri, 10 Mar 2023 19:22:37 +0100 Subject: [PATCH 05/11] Some logging --- .../jahnen/libaums/core/partition/PartitionTableFactory.kt | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableFactory.kt b/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableFactory.kt index ee9da6d6..a4af3dcd 100644 --- a/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableFactory.kt +++ b/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableFactory.kt @@ -17,9 +17,11 @@ package me.jahnen.libaums.core.partition +import android.util.Log import com.github.mjdev.libaums.partition.gpt.GPTCreator import me.jahnen.libaums.core.driver.BlockDeviceDriver import me.jahnen.libaums.core.partition.fs.FileSystemPartitionTableCreator +import me.jahnen.libaums.core.partition.mbr.MasterBootRecord import me.jahnen.libaums.core.partition.mbr.MasterBootRecordCreator import java.io.IOException import java.util.* @@ -30,6 +32,7 @@ import java.util.* * @author mjahnen */ object PartitionTableFactory { + private val TAG = MasterBootRecord::class.java.simpleName private val partitionTables = ArrayList() @@ -62,8 +65,10 @@ object PartitionTableFactory { for (creator in partitionTables) { val table = creator.read(blockDevice) if (table != null) { + Log.d(TAG, "Found partition table ${creator::class.java.simpleName}") return table } + Log.d(TAG, "${creator::class.java.simpleName} returned null") } throw UnsupportedPartitionTableException() From cbbc56cf19940ec6bb9ce51c1ebb314c358ff28d Mon Sep 17 00:00:00 2001 From: Magnus Date: Fri, 10 Mar 2023 19:42:06 +0100 Subject: [PATCH 06/11] Partition fs unknown for gpt --- .../src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt | 2 +- .../me/jahnen/libaums/core/partition/PartitionTableEntry.kt | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt index 8d103f70..4879475d 100644 --- a/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt +++ b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt @@ -31,7 +31,7 @@ class GPT private constructor(): PartitionTable { blockDevice.read(1024L + (result.partitions.size * 128), buffer) while (buffer[0].toInt() != 0) { val offset = 1024 + (result.partitions.size * 128) - val entry = PartitionTableEntry(0, + val entry = PartitionTableEntry(-1, // Unknown buffer.getInt(offset + 32), buffer.getInt(offset + 40)) result.partitions.add(entry) diff --git a/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableEntry.kt b/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableEntry.kt index 847ad4f5..8daf3dc6 100644 --- a/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableEntry.kt +++ b/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableEntry.kt @@ -28,7 +28,7 @@ class PartitionTableEntry * Construct a new PartitionTableEntry with the given information. * * @param partitionType - * The file system type of the partition (eg. FAT32). + * The file system type of the partition (eg. FAT32). -1 if unknown * @param logicalBlockAddress * The logical block address on the device where this partition * starts. From 952b89305415a76688949a8d18f61c3d98fd4ea2 Mon Sep 17 00:00:00 2001 From: Davide Depau Date: Fri, 10 Mar 2023 19:59:38 +0100 Subject: [PATCH 07/11] Prevent libusbcommunication usage after closing --- .../LibusbCommunication.kt | 23 ++++++++++++++++--- 1 file changed, 20 insertions(+), 3 deletions(-) diff --git a/libusbcommunication/src/main/java/me/jahnen/libaums/libusbcommunication/LibusbCommunication.kt b/libusbcommunication/src/main/java/me/jahnen/libaums/libusbcommunication/LibusbCommunication.kt index e8f49193..a35e2d1a 100644 --- a/libusbcommunication/src/main/java/me/jahnen/libaums/libusbcommunication/LibusbCommunication.kt +++ b/libusbcommunication/src/main/java/me/jahnen/libaums/libusbcommunication/LibusbCommunication.kt @@ -28,6 +28,7 @@ class LibusbCommunication( private val libUsbHandle: Long get() = libUsbHandleArray[0] private var deviceConnection: UsbDeviceConnection? + private var closed = false init { System.loadLibrary("libusbcom") @@ -59,6 +60,8 @@ class LibusbCommunication( private external fun nativeControlTransfer(handle: Long, requestType: Int, request: Int, value: Int, index: Int, buffer: ByteArray, length: Int, timeout: Int): Int override fun bulkOutTransfer(src: ByteBuffer): Int { + require(!closed) { "device is closed" } + val transferred = nativeBulkTransfer( libUsbHandle, outEndpoint.address, src.array(), src.position(), src.remaining(), TRANSFER_TIMEOUT @@ -74,6 +77,8 @@ class LibusbCommunication( } override fun bulkInTransfer(dest: ByteBuffer): Int { + require(!closed) { "device is closed" } + val transferred = nativeBulkTransfer( libUsbHandle, inEndpoint.address, dest.array(), dest.position(), dest.remaining(), TRANSFER_TIMEOUT @@ -89,6 +94,8 @@ class LibusbCommunication( } override fun controlTransfer(requestType: Int, request: Int, value: Int, index: Int, buffer: ByteArray, length: Int): Int { + require(!closed) { "device is closed" } + val ret = nativeControlTransfer(libUsbHandle, requestType, request, value, index, buffer, length, TRANSFER_TIMEOUT) if (ret < 0) { throw LibusbException("libusb control transfer failed", LibusbError.fromCode(ret)) @@ -97,6 +104,8 @@ class LibusbCommunication( } override fun resetDevice() { + require(!closed) { "device is closed" } + if (!deviceConnection!!.releaseInterface(usbInterface)) { Log.w(TAG, "Failed to release interface, errno: ${ErrNo.errno} ${ErrNo.errstr}") } @@ -118,14 +127,22 @@ class LibusbCommunication( } override fun clearFeatureHalt(endpoint: UsbEndpoint) { + require(!closed) { "device is closed" } + val ret = nativeClearHalt(libUsbHandle, endpoint.address) Log.d(TAG, "libusb clearFeatureHalt returned $ret: ${LibusbError.fromCode(ret).message}") } override fun close() { - deviceConnection!!.releaseInterface(usbInterface) - nativeClose(libUsbHandle, usbInterface.id) - deviceConnection!!.close() + require(!closed) { "device is already closed" } + + try { + deviceConnection!!.releaseInterface(usbInterface) + nativeClose(libUsbHandle, usbInterface.id) + deviceConnection!!.close() + } finally { + closed = true + } } companion object { From 00bb5aad3f446eb8a0464264d7214bdccea22607 Mon Sep 17 00:00:00 2001 From: Davide Depau Date: Fri, 10 Mar 2023 20:04:44 +0100 Subject: [PATCH 08/11] Prevent Android communications usage after closing --- .../jahnen/libaums/core/usb/AndroidUsbCommunication.kt | 10 +++++++++- .../libaums/core/usb/HoneyCombMr1Communication.kt | 4 ++++ .../libaums/core/usb/JellyBeanMr2Communication.kt | 4 ++++ 3 files changed, 17 insertions(+), 1 deletion(-) diff --git a/libaums/src/main/java/me/jahnen/libaums/core/usb/AndroidUsbCommunication.kt b/libaums/src/main/java/me/jahnen/libaums/core/usb/AndroidUsbCommunication.kt index 58c08326..2ab7acb9 100644 --- a/libaums/src/main/java/me/jahnen/libaums/core/usb/AndroidUsbCommunication.kt +++ b/libaums/src/main/java/me/jahnen/libaums/core/usb/AndroidUsbCommunication.kt @@ -17,7 +17,7 @@ internal abstract class AndroidUsbCommunication( private var isNativeInited: Boolean = false var deviceConnection: UsbDeviceConnection? = null - private var isClosed = false + protected var isClosed = false init { initNativeLibrary() @@ -49,10 +49,14 @@ internal abstract class AndroidUsbCommunication( } override fun controlTransfer(requestType: Int, request: Int, value: Int, index: Int, buffer: ByteArray, length: Int): Int { + require(!isClosed) { "device is closed" } + return deviceConnection!!.controlTransfer(requestType, request, value, index, buffer, length, TRANSFER_TIMEOUT) } override fun resetDevice() { + require(!isClosed) { "device is closed" } + Log.d(TAG, "Performing native reset") if (!deviceConnection!!.releaseInterface(usbInterface)) { @@ -70,6 +74,8 @@ internal abstract class AndroidUsbCommunication( } override fun clearFeatureHalt(endpoint: UsbEndpoint) { + require(!isClosed) { "device is closed" } + Log.w(TAG, "Clearing halt on endpoint $endpoint (direction ${endpoint.direction})") val result = clearHaltNative(deviceConnection!!.fileDescriptor, endpoint.address) if (!result) { @@ -90,6 +96,8 @@ internal abstract class AndroidUsbCommunication( } override fun close() { + require(!isClosed) { "device is already closed" } + Log.d(TAG, "close device") closeUsbConnection() isClosed = true diff --git a/libaums/src/main/java/me/jahnen/libaums/core/usb/HoneyCombMr1Communication.kt b/libaums/src/main/java/me/jahnen/libaums/core/usb/HoneyCombMr1Communication.kt index 33c7e85b..447f6172 100644 --- a/libaums/src/main/java/me/jahnen/libaums/core/usb/HoneyCombMr1Communication.kt +++ b/libaums/src/main/java/me/jahnen/libaums/core/usb/HoneyCombMr1Communication.kt @@ -25,6 +25,8 @@ internal class HoneyCombMr1Communication( @Throws(IOException::class) override fun bulkOutTransfer(src: ByteBuffer): Int { + require(!isClosed) { "device is closed" } + val offset = src.position() if (offset == 0) { @@ -54,6 +56,8 @@ internal class HoneyCombMr1Communication( @Throws(IOException::class) override fun bulkInTransfer(dest: ByteBuffer): Int { + require(!isClosed) { "device is closed" } + val offset = dest.position() if (offset == 0) { diff --git a/libaums/src/main/java/me/jahnen/libaums/core/usb/JellyBeanMr2Communication.kt b/libaums/src/main/java/me/jahnen/libaums/core/usb/JellyBeanMr2Communication.kt index bdc50bb0..bf1b706c 100644 --- a/libaums/src/main/java/me/jahnen/libaums/core/usb/JellyBeanMr2Communication.kt +++ b/libaums/src/main/java/me/jahnen/libaums/core/usb/JellyBeanMr2Communication.kt @@ -30,6 +30,8 @@ internal class JellyBeanMr2Communication( @Throws(IOException::class) override fun bulkOutTransfer(src: ByteBuffer): Int { + require(!isClosed) { "device is closed" } + val result = deviceConnection!!.bulkTransfer(outEndpoint, src.array(), src.position(), src.remaining(), UsbCommunication.TRANSFER_TIMEOUT) @@ -46,6 +48,8 @@ internal class JellyBeanMr2Communication( @Throws(IOException::class) override fun bulkInTransfer(dest: ByteBuffer): Int { + require(!isClosed) { "device is closed" } + val result = deviceConnection!!.bulkTransfer(inEndpoint, dest.array(), dest.position(), dest.remaining(), UsbCommunication.TRANSFER_TIMEOUT) From bdf1f77da3c5da588471b1b896bb17fd4337ff63 Mon Sep 17 00:00:00 2001 From: Magnus Date: Fri, 10 Mar 2023 23:38:40 +0100 Subject: [PATCH 09/11] fix GPT --- .../github/mjdev/libaums/partition/gpt/GPT.kt | 53 +++++++++++++------ .../core/partition/PartitionTableFactory.kt | 2 +- 2 files changed, 38 insertions(+), 17 deletions(-) diff --git a/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt index 4879475d..ae5e74dd 100644 --- a/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt +++ b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt @@ -1,15 +1,17 @@ package com.github.mjdev.libaums.partition.gpt +import android.util.Log import me.jahnen.libaums.core.driver.BlockDeviceDriver import me.jahnen.libaums.core.partition.PartitionTable import me.jahnen.libaums.core.partition.PartitionTableEntry import java.io.IOException import java.nio.ByteBuffer +import java.nio.ByteOrder import java.util.ArrayList class GPT private constructor(): PartitionTable { - // See also https://zh.wikipedia.org/wiki/GUID%E7%A3%81%E7%A2%9F%E5%88%86%E5%89%B2%E8%A1% + // See also https://en.wikipedia.org/wiki/GUID_Partition_Table private val partitions = ArrayList() @@ -18,28 +20,47 @@ class GPT private constructor(): PartitionTable { get() = partitions companion object { + private val TAG = GPT::class.java.simpleName + const val EFI_PART = "EFI PART" - const val EFI_PART = "EFI_PART" + const val GPT_OFFSET = 512 // GPT has a protective MBR, GPT starts after + + const val ENTRY_SIZE = 128 + + const val FIRST_LBA_OFFSET = 32 + const val LAST_LBA_OFFSET = 40 @Throws(IOException::class) fun read(blockDevice: BlockDeviceDriver): GPT? { val result = GPT() - val buffer = ByteBuffer.allocate(Math.max(128, blockDevice.blockSize)) - blockDevice.read(512, buffer) // LBA 0 - - if (String(buffer.array(), 0x00, 8) == EFI_PART) { - blockDevice.read(1024L + (result.partitions.size * 128), buffer) - while (buffer[0].toInt() != 0) { - val offset = 1024 + (result.partitions.size * 128) - val entry = PartitionTableEntry(-1, // Unknown - buffer.getInt(offset + 32), buffer.getInt(offset + 40)) - - result.partitions.add(entry) - blockDevice.read(offset + 128L, buffer) - } - } else { + var buffer = ByteBuffer.allocate(512 * 2) + blockDevice.read(0, buffer) + + val efiTestString = String(buffer.array(), GPT_OFFSET, 8, Charsets.US_ASCII) + Log.d(TAG, "EFI test string $efiTestString") + + if (efiTestString != EFI_PART) { return null } + Log.d(TAG, "EFI test string matches!") + + + buffer = ByteBuffer.allocate(512 * 34) // at LBA 34 GPT should stop + blockDevice.read(0, buffer) + buffer.order(ByteOrder.LITTLE_ENDIAN) + + var entry_offset = 1024 + + while (buffer[entry_offset].toInt() != 0) { + val entry = PartitionTableEntry(-1, // Unknown + buffer.getLong(entry_offset + FIRST_LBA_OFFSET).toInt(), + buffer.getLong(entry_offset + LAST_LBA_OFFSET).toInt()) + + result.partitions.add(entry) + + entry_offset += ENTRY_SIZE + } + return result } diff --git a/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableFactory.kt b/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableFactory.kt index a4af3dcd..6eb3ba37 100644 --- a/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableFactory.kt +++ b/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableFactory.kt @@ -32,7 +32,7 @@ import java.util.* * @author mjahnen */ object PartitionTableFactory { - private val TAG = MasterBootRecord::class.java.simpleName + private val TAG = PartitionTableFactory::class.java.simpleName private val partitionTables = ArrayList() From ba99350969d6325e052aa21f66406b3a38a750f9 Mon Sep 17 00:00:00 2001 From: Magnus Date: Sat, 11 Mar 2023 00:01:09 +0100 Subject: [PATCH 10/11] Make lba address Long instead of int --- .../main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt | 5 +++-- .../java/me/jahnen/libaums/core/driver/ByteBlockDevice.kt | 2 +- .../me/jahnen/libaums/core/partition/PartitionTableEntry.kt | 6 +++--- .../libaums/core/partition/fs/FileSystemPartitionTable.kt | 2 +- .../jahnen/libaums/core/partition/mbr/MasterBootRecord.kt | 2 +- 5 files changed, 9 insertions(+), 8 deletions(-) diff --git a/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt index ae5e74dd..b8020182 100644 --- a/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt +++ b/libaums/src/main/java/com/github/mjdev/libaums/partition/gpt/GPT.kt @@ -52,9 +52,10 @@ class GPT private constructor(): PartitionTable { var entry_offset = 1024 while (buffer[entry_offset].toInt() != 0) { + val firstLba = buffer.getLong(entry_offset + FIRST_LBA_OFFSET) val entry = PartitionTableEntry(-1, // Unknown - buffer.getLong(entry_offset + FIRST_LBA_OFFSET).toInt(), - buffer.getLong(entry_offset + LAST_LBA_OFFSET).toInt()) + firstLba, + buffer.getLong(entry_offset + LAST_LBA_OFFSET) - firstLba) result.partitions.add(entry) diff --git a/libaums/src/main/java/me/jahnen/libaums/core/driver/ByteBlockDevice.kt b/libaums/src/main/java/me/jahnen/libaums/core/driver/ByteBlockDevice.kt index 7c00c2c2..9c1c77c2 100644 --- a/libaums/src/main/java/me/jahnen/libaums/core/driver/ByteBlockDevice.kt +++ b/libaums/src/main/java/me/jahnen/libaums/core/driver/ByteBlockDevice.kt @@ -9,7 +9,7 @@ import java.nio.ByteBuffer * and [ByteBlockDevice.read]. Uses [BlockDeviceDriver.getBlockSize] * to calculate device offsets. */ -open class ByteBlockDevice @JvmOverloads constructor(private val targetBlockDevice: BlockDeviceDriver, private val logicalOffsetToAdd: Int = 0) : BlockDeviceDriver { +open class ByteBlockDevice @JvmOverloads constructor(private val targetBlockDevice: BlockDeviceDriver, private val logicalOffsetToAdd: Long = 0) : BlockDeviceDriver { override val blockSize: Int get() = targetBlockDevice.blockSize diff --git a/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableEntry.kt b/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableEntry.kt index 8daf3dc6..e8d290b9 100644 --- a/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableEntry.kt +++ b/libaums/src/main/java/me/jahnen/libaums/core/partition/PartitionTableEntry.kt @@ -35,7 +35,7 @@ class PartitionTableEntry * @param totalNumberOfSectors * The total numbers of sectors occupied by the partition. */ -(partitionType: Int, logicalBlockAddress: Int, totalNumberOfSectors: Int) { +(partitionType: Int, logicalBlockAddress: Long, totalNumberOfSectors: Long) { /** * @@ -48,7 +48,7 @@ class PartitionTableEntry * @return The logical block address where this partitions starts on the * device. */ - var logicalBlockAddress: Int = 0 + var logicalBlockAddress: Long = 0 internal set /** * @@ -56,7 +56,7 @@ class PartitionTableEntry * value is often unused because the same information is also stored * in the specific file system. */ - var totalNumberOfSectors: Int = 0 + var totalNumberOfSectors: Long = 0 internal set init { diff --git a/libaums/src/main/java/me/jahnen/libaums/core/partition/fs/FileSystemPartitionTable.kt b/libaums/src/main/java/me/jahnen/libaums/core/partition/fs/FileSystemPartitionTable.kt index d30813da..1874c75e 100644 --- a/libaums/src/main/java/me/jahnen/libaums/core/partition/fs/FileSystemPartitionTable.kt +++ b/libaums/src/main/java/me/jahnen/libaums/core/partition/fs/FileSystemPartitionTable.kt @@ -24,7 +24,7 @@ class FileSystemPartitionTable(blockDevice: BlockDeviceDriver, fs: FileSystem) : init { Log.i(TAG, "Found a device without partition table, yay!") - val totalNumberOfSectors = fs.capacity.toInt() / blockDevice.blockSize + val totalNumberOfSectors = fs.capacity / blockDevice.blockSize if (fs.capacity % blockDevice.blockSize != 0L) { Log.w(TAG, "fs capacity is not multiple of block size") } diff --git a/libaums/src/main/java/me/jahnen/libaums/core/partition/mbr/MasterBootRecord.kt b/libaums/src/main/java/me/jahnen/libaums/core/partition/mbr/MasterBootRecord.kt index ad643a2c..7b6c7315 100644 --- a/libaums/src/main/java/me/jahnen/libaums/core/partition/mbr/MasterBootRecord.kt +++ b/libaums/src/main/java/me/jahnen/libaums/core/partition/mbr/MasterBootRecord.kt @@ -111,7 +111,7 @@ class MasterBootRecord private constructor() : PartitionTable { } val entry = PartitionTableEntry(type, - buffer.getInt(offset + 8), buffer.getInt(offset + 12)) + buffer.getInt(offset + 8).toLong(), buffer.getInt(offset + 12).toLong()) result.partitions.add(entry) } From e5a31e98b3241cee4086848f49a5a370938bdb71 Mon Sep 17 00:00:00 2001 From: Magnus Date: Sat, 11 Mar 2023 11:59:03 +0100 Subject: [PATCH 11/11] bump version numbers --- README.md | 2 +- libaums/build.gradle | 2 +- libusbcommunication/README.md | 2 +- libusbcommunication/build.gradle | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index abba7c6b..4edb4869 100644 --- a/README.md +++ b/README.md @@ -13,7 +13,7 @@ A library to access USB mass storage devices (pen drives, external HDDs, card re The library can be included into your project like this: ```ruby -implementation 'me.jahnen.libaums:core:0.9.4' +implementation 'me.jahnen.libaums:core:0.10.0' ``` If you need the HTTP or the storage provider module: diff --git a/libaums/build.gradle b/libaums/build.gradle index 1ce572b8..3cc63eea 100644 --- a/libaums/build.gradle +++ b/libaums/build.gradle @@ -9,7 +9,7 @@ jacoco { ext { PUBLISH_GROUP_ID = 'me.jahnen.libaums' - PUBLISH_VERSION = '0.9.4' + PUBLISH_VERSION = '0.10.0' PUBLISH_ARTIFACT_ID = 'core' } diff --git a/libusbcommunication/README.md b/libusbcommunication/README.md index cdd31f3c..3aab9409 100644 --- a/libusbcommunication/README.md +++ b/libusbcommunication/README.md @@ -38,7 +38,7 @@ Refer to the following blog where someone claims that LPGL cannot be used in clo #### Inclusion in your build.gradle ```ruby -implementation 'me.jahnen.libaums:libusbcommunication:0.2.4' +implementation 'me.jahnen.libaums:libusbcommunication:0.3.0' ``` ### Activate libusb communication diff --git a/libusbcommunication/build.gradle b/libusbcommunication/build.gradle index 4444ccc2..7b958f07 100644 --- a/libusbcommunication/build.gradle +++ b/libusbcommunication/build.gradle @@ -8,7 +8,7 @@ String libusbDir = props['libusb.dir'] ext { PUBLISH_GROUP_ID = 'me.jahnen.libaums' - PUBLISH_VERSION = '0.2.4' + PUBLISH_VERSION = '0.3.0' PUBLISH_ARTIFACT_ID = 'libusbcommunication' }