mirror of
https://github.com/revanced/revanced-patcher
synced 2025-02-28 13:13:01 +01:00
feat: Closeable
patches
This commit is contained in:
parent
3de999a2d3
commit
bbd40bf2f6
@ -32,6 +32,7 @@ import org.jf.dexlib2.Opcodes
|
|||||||
import org.jf.dexlib2.iface.ClassDef
|
import org.jf.dexlib2.iface.ClassDef
|
||||||
import org.jf.dexlib2.iface.DexFile
|
import org.jf.dexlib2.iface.DexFile
|
||||||
import org.jf.dexlib2.writer.io.MemoryDataStore
|
import org.jf.dexlib2.writer.io.MemoryDataStore
|
||||||
|
import java.io.Closeable
|
||||||
import java.io.File
|
import java.io.File
|
||||||
import java.nio.file.Files
|
import java.nio.file.Files
|
||||||
|
|
||||||
@ -247,13 +248,13 @@ class Patcher(private val options: PatcherOptions) {
|
|||||||
*/
|
*/
|
||||||
private fun applyPatch(
|
private fun applyPatch(
|
||||||
patch: Class<out Patch<Data>>,
|
patch: Class<out Patch<Data>>,
|
||||||
appliedPatches: MutableMap<String, Boolean>
|
appliedPatches: LinkedHashMap<String, AppliedPatch>
|
||||||
): PatchResult {
|
): PatchResult {
|
||||||
val patchName = patch.patchName
|
val patchName = patch.patchName
|
||||||
|
|
||||||
// if the patch has already applied silently skip it
|
// if the patch has already applied silently skip it
|
||||||
if (appliedPatches.contains(patchName)) {
|
if (appliedPatches.contains(patchName)) {
|
||||||
if (!appliedPatches[patchName]!!)
|
if (!appliedPatches[patchName]!!.success)
|
||||||
return PatchResultError("'$patchName' did not succeed previously")
|
return PatchResultError("'$patchName' did not succeed previously")
|
||||||
|
|
||||||
logger.trace("Skipping '$patchName' because it has already been applied")
|
logger.trace("Skipping '$patchName' because it has already been applied")
|
||||||
@ -298,10 +299,10 @@ class Patcher(private val options: PatcherOptions) {
|
|||||||
|
|
||||||
return try {
|
return try {
|
||||||
val result = patchInstance.execute(data)
|
val result = patchInstance.execute(data)
|
||||||
appliedPatches[patchName] = result.isSuccess()
|
appliedPatches[patchName] = AppliedPatch(patchInstance, result.isSuccess())
|
||||||
result
|
result
|
||||||
} catch (e: Exception) {
|
} catch (e: Exception) {
|
||||||
appliedPatches[patchName] = false
|
appliedPatches[patchName] = AppliedPatch(patchInstance, false)
|
||||||
PatchResultError(e)
|
PatchResultError(e)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -313,23 +314,41 @@ class Patcher(private val options: PatcherOptions) {
|
|||||||
*/
|
*/
|
||||||
fun applyPatches(stopOnError: Boolean = false) = sequence {
|
fun applyPatches(stopOnError: Boolean = false) = sequence {
|
||||||
logger.trace("Applying all patches")
|
logger.trace("Applying all patches")
|
||||||
val appliedPatches = mutableMapOf<String, Boolean>() // first is success, second is name
|
|
||||||
|
|
||||||
for (patch in data.patches) {
|
val appliedPatches = LinkedHashMap<String, AppliedPatch>() // first is name
|
||||||
val patchResult = applyPatch(patch, appliedPatches)
|
|
||||||
|
|
||||||
val result = if (patchResult.isSuccess()) {
|
try {
|
||||||
Result.success(patchResult.success()!!)
|
for (patch in data.patches) {
|
||||||
} else {
|
val patchResult = applyPatch(patch, appliedPatches)
|
||||||
Result.failure(patchResult.error()!!)
|
|
||||||
|
val result = if (patchResult.isSuccess()) {
|
||||||
|
Result.success(patchResult.success()!!)
|
||||||
|
} else {
|
||||||
|
Result.failure(patchResult.error()!!)
|
||||||
|
}
|
||||||
|
|
||||||
|
yield(patch.patchName to result)
|
||||||
|
if (stopOnError && patchResult.isError()) break
|
||||||
}
|
}
|
||||||
|
} finally {
|
||||||
|
// close all closeable patches in order
|
||||||
|
for ((patch, _) in appliedPatches.values.reversed()) {
|
||||||
|
if (patch !is Closeable) continue
|
||||||
|
|
||||||
yield(patch.patchName to result)
|
patch.close()
|
||||||
if (stopOnError && patchResult.isError()) break
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A result of applying a [Patch].
|
||||||
|
*
|
||||||
|
* @param patchInstance The instance of the [Patch] that was applied.
|
||||||
|
* @param success The result of the [Patch].
|
||||||
|
*/
|
||||||
|
internal data class AppliedPatch(val patchInstance: Patch<Data>, val success: Boolean)
|
||||||
|
|
||||||
private fun BuildOptions.setBuildOptions(options: PatcherOptions) {
|
private fun BuildOptions.setBuildOptions(options: PatcherOptions) {
|
||||||
this.aaptPath = options.aaptPath
|
this.aaptPath = options.aaptPath
|
||||||
this.useAapt2 = true
|
this.useAapt2 = true
|
||||||
|
@ -3,14 +3,16 @@ package app.revanced.patcher.patch
|
|||||||
import app.revanced.patcher.data.Data
|
import app.revanced.patcher.data.Data
|
||||||
import app.revanced.patcher.patch.impl.BytecodePatch
|
import app.revanced.patcher.patch.impl.BytecodePatch
|
||||||
import app.revanced.patcher.patch.impl.ResourcePatch
|
import app.revanced.patcher.patch.impl.ResourcePatch
|
||||||
|
import java.io.Closeable
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A ReVanced patch.
|
* A ReVanced patch.
|
||||||
|
*
|
||||||
* Can either be a [ResourcePatch] or a [BytecodePatch].
|
* Can either be a [ResourcePatch] or a [BytecodePatch].
|
||||||
|
* If it implements [Closeable], it will be closed after all patches have been executed.
|
||||||
|
* Closing will be done in reverse execution order.
|
||||||
*/
|
*/
|
||||||
abstract class Patch<out T : Data> {
|
abstract class Patch<out T : Data> {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The main function of the [Patch] which the patcher will call.
|
* The main function of the [Patch] which the patcher will call.
|
||||||
*/
|
*/
|
||||||
|
Loading…
x
Reference in New Issue
Block a user