19 package org.sleuthkit.autopsy.centralrepository.eventlisteners;
21 import com.google.common.util.concurrent.ThreadFactoryBuilder;
22 import java.beans.PropertyChangeEvent;
23 import java.beans.PropertyChangeListener;
24 import java.util.ArrayList;
25 import java.util.Arrays;
26 import java.util.Collection;
27 import java.util.EnumSet;
28 import java.util.List;
29 import java.util.Optional;
31 import java.util.concurrent.ExecutorService;
32 import java.util.concurrent.Executors;
33 import java.util.logging.Level;
34 import java.util.stream.Collectors;
35 import org.apache.commons.lang.StringUtils;
36 import org.openide.util.NbBundle;
37 import org.openide.util.NbBundle.Messages;
71 import static org.
sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE.TSK_OTHER_CASES;
72 import static org.
sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE.TSK_SET_NAME;
73 import static org.
sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE.TSK_CORRELATION_TYPE;
74 import static org.
sleuthkit.datamodel.BlackboardAttribute.ATTRIBUTE_TYPE.TSK_CORRELATION_VALUE;
85 @Messages({
"caseeventlistener.evidencetag=Evidence"})
90 private static final String CASE_EVENT_THREAD_NAME =
"Case-Event-Listener-%d";
92 private static final Set<
Case.
Events> CASE_EVENTS_OF_INTEREST = EnumSet.of(
103 jobProcessingExecutor = Executors.newSingleThreadExecutor(
new ThreadFactoryBuilder().setNameFormat(CASE_EVENT_THREAD_NAME).build());
112 if (!(evt instanceof
AutopsyEvent) || (((AutopsyEvent) evt).getSourceType() != AutopsyEvent.SourceType.LOCAL)) {
120 LOGGER.log(Level.SEVERE,
"Failed to get instance of db manager.", ex);
126 switch (
Case.
Events.valueOf(evt.getPropertyName())) {
127 case CONTENT_TAG_ADDED:
128 case CONTENT_TAG_DELETED: {
133 case BLACKBOARD_ARTIFACT_TAG_DELETED:
134 case BLACKBOARD_ARTIFACT_TAG_ADDED: {
139 case DATA_SOURCE_ADDED: {
143 case TAG_DEFINITION_CHANGED: {
151 case DATA_SOURCE_NAME_CHANGED: {
155 case OS_ACCT_INSTANCES_ADDED: {
156 if (((AutopsyEvent) evt).getSourceType() == AutopsyEvent.SourceType.LOCAL) {
186 return (t != null && isNotableTagName(t.getName()));
226 List<CorrelationAttributeInstance> convertedArtifacts =
new ArrayList<>();
227 if (bbArtifact instanceof DataArtifact) {
229 }
else if (bbArtifact instanceof AnalysisResult) {
236 LOGGER.log(Level.SEVERE,
"Error connecting to Central Repository database while setting artifact known status.", ex);
244 private final PropertyChangeEvent
event;
259 handleTagAdded((ContentTagAddedEvent) event);
261 handleTagDeleted((ContentTagDeletedEvent) event);
263 LOGGER.log(Level.SEVERE,
264 String.format(
"Received an event %s of type %s and was expecting either CONTENT_TAG_ADDED or CONTENT_TAG_DELETED.",
265 event, curEventType));
272 LOGGER.log(Level.SEVERE,
"ContentTagDeletedEvent did not have valid content to provide a content id.");
279 if (content == null) {
280 LOGGER.log(Level.WARNING,
286 handleTagChange(content);
294 if (evt.getAddedTag() == null || evt.getAddedTag().getContent() == null) {
295 LOGGER.log(Level.SEVERE,
"ContentTagAddedEvent did not have valid content to provide a content id.");
300 handleTagChange(evt.getAddedTag().getContent());
311 AbstractFile af = null;
315 Long contentID = (content != null) ? content.getId() : null;
316 LOGGER.log(Level.WARNING,
"Error updating non-file object: " + contentID, ex);
329 setContentKnownStatus(af, TskData.FileKnown.BAD);
332 setContentKnownStatus(af, TskData.FileKnown.UNKNOWN);
335 LOGGER.log(Level.SEVERE,
"Failed to obtain tags manager for case.", ex);
350 if (!md5CorrelationAttr.isEmpty()) {
356 LOGGER.log(Level.SEVERE,
"Error connecting to Central Repository database while setting artifact known status.", ex);
365 private final PropertyChangeEvent
event;
380 handleTagAdded((BlackBoardArtifactTagAddedEvent) event);
382 handleTagDeleted((BlackBoardArtifactTagDeletedEvent) event);
384 LOGGER.log(Level.WARNING,
385 String.format(
"Received an event %s of type %s and was expecting either CONTENT_TAG_ADDED or CONTENT_TAG_DELETED.",
386 event, curEventType));
393 LOGGER.log(Level.SEVERE,
"BlackBoardArtifactTagDeletedEvent did not have valid content to provide a content id.");
402 if (content == null) {
403 LOGGER.log(Level.WARNING,
410 if (bbArtifact == null) {
411 LOGGER.log(Level.WARNING,
417 handleTagChange(content, bbArtifact);
419 LOGGER.log(Level.WARNING,
"Error updating non-file object.", ex);
425 if (evt.getAddedTag() == null || evt.getAddedTag().getContent() == null || evt.getAddedTag().getArtifact() == null) {
426 LOGGER.log(Level.SEVERE,
"BlackBoardArtifactTagAddedEvent did not have valid content to provide a content id.");
431 handleTagChange(evt.getAddedTag().getContent(), evt.getAddedTag().getArtifact());
447 LOGGER.log(Level.SEVERE,
"Exception while getting open case.", ex);
452 if (isKnownFile(content)) {
458 if (hasNotableTag(tags)) {
459 setArtifactKnownStatus(dbManager, bbArtifact, TskData.FileKnown.BAD);
461 setArtifactKnownStatus(dbManager, bbArtifact, TskData.FileKnown.UNKNOWN);
463 }
catch (TskCoreException ex) {
464 LOGGER.log(Level.SEVERE,
"Failed to obtain tags manager for case.", ex);
476 return ((content instanceof AbstractFile) && (((AbstractFile) content).getKnown() == TskData.FileKnown.KNOWN));
483 private final PropertyChangeEvent
event;
495 String modifiedTagName = (String) event.getOldValue();
506 for (BlackboardArtifactTag bbTag : artifactTags) {
508 boolean hasTagWithConflictingKnownStatus =
false;
512 if (tagName.getKnownStatus() == TskData.FileKnown.UNKNOWN) {
513 Content content = bbTag.getContent();
516 if ((content instanceof AbstractFile) && (((AbstractFile) content).getKnown() == TskData.FileKnown.KNOWN)) {
520 BlackboardArtifact bbArtifact = bbTag.getArtifact();
524 for (BlackboardArtifactTag t : tags) {
526 if (t.getName().equals(tagName)) {
530 if (TskData.FileKnown.BAD == t.getName().getKnownStatus()) {
532 hasTagWithConflictingKnownStatus =
true;
538 if (!hasTagWithConflictingKnownStatus) {
546 for (ContentTag contentTag : fileTags) {
548 boolean hasTagWithConflictingKnownStatus =
false;
552 if (tagName.getKnownStatus() == TskData.FileKnown.UNKNOWN) {
553 Content content = contentTag.getContent();
557 for (ContentTag t : tags) {
559 if (t.getName().equals(tagName)) {
563 if (TskData.FileKnown.BAD == t.getName().getKnownStatus()) {
565 hasTagWithConflictingKnownStatus =
true;
571 if (!hasTagWithConflictingKnownStatus) {
572 Content taggedContent = contentTag.getContent();
573 if (taggedContent instanceof AbstractFile) {
575 if (!eamArtifact.isEmpty()) {
582 }
catch (TskCoreException ex) {
583 LOGGER.log(Level.SEVERE,
"Cannot update known status in central repository for tag: " + modifiedTagName, ex);
585 LOGGER.log(Level.SEVERE,
"Cannot get central repository for tag: " + modifiedTagName, ex);
587 LOGGER.log(Level.SEVERE,
"Exception while getting open case.", ex);
595 private final PropertyChangeEvent
event;
611 LOGGER.log(Level.SEVERE,
"Exception while getting open case.", ex);
616 Content newDataSource = dataSourceAddedEvent.
getDataSource();
620 if (null == dbManager.
getDataSource(correlationCase, newDataSource.getId())) {
624 LOGGER.log(Level.SEVERE,
"Error adding new data source to the central repository", ex);
632 private final PropertyChangeEvent
event;
645 if ((null == event.getOldValue()) && (event.getNewValue() instanceof
Case)) {
646 Case curCase = (
Case) event.getNewValue();
656 if (dbManager.
getCase(curCase) == null) {
660 LOGGER.log(Level.SEVERE,
"Error connecting to Central Repository database.", ex);
666 @NbBundle.Messages({
"CaseEventsListener.module.name=Central Repository",
667 "CaseEventsListener.prevCaseComment.text=Users seen in previous cases",
668 "CaseEventsListener.prevExists.text=Previously Seen Users (Central Repository)"})
676 private final PropertyChangeEvent
event;
677 private final String MODULE_NAME = Bundle.CaseEventsListener_module_name();
694 for (OsAccountInstance osAccountInstance : addedOsAccountNew) {
696 OsAccount osAccount = osAccountInstance.getOsAccount();
698 if (correlationAttributeInstances.isEmpty()) {
702 Optional<String> accountAddr = osAccount.getAddr();
714 List<CorrelationAttributeInstance> previousOccurences = dbManager.
getArtifactInstancesByTypeValue(osAcctType, correlationAttributeInstances.get(0).getCorrelationValue());
716 if (!instance.getCorrelationCase().getCaseUUID().equals(correlationAttributeInstances.get(0).getCorrelationCase().getCaseUUID())) {
717 SleuthkitCase tskCase = osAccount.getSleuthkitCase();
718 Blackboard blackboard = tskCase.getBlackboard();
724 int numCases = caseDisplayNames.size();
726 score = Score.SCORE_LIKELY_NOTABLE;
728 score = Score.SCORE_NONE;
734 String prevCases = caseDisplayNames.stream().distinct().collect(Collectors.joining(
","));
735 String justification =
"Previously seen in cases " + prevCases;
736 Collection<BlackboardAttribute> attributesForNewArtifact = Arrays.asList(
737 new BlackboardAttribute(
738 TSK_SET_NAME, MODULE_NAME,
739 Bundle.CaseEventsListener_prevExists_text()),
740 new BlackboardAttribute(
741 TSK_CORRELATION_TYPE, MODULE_NAME,
742 osAcctType.getDisplayName()),
743 new BlackboardAttribute(
744 TSK_CORRELATION_VALUE, MODULE_NAME,
745 correlationAttributeInstances.get(0).getCorrelationValue()),
746 new BlackboardAttribute(
747 TSK_OTHER_CASES, MODULE_NAME,
749 BlackboardArtifact newAnalysisResult = osAccount.newAnalysisResult(
750 BlackboardArtifact.Type.TSK_PREVIOUSLY_SEEN, score,
751 null, Bundle.CaseEventsListener_prevExists_text(), justification, attributesForNewArtifact, osAccountInstance.getDataSource().getId()).getAnalysisResult();
754 blackboard.postArtifact(newAnalysisResult, MODULE_NAME);
756 }
catch (Blackboard.BlackboardException ex) {
757 LOGGER.log(Level.SEVERE,
"Unable to index blackboard artifact " + newAnalysisResult.getArtifactID(), ex);
764 LOGGER.log(Level.SEVERE,
"Exception with Correlation Attribute Normalization.", ex);
766 LOGGER.log(Level.SEVERE, String.format(
"Cannot get central repository for OsAccount: %s.", accountAddr.get()), ex);
768 }
catch (TskCoreException ex) {
769 LOGGER.log(Level.SEVERE,
"Cannot get central repository for OsAccount: " +
"OsAccount", ex);
778 private final PropertyChangeEvent
event;
789 Content dataSource = dataSourceNameChangedEvent.
getDataSource();
790 String newName = (String) event.getNewValue();
792 if (!StringUtils.isEmpty(newName)) {
803 LOGGER.log(Level.SEVERE,
"Error updating data source with ID " + dataSource.getId() +
" to " + newName, ex);
805 LOGGER.log(Level.SEVERE,
"No open case", ex);
final PropertyChangeEvent event
final CentralRepository dbManager
ContentTagTask(CentralRepository db, PropertyChangeEvent evt)
static synchronized IngestManager getInstance()
List< String > getListCasesHavingArtifactInstances(CorrelationAttributeInstance.Type aType, String value)
static boolean isNotableTag(Tag t)
DataSourceAddedTask(CentralRepository db, PropertyChangeEvent evt)
static synchronized boolean isFlagSeenDevices()
OsAccountInstancesAddedTask(CentralRepository db, PropertyChangeEvent evt)
final PropertyChangeEvent event
void handleTagAdded(BlackBoardArtifactTagAddedEvent evt)
final CentralRepository dbManager
final PropertyChangeEvent event
List< CorrelationAttributeInstance > getArtifactInstancesByTypeValue(CorrelationAttributeInstance.Type aType, String value)
DeletedBlackboardArtifactTagInfo getDeletedTagInfo()
static CorrelationDataSource fromTSKDataSource(CorrelationCase correlationCase, Content dataSource)
boolean isIngestRunning()
CorrelationCase getCase(Case autopsyCase)
void setAttributeInstanceKnownStatus(CorrelationAttributeInstance eamArtifact, TskData.FileKnown knownStatus)
void handleTagDeleted(BlackBoardArtifactTagDeletedEvent evt)
final ExecutorService jobProcessingExecutor
CurrentCaseTask(CentralRepository db, PropertyChangeEvent evt)
void addArtifactInstance(CorrelationAttributeInstance eamArtifact)
void uninstallListeners()
TagDefinitionChangeTask(PropertyChangeEvent evt)
static void shutDownTaskExecutor(ExecutorService executor)
final CentralRepository dbManager
boolean isKnownFile(Content content)
TagsManager getTagsManager()
static List< CorrelationAttributeInstance > makeCorrAttrsForSearch(AnalysisResult analysisResult)
void handleTagChange(Content content, BlackboardArtifact bbArtifact)
final CentralRepository dbManager
CorrelationCase newCase(CorrelationCase eamCase)
final CentralRepository dbManager
SleuthkitCase getSleuthkitCase()
void handleTagChange(Content content)
DataSourceNameChangedTask(CentralRepository db, PropertyChangeEvent evt)
void updateDataSourceName(CorrelationDataSource eamDataSource, String newName)
static boolean isNotableTagName(TagName t)
BLACKBOARD_ARTIFACT_TAG_ADDED
BlackboardTagTask(CentralRepository db, PropertyChangeEvent evt)
void handleTagDeleted(ContentTagDeletedEvent evt)
void propertyChange(PropertyChangeEvent evt)
CorrelationDataSource getDataSource(CorrelationCase correlationCase, Long caseDbDataSourceId)
synchronized static Logger getLogger(String name)
void setContentKnownStatus(AbstractFile af, TskData.FileKnown knownStatus)
static final int OSACCOUNT_TYPE_ID
CorrelationAttributeInstance.Type getCorrelationTypeById(int typeId)
static Case getCurrentCaseThrows()
static void addEventTypeSubscriber(Set< Events > eventTypes, PropertyChangeListener subscriber)
static synchronized boolean shouldCreateCrProperties()
List< OsAccountInstance > getOsAccountInstances()
static void setArtifactKnownStatus(CentralRepository dbManager, BlackboardArtifact bbArtifact, TskData.FileKnown knownStatus)
final PropertyChangeEvent event
final PropertyChangeEvent event
DeletedContentTagInfo getDeletedTagInfo()
void handleTagAdded(ContentTagAddedEvent evt)
final PropertyChangeEvent event
final CentralRepository dbManager
static void removeEventTypeSubscriber(Set< Events > eventTypes, PropertyChangeListener subscriber)
static boolean hasNotableTag(List<?extends Tag > tags)
static CentralRepository getInstance()
final PropertyChangeEvent event
BLACKBOARD_ARTIFACT_TAG_DELETED
static boolean isEnabled()