From b5ccf1f06329024cc8884515e4964bd8a1c9adb7 Mon Sep 17 00:00:00 2001 From: ghidra1 Date: Tue, 8 Apr 2025 14:57:51 -0400 Subject: [PATCH 1/2] GP-0 Expose StandAloneDataTypeManager from DataTypeArchive.getDataTypeManager to allow architecture manipulation --- .../program/database/DataTypeArchiveDB.java | 21 +++++-------------- .../model/listing/DataTypeArchive.java | 13 ++++++------ 2 files changed, 12 insertions(+), 22 deletions(-) diff --git a/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/program/database/DataTypeArchiveDB.java b/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/program/database/DataTypeArchiveDB.java index a3ba467476..ed4455b844 100644 --- a/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/program/database/DataTypeArchiveDB.java +++ b/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/program/database/DataTypeArchiveDB.java @@ -4,9 +4,9 @@ * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at - * + * * http://www.apache.org/licenses/LICENSE-2.0 - * + * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. @@ -26,7 +26,8 @@ import ghidra.framework.data.OpenMode; import ghidra.framework.model.DomainFile; import ghidra.framework.model.DomainFolder; import ghidra.framework.options.Options; -import ghidra.program.model.data.*; +import ghidra.program.model.data.PointerDataType; +import ghidra.program.model.data.StandAloneDataTypeManager; import ghidra.program.model.listing.DataTypeArchive; import ghidra.program.model.listing.Program; import ghidra.program.util.ProgramChangeRecord; @@ -255,26 +256,17 @@ public class DataTypeArchiveDB extends DomainObjectAdapterDB implements DataType return pointerSize > 0 && pointerSize <= PointerDataType.MAX_POINTER_SIZE_BYTES; } - /** - * @see ghidra.program.model.listing.Program#getDataTypeManager() - */ @Override - public DataTypeManager getDataTypeManager() { + public ProjectDataTypeManager getDataTypeManager() { return dataTypeManager; } - /** - * @see ghidra.program.model.listing.Program#getCreationDate() - */ @Override public Date getCreationDate() { Options pl = getOptions(ARCHIVE_INFO); return pl.getDate(DATE_CREATED, new Date(0)); } - /** - * @see ghidra.program.model.listing.Program#getDefaultPointerSize() - */ @Override public int getDefaultPointerSize() { // Not sure what size this should be so use 4 for now. @@ -283,9 +275,6 @@ public class DataTypeArchiveDB extends DomainObjectAdapterDB implements DataType return pl.getInt(DEFAULT_POINTER_SIZE, 4); } - /** - * @see ghidra.program.model.listing.Program#getChanges() - */ @Override public DataTypeArchiveDBChangeSet getChanges() { return (DataTypeArchiveDBChangeSet) changeSet; diff --git a/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/program/model/listing/DataTypeArchive.java b/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/program/model/listing/DataTypeArchive.java index 1ff2dbaa2b..70c261d5fa 100644 --- a/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/program/model/listing/DataTypeArchive.java +++ b/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/program/model/listing/DataTypeArchive.java @@ -4,9 +4,9 @@ * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at - * + * * http://www.apache.org/licenses/LICENSE-2.0 - * + * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. @@ -18,6 +18,7 @@ package ghidra.program.model.listing; import java.util.Date; import ghidra.program.model.data.DataTypeManagerDomainObject; +import ghidra.program.model.data.StandAloneDataTypeManager; /** * This interface represents the main entry point into an object which @@ -37,11 +38,11 @@ public interface DataTypeArchive extends DataTypeManagerDomainObject { public static final Date JANUARY_1_1970 = new Date(0); /** - * Determine if this archive has exclusive-write access which may be neccessary for some - * operations. - * @return true if archive has exclusive-write access + * Gets the associated standalone data type manager. + * @return the data type manager. */ - public boolean hasExclusiveAccess(); + @Override + public StandAloneDataTypeManager getDataTypeManager(); /** * Gets the default pointer size as it may be stored within the data type archive. From 2c5669dbd0af5b566f4b47a603d95b8753d3de94 Mon Sep 17 00:00:00 2001 From: ghidra1 Date: Tue, 8 Apr 2025 15:15:53 -0400 Subject: [PATCH 2/2] GP-0 Minor cleanup --- .../plugin/core/datamgr/archive/Archive.java | 6 ++-- .../core/datamgr/archive/ProjectArchive.java | 35 ++++++++++++++----- .../program/database/DataTypeArchiveDB.java | 5 --- .../model/listing/DataTypeArchive.java | 12 ++----- 4 files changed, 33 insertions(+), 25 deletions(-) diff --git a/Ghidra/Features/Base/src/main/java/ghidra/app/plugin/core/datamgr/archive/Archive.java b/Ghidra/Features/Base/src/main/java/ghidra/app/plugin/core/datamgr/archive/Archive.java index 77a349dbba..bead7b085c 100644 --- a/Ghidra/Features/Base/src/main/java/ghidra/app/plugin/core/datamgr/archive/Archive.java +++ b/Ghidra/Features/Base/src/main/java/ghidra/app/plugin/core/datamgr/archive/Archive.java @@ -4,9 +4,9 @@ * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at - * + * * http://www.apache.org/licenses/LICENSE-2.0 - * + * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. @@ -31,7 +31,7 @@ public interface Archive extends DataTypeManagerOwner, Comparable { /** * Gets the name for this data type archive. * This is the name to be presented to the user for this archive. - * @return the name + * @return the name or null if closed */ public String getName(); diff --git a/Ghidra/Features/Base/src/main/java/ghidra/app/plugin/core/datamgr/archive/ProjectArchive.java b/Ghidra/Features/Base/src/main/java/ghidra/app/plugin/core/datamgr/archive/ProjectArchive.java index fc3cb58c1e..3cb1adda5f 100644 --- a/Ghidra/Features/Base/src/main/java/ghidra/app/plugin/core/datamgr/archive/ProjectArchive.java +++ b/Ghidra/Features/Base/src/main/java/ghidra/app/plugin/core/datamgr/archive/ProjectArchive.java @@ -4,9 +4,9 @@ * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at - * + * * http://www.apache.org/licenses/LICENSE-2.0 - * + * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. @@ -24,6 +24,7 @@ import generic.theme.GIcon; import ghidra.framework.model.DomainFile; import ghidra.program.model.data.*; import ghidra.program.model.listing.DataTypeArchive; +import ghidra.util.exception.ClosedException; public class ProjectArchive implements DomainFileArchive { @@ -34,7 +35,7 @@ public class ProjectArchive implements DomainFileArchive { private DomainFile sourceDomainFile; private DataTypeManagerChangeListener categoryListener; // hold on to since it is stored in a weak set private DataTypeManagerHandler archiveManager; - private DataTypeManager dataTypeManager; + private StandAloneDataTypeManager dataTypeManager; ProjectArchive(DataTypeManagerHandler archiveManager, DataTypeArchive dataTypeArchive, DomainFile sourceDomainFile) { @@ -53,6 +54,9 @@ public class ProjectArchive implements DomainFileArchive { @Override public String getName() { + if (dataTypeManager == null) { + return null; + } return dataTypeManager.getName(); } @@ -74,6 +78,9 @@ public class ProjectArchive implements DomainFileArchive { @Override public boolean isModifiable() { + if (dataTypeManager == null) { + return false; + } DomainFile df = getDomainObject().getDomainFile(); return df.canSave(); } @@ -90,6 +97,9 @@ public class ProjectArchive implements DomainFileArchive { @Override public boolean isChanged() { + if (dataTypeManager == null) { + return false; + } DomainFile df = dataTypeArchive.getDomainFile(); long lastModifiedTime = df.getLastModifiedTime(); return (lastModifiedTime == 0) || dataTypeArchive.isChanged(); @@ -97,26 +107,35 @@ public class ProjectArchive implements DomainFileArchive { @Override public boolean isSavable() { - return !dataTypeArchive.getDomainFile().isReadOnly() && dataTypeArchive.isChangeable(); + return dataTypeManager != null && !dataTypeArchive.getDomainFile().isReadOnly() && + dataTypeArchive.isChangeable(); } @Override public void save() throws IOException { + if (dataTypeManager == null) { + throw new ClosedException(); + } archiveManager.save(getDomainObject()); } @Override public void close() { - dataTypeManager.close(); - archiveManager.archiveClosed(this); - dataTypeManager = null; + if (dataTypeManager != null) { + dataTypeManager.close(); + archiveManager.archiveClosed(this); + dataTypeManager = null; + } } @Override public void saveAs(Component component) throws IOException { + if (dataTypeManager == null) { + throw new ClosedException(); + } archiveManager.saveAs(dataTypeArchive); sourceDomainFile = dataTypeArchive.getDomainFile(); // update with new domain file - dataTypeArchive.updateID(); + dataTypeManager.updateID(); } @Override diff --git a/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/program/database/DataTypeArchiveDB.java b/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/program/database/DataTypeArchiveDB.java index ed4455b844..79fc46cc49 100644 --- a/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/program/database/DataTypeArchiveDB.java +++ b/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/program/database/DataTypeArchiveDB.java @@ -570,11 +570,6 @@ public class DataTypeArchiveDB extends DomainObjectAdapterDB implements DataType super.updateMetadata(); } - @Override - public void updateID() { - dataTypeManager.updateID(); - } - @Override protected void domainObjectRestored() { super.domainObjectRestored(); diff --git a/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/program/model/listing/DataTypeArchive.java b/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/program/model/listing/DataTypeArchive.java index 70c261d5fa..ef347c544f 100644 --- a/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/program/model/listing/DataTypeArchive.java +++ b/Ghidra/Framework/SoftwareModeling/src/main/java/ghidra/program/model/listing/DataTypeArchive.java @@ -38,22 +38,18 @@ public interface DataTypeArchive extends DataTypeManagerDomainObject { public static final Date JANUARY_1_1970 = new Date(0); /** - * Gets the associated standalone data type manager. - * @return the data type manager. + * {@return the associated standalone data type manager.} */ @Override public StandAloneDataTypeManager getDataTypeManager(); /** - * Gets the default pointer size as it may be stored within the data type archive. - * @return default pointer size. + * {@return the default pointer size as it may be stored within the data type archive.} */ public int getDefaultPointerSize(); /** - * Returns the creation date of this data type archive. - * existed, then Jan 1, 1970 is returned. - * @return the creation date of this data type archive + * {@return the creation date of this data type archive or Jan 1, 1970 if unknown.} */ public Date getCreationDate(); @@ -69,6 +65,4 @@ public interface DataTypeArchive extends DataTypeManagerDomainObject { */ public void invalidate(); - public void updateID(); - }