19 package org.sleuthkit.autopsy.recentactivity;
21 import java.util.ArrayList;
22 import java.util.Collection;
23 import java.util.List;
24 import java.util.logging.Level;
25 import org.apache.commons.io.FilenameUtils;
26 import org.openide.util.NbBundle.Messages;
45 @Messages({
"DataSourceUsageAnalyzer.parentModuleName=Recent Activity"})
46 class DataSourceUsageAnalyzer extends Extract {
48 private static final Logger logger = Logger.getLogger(DataSourceUsageAnalyzer.class.getName());
49 private static final int FAT_EXFAT_FLAGS = TskData.TSK_FS_TYPE_ENUM.TSK_FS_TYPE_FAT16.getValue()
50 | TskData.TSK_FS_TYPE_ENUM.TSK_FS_TYPE_FAT32.getValue()
51 | TskData.TSK_FS_TYPE_ENUM.TSK_FS_TYPE_EXFAT.getValue();
52 private static final long HUNDRED_GB = 100 * 1024 * 1024 * 1024l;
54 private static final String ANDROID_MEDIACARD_ROOT_FILENAMES[]
56 {
".android_secure",
"android",
"audio",
57 "photos",
"dcim",
"music",
"pictures",
"videos"};
58 private Content dataSource;
62 "DataSourceUsageAnalyzer.customVolume.label=OS Drive ({0})",
63 "Progress_Message_Analyze_Usage=Data Sources Usage Analysis",})
65 void process(Content dataSource, IngestJobContext context, DataSourceIngestModuleProgress progressBar) {
66 this.dataSource = dataSource;
68 progressBar.progress(Bundle.Progress_Message_Analyze_Usage());
69 createDataSourceUsageArtifacts();
70 }
catch (TskCoreException ex) {
71 logger.log(Level.WARNING,
"Failed to check if datasource contained a volume with operating system specific files", ex);
76 private void createDataSourceUsageArtifacts() throws TskCoreException {
78 createOSInfoDataSourceUsageArtifacts();
79 createAndroidMediaCardArtifacts();
80 createDJIDroneDATArtitifacts();
89 private void createOSInfoDataSourceUsageArtifacts() throws TskCoreException {
90 boolean windowsOsDetected =
false;
91 List<BlackboardArtifact> osInfoArtifacts = tskCase.getBlackboardArtifacts(BlackboardArtifact.ARTIFACT_TYPE.TSK_OS_INFO);
92 for (BlackboardArtifact osInfoArt : osInfoArtifacts) {
94 if (osInfoArt.getDataSource().getId() == dataSource.getId()) {
95 BlackboardAttribute progNameAttr = osInfoArt.getAttribute(
new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_PROG_NAME));
96 if (progNameAttr != null) {
97 if (progNameAttr.getValueString().isEmpty()) {
99 }
else if (progNameAttr.getDisplayString().toLowerCase().contains(
"windows")) {
100 windowsOsDetected =
true;
102 createDataSourceUsageArtifact(Bundle.DataSourceUsageAnalyzer_customVolume_label(progNameAttr.getDisplayString()));
104 ExtractOs.OS_TYPE osType = ExtractOs.OS_TYPE.fromOsInfoLabel(progNameAttr.getValueString());
105 if (osType != null) {
106 createDataSourceUsageArtifact(osType.getDsUsageLabel());
109 createDataSourceUsageArtifact(Bundle.DataSourceUsageAnalyzer_customVolume_label(progNameAttr.getDisplayString()));
115 if (!windowsOsDetected) {
116 checkIfOsSpecificVolume(ExtractOs.OS_TYPE.WINDOWS);
129 private void createDataSourceUsageArtifact(String dataSourceUsageDescription)
throws TskCoreException {
131 List<BlackboardArtifact> artifacts = tskCase.getBlackboardArtifacts(BlackboardArtifact.ARTIFACT_TYPE.TSK_DATA_SOURCE_USAGE, dataSource.getId());
132 for (BlackboardArtifact artifact : artifacts) {
133 if (artifact.getAttribute(
new BlackboardAttribute.Type(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_DESCRIPTION)).getValueString().equals(dataSourceUsageDescription)) {
137 Collection<BlackboardAttribute> bbattributes =
new ArrayList<>();
138 bbattributes.add(
new BlackboardAttribute(BlackboardAttribute.ATTRIBUTE_TYPE.TSK_DESCRIPTION,
139 Bundle.DataSourceUsageAnalyzer_parentModuleName(),
140 dataSourceUsageDescription));
141 BlackboardArtifact bba = createArtifactWithAttributes(BlackboardArtifact.ARTIFACT_TYPE.TSK_DATA_SOURCE_USAGE, dataSource, bbattributes);
156 private void checkIfOsSpecificVolume(ExtractOs.OS_TYPE osType) throws TskCoreException {
157 FileManager fileManager = currentCase.getServices().getFileManager();
158 for (String filePath : osType.getFilePaths()) {
159 for (AbstractFile file : fileManager.findFiles(dataSource, FilenameUtils.getName(filePath), FilenameUtils.getPath(filePath))) {
160 if ((file.getParentPath() + file.getName()).equals(filePath)) {
161 createDataSourceUsageArtifact(osType.getDsUsageLabel());
177 "DataSourceUsage_AndroidMedia=Android Media Card",
178 "DataSourceUsage_FlashDrive=Flash Drive"
180 private void createAndroidMediaCardArtifacts() {
182 if (dataSource instanceof Image) {
183 Image image = (Image) dataSource;
185 if (image.getSize() > HUNDRED_GB) {
189 List<FileSystem> fileSystems = image.getFileSystems();
190 if (fileSystems.isEmpty() || fileSystems.size() > 1) {
194 FileSystem fileSystem = fileSystems.get(0);
195 if (fileSystem == null || (fileSystem.getFsType().getValue() & FAT_EXFAT_FLAGS) == 0) {
199 if(hasAndroidMediaCardRootNames()) {
204 createDataSourceUsageArtifact(Bundle.DataSourceUsage_FlashDrive());
206 }
catch (TskCoreException ex) {
207 logger.log(Level.SEVERE,
"Exception while checking image: {0} for Andriod media card", image.getName() + ex.getMessage());
219 private boolean hasAndroidMediaCardRootNames() throws TskCoreException{
220 FileManager fileManager = currentCase.getServices().getFileManager();
221 for (String fileName : ANDROID_MEDIACARD_ROOT_FILENAMES) {
222 for (AbstractFile file : fileManager.findFiles(dataSource, fileName,
"/")) {
223 if (file.getParentPath().equals(
"/") && file.getName().equalsIgnoreCase(fileName)) {
224 createDataSourceUsageArtifact(Bundle.DataSourceUsage_AndroidMedia());
242 "DataSourceUsage_DJU_Drone_DAT=DJI Internal SD Card"
244 private void createDJIDroneDATArtitifacts() throws TskCoreException {
245 FileManager fileManager = currentCase.getServices().getFileManager();
247 List<AbstractFile> files = fileManager.findFiles(dataSource,
"FLY___.DAT");
248 if (files != null && !files.isEmpty()) {
249 createDataSourceUsageArtifact(Bundle.DataSourceUsage_DJU_Drone_DAT());