mirror of
https://github.com/overcuriousity/autopsy-flatpak.git
synced 2025-07-06 21:00:22 +00:00
Merge branch 'develop' of https://www.github.com/sleuthkit/autopsy into develop
This commit is contained in:
commit
62476f6ffe
@ -1,4 +1,4 @@
|
|||||||
# To change this template, choose Tools | Templates
|
|
||||||
# and open the template in the editor.
|
|
||||||
|
|
||||||
SampleContentViewer.jLabel1.text=jLabel1
|
SampleContentViewer.jLabel1.text=jLabel1
|
||||||
|
SampleIngestModuleFactory.moduleName=Sample Ingest Module
|
||||||
|
SampleIngestModuleFactory.moduleDescription=This module serves as a sample ingest module for software developers.
|
||||||
|
SampleIngestModuleIngestJobSettingsPanel.skipKnownFilesCheckBox.text=Skip Known Files (NSRL)
|
||||||
|
@ -29,56 +29,199 @@
|
|||||||
*/
|
*/
|
||||||
package org.sleuthkit.autopsy.examples;
|
package org.sleuthkit.autopsy.examples;
|
||||||
|
|
||||||
|
import java.util.HashMap;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import org.apache.log4j.Logger;
|
import java.util.logging.Level;
|
||||||
import org.sleuthkit.autopsy.casemodule.Case;
|
import org.sleuthkit.autopsy.casemodule.Case;
|
||||||
import org.sleuthkit.autopsy.casemodule.services.FileManager;
|
import org.sleuthkit.autopsy.casemodule.services.FileManager;
|
||||||
import org.sleuthkit.autopsy.casemodule.services.Services;
|
import org.sleuthkit.autopsy.casemodule.services.Services;
|
||||||
import org.sleuthkit.autopsy.ingest.DataSourceIngestModule;
|
|
||||||
import org.sleuthkit.autopsy.ingest.DataSourceIngestModuleStatusHelper;
|
import org.sleuthkit.autopsy.ingest.DataSourceIngestModuleStatusHelper;
|
||||||
import org.sleuthkit.autopsy.ingest.IngestModule;
|
import org.sleuthkit.autopsy.ingest.IngestModule;
|
||||||
import org.sleuthkit.autopsy.ingest.IngestModuleAdapter;
|
|
||||||
import org.sleuthkit.datamodel.AbstractFile;
|
import org.sleuthkit.datamodel.AbstractFile;
|
||||||
import org.sleuthkit.datamodel.Content;
|
import org.sleuthkit.datamodel.Content;
|
||||||
import org.sleuthkit.datamodel.FsContent;
|
import org.sleuthkit.datamodel.FsContent;
|
||||||
import org.sleuthkit.datamodel.SleuthkitCase;
|
import org.sleuthkit.datamodel.SleuthkitCase;
|
||||||
import org.sleuthkit.datamodel.TskCoreException;
|
import org.sleuthkit.datamodel.TskCoreException;
|
||||||
|
import org.sleuthkit.autopsy.coreutils.Logger;
|
||||||
|
import org.sleuthkit.autopsy.ingest.DataSourceIngestModule;
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestJobContext;
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestMessage;
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestServices;
|
||||||
|
import org.sleuthkit.datamodel.TskData;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Sample data source ingest module that doesn't do much. Note that the
|
* Sample data source ingest module that doesn't do much. Demonstrates per
|
||||||
* IngestModuleAdapter abstract class could have been used as a base class to
|
* ingest job module settings, use of a subset of the available ingest services
|
||||||
* obtain default implementations of many of the DataSourceIngestModule methods.
|
* and thread-safe sharing of per ingest job resources.
|
||||||
|
* <p>
|
||||||
|
* IMPORTANT TIP: This sample data source ingest module directly implements
|
||||||
|
* DataSourceIngestModule, which extends IngestModule. A practical alternative,
|
||||||
|
* recommended if you do not need to provide implementations of all of the
|
||||||
|
* IngestModule methods, is to extend the abstract class IngestModuleAdapter to
|
||||||
|
* get default "do nothing" implementations of the IngestModule methods.
|
||||||
*/
|
*/
|
||||||
// RJCTODO: Remove inheritance from IngestModuleAdapter to show full implementation of interface
|
class SampleDataSourceIngestModule implements DataSourceIngestModule {
|
||||||
// provide better documentation, and provide more extensive demonstration of how to
|
|
||||||
// use various ingest services.
|
|
||||||
class SampleDataSourceIngestModule extends IngestModuleAdapter implements DataSourceIngestModule {
|
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(SampleDataSourceIngestModule.class);
|
private static final HashMap<Long, Integer> moduleReferenceCountsForIngestJobs = new HashMap<>();
|
||||||
|
private static final HashMap<Long, Long> fileCountsForIngestJobs = new HashMap<>();
|
||||||
|
private static long messageCount = 0;
|
||||||
|
private final boolean skipKnownFiles;
|
||||||
|
private IngestJobContext context = null;
|
||||||
|
|
||||||
|
SampleDataSourceIngestModule(SampleModuleIngestJobSettings settings) {
|
||||||
|
this.skipKnownFiles = settings.skipKnownFiles();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Invoked by Autopsy to allow an ingest module instance to set up any
|
||||||
|
* internal data structures and acquire any private resources it will need
|
||||||
|
* during an ingest job.
|
||||||
|
* <p>
|
||||||
|
* Autopsy will generally use several instances of an ingest module for each
|
||||||
|
* ingest job it performs. Completing an ingest job entails processing a
|
||||||
|
* single data source (e.g., a disk image) and all of the files from the
|
||||||
|
* data source, including files extracted from archives and any unallocated
|
||||||
|
* space (made to look like a series of files). The data source is passed
|
||||||
|
* through one or more pipelines of data source ingest modules. The files
|
||||||
|
* are passed through one or more pipelines of file ingest modules.
|
||||||
|
* <p>
|
||||||
|
* Autopsy may use multiple threads to complete an ingest job, but it is
|
||||||
|
* guaranteed that there will be no more than one module instance per
|
||||||
|
* thread. However, if the module instances must share resources, the
|
||||||
|
* modules are responsible for synchronizing access to the shared resources
|
||||||
|
* and doing reference counting as required to release those resources
|
||||||
|
* correctly. Also, more than one ingest job may be in progress at any given
|
||||||
|
* time. This must also be taken into consideration when sharing resources
|
||||||
|
* between module instances.
|
||||||
|
* <p>
|
||||||
|
* An ingest module that does not require initialization may extend the
|
||||||
|
* abstract IngestModuleAdapter class to get a default "do nothing"
|
||||||
|
* implementation of this method.
|
||||||
|
*
|
||||||
|
* @param context Provides data and services specific to the ingest job and
|
||||||
|
* the ingest pipeline of which the module is a part.
|
||||||
|
* @throws org.sleuthkit.autopsy.ingest.IngestModule.IngestModuleException
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public void startUp(IngestJobContext context) throws IngestModuleException {
|
||||||
|
this.context = context;
|
||||||
|
|
||||||
|
// This method is thread-safe with per ingest job reference counting.
|
||||||
|
initFileCount(context.getJobId());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Processes a data source.
|
||||||
|
*
|
||||||
|
* @param dataSource The data source to process.
|
||||||
|
* @param statusHelper A status helper to be used to report progress and
|
||||||
|
* detect ingest job cancellation.
|
||||||
|
* @return A result code indicating success or failure of the processing.
|
||||||
|
*/
|
||||||
@Override
|
@Override
|
||||||
public ProcessResult process(Content dataSource, DataSourceIngestModuleStatusHelper statusHelper) {
|
public ProcessResult process(Content dataSource, DataSourceIngestModuleStatusHelper statusHelper) {
|
||||||
Case case1 = Case.getCurrentCase();
|
Case autopsyCase = Case.getCurrentCase();
|
||||||
SleuthkitCase sleuthkitCase = case1.getSleuthkitCase();
|
SleuthkitCase sleuthkitCase = autopsyCase.getSleuthkitCase();
|
||||||
|
|
||||||
Services services = new Services(sleuthkitCase);
|
Services services = new Services(sleuthkitCase);
|
||||||
FileManager fileManager = services.getFileManager();
|
FileManager fileManager = services.getFileManager();
|
||||||
try {
|
try {
|
||||||
|
// Get count of files with .doc extension.
|
||||||
|
long fileCount = 0;
|
||||||
List<AbstractFile> docFiles = fileManager.findFiles(dataSource, "%.doc");
|
List<AbstractFile> docFiles = fileManager.findFiles(dataSource, "%.doc");
|
||||||
for (AbstractFile file : docFiles) {
|
for (AbstractFile docFile : docFiles) {
|
||||||
// do something with each doc file
|
if (!skipKnownFiles || docFile.getKnown() != TskData.FileKnown.KNOWN) {
|
||||||
|
++fileCount;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Get files by creation time.
|
||||||
long currentTime = System.currentTimeMillis() / 1000;
|
long currentTime = System.currentTimeMillis() / 1000;
|
||||||
long minTime = currentTime - (14 * 24 * 60 * 60); // Go back two weeks.
|
long minTime = currentTime - (14 * 24 * 60 * 60); // Go back two weeks.
|
||||||
List<FsContent> otherFiles = sleuthkitCase.findFilesWhere("crtime > " + minTime);
|
List<FsContent> otherFiles = sleuthkitCase.findFilesWhere("crtime > " + minTime);
|
||||||
// do something with these files...
|
for (FsContent otherFile : otherFiles) {
|
||||||
|
if (!skipKnownFiles || otherFile.getKnown() != TskData.FileKnown.KNOWN) {
|
||||||
|
++fileCount;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// This method is thread-safe and keeps per ingest job counters.
|
||||||
|
addToFileCount(context.getJobId(), fileCount);
|
||||||
|
|
||||||
} catch (TskCoreException ex) {
|
} catch (TskCoreException ex) {
|
||||||
logger.fatal("Error retrieving files from database: " + ex.getLocalizedMessage());
|
IngestServices ingestServices = IngestServices.getInstance();
|
||||||
return IngestModule.ProcessResult.OK;
|
Logger logger = ingestServices.getLogger(SampleIngestModuleFactory.getModuleName());
|
||||||
|
logger.log(Level.SEVERE, "File query failed", ex);
|
||||||
|
return IngestModule.ProcessResult.ERROR;
|
||||||
}
|
}
|
||||||
|
|
||||||
return IngestModule.ProcessResult.OK;
|
return IngestModule.ProcessResult.OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Invoked by Autopsy when an ingest job is completed, before the ingest
|
||||||
|
* module instance is discarded. The module should respond by doing things
|
||||||
|
* like releasing private resources, submitting final results, and posting a
|
||||||
|
* final ingest message.
|
||||||
|
* <p>
|
||||||
|
* Autopsy will generally use several instances of an ingest module for each
|
||||||
|
* ingest job it performs. Completing an ingest job entails processing a
|
||||||
|
* single data source (e.g., a disk image) and all of the files from the
|
||||||
|
* data source, including files extracted from archives and any unallocated
|
||||||
|
* space (made to look like a series of files). The data source is passed
|
||||||
|
* through one or more pipelines of data source ingest modules. The files
|
||||||
|
* are passed through one or more pipelines of file ingest modules.
|
||||||
|
* <p>
|
||||||
|
* Autopsy may use multiple threads to complete an ingest job, but it is
|
||||||
|
* guaranteed that there will be no more than one module instance per
|
||||||
|
* thread. However, if the module instances must share resources, the
|
||||||
|
* modules are responsible for synchronizing access to the shared resources
|
||||||
|
* and doing reference counting as required to release those resources
|
||||||
|
* correctly. Also, more than one ingest job may be in progress at any given
|
||||||
|
* time. This must also be taken into consideration when sharing resources
|
||||||
|
* between module instances.
|
||||||
|
* <p>
|
||||||
|
* An ingest module that does not require initialization may extend the
|
||||||
|
* abstract IngestModuleAdapter class to get a default "do nothing"
|
||||||
|
* implementation of this method.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public void shutDown(boolean ingestJobCancelled) {
|
||||||
|
// This method is thread-safe with per ingest job reference counting.
|
||||||
|
postFileCount(context.getJobId());
|
||||||
|
}
|
||||||
|
|
||||||
|
synchronized static void initFileCount(long ingestJobId) {
|
||||||
|
Integer moduleReferenceCount;
|
||||||
|
if (!moduleReferenceCountsForIngestJobs.containsKey(ingestJobId)) {
|
||||||
|
moduleReferenceCount = 1;
|
||||||
|
fileCountsForIngestJobs.put(ingestJobId, 0L);
|
||||||
|
} else {
|
||||||
|
moduleReferenceCount = moduleReferenceCountsForIngestJobs.get(ingestJobId);
|
||||||
|
++moduleReferenceCount;
|
||||||
|
}
|
||||||
|
moduleReferenceCountsForIngestJobs.put(ingestJobId, moduleReferenceCount);
|
||||||
|
}
|
||||||
|
|
||||||
|
synchronized static void addToFileCount(long ingestJobId, long countToAdd) {
|
||||||
|
Long fileCount = fileCountsForIngestJobs.get(ingestJobId);
|
||||||
|
fileCount += countToAdd;
|
||||||
|
fileCountsForIngestJobs.put(ingestJobId, fileCount);
|
||||||
|
}
|
||||||
|
|
||||||
|
synchronized static void postFileCount(long ingestJobId) {
|
||||||
|
Integer moduleReferenceCount = moduleReferenceCountsForIngestJobs.remove(ingestJobId);
|
||||||
|
--moduleReferenceCount;
|
||||||
|
if (moduleReferenceCount == 0) {
|
||||||
|
Long filesCount = fileCountsForIngestJobs.remove(ingestJobId);
|
||||||
|
String msgText = String.format("Found %d files", filesCount);
|
||||||
|
IngestMessage message = IngestMessage.createMessage(
|
||||||
|
++messageCount,
|
||||||
|
IngestMessage.MessageType.DATA,
|
||||||
|
SampleIngestModuleFactory.getModuleName(),
|
||||||
|
msgText);
|
||||||
|
IngestServices.getInstance().postMessage(message);
|
||||||
|
} else {
|
||||||
|
moduleReferenceCountsForIngestJobs.put(ingestJobId, moduleReferenceCount);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -29,85 +29,143 @@
|
|||||||
*/
|
*/
|
||||||
package org.sleuthkit.autopsy.examples;
|
package org.sleuthkit.autopsy.examples;
|
||||||
|
|
||||||
import org.apache.log4j.Logger;
|
import java.util.HashMap;
|
||||||
import org.openide.util.Exceptions;
|
import java.util.logging.Level;
|
||||||
import org.sleuthkit.autopsy.casemodule.Case;
|
import org.sleuthkit.autopsy.casemodule.Case;
|
||||||
|
import org.sleuthkit.autopsy.coreutils.Logger;
|
||||||
import org.sleuthkit.autopsy.ingest.FileIngestModule;
|
import org.sleuthkit.autopsy.ingest.FileIngestModule;
|
||||||
import org.sleuthkit.autopsy.ingest.IngestModule;
|
import org.sleuthkit.autopsy.ingest.IngestModule;
|
||||||
import org.sleuthkit.autopsy.ingest.IngestModuleAdapter;
|
|
||||||
import org.sleuthkit.autopsy.ingest.IngestJobContext;
|
import org.sleuthkit.autopsy.ingest.IngestJobContext;
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestMessage;
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestServices;
|
||||||
|
import org.sleuthkit.autopsy.ingest.ModuleDataEvent;
|
||||||
import org.sleuthkit.datamodel.AbstractFile;
|
import org.sleuthkit.datamodel.AbstractFile;
|
||||||
import org.sleuthkit.datamodel.BlackboardArtifact;
|
import org.sleuthkit.datamodel.BlackboardArtifact;
|
||||||
|
import org.sleuthkit.datamodel.BlackboardArtifact.ARTIFACT_TYPE;
|
||||||
import org.sleuthkit.datamodel.BlackboardAttribute;
|
import org.sleuthkit.datamodel.BlackboardAttribute;
|
||||||
import org.sleuthkit.datamodel.TskCoreException;
|
import org.sleuthkit.datamodel.TskCoreException;
|
||||||
import org.sleuthkit.datamodel.SleuthkitCase;
|
import org.sleuthkit.datamodel.SleuthkitCase;
|
||||||
import org.sleuthkit.datamodel.TskData;
|
import org.sleuthkit.datamodel.TskData;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* This is a sample and simple module. It is a file-level ingest module, meaning
|
* Sample file ingest module that doesn't do much. Demonstrates per ingest job
|
||||||
* that it will get called on each file in the disk image / logical file set. It
|
* module settings, use of a subset of the available ingest services and
|
||||||
* does a stupid calculation of the number of null bytes in the beginning of the
|
* thread-safe sharing of per ingest job resources.
|
||||||
* file in order to show the basic flow.
|
* <p>
|
||||||
*
|
* IMPORTANT TIP: This sample data source ingest module directly implements
|
||||||
* Autopsy has been hard coded to ignore this module based on the it's package
|
* FileIngestModule, which extends IngestModule. A practical alternative,
|
||||||
* name. IngestModuleLoader will not load things from the
|
* recommended if you do not need to provide implementations of all of the
|
||||||
* org.sleuthkit.autopsy.examples package. Either change the package or the
|
* IngestModule methods, is to extend the abstract class IngestModuleAdapter to
|
||||||
* loading code to make this module actually run.
|
* get default "do nothing" implementations of the IngestModule methods.
|
||||||
*/
|
*/
|
||||||
// RJCTODO: Remove inheritance from IngestModuleAdapter to show full implementation of interface
|
class SampleFileIngestModule implements FileIngestModule {
|
||||||
// provide better documentation, and provide more extensive demonstration of how to
|
|
||||||
// use various ingest services.
|
|
||||||
class SampleFileIngestModule extends IngestModuleAdapter implements FileIngestModule {
|
|
||||||
|
|
||||||
private int attrId = -1;
|
private static final HashMap<Long, Integer> moduleReferenceCountsForIngestJobs = new HashMap<>();
|
||||||
|
private static final HashMap<Long, Long> artifactCountsForIngestJobs = new HashMap<>();
|
||||||
|
private static long messageCount = 0;
|
||||||
|
private static int attrId = -1;
|
||||||
|
private final boolean skipKnownFiles;
|
||||||
|
private IngestJobContext context = null;
|
||||||
|
|
||||||
@Override
|
SampleFileIngestModule(SampleModuleIngestJobSettings settings) {
|
||||||
public void startUp(IngestJobContext initContext) {
|
this.skipKnownFiles = settings.skipKnownFiles();
|
||||||
/* For this demo, we are going to make a private attribute to post our
|
|
||||||
* results to the blackbaord with. There are many standard blackboard artifact
|
|
||||||
* and attribute types and you should first consider using one of those before
|
|
||||||
* making private ones because other modules won't know about provate ones.
|
|
||||||
* Because our demo has results that have no real value, we do not have an
|
|
||||||
* official attribute for them.
|
|
||||||
*/
|
|
||||||
Case case1 = Case.getCurrentCase();
|
|
||||||
SleuthkitCase sleuthkitCase = case1.getSleuthkitCase();
|
|
||||||
|
|
||||||
// see if the type already exists in the blackboard.
|
|
||||||
try {
|
|
||||||
attrId = sleuthkitCase.getAttrTypeID("ATTR_SAMPLE");
|
|
||||||
} catch (TskCoreException ex) {
|
|
||||||
// create it if not
|
|
||||||
try {
|
|
||||||
attrId = sleuthkitCase.addAttrType("ATTR_SAMPLE", "Sample Attribute");
|
|
||||||
} catch (TskCoreException ex1) {
|
|
||||||
Logger log = Logger.getLogger(SampleFileIngestModule.class);
|
|
||||||
log.fatal("Error adding attribute type: " + ex1.getLocalizedMessage());
|
|
||||||
attrId = -1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Invoked by Autopsy to allow an ingest module instance to set up any
|
||||||
|
* internal data structures and acquire any private resources it will need
|
||||||
|
* during an ingest job.
|
||||||
|
* <p>
|
||||||
|
* Autopsy will generally use several instances of an ingest module for each
|
||||||
|
* ingest job it performs. Completing an ingest job entails processing a
|
||||||
|
* single data source (e.g., a disk image) and all of the files from the
|
||||||
|
* data source, including files extracted from archives and any unallocated
|
||||||
|
* space (made to look like a series of files). The data source is passed
|
||||||
|
* through one or more pipelines of data source ingest modules. The files
|
||||||
|
* are passed through one or more pipelines of file ingest modules.
|
||||||
|
* <p>
|
||||||
|
* Autopsy may use multiple threads to complete an ingest job, but it is
|
||||||
|
* guaranteed that there will be no more than one module instance per
|
||||||
|
* thread. However, if the module instances must share resources, the
|
||||||
|
* modules are responsible for synchronizing access to the shared resources
|
||||||
|
* and doing reference counting as required to release those resources
|
||||||
|
* correctly. Also, more than one ingest job may be in progress at any given
|
||||||
|
* time. This must also be taken into consideration when sharing resources
|
||||||
|
* between module instances.
|
||||||
|
* <p>
|
||||||
|
* An ingest module that does not require initialization may extend the
|
||||||
|
* abstract IngestModuleAdapter class to get a default "do nothing"
|
||||||
|
* implementation of this method.
|
||||||
|
*
|
||||||
|
* @param context Provides data and services specific to the ingest job and
|
||||||
|
* the ingest pipeline of which the module is a part.
|
||||||
|
* @throws org.sleuthkit.autopsy.ingest.IngestModule.IngestModuleException
|
||||||
|
*/
|
||||||
@Override
|
@Override
|
||||||
public IngestModule.ProcessResult process(AbstractFile abstractFile) {
|
public void startUp(IngestJobContext context) throws IngestModuleException {
|
||||||
// skip non-files
|
this.context = context;
|
||||||
if ((abstractFile.getType() == TskData.TSK_DB_FILES_TYPE_ENUM.UNALLOC_BLOCKS)
|
|
||||||
|| (abstractFile.getType() == TskData.TSK_DB_FILES_TYPE_ENUM.UNUSED_BLOCKS)) {
|
synchronized (SampleFileIngestModule.class) {
|
||||||
|
if (attrId == -1) {
|
||||||
|
// For this sample, make a new attribute type to use to post
|
||||||
|
// results to the blackboard. There are many standard blackboard
|
||||||
|
// artifact and attribute types and you should use them instead
|
||||||
|
// creating new ones to facilitate use of your results by other
|
||||||
|
// modules.
|
||||||
|
Case autopsyCase = Case.getCurrentCase();
|
||||||
|
SleuthkitCase sleuthkitCase = autopsyCase.getSleuthkitCase();
|
||||||
|
|
||||||
|
// See if the attribute type has already been defined.
|
||||||
|
try {
|
||||||
|
attrId = sleuthkitCase.getAttrTypeID("ATTR_SAMPLE");
|
||||||
|
} catch (TskCoreException e) {
|
||||||
|
// If not, create the the attribute type.
|
||||||
|
try {
|
||||||
|
attrId = sleuthkitCase.addAttrType("ATTR_SAMPLE", "Sample Attribute");
|
||||||
|
} catch (TskCoreException ex) {
|
||||||
|
IngestServices ingestServices = IngestServices.getInstance();
|
||||||
|
Logger logger = ingestServices.getLogger(SampleIngestModuleFactory.getModuleName());
|
||||||
|
logger.log(Level.SEVERE, "Failed to create blackboard attribute", ex);
|
||||||
|
attrId = -1;
|
||||||
|
throw new IngestModuleException(ex.getLocalizedMessage());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// This method is thread-safe with per ingest job reference counting.
|
||||||
|
initBlackboardPostCount(context.getJobId());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Processes a file.
|
||||||
|
*
|
||||||
|
* @param file The file.
|
||||||
|
* @return A result code indicating success or failure of the processing.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public IngestModule.ProcessResult process(AbstractFile file) {
|
||||||
|
if (attrId != -1) {
|
||||||
|
return IngestModule.ProcessResult.ERROR;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Skip anything other than actual file system files.
|
||||||
|
if ((file.getType() == TskData.TSK_DB_FILES_TYPE_ENUM.UNALLOC_BLOCKS)
|
||||||
|
|| (file.getType() == TskData.TSK_DB_FILES_TYPE_ENUM.UNUSED_BLOCKS)) {
|
||||||
return IngestModule.ProcessResult.OK;
|
return IngestModule.ProcessResult.OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
// skip NSRL / known files
|
// Skip NSRL / known files.
|
||||||
if (abstractFile.getKnown() == TskData.FileKnown.KNOWN) {
|
if (skipKnownFiles && file.getKnown() == TskData.FileKnown.KNOWN) {
|
||||||
return IngestModule.ProcessResult.OK;
|
return IngestModule.ProcessResult.OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Do a non-sensical calculation of the number of 0x00 bytes
|
// Do a nonsensical calculation of the number of 0x00 bytes
|
||||||
* in the first 1024-bytes of the file. This is for demo
|
// in the first 1024-bytes of the file. This is for demo
|
||||||
* purposes only.
|
// purposes only.
|
||||||
*/
|
|
||||||
try {
|
try {
|
||||||
byte buffer[] = new byte[1024];
|
byte buffer[] = new byte[1024];
|
||||||
int len = abstractFile.read(buffer, 0, 1024);
|
int len = file.read(buffer, 0, 1024);
|
||||||
int count = 0;
|
int count = 0;
|
||||||
for (int i = 0; i < len; i++) {
|
for (int i = 0; i < len; i++) {
|
||||||
if (buffer[i] == 0x00) {
|
if (buffer[i] == 0x00) {
|
||||||
@ -115,23 +173,98 @@ class SampleFileIngestModule extends IngestModuleAdapter implements FileIngestMo
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (attrId != -1) {
|
// Make an attribute using the ID for the attribute type that
|
||||||
// Make an attribute using the ID for the private type that we previously created.
|
// was previously created.
|
||||||
BlackboardAttribute attr = new BlackboardAttribute(attrId, "SampleFileIngestModule", count); // RJCTODO: Set up factory with static module name function as example
|
BlackboardAttribute attr = new BlackboardAttribute(attrId, SampleIngestModuleFactory.getModuleName(), count);
|
||||||
|
|
||||||
/* add it to the general info artifact. In real modules, you would likely have
|
// Add the to the general info artifact for the file. In a
|
||||||
* more complex data types and be making more specific artifacts.
|
// real module, you would likely have more complex data types
|
||||||
*/
|
// and be making more specific artifacts.
|
||||||
BlackboardArtifact art = abstractFile.getGenInfoArtifact();
|
BlackboardArtifact art = file.getGenInfoArtifact();
|
||||||
art.addAttribute(attr);
|
art.addAttribute(attr);
|
||||||
}
|
|
||||||
|
// Thread-safe.
|
||||||
|
addToBlackboardPostCount(context.getJobId(), 1L);
|
||||||
|
|
||||||
|
// Fire an event to notify any listeners for blackboard postings.
|
||||||
|
ModuleDataEvent event = new ModuleDataEvent(SampleIngestModuleFactory.getModuleName(), ARTIFACT_TYPE.TSK_GEN_INFO);
|
||||||
|
IngestServices.getInstance().fireModuleDataEvent(event);
|
||||||
|
|
||||||
return IngestModule.ProcessResult.OK;
|
return IngestModule.ProcessResult.OK;
|
||||||
|
|
||||||
} catch (TskCoreException ex) {
|
} catch (TskCoreException ex) {
|
||||||
Exceptions.printStackTrace(ex);
|
IngestServices ingestServices = IngestServices.getInstance();
|
||||||
|
Logger logger = ingestServices.getLogger(SampleIngestModuleFactory.getModuleName());
|
||||||
|
logger.log(Level.SEVERE, "Error processing file (id = " + file.getId() + ")", ex);
|
||||||
return IngestModule.ProcessResult.ERROR;
|
return IngestModule.ProcessResult.ERROR;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// RJCTODO: Add a module factory with service provider annotation (commented out)
|
/**
|
||||||
|
* Invoked by Autopsy when an ingest job is completed, before the ingest
|
||||||
|
* module instance is discarded. The module should respond by doing things
|
||||||
|
* like releasing private resources, submitting final results, and posting a
|
||||||
|
* final ingest message.
|
||||||
|
* <p>
|
||||||
|
* Autopsy will generally use several instances of an ingest module for each
|
||||||
|
* ingest job it performs. Completing an ingest job entails processing a
|
||||||
|
* single data source (e.g., a disk image) and all of the files from the
|
||||||
|
* data source, including files extracted from archives and any unallocated
|
||||||
|
* space (made to look like a series of files). The data source is passed
|
||||||
|
* through one or more pipelines of data source ingest modules. The files
|
||||||
|
* are passed through one or more pipelines of file ingest modules.
|
||||||
|
* <p>
|
||||||
|
* Autopsy may use multiple threads to complete an ingest job, but it is
|
||||||
|
* guaranteed that there will be no more than one module instance per
|
||||||
|
* thread. However, if the module instances must share resources, the
|
||||||
|
* modules are responsible for synchronizing access to the shared resources
|
||||||
|
* and doing reference counting as required to release those resources
|
||||||
|
* correctly. Also, more than one ingest job may be in progress at any given
|
||||||
|
* time. This must also be taken into consideration when sharing resources
|
||||||
|
* between module instances.
|
||||||
|
* <p>
|
||||||
|
* An ingest module that does not require initialization may extend the
|
||||||
|
* abstract IngestModuleAdapter class to get a default "do nothing"
|
||||||
|
* implementation of this method.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public void shutDown(boolean ingestJobCancelled) {
|
||||||
|
// This method is thread-safe with per ingest job reference counting.
|
||||||
|
reportBlackboardPostCount(context.getJobId());
|
||||||
|
}
|
||||||
|
|
||||||
|
synchronized static void initBlackboardPostCount(long ingestJobId) {
|
||||||
|
Integer moduleReferenceCount;
|
||||||
|
if (!moduleReferenceCountsForIngestJobs.containsKey(ingestJobId)) {
|
||||||
|
moduleReferenceCount = 1;
|
||||||
|
artifactCountsForIngestJobs.put(ingestJobId, 0L);
|
||||||
|
} else {
|
||||||
|
moduleReferenceCount = moduleReferenceCountsForIngestJobs.get(ingestJobId);
|
||||||
|
++moduleReferenceCount;
|
||||||
|
}
|
||||||
|
moduleReferenceCountsForIngestJobs.put(ingestJobId, moduleReferenceCount);
|
||||||
|
}
|
||||||
|
|
||||||
|
synchronized static void addToBlackboardPostCount(long ingestJobId, long countToAdd) {
|
||||||
|
Long fileCount = artifactCountsForIngestJobs.get(ingestJobId);
|
||||||
|
fileCount += countToAdd;
|
||||||
|
artifactCountsForIngestJobs.put(ingestJobId, fileCount);
|
||||||
|
}
|
||||||
|
|
||||||
|
synchronized static void reportBlackboardPostCount(long ingestJobId) {
|
||||||
|
Integer moduleReferenceCount = moduleReferenceCountsForIngestJobs.remove(ingestJobId);
|
||||||
|
--moduleReferenceCount;
|
||||||
|
if (moduleReferenceCount == 0) {
|
||||||
|
Long filesCount = artifactCountsForIngestJobs.remove(ingestJobId);
|
||||||
|
String msgText = String.format("Posted %d times to the blackboard", filesCount);
|
||||||
|
IngestMessage message = IngestMessage.createMessage(
|
||||||
|
++messageCount,
|
||||||
|
IngestMessage.MessageType.INFO,
|
||||||
|
SampleIngestModuleFactory.getModuleName(),
|
||||||
|
msgText);
|
||||||
|
IngestServices.getInstance().postMessage(message);
|
||||||
|
} else {
|
||||||
|
moduleReferenceCountsForIngestJobs.put(ingestJobId, moduleReferenceCount);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
326
Core/src/org/sleuthkit/autopsy/examples/SampleIngestModuleFactory.java
Executable file
326
Core/src/org/sleuthkit/autopsy/examples/SampleIngestModuleFactory.java
Executable file
@ -0,0 +1,326 @@
|
|||||||
|
/*
|
||||||
|
* Sample ingest module factory in the public domain.
|
||||||
|
* Feel free to use this as a template for your inget module factories.
|
||||||
|
*
|
||||||
|
* Contact: Brian Carrier [carrier <at> sleuthkit [dot] org]
|
||||||
|
*
|
||||||
|
* This is free and unencumbered software released into the public domain.
|
||||||
|
*
|
||||||
|
* Anyone is free to copy, modify, publish, use, compile, sell, or
|
||||||
|
* distribute this software, either in source code form or as a compiled
|
||||||
|
* binary, for any purpose, commercial or non-commercial, and by any
|
||||||
|
* means.
|
||||||
|
*
|
||||||
|
* In jurisdictions that recognize copyright laws, the author or authors
|
||||||
|
* of this software dedicate any and all copyright interest in the
|
||||||
|
* software to the public domain. We make this dedication for the benefit
|
||||||
|
* of the public at large and to the detriment of our heirs and
|
||||||
|
* successors. We intend this dedication to be an overt act of
|
||||||
|
* relinquishment in perpetuity of all present and future rights to this
|
||||||
|
* software under copyright law.
|
||||||
|
*
|
||||||
|
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||||
|
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||||
|
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
||||||
|
* IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR
|
||||||
|
* OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
|
||||||
|
* ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
||||||
|
* OTHER DEALINGS IN THE SOFTWARE.
|
||||||
|
*/
|
||||||
|
package org.sleuthkit.autopsy.examples;
|
||||||
|
|
||||||
|
// The following import is required for the ServiceProvider annotation (see
|
||||||
|
// below) used by the Autopsy ingest framework to locate ingest module
|
||||||
|
// factories. You will need to add a dependency on the Lookup API NetBeans
|
||||||
|
// module to your NetBeans module to use this import.
|
||||||
|
import org.openide.util.lookup.ServiceProvider;
|
||||||
|
|
||||||
|
// The following import is required to participate in Autopsy
|
||||||
|
// internationalization and localization. Autopsy core is currently localized
|
||||||
|
// for Japan. Please consult the NetBeans documentation for details.
|
||||||
|
import org.openide.util.NbBundle;
|
||||||
|
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestModuleFactory;
|
||||||
|
import org.sleuthkit.autopsy.ingest.DataSourceIngestModule;
|
||||||
|
import org.sleuthkit.autopsy.ingest.FileIngestModule;
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestModuleGlobalSetttingsPanel;
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestModuleIngestJobSettings;
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestModuleIngestJobSettingsPanel;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A factory that creates sample data source and file ingest modules.
|
||||||
|
* <p>
|
||||||
|
* This factory implements an interface that must be implemented by all
|
||||||
|
* providers of Autopsy ingest modules. An ingest module factory is used to
|
||||||
|
* create instances of a type of data source ingest module, a type of file
|
||||||
|
* ingest module, or both.
|
||||||
|
* <p>
|
||||||
|
* Autopsy will generally use the factory to several instances of each type of
|
||||||
|
* module for each ingest job it performs. Completing an ingest job entails
|
||||||
|
* processing a single data source (e.g., a disk image) and all of the files
|
||||||
|
* from the data source, including files extracted from archives and any
|
||||||
|
* unallocated space (made to look like a series of files). The data source is
|
||||||
|
* passed through one or more pipelines of data source ingest modules. The files
|
||||||
|
* are passed through one or more pipelines of file ingest modules.
|
||||||
|
* <p>
|
||||||
|
* Autopsy may use multiple threads to complete an ingest job, but it is
|
||||||
|
* guaranteed that there will be no more than one module instance per thread.
|
||||||
|
* However, if the module instances must share resources, the modules are
|
||||||
|
* responsible for synchronizing access to the shared resources and doing
|
||||||
|
* reference counting as required to release those resources correctly. Also,
|
||||||
|
* more than one ingest job may be in progress at any given time. This must also
|
||||||
|
* be taken into consideration when sharing resources between module instances.
|
||||||
|
* <p>
|
||||||
|
* An ingest module factory may provide global and per ingest job settings user
|
||||||
|
* interface panels. The global settings should apply to all module instances.
|
||||||
|
* The per ingest job settings should apply to all module instances working on a
|
||||||
|
* particular ingest job. Autopsy supports context-sensitive and persistent per
|
||||||
|
* ingest job settings, so per ingest job settings must be serializable.
|
||||||
|
* <p>
|
||||||
|
* To be discovered at runtime by the ingest framework, IngestModuleFactory
|
||||||
|
* implementations must be marked with the following NetBeans Service provider
|
||||||
|
* annotation (see below).
|
||||||
|
* <p>
|
||||||
|
* IMPORTANT TIP: This sample ingest module factory directly implements
|
||||||
|
* IngestModuleFactory. A practical alternative, recommended if you do not need
|
||||||
|
* to provide implementations of all of the IngestModuleFactory methods, is to
|
||||||
|
* extend the abstract class IngestModuleFactoryAdapter to get default
|
||||||
|
* implementations of most of the IngestModuleFactory methods.
|
||||||
|
*/
|
||||||
|
// @ServiceProvider(service = IngestModuleFactory.class)
|
||||||
|
public class SampleIngestModuleFactory implements IngestModuleFactory {
|
||||||
|
|
||||||
|
private static final String VERSION_NUMBER = "1.0.0";
|
||||||
|
|
||||||
|
// This class method allows the ingest module instances created by this
|
||||||
|
// factory to use the same display name that is provided to the Autopsy
|
||||||
|
// ingest framework by the factory.
|
||||||
|
static String getModuleName() {
|
||||||
|
return NbBundle.getMessage(SampleIngestModuleFactory.class, "SampleIngestModuleFactory.moduleName");
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the display name that identifies the family of ingest modules the
|
||||||
|
* factory creates. Autopsy uses this string to identify the module in user
|
||||||
|
* interface components and log messages. The module name must be unique. so
|
||||||
|
* a brief but distinctive name is recommended.
|
||||||
|
*
|
||||||
|
* @return The module family display name.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public String getModuleDisplayName() {
|
||||||
|
return getModuleName();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets a brief, user-friendly description of the family of ingest modules
|
||||||
|
* the factory creates. Autopsy uses this string to describe the module in
|
||||||
|
* user interface components.
|
||||||
|
*
|
||||||
|
* @return The module family description.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public String getModuleDescription() {
|
||||||
|
return NbBundle.getMessage(SampleIngestModuleFactory.class, "SampleIngestModuleFactory.moduleDescription");
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the version number of the family of ingest modules the factory
|
||||||
|
* creates.
|
||||||
|
*
|
||||||
|
* @return The module family version number.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public String getModuleVersionNumber() {
|
||||||
|
return VERSION_NUMBER;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Queries the factory to determine if it provides a user interface panel to
|
||||||
|
* allow a user to change settings that are used by all instances of the
|
||||||
|
* family of ingest modules the factory creates. For example, the Autopsy
|
||||||
|
* core hash lookup ingest module factory provides a global settings panel
|
||||||
|
* to import and create hash databases. The hash databases are then enabled
|
||||||
|
* or disabled per ingest job using an ingest job settings panel. If the
|
||||||
|
* module family does not have global settings, the factory may extend
|
||||||
|
* IngestModuleFactoryAdapter to get an implementation of this method that
|
||||||
|
* returns false.
|
||||||
|
*
|
||||||
|
* @return True if the factory provides a global settings panel.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public boolean hasGlobalSettingsPanel() {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets a user interface panel that allows a user to change settings that
|
||||||
|
* are used by all instances of the family of ingest modules the factory
|
||||||
|
* creates. For example, the Autopsy core hash lookup ingest module factory
|
||||||
|
* provides a global settings panel to import and create hash databases. The
|
||||||
|
* imported hash databases are then enabled or disabled per ingest job using
|
||||||
|
* ingest an ingest job settings panel. If the module family does not have a
|
||||||
|
* global settings, the factory may extend IngestModuleFactoryAdapter to get
|
||||||
|
* an implementation of this method that throws an
|
||||||
|
* UnsupportedOperationException.
|
||||||
|
*
|
||||||
|
* @return A global settings panel.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public IngestModuleGlobalSetttingsPanel getGlobalSettingsPanel() {
|
||||||
|
throw new UnsupportedOperationException();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the default per ingest job settings for instances of the family of
|
||||||
|
* ingest modules the factory creates. For example, the Autopsy core hash
|
||||||
|
* lookup ingest modules family uses hash databases imported or created
|
||||||
|
* using its global settings panel. All of the hash databases are enabled by
|
||||||
|
* default for an ingest job. If the module family does not have per ingest
|
||||||
|
* job settings, the factory may extend IngestModuleFactoryAdapter to get an
|
||||||
|
* implementation of this method that returns an instance of the
|
||||||
|
* NoIngestModuleJobSettings class.
|
||||||
|
*
|
||||||
|
* @return The default ingest job settings.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public IngestModuleIngestJobSettings getDefaultIngestJobSettings() {
|
||||||
|
return new SampleModuleIngestJobSettings();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Queries the factory to determine if it provides user a interface panel to
|
||||||
|
* allow a user to make per ingest job settings for instances of the family
|
||||||
|
* of ingest modules the factory creates. For example, the Autopsy core hash
|
||||||
|
* lookup ingest module factory provides an ingest job settings panels to
|
||||||
|
* enable or disable hash databases per ingest job. If the module family
|
||||||
|
* does not have per ingest job settings, the factory may extend
|
||||||
|
* IngestModuleFactoryAdapter to get an implementation of this method that
|
||||||
|
* returns false.
|
||||||
|
*
|
||||||
|
* @return True if the factory provides ingest job settings panels.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public boolean hasIngestJobSettingsPanel() {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets a user interface panel that can be used to set per ingest job
|
||||||
|
* settings for instances of the family of ingest modules the factory
|
||||||
|
* creates. For example, the core hash lookup ingest module factory provides
|
||||||
|
* an ingest job settings panel to enable or disable hash databases per
|
||||||
|
* ingest job. If the module family does not have per ingest job settings,
|
||||||
|
* the factory may extend IngestModuleFactoryAdapter to get an
|
||||||
|
* implementation of this method that throws an
|
||||||
|
* UnsupportedOperationException.
|
||||||
|
*
|
||||||
|
* @param setting Per ingest job settings to initialize the panel.
|
||||||
|
* @return An ingest job settings panel.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public IngestModuleIngestJobSettingsPanel getIngestJobSettingsPanel(IngestModuleIngestJobSettings settings) {
|
||||||
|
if (!(settings instanceof SampleModuleIngestJobSettings)) {
|
||||||
|
throw new IllegalArgumentException("Expected settings argument to be instanceof SampleModuleIngestJobSettings");
|
||||||
|
}
|
||||||
|
return new SampleIngestModuleIngestJobSettingsPanel((SampleModuleIngestJobSettings) settings);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Queries the factory to determine if it is capable of creating data source
|
||||||
|
* ingest modules. If the module family does not include data source ingest
|
||||||
|
* modules, the factory may extend IngestModuleFactoryAdapter to get an
|
||||||
|
* implementation of this method that returns false.
|
||||||
|
*
|
||||||
|
* @return True if the factory can create data source ingest modules.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public boolean isDataSourceIngestModuleFactory() {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates a data source ingest module instance.
|
||||||
|
* <p>
|
||||||
|
* Autopsy will generally use the factory to several instances of each type
|
||||||
|
* of module for each ingest job it performs. Completing an ingest job
|
||||||
|
* entails processing a single data source (e.g., a disk image) and all of
|
||||||
|
* the files from the data source, including files extracted from archives
|
||||||
|
* and any unallocated space (made to look like a series of files). The data
|
||||||
|
* source is passed through one or more pipelines of data source ingest
|
||||||
|
* modules. The files are passed through one or more pipelines of file
|
||||||
|
* ingest modules.
|
||||||
|
* <p>
|
||||||
|
* The ingest framework may use multiple threads to complete an ingest job,
|
||||||
|
* but it is guaranteed that there will be no more than one module instance
|
||||||
|
* per thread. However, if the module instances must share resources, the
|
||||||
|
* modules are responsible for synchronizing access to the shared resources
|
||||||
|
* and doing reference counting as required to release those resources
|
||||||
|
* correctly. Also, more than one ingest job may be in progress at any given
|
||||||
|
* time. This must also be taken into consideration when sharing resources
|
||||||
|
* between module instances. modules.
|
||||||
|
* <p>
|
||||||
|
* If the module family does not include data source ingest modules, the
|
||||||
|
* factory may extend IngestModuleFactoryAdapter to get an implementation of
|
||||||
|
* this method that throws an UnsupportedOperationException.
|
||||||
|
*
|
||||||
|
* @param settings The settings for the ingest job.
|
||||||
|
* @return A data source ingest module instance.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public DataSourceIngestModule createDataSourceIngestModule(IngestModuleIngestJobSettings settings) {
|
||||||
|
if (!(settings instanceof SampleModuleIngestJobSettings)) {
|
||||||
|
throw new IllegalArgumentException("Expected settings argument to be instanceof SampleModuleIngestJobSettings");
|
||||||
|
}
|
||||||
|
return new SampleDataSourceIngestModule((SampleModuleIngestJobSettings) settings);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Queries the factory to determine if it is capable of creating file ingest
|
||||||
|
* modules. If the module family does not include file ingest modules, the
|
||||||
|
* factory may extend IngestModuleFactoryAdapter to get an implementation of
|
||||||
|
* this method that returns false.
|
||||||
|
*
|
||||||
|
* @return True if the factory can create file ingest modules.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public boolean isFileIngestModuleFactory() {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates a file ingest module instance.
|
||||||
|
* <p>
|
||||||
|
* Autopsy will generally use the factory to several instances of each type
|
||||||
|
* of module for each ingest job it performs. Completing an ingest job
|
||||||
|
* entails processing a single data source (e.g., a disk image) and all of
|
||||||
|
* the files from the data source, including files extracted from archives
|
||||||
|
* and any unallocated space (made to look like a series of files). The data
|
||||||
|
* source is passed through one or more pipelines of data source ingest
|
||||||
|
* modules. The files are passed through one or more pipelines of file
|
||||||
|
* ingest modules.
|
||||||
|
* <p>
|
||||||
|
* The ingest framework may use multiple threads to complete an ingest job,
|
||||||
|
* but it is guaranteed that there will be no more than one module instance
|
||||||
|
* per thread. However, if the module instances must share resources, the
|
||||||
|
* modules are responsible for synchronizing access to the shared resources
|
||||||
|
* and doing reference counting as required to release those resources
|
||||||
|
* correctly. Also, more than one ingest job may be in progress at any given
|
||||||
|
* time. This must also be taken into consideration when sharing resources
|
||||||
|
* between module instances. modules.
|
||||||
|
* <p>
|
||||||
|
* If the module family does not include file ingest modules, the factory
|
||||||
|
* may extend IngestModuleFactoryAdapter to get an implementation of this
|
||||||
|
* method that throws an UnsupportedOperationException.
|
||||||
|
*
|
||||||
|
* @param settings The settings for the ingest job.
|
||||||
|
* @return A file ingest module instance.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public FileIngestModule createFileIngestModule(IngestModuleIngestJobSettings settings) {
|
||||||
|
if (!(settings instanceof SampleModuleIngestJobSettings)) {
|
||||||
|
throw new IllegalArgumentException("Expected settings argument to be instanceof SampleModuleIngestJobSettings");
|
||||||
|
}
|
||||||
|
return new SampleFileIngestModule((SampleModuleIngestJobSettings) settings);
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,45 @@
|
|||||||
|
<?xml version="1.0" encoding="UTF-8" ?>
|
||||||
|
|
||||||
|
<Form version="1.5" maxVersion="1.8" type="org.netbeans.modules.form.forminfo.JPanelFormInfo">
|
||||||
|
<AuxValues>
|
||||||
|
<AuxValue name="FormSettings_autoResourcing" type="java.lang.Integer" value="1"/>
|
||||||
|
<AuxValue name="FormSettings_autoSetComponentName" type="java.lang.Boolean" value="false"/>
|
||||||
|
<AuxValue name="FormSettings_generateFQN" type="java.lang.Boolean" value="true"/>
|
||||||
|
<AuxValue name="FormSettings_generateMnemonicsCode" type="java.lang.Boolean" value="true"/>
|
||||||
|
<AuxValue name="FormSettings_i18nAutoMode" type="java.lang.Boolean" value="true"/>
|
||||||
|
<AuxValue name="FormSettings_layoutCodeTarget" type="java.lang.Integer" value="1"/>
|
||||||
|
<AuxValue name="FormSettings_listenerGenerationStyle" type="java.lang.Integer" value="0"/>
|
||||||
|
<AuxValue name="FormSettings_variablesLocal" type="java.lang.Boolean" value="false"/>
|
||||||
|
<AuxValue name="FormSettings_variablesModifier" type="java.lang.Integer" value="2"/>
|
||||||
|
</AuxValues>
|
||||||
|
|
||||||
|
<Layout>
|
||||||
|
<DimensionLayout dim="0">
|
||||||
|
<Group type="103" groupAlignment="0" attributes="0">
|
||||||
|
<Group type="102" alignment="0" attributes="0">
|
||||||
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
|
<Component id="skipKnownFilesCheckBox" min="-2" max="-2" attributes="0"/>
|
||||||
|
<EmptySpace pref="255" max="32767" attributes="0"/>
|
||||||
|
</Group>
|
||||||
|
</Group>
|
||||||
|
</DimensionLayout>
|
||||||
|
<DimensionLayout dim="1">
|
||||||
|
<Group type="103" groupAlignment="0" attributes="0">
|
||||||
|
<Group type="102" alignment="0" attributes="0">
|
||||||
|
<EmptySpace max="-2" attributes="0"/>
|
||||||
|
<Component id="skipKnownFilesCheckBox" min="-2" max="-2" attributes="0"/>
|
||||||
|
<EmptySpace pref="270" max="32767" attributes="0"/>
|
||||||
|
</Group>
|
||||||
|
</Group>
|
||||||
|
</DimensionLayout>
|
||||||
|
</Layout>
|
||||||
|
<SubComponents>
|
||||||
|
<Component class="javax.swing.JCheckBox" name="skipKnownFilesCheckBox">
|
||||||
|
<Properties>
|
||||||
|
<Property name="text" type="java.lang.String" editor="org.netbeans.modules.i18n.form.FormI18nStringEditor">
|
||||||
|
<ResourceString bundle="org/sleuthkit/autopsy/examples/Bundle.properties" key="SampleIngestModuleIngestJobSettingsPanel.skipKnownFilesCheckBox.text" replaceFormat="org.openide.util.NbBundle.getMessage({sourceFileName}.class, "{key}")"/>
|
||||||
|
</Property>
|
||||||
|
</Properties>
|
||||||
|
</Component>
|
||||||
|
</SubComponents>
|
||||||
|
</Form>
|
@ -0,0 +1,96 @@
|
|||||||
|
/*
|
||||||
|
* Sample module ingest job settings panel in the public domain.
|
||||||
|
* Feel free to use this as a template for your module ingest job settings
|
||||||
|
* panels.
|
||||||
|
*
|
||||||
|
* Contact: Brian Carrier [carrier <at> sleuthkit [dot] org]
|
||||||
|
*
|
||||||
|
* This is free and unencumbered software released into the public domain.
|
||||||
|
*
|
||||||
|
* Anyone is free to copy, modify, publish, use, compile, sell, or
|
||||||
|
* distribute this software, either in source code form or as a compiled
|
||||||
|
* binary, for any purpose, commercial or non-commercial, and by any
|
||||||
|
* means.
|
||||||
|
*
|
||||||
|
* In jurisdictions that recognize copyright laws, the author or authors
|
||||||
|
* of this software dedicate any and all copyright interest in the
|
||||||
|
* software to the public domain. We make this dedication for the benefit
|
||||||
|
* of the public at large and to the detriment of our heirs and
|
||||||
|
* successors. We intend this dedication to be an overt act of
|
||||||
|
* relinquishment in perpetuity of all present and future rights to this
|
||||||
|
* software under copyright law.
|
||||||
|
*
|
||||||
|
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||||
|
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||||
|
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
||||||
|
* IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR
|
||||||
|
* OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
|
||||||
|
* ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
||||||
|
* OTHER DEALINGS IN THE SOFTWARE.
|
||||||
|
*/
|
||||||
|
package org.sleuthkit.autopsy.examples;
|
||||||
|
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestModuleIngestJobSettings;
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestModuleIngestJobSettingsPanel;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UI component used to make per ingest job settings for sample ingest modules.
|
||||||
|
*/
|
||||||
|
public class SampleIngestModuleIngestJobSettingsPanel extends IngestModuleIngestJobSettingsPanel {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates new form SampleIngestModuleIngestJobSettings
|
||||||
|
*/
|
||||||
|
public SampleIngestModuleIngestJobSettingsPanel(SampleModuleIngestJobSettings settings) {
|
||||||
|
initComponents();
|
||||||
|
customizeComponents(settings);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void customizeComponents(SampleModuleIngestJobSettings settings) {
|
||||||
|
skipKnownFilesCheckBox.setSelected(settings.skipKnownFiles());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the ingest job settings for an ingest module.
|
||||||
|
*
|
||||||
|
* @return The ingest settings.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public IngestModuleIngestJobSettings getSettings() {
|
||||||
|
return new SampleModuleIngestJobSettings(skipKnownFilesCheckBox.isSelected());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This method is called from within the constructor to initialize the form.
|
||||||
|
* WARNING: Do NOT modify this code. The content of this method is always
|
||||||
|
* regenerated by the Form Editor.
|
||||||
|
*/
|
||||||
|
@SuppressWarnings("unchecked")
|
||||||
|
// <editor-fold defaultstate="collapsed" desc="Generated Code">//GEN-BEGIN:initComponents
|
||||||
|
private void initComponents() {
|
||||||
|
|
||||||
|
skipKnownFilesCheckBox = new javax.swing.JCheckBox();
|
||||||
|
|
||||||
|
org.openide.awt.Mnemonics.setLocalizedText(skipKnownFilesCheckBox, org.openide.util.NbBundle.getMessage(SampleIngestModuleIngestJobSettingsPanel.class, "SampleIngestModuleIngestJobSettingsPanel.skipKnownFilesCheckBox.text")); // NOI18N
|
||||||
|
|
||||||
|
javax.swing.GroupLayout layout = new javax.swing.GroupLayout(this);
|
||||||
|
this.setLayout(layout);
|
||||||
|
layout.setHorizontalGroup(
|
||||||
|
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||||
|
.addGroup(layout.createSequentialGroup()
|
||||||
|
.addContainerGap()
|
||||||
|
.addComponent(skipKnownFilesCheckBox)
|
||||||
|
.addContainerGap(255, Short.MAX_VALUE))
|
||||||
|
);
|
||||||
|
layout.setVerticalGroup(
|
||||||
|
layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
|
||||||
|
.addGroup(layout.createSequentialGroup()
|
||||||
|
.addContainerGap()
|
||||||
|
.addComponent(skipKnownFilesCheckBox)
|
||||||
|
.addContainerGap(270, Short.MAX_VALUE))
|
||||||
|
);
|
||||||
|
}// </editor-fold>//GEN-END:initComponents
|
||||||
|
// Variables declaration - do not modify//GEN-BEGIN:variables
|
||||||
|
private javax.swing.JCheckBox skipKnownFilesCheckBox;
|
||||||
|
// End of variables declaration//GEN-END:variables
|
||||||
|
}
|
56
Core/src/org/sleuthkit/autopsy/examples/SampleModuleIngestJobSettings.java
Executable file
56
Core/src/org/sleuthkit/autopsy/examples/SampleModuleIngestJobSettings.java
Executable file
@ -0,0 +1,56 @@
|
|||||||
|
/*
|
||||||
|
* Sample module ingest job settings in the public domain.
|
||||||
|
* Feel free to use this as a template for your module job settings.
|
||||||
|
*
|
||||||
|
* Contact: Brian Carrier [carrier <at> sleuthkit [dot] org]
|
||||||
|
*
|
||||||
|
* This is free and unencumbered software released into the public domain.
|
||||||
|
*
|
||||||
|
* Anyone is free to copy, modify, publish, use, compile, sell, or
|
||||||
|
* distribute this software, either in source code form or as a compiled
|
||||||
|
* binary, for any purpose, commercial or non-commercial, and by any
|
||||||
|
* means.
|
||||||
|
*
|
||||||
|
* In jurisdictions that recognize copyright laws, the author or authors
|
||||||
|
* of this software dedicate any and all copyright interest in the
|
||||||
|
* software to the public domain. We make this dedication for the benefit
|
||||||
|
* of the public at large and to the detriment of our heirs and
|
||||||
|
* successors. We intend this dedication to be an overt act of
|
||||||
|
* relinquishment in perpetuity of all present and future rights to this
|
||||||
|
* software under copyright law.
|
||||||
|
*
|
||||||
|
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||||
|
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||||
|
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
||||||
|
* IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR
|
||||||
|
* OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
|
||||||
|
* ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
||||||
|
* OTHER DEALINGS IN THE SOFTWARE.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package org.sleuthkit.autopsy.examples;
|
||||||
|
|
||||||
|
import org.sleuthkit.autopsy.ingest.IngestModuleIngestJobSettings;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Ingest job options for sample ingest module instances.
|
||||||
|
*/
|
||||||
|
public class SampleModuleIngestJobSettings implements IngestModuleIngestJobSettings {
|
||||||
|
|
||||||
|
private boolean skipKnownFiles = true;
|
||||||
|
|
||||||
|
SampleModuleIngestJobSettings() {
|
||||||
|
}
|
||||||
|
|
||||||
|
SampleModuleIngestJobSettings(boolean skipKnownFiles) {
|
||||||
|
this.skipKnownFiles = skipKnownFiles;
|
||||||
|
}
|
||||||
|
|
||||||
|
void setSkipKnownFiles(boolean enabled) {
|
||||||
|
skipKnownFiles = enabled;
|
||||||
|
}
|
||||||
|
|
||||||
|
boolean skipKnownFiles() {
|
||||||
|
return skipKnownFiles;
|
||||||
|
}
|
||||||
|
}
|
@ -87,7 +87,7 @@ public final class IngestJobLauncher {
|
|||||||
// NOTE: In the future, this code will be modified to get the
|
// NOTE: In the future, this code will be modified to get the
|
||||||
// module settings for the current context, if available, from
|
// module settings for the current context, if available, from
|
||||||
// storage; for now always use the defaults.
|
// storage; for now always use the defaults.
|
||||||
IngestModuleTemplate moduleTemplate = new IngestModuleTemplate(moduleFactory, moduleFactory.getDefaultModuleSettings());
|
IngestModuleTemplate moduleTemplate = new IngestModuleTemplate(moduleFactory, moduleFactory.getDefaultIngestJobSettings());
|
||||||
String moduleName = moduleTemplate.getModuleName();
|
String moduleName = moduleTemplate.getModuleName();
|
||||||
if (enabledModuleNames.contains(moduleName)) {
|
if (enabledModuleNames.contains(moduleName)) {
|
||||||
moduleTemplate.setEnabled(true);
|
moduleTemplate.setEnabled(true);
|
||||||
|
@ -20,28 +20,110 @@ package org.sleuthkit.autopsy.ingest;
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* The interface that must be implemented by all ingest modules.
|
* The interface that must be implemented by all ingest modules.
|
||||||
|
* <p>
|
||||||
|
* Autopsy will generally use several instances of an ingest module for each
|
||||||
|
* ingest job it performs. Completing an ingest job entails processing a single
|
||||||
|
* data source (e.g., a disk image) and all of the files from the data source,
|
||||||
|
* including files extracted from archives and any unallocated space (made to
|
||||||
|
* look like a series of files). The data source is passed through one or more
|
||||||
|
* pipelines of data source ingest modules. The files are passed through one or
|
||||||
|
* more pipelines of file ingest modules.
|
||||||
|
* <p>
|
||||||
|
* Autopsy may use multiple threads to complete an ingest job, but it is
|
||||||
|
* guaranteed that there will be no more than one module instance per thread.
|
||||||
|
* However, if the module instances must share resources, the modules are
|
||||||
|
* responsible for synchronizing access to the shared resources and doing
|
||||||
|
* reference counting as required to release those resources correctly. Also,
|
||||||
|
* more than one ingest job may be in progress at any given time. This must also
|
||||||
|
* be taken into consideration when sharing resources between module instances.
|
||||||
|
* <p>
|
||||||
|
* TIP: An ingest module that does not require initialization or clean up may
|
||||||
|
* extend the abstract IngestModuleAdapter class to get a default "do nothing"
|
||||||
|
* implementation of this interface.
|
||||||
|
*
|
||||||
*/
|
*/
|
||||||
public interface IngestModule {
|
public interface IngestModule {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A return code for derived class process() methods.
|
||||||
|
*/
|
||||||
public enum ProcessResult {
|
public enum ProcessResult {
|
||||||
|
|
||||||
OK,
|
OK,
|
||||||
ERROR
|
ERROR
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A custom exception for the use of ingest modules.
|
||||||
|
*/
|
||||||
public class IngestModuleException extends Exception {
|
public class IngestModuleException extends Exception {
|
||||||
|
|
||||||
|
public IngestModuleException() {
|
||||||
|
}
|
||||||
|
|
||||||
public IngestModuleException(String message) {
|
public IngestModuleException(String message) {
|
||||||
super(message);
|
super(message);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// RJCTODO: Write header comment, make sure to mention "one module instance per thread"
|
|
||||||
/**
|
/**
|
||||||
* Invoked by the ingest frame
|
* Invoked by Autopsy to allow an ingest module instance to set up any
|
||||||
* @param context
|
* internal data structures and acquire any private resources it will need
|
||||||
* @throws org.sleuthkit.autopsy.ingest.IngestModule.IngestModuleException
|
* during an ingest job.
|
||||||
|
* <p>
|
||||||
|
* Autopsy will generally use several instances of an ingest module for each
|
||||||
|
* ingest job it performs. Completing an ingest job entails processing a
|
||||||
|
* single data source (e.g., a disk image) and all of the files from the
|
||||||
|
* data source, including files extracted from archives and any unallocated
|
||||||
|
* space (made to look like a series of files). The data source is passed
|
||||||
|
* through one or more pipelines of data source ingest modules. The files
|
||||||
|
* are passed through one or more pipelines of file ingest modules.
|
||||||
|
* <p>
|
||||||
|
* Autopsy may use multiple threads to complete an ingest job, but it is
|
||||||
|
* guaranteed that there will be no more than one module instance per
|
||||||
|
* thread. However, if the module instances must share resources, the
|
||||||
|
* modules are responsible for synchronizing access to the shared resources
|
||||||
|
* and doing reference counting as required to release those resources
|
||||||
|
* correctly. Also, more than one ingest job may be in progress at any given
|
||||||
|
* time. This must also be taken into consideration when sharing resources
|
||||||
|
* between module instances.
|
||||||
|
* <p>
|
||||||
|
* An ingest module that does not require initialization may extend the
|
||||||
|
* abstract IngestModuleAdapter class to get a default "do nothing"
|
||||||
|
* implementation of this method.
|
||||||
|
*
|
||||||
|
* @param context Provides data and services specific to the ingest job and
|
||||||
|
* the ingest pipeline of which the module is a part.
|
||||||
|
* @throws org.sleuthkit.autopsy.ingest.IngestModule.IngestModuleException
|
||||||
*/
|
*/
|
||||||
void startUp(IngestJobContext context) throws IngestModuleException;
|
void startUp(IngestJobContext context) throws IngestModuleException;
|
||||||
|
|
||||||
// RJCTODO: Write header comment, make sure to mention "one module instance per thread"
|
/**
|
||||||
|
* Invoked by Autopsy when an ingest job is completed, before the ingest
|
||||||
|
* module instance is discarded. The module should respond by doing things
|
||||||
|
* like releasing private resources, submitting final results, and posting a
|
||||||
|
* final ingest message.
|
||||||
|
* <p>
|
||||||
|
* Autopsy will generally use several instances of an ingest module for each
|
||||||
|
* ingest job it performs. Completing an ingest job entails processing a
|
||||||
|
* single data source (e.g., a disk image) and all of the files from the
|
||||||
|
* data source, including files extracted from archives and any unallocated
|
||||||
|
* space (made to look like a series of files). The data source is passed
|
||||||
|
* through one or more pipelines of data source ingest modules. The files
|
||||||
|
* are passed through one or more pipelines of file ingest modules.
|
||||||
|
* <p>
|
||||||
|
* Autopsy may use multiple threads to complete an ingest job, but it is
|
||||||
|
* guaranteed that there will be no more than one module instance per
|
||||||
|
* thread. However, if the module instances must share resources, the
|
||||||
|
* modules are responsible for synchronizing access to the shared resources
|
||||||
|
* and doing reference counting as required to release those resources
|
||||||
|
* correctly. Also, more than one ingest job may be in progress at any given
|
||||||
|
* time. This must also be taken into consideration when sharing resources
|
||||||
|
* between module instances.
|
||||||
|
* <p>
|
||||||
|
* An ingest module that does not require initialization may extend the
|
||||||
|
* abstract IngestModuleAdapter class to get a default "do nothing"
|
||||||
|
* implementation of this method.
|
||||||
|
*/
|
||||||
void shutDown(boolean ingestJobWasCancelled);
|
void shutDown(boolean ingestJobWasCancelled);
|
||||||
}
|
}
|
||||||
|
@ -19,34 +19,50 @@
|
|||||||
package org.sleuthkit.autopsy.ingest;
|
package org.sleuthkit.autopsy.ingest;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* An interface that must be implemented by all providers of ingest modules. An
|
* An interface that must be implemented by all providers of Autopsy ingest
|
||||||
* ingest module factory will be used to create instances of a type of data
|
* modules. An ingest module factory is used to create instances of a type of
|
||||||
* source ingest module, a type of file ingest module, or both.
|
* data source ingest module, a type of file ingest module, or both.
|
||||||
* <P>
|
|
||||||
* IMPORTANT: The factory should be stateless to support context-sensitive use
|
|
||||||
* of the factory. The ingest framework is responsible for managing context
|
|
||||||
* switching and the persistence of resource configurations and per ingest job
|
|
||||||
* options.
|
|
||||||
* <p>
|
* <p>
|
||||||
* IMPORTANT: The ingest framework will create one or more instances of each
|
* Autopsy will generally use the factory to several instances of each type of
|
||||||
* module type for each ingest job it performs. The ingest framework may use
|
* module for each ingest job it performs. Completing an ingest job entails
|
||||||
* multiple threads to complete an ingest job, but it is guaranteed that there
|
* processing a single data source (e.g., a disk image) and all of the files
|
||||||
* will be no more than one module instance per thread. However, if these
|
* from the data source, including files extracted from archives and any
|
||||||
* instances must share resources, the modules are responsible for synchronizing
|
* unallocated space (made to look like a series of files). The data source is
|
||||||
* access to the shared resources and doing reference counting as required to
|
* passed through one or more pipelines of data source ingest modules. The files
|
||||||
* release those resources correctly.
|
* are passed through one or more pipelines of file ingest modules.
|
||||||
* <p>
|
* <p>
|
||||||
* IMPORTANT: To be discovered at runtime by the ingest framework,
|
* Autopsy may use multiple threads to complete an ingest job, but it is
|
||||||
* IngestModuleFactory implementations must be marked with the following
|
* guaranteed that there will be no more than one module instance per thread.
|
||||||
* NetBeans Service provider annotation:
|
* However, if the module instances must share resources, the modules are
|
||||||
|
* responsible for synchronizing access to the shared resources and doing
|
||||||
|
* reference counting as required to release those resources correctly. Also,
|
||||||
|
* more than one ingest job may be in progress at any given time. This must also
|
||||||
|
* be taken into consideration when sharing resources between module instances.
|
||||||
|
* <p>
|
||||||
|
* An ingest module factory may provide global and per ingest job settings user
|
||||||
|
* interface panels. The global settings should apply to all module instances.
|
||||||
|
* The per ingest job settings should apply to all module instances working on a
|
||||||
|
* particular ingest job. Autopsy supports context-sensitive and persistent per
|
||||||
|
* ingest job settings, so per ingest job settings must be serializable.
|
||||||
|
* <p>
|
||||||
|
* To be discovered at runtime by the ingest framework, IngestModuleFactory
|
||||||
|
* implementations must be marked with the following NetBeans Service provider
|
||||||
|
* annotation:
|
||||||
*
|
*
|
||||||
* @ServiceProvider(service=IngestModuleFactory.class)
|
* @ServiceProvider(service=IngestModuleFactory.class)
|
||||||
|
* <p>
|
||||||
|
* IMPORTANT TIP: If an implementation of IngestModuleFactory does not need to
|
||||||
|
* provide implementations of all of the IngestModuleFactory methods, it can
|
||||||
|
* extend the abstract class IngestModuleFactoryAdapter to get default
|
||||||
|
* implementations of most of the IngestModuleFactory methods.
|
||||||
*/
|
*/
|
||||||
public interface IngestModuleFactory {
|
public interface IngestModuleFactory {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets the display name that identifies the family of ingest modules the
|
* Gets the display name that identifies the family of ingest modules the
|
||||||
* factory creates.
|
* factory creates. Autopsy uses this string to identify the module in user
|
||||||
|
* interface components and log messages. The module name must be unique. so
|
||||||
|
* a brief but distinctive name is recommended.
|
||||||
*
|
*
|
||||||
* @return The module family display name.
|
* @return The module family display name.
|
||||||
*/
|
*/
|
||||||
@ -54,7 +70,8 @@ public interface IngestModuleFactory {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets a brief, user-friendly description of the family of ingest modules
|
* Gets a brief, user-friendly description of the family of ingest modules
|
||||||
* the factory creates.
|
* the factory creates. Autopsy uses this string to describe the module in
|
||||||
|
* user interface components.
|
||||||
*
|
*
|
||||||
* @return The module family description.
|
* @return The module family description.
|
||||||
*/
|
*/
|
||||||
@ -69,147 +86,154 @@ public interface IngestModuleFactory {
|
|||||||
String getModuleVersionNumber();
|
String getModuleVersionNumber();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Queries the factory to determine if it provides user interface panels to
|
* Queries the factory to determine if it provides a user interface panel to
|
||||||
* configure resources to be used by instances of the family of ingest
|
* allow a user to change settings that are used by all instances of the
|
||||||
* modules the factory creates. For example, the core hash lookup ingest
|
* family of ingest modules the factory creates. For example, the Autopsy
|
||||||
* module factory provides resource configuration panels to import and
|
* core hash lookup ingest module factory provides a global settings panel
|
||||||
* create hash databases. The hash databases are then enabled or disabled
|
* to import and create hash databases. The hash databases are then enabled
|
||||||
* per ingest job using ingest job options panels. If the module family does
|
* or disabled per ingest job using an ingest job settings panel. If the
|
||||||
* not have a resources configuration, the factory should extend
|
* module family does not have global settings, the factory may extend
|
||||||
* IngestModuleFactoryAdapter to get an implementation of this method that
|
* IngestModuleFactoryAdapter to get an implementation of this method that
|
||||||
* returns false.
|
* returns false.
|
||||||
*
|
*
|
||||||
* @return True if the factory provides resource configuration panels.
|
* @return True if the factory provides a global settings panel.
|
||||||
*/
|
*/
|
||||||
boolean hasGlobalSettingsPanel();
|
boolean hasGlobalSettingsPanel();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets a user interface panel that can be used to configure resources for
|
* Gets a user interface panel that allows a user to change settings that
|
||||||
* instances of the family of ingest modules the factory creates. For
|
* are used by all instances of the family of ingest modules the factory
|
||||||
* example, the core hash lookup ingest module factory provides a resource
|
* creates. For example, the Autopsy core hash lookup ingest module factory
|
||||||
* configuration panel to import and create hash databases. The imported
|
* provides a global settings panel to import and create hash databases. The
|
||||||
* hash databases are then enabled or disabled per ingest job using ingest
|
* imported hash databases are then enabled or disabled per ingest job using
|
||||||
* options panels. If the module family does not have a resources
|
* ingest an ingest job settings panel. If the module family does not have a
|
||||||
* configuration, the factory should extend IngestModuleFactoryAdapter to
|
* global settings, the factory may extend IngestModuleFactoryAdapter to get
|
||||||
* get an implementation of this method that throws an
|
* an implementation of this method that throws an
|
||||||
* UnsupportedOperationException.
|
* UnsupportedOperationException.
|
||||||
* <p>
|
|
||||||
* IMPORTANT: The ingest framework assumes that ingest module factories are
|
|
||||||
* stateless to support context-sensitive use of the factory, with the
|
|
||||||
* ingest framework managing context switching and the persistence of
|
|
||||||
* resource configurations and per ingest job options. A factory should not
|
|
||||||
* retain references to the resources configuration panels it creates.
|
|
||||||
*
|
*
|
||||||
* @param resourcesConfig A resources configuration with which to initialize
|
* @return A global settings panel.
|
||||||
* the panel.
|
|
||||||
* @return A user interface panel for configuring ingest module resources.
|
|
||||||
*/
|
*/
|
||||||
IngestModuleGlobalSetttingsPanel getGlobalSettingsPanel();
|
IngestModuleGlobalSetttingsPanel getGlobalSettingsPanel();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets the default per ingest job options for instances of the family of
|
* Gets the default per ingest job settings for instances of the family of
|
||||||
* ingest modules the factory creates. For example, the core hash lookup
|
* ingest modules the factory creates. For example, the Autopsy core hash
|
||||||
* ingest modules family has a resources configuration consisting of hash
|
* lookup ingest modules family uses hash databases imported or created
|
||||||
* databases, all of which are enabled by default for an ingest job. If the
|
* using its global settings panel. All of the hash databases are enabled by
|
||||||
* module family does not have per ingest job options, the factory should
|
* default for an ingest job. If the module family does not have per ingest
|
||||||
* extend IngestModuleFactoryAdapter to get an implementation of this method
|
* job settings, the factory may extend IngestModuleFactoryAdapter to get an
|
||||||
* that returns an instance of the NoIngestJobOptions class.
|
* implementation of this method that returns an instance of the
|
||||||
|
* NoIngestModuleJobSettings class.
|
||||||
*
|
*
|
||||||
* @return The ingest options.
|
* @return The default ingest job settings.
|
||||||
*/
|
*/
|
||||||
IngestModuleIngestJobSettings getDefaultModuleSettings();
|
IngestModuleIngestJobSettings getDefaultIngestJobSettings();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Queries the factory to determine if it provides user interface panels to
|
* Queries the factory to determine if it provides user a interface panel to
|
||||||
* set per ingest job options for instances of the family of ingest modules
|
* allow a user to make per ingest job settings for instances of the family
|
||||||
* the factory creates. For example, the core hash lookup ingest module
|
* of ingest modules the factory creates. For example, the Autopsy core hash
|
||||||
* factory provides ingest options panels to enable or disable hash
|
* lookup ingest module factory provides an ingest job settings panels to
|
||||||
* databases per ingest job. If the module family does not have per ingest
|
* enable or disable hash databases per ingest job. If the module family
|
||||||
* job options, the factory should extend IngestModuleFactoryAdapter to get
|
* does not have per ingest job settings, the factory may extend
|
||||||
* an implementation of this method that returns false.
|
* IngestModuleFactoryAdapter to get an implementation of this method that
|
||||||
|
* returns false.
|
||||||
*
|
*
|
||||||
* @return True if the factory provides ingest job options panels.
|
* @return True if the factory provides ingest job settings panels.
|
||||||
*/
|
*/
|
||||||
boolean hasModuleSettingsPanel();
|
boolean hasIngestJobSettingsPanel();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets a user interface panel that can be used to set per ingest job
|
* Gets a user interface panel that can be used to set per ingest job
|
||||||
* options for instances of the family of ingest modules the factory
|
* settings for instances of the family of ingest modules the factory
|
||||||
* creates. For example, the core hash lookup ingest module factory provides
|
* creates. For example, the core hash lookup ingest module factory provides
|
||||||
* ingest options panels to enable or disable hash databases per ingest job.
|
* an ingest job settings panel to enable or disable hash databases per
|
||||||
* If the module family does not have ingest job options, the factory should
|
* ingest job. If the module family does not have per ingest job settings,
|
||||||
* extend IngestModuleFactoryAdapter to get an implementation of this method
|
* the factory may extend IngestModuleFactoryAdapter to get an
|
||||||
* that throws an UnsupportedOperationException.
|
* implementation of this method that throws an
|
||||||
* <p>
|
* UnsupportedOperationException.
|
||||||
* IMPORTANT: The ingest framework assumes that ingest module factories are
|
|
||||||
* stateless to support context-sensitive use of the factory. The ingest
|
|
||||||
* framework is responsible for managing context switching and the
|
|
||||||
* persistence of resource configurations and per ingest job options. A
|
|
||||||
* factory should not retain references to the ingest job options panels it
|
|
||||||
* creates.
|
|
||||||
*
|
*
|
||||||
* @param resourcesConfig
|
* @param setting Per ingest job settings to initialize the panel.
|
||||||
* @param ingestOptions Per ingest job options to initialize the panel.
|
* @return An ingest job settings panel.
|
||||||
* @return A user interface panel.
|
|
||||||
*/
|
*/
|
||||||
IngestModuleIngestJobSettingsPanel getModuleSettingsPanel(IngestModuleIngestJobSettings settings); // RJCTODO: Can these be made into generics?
|
IngestModuleIngestJobSettingsPanel getIngestJobSettingsPanel(IngestModuleIngestJobSettings settings);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Queries the factory to determine if it is capable of creating file ingest
|
* Queries the factory to determine if it is capable of creating data source
|
||||||
* modules.
|
* ingest modules. If the module family does not include data source ingest
|
||||||
|
* modules, the factory may extend IngestModuleFactoryAdapter to get an
|
||||||
|
* implementation of this method that returns false.
|
||||||
*
|
*
|
||||||
* @return True if the factory can create file ingest modules.
|
* @return True if the factory can create data source ingest modules.
|
||||||
*/
|
*/
|
||||||
boolean isDataSourceIngestModuleFactory();
|
boolean isDataSourceIngestModuleFactory();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Creates a data source ingest module instance.
|
* Creates a data source ingest module instance.
|
||||||
* <p>
|
* <p>
|
||||||
* IMPORTANT: The factory should be stateless to support context-sensitive
|
* Autopsy will generally use the factory to several instances of each type
|
||||||
* use of the factory. The ingest framework is responsible for managing
|
* of module for each ingest job it performs. Completing an ingest job
|
||||||
* context switching and the persistence of resource configurations and per
|
* entails processing a single data source (e.g., a disk image) and all of
|
||||||
* ingest job options. A factory should not retain references to the data
|
* the files from the data source, including files extracted from archives
|
||||||
* source ingest module instances it creates.
|
* and any unallocated space (made to look like a series of files). The data
|
||||||
|
* source is passed through one or more pipelines of data source ingest
|
||||||
|
* modules. The files are passed through one or more pipelines of file
|
||||||
|
* ingest modules.
|
||||||
* <p>
|
* <p>
|
||||||
* IMPORTANT: The ingest framework will create one or more data source
|
* The ingest framework may use multiple threads to complete an ingest job,
|
||||||
* ingest module instances for each ingest job it performs. The ingest
|
* but it is guaranteed that there will be no more than one module instance
|
||||||
* framework may use multiple threads to complete an ingest job, but it is
|
* per thread. However, if the module instances must share resources, the
|
||||||
* guaranteed that there will be no more than one module instance per
|
* modules are responsible for synchronizing access to the shared resources
|
||||||
* thread. However, if these instances must share resources, the modules are
|
* and doing reference counting as required to release those resources
|
||||||
* responsible for synchronizing access to the shared resources and doing
|
* correctly. Also, more than one ingest job may be in progress at any given
|
||||||
* reference counting as required to release those resources correctly.
|
* time. This must also be taken into consideration when sharing resources
|
||||||
|
* between module instances. modules.
|
||||||
|
* <p>
|
||||||
|
* If the module family does not include data source ingest modules, the
|
||||||
|
* factory may extend IngestModuleFactoryAdapter to get an implementation of
|
||||||
|
* this method that throws an UnsupportedOperationException.
|
||||||
*
|
*
|
||||||
* @param ingestOptions The ingest options for the module instance.
|
* @param settings The settings for the ingest job.
|
||||||
* @return A data source ingest module instance.
|
* @return A data source ingest module instance.
|
||||||
*/
|
*/
|
||||||
DataSourceIngestModule createDataSourceIngestModule(IngestModuleIngestJobSettings settings);
|
DataSourceIngestModule createDataSourceIngestModule(IngestModuleIngestJobSettings settings);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Queries the factory to determine if it is capable of creating file ingest
|
* Queries the factory to determine if it is capable of creating file ingest
|
||||||
* module instances.
|
* modules. If the module family does not include file ingest modules, the
|
||||||
|
* factory may extend IngestModuleFactoryAdapter to get an implementation of
|
||||||
|
* this method that returns false.
|
||||||
*
|
*
|
||||||
* @return True if the factory can create file ingest module instances.
|
* @return True if the factory can create file ingest modules.
|
||||||
*/
|
*/
|
||||||
boolean isFileIngestModuleFactory();
|
boolean isFileIngestModuleFactory();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Creates a file ingest module instance.
|
* Creates a file ingest module instance.
|
||||||
* <p>
|
* <p>
|
||||||
* IMPORTANT: The factory should be stateless to support context-sensitive
|
* Autopsy will generally use the factory to several instances of each type
|
||||||
* use of the factory. The ingest framework is responsible for managing
|
* of module for each ingest job it performs. Completing an ingest job
|
||||||
* context switching and the persistence of resource configurations and per
|
* entails processing a single data source (e.g., a disk image) and all of
|
||||||
* ingest job options. A factory should not retain references to the file
|
* the files from the data source, including files extracted from archives
|
||||||
* ingest module instances it creates.
|
* and any unallocated space (made to look like a series of files). The data
|
||||||
|
* source is passed through one or more pipelines of data source ingest
|
||||||
|
* modules. The files are passed through one or more pipelines of file
|
||||||
|
* ingest modules.
|
||||||
* <p>
|
* <p>
|
||||||
* IMPORTANT: The ingest framework will create one or more file ingest
|
* The ingest framework may use multiple threads to complete an ingest job,
|
||||||
* module instances for each ingest job it performs. The ingest framework
|
* but it is guaranteed that there will be no more than one module instance
|
||||||
* may use multiple threads to complete an ingest job, but it is guaranteed
|
* per thread. However, if the module instances must share resources, the
|
||||||
* that there will be no more than one module instance per thread. However,
|
* modules are responsible for synchronizing access to the shared resources
|
||||||
* if these instances must share resources, the modules are responsible for
|
* and doing reference counting as required to release those resources
|
||||||
* synchronizing access to the shared resources and doing reference counting
|
* correctly. Also, more than one ingest job may be in progress at any given
|
||||||
* as required to release those resources correctly.
|
* time. This must also be taken into consideration when sharing resources
|
||||||
|
* between module instances. modules.
|
||||||
|
* <p>
|
||||||
|
* If the module family does not include file ingest modules, the factory
|
||||||
|
* may extend IngestModuleFactoryAdapter to get an implementation of this
|
||||||
|
* method that throws an UnsupportedOperationException.
|
||||||
*
|
*
|
||||||
* @param ingestOptions The ingest options for the module instance.
|
* @param settings The settings for the ingest job.
|
||||||
* @return A file ingest module instance.
|
* @return A file ingest module instance.
|
||||||
*/
|
*/
|
||||||
FileIngestModule createFileIngestModule(IngestModuleIngestJobSettings settings);
|
FileIngestModule createFileIngestModule(IngestModuleIngestJobSettings settings);
|
||||||
|
@ -44,17 +44,17 @@ public abstract class IngestModuleFactoryAdapter implements IngestModuleFactory
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public IngestModuleIngestJobSettings getDefaultModuleSettings() {
|
public IngestModuleIngestJobSettings getDefaultIngestJobSettings() {
|
||||||
return new NoIngestModuleIngestJobSettings();
|
return new NoIngestModuleIngestJobSettings();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean hasModuleSettingsPanel() {
|
public boolean hasIngestJobSettingsPanel() {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public IngestModuleIngestJobSettingsPanel getModuleSettingsPanel(IngestModuleIngestJobSettings ingestOptions) {
|
public IngestModuleIngestJobSettingsPanel getIngestJobSettingsPanel(IngestModuleIngestJobSettings ingestOptions) {
|
||||||
throw new UnsupportedOperationException();
|
throw new UnsupportedOperationException();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -21,7 +21,7 @@ package org.sleuthkit.autopsy.ingest;
|
|||||||
import javax.swing.JPanel;
|
import javax.swing.JPanel;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Base class for ingest module resources configuration panels.
|
* Base class for ingest module global settings panels.
|
||||||
*/
|
*/
|
||||||
public abstract class IngestModuleGlobalSetttingsPanel extends JPanel {
|
public abstract class IngestModuleGlobalSetttingsPanel extends JPanel {
|
||||||
|
|
||||||
|
@ -50,11 +50,11 @@ final class IngestModuleTemplate {
|
|||||||
}
|
}
|
||||||
|
|
||||||
boolean hasModuleSettingsPanel() {
|
boolean hasModuleSettingsPanel() {
|
||||||
return moduleFactory.hasModuleSettingsPanel();
|
return moduleFactory.hasIngestJobSettingsPanel();
|
||||||
}
|
}
|
||||||
|
|
||||||
IngestModuleIngestJobSettingsPanel getModuleSettingsPanel() {
|
IngestModuleIngestJobSettingsPanel getModuleSettingsPanel() {
|
||||||
return moduleFactory.getModuleSettingsPanel(settings);
|
return moduleFactory.getIngestJobSettingsPanel(settings);
|
||||||
}
|
}
|
||||||
|
|
||||||
boolean hasGlobalSettingsPanel() {
|
boolean hasGlobalSettingsPanel() {
|
||||||
|
@ -88,7 +88,4 @@ public class ModuleDataEvent extends ChangeEvent {
|
|||||||
public String getModuleName() {
|
public String getModuleName() {
|
||||||
return moduleName;
|
return moduleName;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -57,17 +57,17 @@ public class FileExtMismatchDetectorModuleFactory extends IngestModuleFactoryAda
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public IngestModuleIngestJobSettings getDefaultModuleSettings() {
|
public IngestModuleIngestJobSettings getDefaultIngestJobSettings() {
|
||||||
return new FileExtMismatchDetectorModuleSettings();
|
return new FileExtMismatchDetectorModuleSettings();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean hasModuleSettingsPanel() {
|
public boolean hasIngestJobSettingsPanel() {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public IngestModuleIngestJobSettingsPanel getModuleSettingsPanel(IngestModuleIngestJobSettings settings) {
|
public IngestModuleIngestJobSettingsPanel getIngestJobSettingsPanel(IngestModuleIngestJobSettings settings) {
|
||||||
assert settings instanceof FileExtMismatchDetectorModuleSettings;
|
assert settings instanceof FileExtMismatchDetectorModuleSettings;
|
||||||
if (!(settings instanceof FileExtMismatchDetectorModuleSettings)) {
|
if (!(settings instanceof FileExtMismatchDetectorModuleSettings)) {
|
||||||
throw new IllegalArgumentException("Expected settings argument to be instanceof FileExtMismatchDetectorModuleSettings");
|
throw new IllegalArgumentException("Expected settings argument to be instanceof FileExtMismatchDetectorModuleSettings");
|
||||||
|
@ -56,17 +56,17 @@ public class FileTypeIdModuleFactory extends IngestModuleFactoryAdapter {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public IngestModuleIngestJobSettings getDefaultModuleSettings() {
|
public IngestModuleIngestJobSettings getDefaultIngestJobSettings() {
|
||||||
return new FileTypeIdModuleSettings();
|
return new FileTypeIdModuleSettings();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean hasModuleSettingsPanel() {
|
public boolean hasIngestJobSettingsPanel() {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public IngestModuleIngestJobSettingsPanel getModuleSettingsPanel(IngestModuleIngestJobSettings settings) {
|
public IngestModuleIngestJobSettingsPanel getIngestJobSettingsPanel(IngestModuleIngestJobSettings settings) {
|
||||||
assert settings instanceof FileTypeIdModuleSettings;
|
assert settings instanceof FileTypeIdModuleSettings;
|
||||||
if (!(settings instanceof FileTypeIdModuleSettings)) {
|
if (!(settings instanceof FileTypeIdModuleSettings)) {
|
||||||
throw new IllegalArgumentException("Expected settings argument to be instanceof FileTypeIdModuleSettings");
|
throw new IllegalArgumentException("Expected settings argument to be instanceof FileTypeIdModuleSettings");
|
||||||
|
@ -58,7 +58,7 @@ public class HashLookupModuleFactory extends IngestModuleFactoryAdapter {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public IngestModuleIngestJobSettings getDefaultModuleSettings() {
|
public IngestModuleIngestJobSettings getDefaultIngestJobSettings() {
|
||||||
// All available hash sets are enabled by default.
|
// All available hash sets are enabled by default.
|
||||||
HashDbManager hashDbManager = HashDbManager.getInstance();
|
HashDbManager hashDbManager = HashDbManager.getInstance();
|
||||||
List<String> knownHashSetNames = getHashSetNames(hashDbManager.getKnownFileHashSets());
|
List<String> knownHashSetNames = getHashSetNames(hashDbManager.getKnownFileHashSets());
|
||||||
@ -75,12 +75,12 @@ public class HashLookupModuleFactory extends IngestModuleFactoryAdapter {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean hasModuleSettingsPanel() {
|
public boolean hasIngestJobSettingsPanel() {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public IngestModuleIngestJobSettingsPanel getModuleSettingsPanel(IngestModuleIngestJobSettings settings) {
|
public IngestModuleIngestJobSettingsPanel getIngestJobSettingsPanel(IngestModuleIngestJobSettings settings) {
|
||||||
if (!(settings instanceof HashLookupModuleSettings)) {
|
if (!(settings instanceof HashLookupModuleSettings)) {
|
||||||
throw new IllegalArgumentException("Expected settings argument to be instanceof HashLookupModuleSettings");
|
throw new IllegalArgumentException("Expected settings argument to be instanceof HashLookupModuleSettings");
|
||||||
}
|
}
|
||||||
|
@ -59,7 +59,7 @@ public class KeywordSearchModuleFactory extends IngestModuleFactoryAdapter {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public IngestModuleIngestJobSettings getDefaultModuleSettings() {
|
public IngestModuleIngestJobSettings getDefaultIngestJobSettings() {
|
||||||
KeywordSearchListsXML listManager = KeywordSearchListsXML.getCurrent();
|
KeywordSearchListsXML listManager = KeywordSearchListsXML.getCurrent();
|
||||||
List<String> enabledKeywordLists = new ArrayList<>();
|
List<String> enabledKeywordLists = new ArrayList<>();
|
||||||
List<KeywordList> keywordLists = listManager.getListsL();
|
List<KeywordList> keywordLists = listManager.getListsL();
|
||||||
@ -71,12 +71,12 @@ public class KeywordSearchModuleFactory extends IngestModuleFactoryAdapter {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean hasModuleSettingsPanel() {
|
public boolean hasIngestJobSettingsPanel() {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public IngestModuleIngestJobSettingsPanel getModuleSettingsPanel(IngestModuleIngestJobSettings settings) {
|
public IngestModuleIngestJobSettingsPanel getIngestJobSettingsPanel(IngestModuleIngestJobSettings settings) {
|
||||||
assert settings instanceof KeywordSearchJobSettings;
|
assert settings instanceof KeywordSearchJobSettings;
|
||||||
if (!(settings instanceof KeywordSearchJobSettings)) {
|
if (!(settings instanceof KeywordSearchJobSettings)) {
|
||||||
throw new IllegalArgumentException("Expected settings argument to be instanceof KeywordSearchJobSettings");
|
throw new IllegalArgumentException("Expected settings argument to be instanceof KeywordSearchJobSettings");
|
||||||
|
Loading…
x
Reference in New Issue
Block a user