mirror of
https://github.com/NationalSecurityAgency/ghidra.git
synced 2025-10-05 19:42:36 +02:00
GP-3122 Added AutoCloseable Transaction API to DBHandle and
UndoableDomainObject. Performed renaming of some internal classes.
This commit is contained in:
parent
b4de95f4f5
commit
1795c35dfc
209 changed files with 1892 additions and 2054 deletions
|
@ -53,7 +53,7 @@ abstract class AbstractTransactionManager {
|
|||
checkLockingTask();
|
||||
|
||||
synchronized (this) {
|
||||
if (getCurrentTransaction() != null && !transactionTerminated) {
|
||||
if (getCurrentTransactionInfo() != null && !transactionTerminated) {
|
||||
return false;
|
||||
}
|
||||
if (lockCount == 0) {
|
||||
|
@ -85,7 +85,7 @@ abstract class AbstractTransactionManager {
|
|||
return null;
|
||||
}
|
||||
checkDomainObject(domainObj);
|
||||
if (lockCount != 0 || getCurrentTransaction() != null || lockingTaskMonitor != null) {
|
||||
if (lockCount != 0 || getCurrentTransactionInfo() != null || lockingTaskMonitor != null) {
|
||||
return null;
|
||||
}
|
||||
++lockCount; // prevent prepareToSave
|
||||
|
@ -192,14 +192,15 @@ abstract class AbstractTransactionManager {
|
|||
}
|
||||
|
||||
final int startTransaction(DomainObjectAdapterDB object, String description,
|
||||
AbortedTransactionListener listener, boolean notify) {
|
||||
AbortedTransactionListener listener, boolean notify)
|
||||
throws TerminatedTransactionException {
|
||||
|
||||
checkLockingTask();
|
||||
|
||||
synchronized (this) {
|
||||
checkDomainObject(object);
|
||||
|
||||
if (getCurrentTransaction() != null && transactionTerminated) {
|
||||
if (getCurrentTransactionInfo() != null && transactionTerminated) {
|
||||
throw new TerminatedTransactionException();
|
||||
}
|
||||
|
||||
|
@ -210,8 +211,8 @@ abstract class AbstractTransactionManager {
|
|||
abstract int startTransaction(DomainObjectAdapterDB object, String description,
|
||||
AbortedTransactionListener listener, boolean force, boolean notify);
|
||||
|
||||
abstract Transaction endTransaction(DomainObjectAdapterDB object, int transactionID,
|
||||
boolean commit, boolean notify);
|
||||
abstract TransactionInfo endTransaction(DomainObjectAdapterDB object, int transactionID,
|
||||
boolean commit, boolean notify) throws IllegalStateException;
|
||||
|
||||
/**
|
||||
* Returns the undo stack depth.
|
||||
|
@ -229,14 +230,14 @@ abstract class AbstractTransactionManager {
|
|||
|
||||
abstract String getUndoName();
|
||||
|
||||
abstract Transaction getCurrentTransaction();
|
||||
abstract TransactionInfo getCurrentTransactionInfo();
|
||||
|
||||
final void redo() throws IOException {
|
||||
|
||||
checkLockingTask();
|
||||
|
||||
synchronized (this) {
|
||||
if (getCurrentTransaction() != null) {
|
||||
if (getCurrentTransactionInfo() != null) {
|
||||
throw new IllegalStateException("Can not redo while transaction is open");
|
||||
}
|
||||
verifyNoLock();
|
||||
|
@ -251,9 +252,9 @@ abstract class AbstractTransactionManager {
|
|||
checkLockingTask();
|
||||
|
||||
synchronized (this) {
|
||||
if (getCurrentTransaction() != null) {
|
||||
if (getCurrentTransactionInfo() != null) {
|
||||
throw new IllegalStateException("Can not undo while transaction is open: " +
|
||||
getCurrentTransaction().getDescription());
|
||||
getCurrentTransactionInfo().getDescription());
|
||||
}
|
||||
verifyNoLock();
|
||||
doUndo(true);
|
||||
|
|
|
@ -20,8 +20,7 @@ import java.io.IOException;
|
|||
import java.util.*;
|
||||
import java.util.function.Function;
|
||||
|
||||
import db.DBConstants;
|
||||
import db.DBHandle;
|
||||
import db.*;
|
||||
import db.util.ErrorHandler;
|
||||
import ghidra.framework.model.*;
|
||||
import ghidra.framework.options.Options;
|
||||
|
@ -32,7 +31,6 @@ import ghidra.util.Msg;
|
|||
import ghidra.util.ReadOnlyException;
|
||||
import ghidra.util.exception.CancelledException;
|
||||
import ghidra.util.task.TaskMonitor;
|
||||
import ghidra.util.task.TaskMonitorAdapter;
|
||||
|
||||
/**
|
||||
* Database version of the DomainObjectAdapter; this version adds the
|
||||
|
@ -273,7 +271,7 @@ public abstract class DomainObjectAdapterDB extends DomainObjectAdapter
|
|||
|
||||
@Override
|
||||
public boolean canLock() {
|
||||
return transactionMgr.getCurrentTransaction() == null && !closed;
|
||||
return transactionMgr.getCurrentTransactionInfo() == null && !closed;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -329,18 +327,40 @@ public abstract class DomainObjectAdapterDB extends DomainObjectAdapter
|
|||
}
|
||||
|
||||
@Override
|
||||
public int startTransaction(String description) {
|
||||
public Transaction openTransaction(String description)
|
||||
throws TerminatedTransactionException, IllegalStateException {
|
||||
return new Transaction() {
|
||||
|
||||
int txId = startTransaction(description);
|
||||
|
||||
@Override
|
||||
protected boolean endTransaction(boolean commit) {
|
||||
DomainObjectAdapterDB.this.endTransaction(txId, commit);
|
||||
return commit;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isSubTransaction() {
|
||||
return true;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public int startTransaction(String description) throws TerminatedTransactionException {
|
||||
return startTransaction(description, null);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int startTransaction(String description, AbortedTransactionListener listener) {
|
||||
public int startTransaction(String description, AbortedTransactionListener listener)
|
||||
throws TerminatedTransactionException {
|
||||
return startTransaction(description, listener, tryForeverExceptionHandler);
|
||||
}
|
||||
|
||||
// open for testing
|
||||
int startTransaction(String description, AbortedTransactionListener listener,
|
||||
Function<DomainObjectLockedException, Boolean> exceptionHandler) {
|
||||
Function<DomainObjectLockedException, Boolean> exceptionHandler)
|
||||
throws TerminatedTransactionException {
|
||||
|
||||
while (true) {
|
||||
try {
|
||||
|
@ -355,7 +375,7 @@ public abstract class DomainObjectAdapterDB extends DomainObjectAdapter
|
|||
}
|
||||
|
||||
@Override
|
||||
public void endTransaction(int transactionID, boolean commit) {
|
||||
public void endTransaction(int transactionID, boolean commit) throws IllegalStateException {
|
||||
transactionMgr.endTransaction(this, transactionID, commit, true);
|
||||
}
|
||||
|
||||
|
@ -408,8 +428,8 @@ public abstract class DomainObjectAdapterDB extends DomainObjectAdapter
|
|||
}
|
||||
|
||||
@Override
|
||||
public Transaction getCurrentTransaction() {
|
||||
return transactionMgr.getCurrentTransaction();
|
||||
public TransactionInfo getCurrentTransactionInfo() {
|
||||
return transactionMgr.getCurrentTransactionInfo();
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -28,14 +28,14 @@ import ghidra.util.datastruct.WeakSet;
|
|||
* <code>DomainObjectDBTransaction</code> represents an atomic undoable operation performed
|
||||
* on a single domain object.
|
||||
*/
|
||||
class DomainObjectDBTransaction implements Transaction {
|
||||
class DomainObjectDBTransaction implements TransactionInfo {
|
||||
|
||||
private static int nextBaseId = 1234;
|
||||
|
||||
private ArrayList<TransactionEntry> list;
|
||||
private HashMap<PluginTool, ToolState> toolStates;
|
||||
private int activeEntries = 0;
|
||||
private int status = NOT_DONE;
|
||||
private Status status = Status.NOT_DONE;
|
||||
private boolean hasDBTransaction = false;
|
||||
private final long id;
|
||||
private WeakSet<AbortedTransactionListener> abortedTransactionListeners =
|
||||
|
@ -106,7 +106,7 @@ class DomainObjectDBTransaction implements Transaction {
|
|||
* database transaction/checkpoint.
|
||||
*/
|
||||
void setHasCommittedDBTransaction() {
|
||||
if (getStatus() != COMMITTED) {
|
||||
if (getStatus() != Status.COMMITTED) {
|
||||
throw new IllegalStateException("transaction was not committed");
|
||||
}
|
||||
hasDBTransaction = true;
|
||||
|
@ -147,23 +147,23 @@ class DomainObjectDBTransaction implements Transaction {
|
|||
catch (IndexOutOfBoundsException e) {
|
||||
throw new IllegalStateException("Transaction not found");
|
||||
}
|
||||
if (entry.status != NOT_DONE) {
|
||||
if (entry.status != Status.NOT_DONE) {
|
||||
throw new IllegalStateException("Attempted to end Transaction " + "more that once: " +
|
||||
entry.description);
|
||||
}
|
||||
entry.status = commit ? COMMITTED : ABORTED;
|
||||
entry.status = commit ? Status.COMMITTED : Status.ABORTED;
|
||||
if (!commit) {
|
||||
status = ABORTED;
|
||||
status = Status.ABORTED;
|
||||
}
|
||||
if (--activeEntries == 0 && status == NOT_DONE) {
|
||||
status = COMMITTED;
|
||||
if (--activeEntries == 0 && status == Status.NOT_DONE) {
|
||||
status = Status.COMMITTED;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getStatus() {
|
||||
if (status == ABORTED && activeEntries > 0) {
|
||||
return NOT_DONE_BUT_ABORTED;
|
||||
public Status getStatus() {
|
||||
if (status == Status.ABORTED && activeEntries > 0) {
|
||||
return Status.NOT_DONE_BUT_ABORTED;
|
||||
}
|
||||
return status;
|
||||
}
|
||||
|
@ -224,7 +224,7 @@ class DomainObjectDBTransaction implements Transaction {
|
|||
Iterator<TransactionEntry> iter = list.iterator();
|
||||
while (iter.hasNext()) {
|
||||
TransactionEntry entry = iter.next();
|
||||
if (entry.status == NOT_DONE) {
|
||||
if (entry.status == Status.NOT_DONE) {
|
||||
subTxList.add(entry.description);
|
||||
}
|
||||
}
|
||||
|
@ -233,11 +233,11 @@ class DomainObjectDBTransaction implements Transaction {
|
|||
|
||||
private static class TransactionEntry {
|
||||
String description;
|
||||
int status;
|
||||
Status status;
|
||||
|
||||
TransactionEntry(String description) {
|
||||
this.description = description;
|
||||
status = NOT_DONE;
|
||||
status = Status.NOT_DONE;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -256,7 +256,7 @@ class DomainObjectDBTransaction implements Transaction {
|
|||
}
|
||||
|
||||
void abort() {
|
||||
status = ABORTED;
|
||||
status = Status.ABORTED;
|
||||
for (AbortedTransactionListener listener : abortedTransactionListeners) {
|
||||
listener.transactionAborted(id);
|
||||
}
|
||||
|
|
|
@ -19,6 +19,7 @@ import java.io.IOException;
|
|||
import java.util.LinkedList;
|
||||
|
||||
import ghidra.framework.model.*;
|
||||
import ghidra.framework.model.TransactionInfo.Status;
|
||||
import ghidra.util.Msg;
|
||||
import ghidra.util.SystemUtilities;
|
||||
import ghidra.util.datastruct.WeakDataStructureFactory;
|
||||
|
@ -138,8 +139,8 @@ class DomainObjectTransactionManager extends AbstractTransactionManager {
|
|||
}
|
||||
|
||||
@Override
|
||||
synchronized Transaction endTransaction(DomainObjectAdapterDB object, int transactionID,
|
||||
boolean commit, boolean notify) {
|
||||
synchronized TransactionInfo endTransaction(DomainObjectAdapterDB object, int transactionID,
|
||||
boolean commit, boolean notify) throws IllegalStateException {
|
||||
if (object != domainObj) {
|
||||
throw new IllegalArgumentException("invalid domain object");
|
||||
}
|
||||
|
@ -149,8 +150,8 @@ class DomainObjectTransactionManager extends AbstractTransactionManager {
|
|||
DomainObjectDBTransaction returnedTransaction = transaction;
|
||||
try {
|
||||
transaction.endEntry(transactionID, commit && !transactionTerminated);
|
||||
int status = transaction.getStatus();
|
||||
if (status == Transaction.COMMITTED) {
|
||||
Status status = transaction.getStatus();
|
||||
if (status == Status.COMMITTED) {
|
||||
object.flushWriteCache();
|
||||
boolean committed = domainObj.dbh.endTransaction(transaction.getID(), true);
|
||||
if (committed) {
|
||||
|
@ -171,7 +172,7 @@ class DomainObjectTransactionManager extends AbstractTransactionManager {
|
|||
}
|
||||
transaction = null;
|
||||
}
|
||||
else if (status == Transaction.ABORTED) {
|
||||
else if (status == Status.ABORTED) {
|
||||
object.invalidateWriteCache();
|
||||
if (!transactionTerminated) {
|
||||
domainObj.dbh.endTransaction(transaction.getID(), false);
|
||||
|
@ -225,7 +226,7 @@ class DomainObjectTransactionManager extends AbstractTransactionManager {
|
|||
@Override
|
||||
synchronized String getRedoName() {
|
||||
if (transaction == null && redoList.size() > 0) {
|
||||
Transaction t = redoList.getLast();
|
||||
TransactionInfo t = redoList.getLast();
|
||||
return t.getDescription();
|
||||
}
|
||||
return "";
|
||||
|
@ -234,14 +235,14 @@ class DomainObjectTransactionManager extends AbstractTransactionManager {
|
|||
@Override
|
||||
synchronized String getUndoName() {
|
||||
if (transaction == null && undoList.size() > 0) {
|
||||
Transaction t = undoList.getLast();
|
||||
TransactionInfo t = undoList.getLast();
|
||||
return t.getDescription();
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
@Override
|
||||
Transaction getCurrentTransaction() {
|
||||
TransactionInfo getCurrentTransactionInfo() {
|
||||
return transaction;
|
||||
}
|
||||
|
||||
|
@ -318,7 +319,7 @@ class DomainObjectTransactionManager extends AbstractTransactionManager {
|
|||
transactionListeners.remove(listener);
|
||||
}
|
||||
|
||||
void notifyStartTransaction(Transaction tx) {
|
||||
void notifyStartTransaction(TransactionInfo tx) {
|
||||
SystemUtilities.runSwingLater(() -> {
|
||||
for (TransactionListener listener : transactionListeners) {
|
||||
listener.transactionStarted(domainObj, tx);
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
/* ###
|
||||
* IP: GHIDRA
|
||||
* REVIEWED: YES
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
@ -16,17 +15,17 @@
|
|||
*/
|
||||
package ghidra.framework.data;
|
||||
|
||||
import ghidra.framework.model.AbortedTransactionListener;
|
||||
import ghidra.framework.model.Transaction;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.ArrayList;
|
||||
|
||||
import ghidra.framework.model.AbortedTransactionListener;
|
||||
import ghidra.framework.model.TransactionInfo;
|
||||
|
||||
/**
|
||||
* <code>SynchronizedTransaction</code> represents an atomic undoable operation performed
|
||||
* on a synchronized set of domain objects.
|
||||
*/
|
||||
class SynchronizedTransaction implements Transaction {
|
||||
class SynchronizedTransaction implements TransactionInfo {
|
||||
|
||||
private DomainObjectTransactionManager[] managers;
|
||||
private int[] holdTransactionIds;
|
||||
|
@ -34,7 +33,7 @@ class SynchronizedTransaction implements Transaction {
|
|||
private String[] descriptions;
|
||||
private int[] activeCounts;
|
||||
|
||||
private int status = NOT_DONE;
|
||||
private Status status = Status.NOT_DONE;
|
||||
private final long id;
|
||||
|
||||
SynchronizedTransaction(DomainObjectTransactionManager[] managers) {
|
||||
|
@ -81,13 +80,13 @@ class SynchronizedTransaction implements Transaction {
|
|||
@Override
|
||||
public ArrayList<String> getOpenSubTransactions() {
|
||||
ArrayList<String> list = new ArrayList<String>();
|
||||
int status = getStatus();
|
||||
if (status == ABORTED || status == COMMITTED) {
|
||||
Status status = getStatus();
|
||||
if (status == Status.ABORTED || status == Status.COMMITTED) {
|
||||
return list;
|
||||
}
|
||||
for (int i = 0; i < managers.length; i++) {
|
||||
String name = getDomainObjectName(managers[i]);
|
||||
for (String str : managers[i].getCurrentTransaction().getOpenSubTransactions()) {
|
||||
for (String str : managers[i].getCurrentTransactionInfo().getOpenSubTransactions()) {
|
||||
list.add(name + ": " + str);
|
||||
}
|
||||
}
|
||||
|
@ -104,9 +103,9 @@ class SynchronizedTransaction implements Transaction {
|
|||
}
|
||||
|
||||
@Override
|
||||
public int getStatus() {
|
||||
if (status == ABORTED && isActive()) {
|
||||
return NOT_DONE_BUT_ABORTED;
|
||||
public Status getStatus() {
|
||||
if (status == Status.ABORTED && isActive()) {
|
||||
return Status.NOT_DONE_BUT_ABORTED;
|
||||
}
|
||||
return status;
|
||||
}
|
||||
|
@ -126,11 +125,11 @@ class SynchronizedTransaction implements Transaction {
|
|||
int index = findDomainObject(domainObj);
|
||||
managers[index].endTransaction(domainObj, transactionID, commit, false);
|
||||
if (!commit) {
|
||||
status = ABORTED;
|
||||
status = Status.ABORTED;
|
||||
}
|
||||
--activeCounts[index];
|
||||
if (!isActive() && status == NOT_DONE) {
|
||||
status = COMMITTED;
|
||||
if (!isActive() && status == Status.NOT_DONE) {
|
||||
status = Status.COMMITTED;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -153,7 +152,7 @@ class SynchronizedTransaction implements Transaction {
|
|||
boolean endAll(boolean commit) {
|
||||
boolean hasChange = false;
|
||||
for (int i = 0; i < managers.length; i++) {
|
||||
Transaction transaction = managers[i].endTransaction(managers[i].getDomainObject(),
|
||||
TransactionInfo transaction = managers[i].endTransaction(managers[i].getDomainObject(),
|
||||
holdTransactionIds[i], commit, false);
|
||||
if (commit && transaction.hasCommittedDBTransaction()) {
|
||||
hasChanges[i] = true;
|
||||
|
|
|
@ -19,6 +19,7 @@ import java.io.IOException;
|
|||
import java.util.LinkedList;
|
||||
|
||||
import ghidra.framework.model.*;
|
||||
import ghidra.framework.model.TransactionInfo.Status;
|
||||
import ghidra.framework.store.LockException;
|
||||
import ghidra.util.Msg;
|
||||
|
||||
|
@ -59,8 +60,8 @@ class SynchronizedTransactionManager extends AbstractTransactionManager {
|
|||
if (!(mgr instanceof DomainObjectTransactionManager)) {
|
||||
throw new IllegalArgumentException("domain object has invalid transaction manager");
|
||||
}
|
||||
if (isLocked() || mgr.isLocked() || getCurrentTransaction() != null ||
|
||||
mgr.getCurrentTransaction() != null) {
|
||||
if (isLocked() || mgr.isLocked() || getCurrentTransactionInfo() != null ||
|
||||
mgr.getCurrentTransactionInfo() != null) {
|
||||
throw new LockException("domain object(s) are busy/locked");
|
||||
}
|
||||
if (!mgr.lock("Transaction manager join")) {
|
||||
|
@ -86,9 +87,9 @@ class SynchronizedTransactionManager extends AbstractTransactionManager {
|
|||
}
|
||||
|
||||
synchronized void removeDomainObject(DomainObjectAdapterDB domainObj) throws LockException {
|
||||
if (getCurrentTransaction() != null) {
|
||||
if (getCurrentTransactionInfo() != null) {
|
||||
throw new LockException(
|
||||
"domain object has open transaction: " + getCurrentTransaction().getDescription());
|
||||
"domain object has open transaction: " + getCurrentTransactionInfo().getDescription());
|
||||
}
|
||||
if (isLocked()) {
|
||||
throw new LockException("domain object is locked!");
|
||||
|
@ -177,15 +178,15 @@ class SynchronizedTransactionManager extends AbstractTransactionManager {
|
|||
}
|
||||
|
||||
@Override
|
||||
synchronized Transaction endTransaction(DomainObjectAdapterDB object, int transactionID,
|
||||
synchronized TransactionInfo endTransaction(DomainObjectAdapterDB object, int transactionID,
|
||||
boolean commit, boolean notify) {
|
||||
if (transaction == null) {
|
||||
throw new IllegalStateException("No transaction is open");
|
||||
}
|
||||
Transaction returnedTransaction = transaction;
|
||||
TransactionInfo returnedTransaction = transaction;
|
||||
transaction.endEntry(object, transactionID, commit && !transactionTerminated);
|
||||
int status = transaction.getStatus();
|
||||
if (status == Transaction.COMMITTED) {
|
||||
Status status = transaction.getStatus();
|
||||
if (status == Status.COMMITTED) {
|
||||
boolean committed = transaction.endAll(true);
|
||||
if (committed) {
|
||||
redoList.clear();
|
||||
|
@ -199,7 +200,7 @@ class SynchronizedTransactionManager extends AbstractTransactionManager {
|
|||
notifyEndTransaction();
|
||||
}
|
||||
}
|
||||
else if (status == Transaction.ABORTED) {
|
||||
else if (status == Status.ABORTED) {
|
||||
if (!transactionTerminated) {
|
||||
transaction.endAll(false);
|
||||
}
|
||||
|
@ -249,7 +250,7 @@ class SynchronizedTransactionManager extends AbstractTransactionManager {
|
|||
@Override
|
||||
synchronized String getRedoName() {
|
||||
if (redoList.size() > 0) {
|
||||
Transaction t = redoList.getLast();
|
||||
TransactionInfo t = redoList.getLast();
|
||||
return t.getDescription();
|
||||
}
|
||||
return "";
|
||||
|
@ -258,14 +259,14 @@ class SynchronizedTransactionManager extends AbstractTransactionManager {
|
|||
@Override
|
||||
synchronized String getUndoName() {
|
||||
if (undoList.size() > 0) {
|
||||
Transaction t = undoList.getLast();
|
||||
TransactionInfo t = undoList.getLast();
|
||||
return t.getDescription();
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
@Override
|
||||
Transaction getCurrentTransaction() {
|
||||
TransactionInfo getCurrentTransactionInfo() {
|
||||
return transaction;
|
||||
}
|
||||
|
||||
|
|
|
@ -370,7 +370,7 @@ class FileActionManager {
|
|||
buf.append("The File " + files.get(lastIndex).getPathname() +
|
||||
" is currently being modified by the\n");
|
||||
buf.append("the following actions:\n \n");
|
||||
Transaction t = udo.getCurrentTransaction();
|
||||
TransactionInfo t = udo.getCurrentTransactionInfo();
|
||||
List<String> list = t.getOpenSubTransactions();
|
||||
Iterator<String> it = list.iterator();
|
||||
while (it.hasNext()) {
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
/* ###
|
||||
* IP: GHIDRA
|
||||
* REVIEWED: YES
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
@ -18,12 +17,11 @@ package ghidra.framework.model;
|
|||
|
||||
import java.util.ArrayList;
|
||||
|
||||
public interface Transaction {
|
||||
public interface TransactionInfo {
|
||||
|
||||
public static final int NOT_DONE = 0;
|
||||
public static final int COMMITTED = 1;
|
||||
public static final int ABORTED = 2;
|
||||
public static final int NOT_DONE_BUT_ABORTED = 3;
|
||||
public enum Status {
|
||||
NOT_DONE, COMMITTED, ABORTED, NOT_DONE_BUT_ABORTED;
|
||||
}
|
||||
|
||||
public long getID();
|
||||
|
||||
|
@ -40,11 +38,16 @@ public interface Transaction {
|
|||
*/
|
||||
public ArrayList<String> getOpenSubTransactions();
|
||||
|
||||
public int getStatus();
|
||||
/**
|
||||
* Get the status of the corresponding transaction.
|
||||
* @return status
|
||||
*/
|
||||
public Status getStatus();
|
||||
|
||||
/**
|
||||
* Returns true if this fully committed transaction has a corresponding
|
||||
* database transaction/checkpoint.
|
||||
* Determine if the corresponding transaction, and all of its sub-transactions, has been
|
||||
* comitted to the underlying database.
|
||||
* @return true if the corresponding transaction has been comitted, else false.
|
||||
*/
|
||||
public boolean hasCommittedDBTransaction();
|
||||
|
|
@ -26,7 +26,7 @@ public interface TransactionListener {
|
|||
* @param domainObj the domain object where the transaction was started
|
||||
* @param tx the transaction that was started
|
||||
*/
|
||||
void transactionStarted(DomainObjectAdapterDB domainObj, Transaction tx);
|
||||
void transactionStarted(DomainObjectAdapterDB domainObj, TransactionInfo tx);
|
||||
|
||||
/**
|
||||
* Invoked when a transaction is ended.
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
/* ###
|
||||
* IP: GHIDRA
|
||||
* REVIEWED: YES
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
@ -16,9 +15,9 @@
|
|||
*/
|
||||
package ghidra.framework.model;
|
||||
|
||||
import ghidra.framework.store.LockException;
|
||||
|
||||
import db.TerminatedTransactionException;
|
||||
import db.Transaction;
|
||||
import ghidra.framework.store.LockException;
|
||||
|
||||
/**
|
||||
* <code>UndoableDomainObject</code> extends a domain object to provide transaction
|
||||
|
@ -35,6 +34,20 @@ import db.TerminatedTransactionException;
|
|||
*/
|
||||
public interface UndoableDomainObject extends DomainObject, Undoable {
|
||||
|
||||
/**
|
||||
* Open new transaction. This should generally be done with a try-with-resources block:
|
||||
* <pre>
|
||||
* try (Transaction tx = dobj.openTransaction(description)) {
|
||||
* // ... Do something
|
||||
* }
|
||||
* </pre>
|
||||
*
|
||||
* @param description a short description of the changes to be made.
|
||||
* @return transaction object
|
||||
* @throws IllegalStateException if this {@link DomainObject} has already been closed.
|
||||
*/
|
||||
public Transaction openTransaction(String description) throws IllegalStateException;
|
||||
|
||||
/**
|
||||
* Start a new transaction in order to make changes to this domain object.
|
||||
* All changes must be made in the context of a transaction.
|
||||
|
@ -71,10 +84,10 @@ public interface UndoableDomainObject extends DomainObject, Undoable {
|
|||
public void endTransaction(int transactionID, boolean commit);
|
||||
|
||||
/**
|
||||
* Returns the current transaction
|
||||
* @return the current transaction
|
||||
* Returns the current transaction info
|
||||
* @return the current transaction info
|
||||
*/
|
||||
public Transaction getCurrentTransaction();
|
||||
public TransactionInfo getCurrentTransactionInfo();
|
||||
|
||||
/**
|
||||
* Returns true if the last transaction was terminated externally from the action that
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue