mirror of
https://github.com/overcuriousity/autopsy-flatpak.git
synced 2025-07-12 16:06:15 +00:00
more error checking in timeline
This commit is contained in:
parent
db89cc5d43
commit
62b8c384ea
@ -78,7 +78,6 @@ import org.openide.modules.InstalledFileLocator;
|
|||||||
import org.openide.nodes.ChildFactory;
|
import org.openide.nodes.ChildFactory;
|
||||||
import org.openide.nodes.Children;
|
import org.openide.nodes.Children;
|
||||||
import org.openide.nodes.Node;
|
import org.openide.nodes.Node;
|
||||||
import org.openide.util.Exceptions;
|
|
||||||
import org.openide.util.HelpCtx;
|
import org.openide.util.HelpCtx;
|
||||||
import org.openide.util.NbBundle;
|
import org.openide.util.NbBundle;
|
||||||
import org.openide.util.actions.CallableSystemAction;
|
import org.openide.util.actions.CallableSystemAction;
|
||||||
@ -109,8 +108,8 @@ import org.sleuthkit.datamodel.TskData;
|
|||||||
@ActionReferences(value = {
|
@ActionReferences(value = {
|
||||||
@ActionReference(path = "Menu/Tools", position = 100)})
|
@ActionReference(path = "Menu/Tools", position = 100)})
|
||||||
@NbBundle.Messages(value = "CTL_TimelineView=Generate Timeline")
|
@NbBundle.Messages(value = "CTL_TimelineView=Generate Timeline")
|
||||||
|
|
||||||
public class Simile2 extends CallableSystemAction implements Presenter.Toolbar, PropertyChangeListener {
|
public class Simile2 extends CallableSystemAction implements Presenter.Toolbar, PropertyChangeListener {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(Simile2.class.getName());
|
private static final Logger logger = Logger.getLogger(Simile2.class.getName());
|
||||||
private final java.io.File macRoot = InstalledFileLocator.getDefault().locate("mactime", Simile2.class.getPackage().getName(), false);
|
private final java.io.File macRoot = InstalledFileLocator.getDefault().locate("mactime", Simile2.class.getPackage().getName(), false);
|
||||||
private JFrame jf; //frame for holding all the elements
|
private JFrame jf; //frame for holding all the elements
|
||||||
@ -123,7 +122,7 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
private ScrollPane scroll_Events; //Scroll Panes for dealing with oversized an oversized chart
|
private ScrollPane scroll_Events; //Scroll Panes for dealing with oversized an oversized chart
|
||||||
private final int Height_Frame = 850; //Sizing constants
|
private final int Height_Frame = 850; //Sizing constants
|
||||||
private final int Width_Frame = 1300;
|
private final int Width_Frame = 1300;
|
||||||
private Button button_DrillUp; //Navigation buttons
|
private Button button_DrillUp; //Navigation buttons
|
||||||
private Button button_Go;
|
private Button button_Go;
|
||||||
private ComboBox<String> dropdown_SelectYears; //Dropdown box for selecting years. Useful when the charts' scale means some years are unclickable, despite having events.
|
private ComboBox<String> dropdown_SelectYears; //Dropdown box for selecting years. Useful when the charts' scale means some years are unclickable, despite having events.
|
||||||
private final Stack<BarChart> stack_PrevCharts = new Stack<BarChart>(); //Stack for storing drill-up information.
|
private final Stack<BarChart> stack_PrevCharts = new Stack<BarChart>(); //Stack for storing drill-up information.
|
||||||
@ -154,11 +153,11 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
private void customize() {
|
private void customize() {
|
||||||
//Making the main frame *
|
//Making the main frame *
|
||||||
jf = new JFrame(Case.getCurrentCase().getName() + " - Autopsy Timeline (Beta)");
|
jf = new JFrame(Case.getCurrentCase().getName() + " - Autopsy Timeline (Beta)");
|
||||||
|
|
||||||
//use the same icon on jframe as main application
|
//use the same icon on jframe as main application
|
||||||
jf.setIconImage(WindowManager.getDefault().getMainWindow().getIconImage());
|
jf.setIconImage(WindowManager.getDefault().getMainWindow().getIconImage());
|
||||||
jf.setSize(Width_Frame, Height_Frame); //(Width, Height)
|
jf.setSize(Width_Frame, Height_Frame); //(Width, Height)
|
||||||
@ -176,7 +175,7 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
|
|
||||||
//ComboJPanel holds both of the above JPanels together,
|
//ComboJPanel holds both of the above JPanels together,
|
||||||
//aligned vertically (Y_AXIS)
|
//aligned vertically (Y_AXIS)
|
||||||
|
|
||||||
// create a horizontal split pane
|
// create a horizontal split pane
|
||||||
final JSplitPane splitPane = new JSplitPane(JSplitPane.VERTICAL_SPLIT, chartJPanel, viewerJPanel);
|
final JSplitPane splitPane = new JSplitPane(JSplitPane.VERTICAL_SPLIT, chartJPanel, viewerJPanel);
|
||||||
splitPane.setDividerLocation(450);
|
splitPane.setDividerLocation(450);
|
||||||
@ -210,7 +209,7 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
if (!moduleDir.exists()) {
|
if (!moduleDir.exists()) {
|
||||||
moduleDir.mkdir();
|
moduleDir.mkdir();
|
||||||
}
|
}
|
||||||
|
|
||||||
java.io.File mactimeFile = new java.io.File(moduleDir, mactimeFileName);
|
java.io.File mactimeFile = new java.io.File(moduleDir, mactimeFileName);
|
||||||
if (!mactimeFile.exists()) {
|
if (!mactimeFile.exists()) {
|
||||||
logger.log(Level.INFO, "Creating mactime file.");
|
logger.log(Level.INFO, "Creating mactime file.");
|
||||||
@ -233,8 +232,8 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
ObservableList<String> listSelect = FXCollections.observableArrayList(lsi);
|
ObservableList<String> listSelect = FXCollections.observableArrayList(lsi);
|
||||||
dropdown_SelectYears = new ComboBox(listSelect);
|
dropdown_SelectYears = new ComboBox(listSelect);
|
||||||
|
|
||||||
//Buttons for navigating up and down the timeline
|
//Buttons for navigating up and down the timeline
|
||||||
button_DrillUp = new Button("Zoom Out");
|
button_DrillUp = new Button("Zoom Out");
|
||||||
button_DrillUp.setOnAction(new EventHandler<ActionEvent>() {
|
button_DrillUp.setOnAction(new EventHandler<ActionEvent>() {
|
||||||
@Override
|
@Override
|
||||||
public void handle(ActionEvent e) {
|
public void handle(ActionEvent e) {
|
||||||
@ -248,7 +247,7 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
scroll_Events.setContent(chart_Events);
|
scroll_Events.setContent(chart_Events);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
button_Go = new Button("►");
|
button_Go = new Button("►");
|
||||||
button_Go.setOnAction(new EventHandler<ActionEvent>() {
|
button_Go.setOnAction(new EventHandler<ActionEvent>() {
|
||||||
@Override
|
@Override
|
||||||
@ -260,9 +259,9 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
//Adding things to the V and H boxes.
|
//Adding things to the V and H boxes.
|
||||||
//hBox_Charts stores the pseudo menu bar at the top of the timeline. |Zoom Out|View Year: [Select Year]|►|
|
//hBox_Charts stores the pseudo menu bar at the top of the timeline. |Zoom Out|View Year: [Select Year]|►|
|
||||||
hBox_Charts.getChildren().addAll(button_DrillUp, new Label("View Year:"), dropdown_SelectYears, button_Go);
|
hBox_Charts.getChildren().addAll(button_DrillUp, new Label("View Year:"), dropdown_SelectYears, button_Go);
|
||||||
vBox_FX.getChildren().addAll(hBox_Charts, scroll_Events); //FxBox_V holds things in a visual stack.
|
vBox_FX.getChildren().addAll(hBox_Charts, scroll_Events); //FxBox_V holds things in a visual stack.
|
||||||
group_Charts.getChildren().add(vBox_FX); //Adding the FxBox to the group. Groups make things easier to manipulate without having to update a hundred things every change.
|
group_Charts.getChildren().add(vBox_FX); //Adding the FxBox to the group. Groups make things easier to manipulate without having to update a hundred things every change.
|
||||||
panel_Charts.setScene(scene_Charts);
|
panel_Charts.setScene(scene_Charts);
|
||||||
@ -286,7 +285,7 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
} finally {
|
} finally {
|
||||||
// stop the progress bar
|
// stop the progress bar
|
||||||
progress.finish();
|
progress.finish();
|
||||||
|
|
||||||
// close the dialog
|
// close the dialog
|
||||||
dialog.doClose(0);
|
dialog.doClose(0);
|
||||||
}
|
}
|
||||||
@ -330,27 +329,27 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
data.getNode().setScaleX(.5);
|
data.getNode().setScaleX(.5);
|
||||||
data.getNode().addEventHandler(MouseEvent.MOUSE_CLICKED,
|
data.getNode().addEventHandler(MouseEvent.MOUSE_CLICKED,
|
||||||
new EventHandler<MouseEvent>() {
|
new EventHandler<MouseEvent>() {
|
||||||
@Override
|
@Override
|
||||||
public void handle(MouseEvent e) {
|
public void handle(MouseEvent e) {
|
||||||
if (e.getButton().equals(MouseButton.PRIMARY)) {
|
if (e.getButton().equals(MouseButton.PRIMARY)) {
|
||||||
if (e.getClickCount() == 2) { //Checking for a doubleclick
|
if (e.getClickCount() == 2) { //Checking for a doubleclick
|
||||||
PlatformImpl.startup(new Runnable() {
|
PlatformImpl.startup(new Runnable() {
|
||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
BarChart b = createMonthsWithDrill((YearEpoch) findYear(allYears, Integer.valueOf((String) data.getXValue())));
|
BarChart b = createMonthsWithDrill((YearEpoch) findYear(allYears, Integer.valueOf((String) data.getXValue())));
|
||||||
chart_Events = b;
|
chart_Events = b;
|
||||||
scroll_Events.setContent(chart_Events);
|
scroll_Events.setContent(chart_Events);
|
||||||
}
|
|
||||||
});
|
|
||||||
//If a single click, hover a label over the cursor with information about the selection
|
|
||||||
} else if (e.getClickCount() == 1) {
|
|
||||||
l.setText(findYear(allYears, Integer.valueOf((String) data.getXValue())).getNumFiles() + " events");
|
|
||||||
l.setTranslateX(e.getX());
|
|
||||||
l.setTranslateY(e.getY());
|
|
||||||
}
|
}
|
||||||
}
|
});
|
||||||
|
//If a single click, hover a label over the cursor with information about the selection
|
||||||
|
} else if (e.getClickCount() == 1) {
|
||||||
|
l.setText(findYear(allYears, Integer.valueOf((String) data.getXValue())).getNumFiles() + " events");
|
||||||
|
l.setTranslateX(e.getX());
|
||||||
|
l.setTranslateY(e.getY());
|
||||||
}
|
}
|
||||||
});
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
bc.autosize(); //Get an auto height
|
bc.autosize(); //Get an auto height
|
||||||
@ -389,24 +388,24 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
// Sometimes I've had it jacked up to as much as x2400 just to see a sliver of information.
|
// Sometimes I've had it jacked up to as much as x2400 just to see a sliver of information.
|
||||||
// But that doesn't work all the time. Adding it to a scrollpane and letting the user scroll up and down to view the chart is the other workaround. Both of these fixes suck.
|
// But that doesn't work all the time. Adding it to a scrollpane and letting the user scroll up and down to view the chart is the other workaround. Both of these fixes suck.
|
||||||
|
|
||||||
data.getNode().setScaleX(.5);
|
data.getNode().setScaleX(.5);
|
||||||
data.getNode().addEventHandler(MouseEvent.MOUSE_PRESSED,
|
data.getNode().addEventHandler(MouseEvent.MOUSE_PRESSED,
|
||||||
new EventHandler<MouseEvent>() {
|
new EventHandler<MouseEvent>() {
|
||||||
@Override
|
@Override
|
||||||
public void handle(MouseEvent e) {
|
public void handle(MouseEvent e) {
|
||||||
if (e.getButton().equals(MouseButton.PRIMARY)) {
|
if (e.getButton().equals(MouseButton.PRIMARY)) {
|
||||||
if (e.getClickCount() == 2) {
|
if (e.getClickCount() == 2) {
|
||||||
PlatformImpl.startup(new Runnable() {
|
PlatformImpl.startup(new Runnable() {
|
||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
chart_Events = createEventsByMonth(findMonth(ye.months, monthStringToInt((String) data.getXValue())), ye);
|
chart_Events = createEventsByMonth(findMonth(ye.months, monthStringToInt((String) data.getXValue())), ye);
|
||||||
scroll_Events.setContent(chart_Events);
|
scroll_Events.setContent(chart_Events);
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
}
|
});
|
||||||
}
|
}
|
||||||
});
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -430,7 +429,7 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
ObservableList<BarChart.Data> bcData = makeObservableListByMonthAllDays(me, ye.getYear());
|
ObservableList<BarChart.Data> bcData = makeObservableListByMonthAllDays(me, ye.getYear());
|
||||||
BarChart.Series<String, Number> series = new BarChart.Series(bcData);
|
BarChart.Series<String, Number> series = new BarChart.Series(bcData);
|
||||||
series.setName(me.getMonthName() + " " + ye.getYear());
|
series.setName(me.getMonthName() + " " + ye.getYear());
|
||||||
|
|
||||||
|
|
||||||
ObservableList<BarChart.Series<String, Number>> ol = FXCollections.observableArrayList(series);
|
ObservableList<BarChart.Series<String, Number>> ol = FXCollections.observableArrayList(series);
|
||||||
|
|
||||||
@ -439,31 +438,31 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
//data.getNode().setScaleX(2);
|
//data.getNode().setScaleX(2);
|
||||||
data.getNode().addEventHandler(MouseEvent.MOUSE_PRESSED,
|
data.getNode().addEventHandler(MouseEvent.MOUSE_PRESSED,
|
||||||
new EventHandler<MouseEvent>() {
|
new EventHandler<MouseEvent>() {
|
||||||
MonthEpoch myme = me;
|
MonthEpoch myme = me;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void handle(MouseEvent e) {
|
||||||
|
int day = (Integer.valueOf(((String) data.getXValue()).split("-")[1]));
|
||||||
|
DayEpoch de = myme.getDay(day);
|
||||||
|
List<AbstractFile> afs = Collections.EMPTY_LIST;
|
||||||
|
if (de != null) {
|
||||||
|
afs = de.getEvents();
|
||||||
|
} else {
|
||||||
|
logger.log(Level.SEVERE, "There were no events for the clicked-on day.");
|
||||||
|
}
|
||||||
|
final FsContentRootNode d = new FsContentRootNode("Test Root", afs);
|
||||||
|
SwingUtilities.invokeLater(new Runnable() {
|
||||||
@Override
|
@Override
|
||||||
public void handle(MouseEvent e) {
|
public void run() {
|
||||||
int day = (Integer.valueOf(((String) data.getXValue()).split("-")[1]));
|
dataResult.setNode(d);
|
||||||
DayEpoch de = myme.getDay(day);
|
|
||||||
List<AbstractFile> afs = Collections.EMPTY_LIST;
|
|
||||||
if (de != null) {
|
|
||||||
afs = de.getEvents();
|
|
||||||
} else {
|
|
||||||
logger.log(Level.SEVERE, "There were no events for the clicked-on day.");
|
|
||||||
}
|
|
||||||
final FsContentRootNode d = new FsContentRootNode("Test Root", afs);
|
|
||||||
SwingUtilities.invokeLater(new Runnable() {
|
|
||||||
@Override
|
|
||||||
public void run() {
|
|
||||||
dataResult.setNode(d);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
//set result viewer title path with the current date
|
|
||||||
String dateString = ye.getYear() + "-" + (1+me.getMonthInt()) + "-" + + de.dayNum;
|
|
||||||
dataResult.setPath(dateString);
|
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
//set result viewer title path with the current date
|
||||||
|
String dateString = ye.getYear() + "-" + (1 + me.getMonthInt()) + "-" + +de.dayNum;
|
||||||
|
dataResult.setPath(dateString);
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
bc.autosize();
|
bc.autosize();
|
||||||
bc.setPrefWidth(Width_Frame);
|
bc.setPrefWidth(Width_Frame);
|
||||||
@ -487,8 +486,9 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
* Section for Utility functions
|
* Section for Utility functions
|
||||||
*/
|
*/
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* @param mon The month to convert. Must be minimum 4 characters long "February" and "Febr" are acceptable.
|
* @param mon The month to convert. Must be minimum 4 characters long
|
||||||
|
* "February" and "Febr" are acceptable.
|
||||||
* @return The integer value of the month. February = 1, July = 6
|
* @return The integer value of the month. February = 1, July = 6
|
||||||
*/
|
*/
|
||||||
private static int monthStringToInt(String mon) {
|
private static int monthStringToInt(String mon) {
|
||||||
@ -505,8 +505,10 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Used for finding the proper month in a list of available months
|
* Used for finding the proper month in a list of available months
|
||||||
* @param lst The list of months to search through. It is assumed that the desired match is in this list.
|
*
|
||||||
* @param match The month, in integer format, to retrieve.
|
* @param lst The list of months to search through. It is assumed that the
|
||||||
|
* desired match is in this list.
|
||||||
|
* @param match The month, in integer format, to retrieve.
|
||||||
* @return The month epoch as specified by match.
|
* @return The month epoch as specified by match.
|
||||||
*/
|
*/
|
||||||
private static MonthEpoch findMonth(List<MonthEpoch> lst, int match) {
|
private static MonthEpoch findMonth(List<MonthEpoch> lst, int match) {
|
||||||
@ -518,10 +520,12 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Used for finding the proper year in a list of available years
|
* Used for finding the proper year in a list of available years
|
||||||
* @param lst The list of years to search through. It is assumed that the desired match is in this list.
|
*
|
||||||
* @param match The year to retrieve.
|
* @param lst The list of years to search through. It is assumed that the
|
||||||
|
* desired match is in this list.
|
||||||
|
* @param match The year to retrieve.
|
||||||
* @return The year epoch as specified by match.
|
* @return The year epoch as specified by match.
|
||||||
*/
|
*/
|
||||||
private static YearEpoch findYear(List<YearEpoch> lst, int match) {
|
private static YearEpoch findYear(List<YearEpoch> lst, int match) {
|
||||||
@ -557,11 +561,11 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
jf.dispose();
|
jf.dispose();
|
||||||
jf = null;
|
jf = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
data = null;
|
data = null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void clearMactimeData() {
|
private void clearMactimeData() {
|
||||||
// get rid of the old data
|
// get rid of the old data
|
||||||
data = null;
|
data = null;
|
||||||
@ -575,11 +579,9 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
jf.dispose();
|
jf.dispose();
|
||||||
|
|
||||||
// remove ourself as change listener on Case
|
// remove ourself as change listener on Case
|
||||||
Case currcase = Case.getCurrentCase();
|
Case.removePropertyChangeListener(this);
|
||||||
if (currcase != null) {
|
listeningToAddImage = false;
|
||||||
currcase.removePropertyChangeListener(this);
|
|
||||||
listeningToAddImage = false;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -587,6 +589,7 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
* All of those are Epochs.
|
* All of those are Epochs.
|
||||||
*/
|
*/
|
||||||
abstract class Epoch {
|
abstract class Epoch {
|
||||||
|
|
||||||
abstract public int getNumFiles();
|
abstract public int getNumFiles();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -594,15 +597,15 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
|
|
||||||
private int year;
|
private int year;
|
||||||
private List<MonthEpoch> months = new ArrayList<>();
|
private List<MonthEpoch> months = new ArrayList<>();
|
||||||
|
|
||||||
YearEpoch(int year) {
|
YearEpoch(int year) {
|
||||||
this.year = year;
|
this.year = year;
|
||||||
}
|
}
|
||||||
|
|
||||||
public int getYear() {
|
public int getYear() {
|
||||||
return year;
|
return year;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getNumFiles() {
|
public int getNumFiles() {
|
||||||
int size = 0;
|
int size = 0;
|
||||||
@ -611,10 +614,10 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
}
|
}
|
||||||
return size;
|
return size;
|
||||||
}
|
}
|
||||||
|
|
||||||
public MonthEpoch getMonth(int monthNum) {
|
public MonthEpoch getMonth(int monthNum) {
|
||||||
MonthEpoch month = null;
|
MonthEpoch month = null;
|
||||||
for (MonthEpoch me :months) {
|
for (MonthEpoch me : months) {
|
||||||
if (me.getMonthInt() == monthNum) {
|
if (me.getMonthInt() == monthNum) {
|
||||||
month = me;
|
month = me;
|
||||||
break;
|
break;
|
||||||
@ -622,7 +625,7 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
}
|
}
|
||||||
return month;
|
return month;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void add(AbstractFile af, int month, int day) {
|
public void add(AbstractFile af, int month, int day) {
|
||||||
// see if this month is in the list
|
// see if this month is in the list
|
||||||
MonthEpoch monthEpoch = null;
|
MonthEpoch monthEpoch = null;
|
||||||
@ -632,12 +635,12 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (monthEpoch == null) {
|
if (monthEpoch == null) {
|
||||||
monthEpoch = new MonthEpoch(month);
|
monthEpoch = new MonthEpoch(month);
|
||||||
months.add(monthEpoch);
|
months.add(monthEpoch);
|
||||||
}
|
}
|
||||||
|
|
||||||
// add the file the the MonthEpoch object
|
// add the file the the MonthEpoch object
|
||||||
monthEpoch.add(af, day);
|
monthEpoch.add(af, day);
|
||||||
}
|
}
|
||||||
@ -651,17 +654,17 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
MonthEpoch(int month) {
|
MonthEpoch(int month) {
|
||||||
this.month = month;
|
this.month = month;
|
||||||
}
|
}
|
||||||
|
|
||||||
public int getMonthInt() {
|
public int getMonthInt() {
|
||||||
return month;
|
return month;
|
||||||
}
|
}
|
||||||
|
|
||||||
public int getTotalNumDays(int year) {
|
public int getTotalNumDays(int year) {
|
||||||
Calendar cal = Calendar.getInstance();
|
Calendar cal = Calendar.getInstance();
|
||||||
cal.set(year, month, 1);
|
cal.set(year, month, 1);
|
||||||
return cal.getActualMaximum(Calendar.DAY_OF_MONTH);
|
return cal.getActualMaximum(Calendar.DAY_OF_MONTH);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getNumFiles() {
|
public int getNumFiles() {
|
||||||
int numFiles = 0;
|
int numFiles = 0;
|
||||||
@ -670,7 +673,7 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
}
|
}
|
||||||
return numFiles;
|
return numFiles;
|
||||||
}
|
}
|
||||||
|
|
||||||
public DayEpoch getDay(int dayNum) {
|
public DayEpoch getDay(int dayNum) {
|
||||||
DayEpoch de = null;
|
DayEpoch de = null;
|
||||||
for (DayEpoch d : days) {
|
for (DayEpoch d : days) {
|
||||||
@ -681,7 +684,7 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
}
|
}
|
||||||
return de;
|
return de;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void add(AbstractFile af, int day) {
|
public void add(AbstractFile af, int day) {
|
||||||
DayEpoch dayEpoch = null;
|
DayEpoch dayEpoch = null;
|
||||||
for (DayEpoch de : days) {
|
for (DayEpoch de : days) {
|
||||||
@ -690,12 +693,12 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (dayEpoch == null) {
|
if (dayEpoch == null) {
|
||||||
dayEpoch = new DayEpoch(day);
|
dayEpoch = new DayEpoch(day);
|
||||||
days.add(dayEpoch);
|
days.add(dayEpoch);
|
||||||
}
|
}
|
||||||
|
|
||||||
dayEpoch.add(af);
|
dayEpoch.add(af);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -718,20 +721,20 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
|
|
||||||
private List<AbstractFile> files = new ArrayList<>();
|
private List<AbstractFile> files = new ArrayList<>();
|
||||||
int dayNum = 0; //Day of the month this Epoch represents, 1 indexed: 28=28.
|
int dayNum = 0; //Day of the month this Epoch represents, 1 indexed: 28=28.
|
||||||
|
|
||||||
DayEpoch(int dayOfMonth) {
|
DayEpoch(int dayOfMonth) {
|
||||||
this.dayNum = dayOfMonth;
|
this.dayNum = dayOfMonth;
|
||||||
}
|
}
|
||||||
|
|
||||||
public int getDayInt() {
|
public int getDayInt() {
|
||||||
return dayNum;
|
return dayNum;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getNumFiles() {
|
public int getNumFiles() {
|
||||||
return files.size();
|
return files.size();
|
||||||
}
|
}
|
||||||
|
|
||||||
public void add(AbstractFile af) {
|
public void add(AbstractFile af) {
|
||||||
files.add(af);
|
files.add(af);
|
||||||
}
|
}
|
||||||
@ -743,37 +746,44 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
|
|
||||||
// The node factories used to make lists of files to send to the result viewer
|
// The node factories used to make lists of files to send to the result viewer
|
||||||
private class FsContentNodeChildFactory extends ChildFactory<AbstractFile> {
|
private class FsContentNodeChildFactory extends ChildFactory<AbstractFile> {
|
||||||
|
|
||||||
List<AbstractFile> l;
|
List<AbstractFile> l;
|
||||||
|
|
||||||
FsContentNodeChildFactory(List<AbstractFile> l) {
|
FsContentNodeChildFactory(List<AbstractFile> l) {
|
||||||
this.l = l;
|
this.l = l;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected boolean createKeys(List<AbstractFile> list) {
|
protected boolean createKeys(List<AbstractFile> list) {
|
||||||
list.addAll(l);
|
list.addAll(l);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected Node createNodeForKey(AbstractFile file) {
|
protected Node createNodeForKey(AbstractFile file) {
|
||||||
Node wrapped;
|
Node wrapped;
|
||||||
if (file.isDir()) {
|
if (file.isDir()) {
|
||||||
wrapped = new DirectoryNode((Directory) file, false);
|
wrapped = new DirectoryNode((Directory) file, false);
|
||||||
} else {
|
} else {
|
||||||
wrapped = new FileNode((File) file, false);
|
wrapped = new FileNode((File) file, false);
|
||||||
}
|
}
|
||||||
return new FilterNodeLeaf(wrapped);
|
return new FilterNodeLeaf(wrapped);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private class FsContentRootNode extends DisplayableItemNode {
|
private class FsContentRootNode extends DisplayableItemNode {
|
||||||
|
|
||||||
FsContentRootNode(String NAME, List<AbstractFile> l) {
|
FsContentRootNode(String NAME, List<AbstractFile> l) {
|
||||||
super(Children.create(new FsContentNodeChildFactory(l), true));
|
super(Children.create(new FsContentNodeChildFactory(l), true));
|
||||||
super.setName(NAME);
|
super.setName(NAME);
|
||||||
super.setDisplayName(NAME);
|
super.setDisplayName(NAME);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public DisplayableItemNode.TYPE getDisplayableItemNodeType() {
|
public DisplayableItemNode.TYPE getDisplayableItemNodeType() {
|
||||||
return DisplayableItemNode.TYPE.CONTENT;
|
return DisplayableItemNode.TYPE.CONTENT;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public <T> T accept(DisplayableItemNodeVisitor<T> v) {
|
public <T> T accept(DisplayableItemNodeVisitor<T> v) {
|
||||||
return null;
|
return null;
|
||||||
@ -823,20 +833,26 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
ye.add(file, month, day);
|
ye.add(file, month, day);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
scan.close();
|
scan.close();
|
||||||
|
|
||||||
return years;
|
return years;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Crate a body file and return its path or null if error
|
||||||
|
*
|
||||||
|
* @return absolute path string or null if error
|
||||||
|
*/
|
||||||
private String makeBodyFile() {
|
private String makeBodyFile() {
|
||||||
// Setup timestamp
|
// Setup timestamp
|
||||||
DateFormat dateFormat = new SimpleDateFormat("MM-dd-yyyy-HH-mm-ss");
|
DateFormat dateFormat = new SimpleDateFormat("MM-dd-yyyy-HH-mm-ss");
|
||||||
Date date = new Date();
|
Date date = new Date();
|
||||||
String datenotime = dateFormat.format(date);
|
String datenotime = dateFormat.format(date);
|
||||||
|
|
||||||
Case currentCase = Case.getCurrentCase();
|
final Case currentCase = Case.getCurrentCase();
|
||||||
SleuthkitCase skCase = currentCase.getSleuthkitCase();
|
final SleuthkitCase skCase = currentCase.getSleuthkitCase();
|
||||||
|
|
||||||
// Get report path
|
// Get report path
|
||||||
String bodyFilePath = moduleDir.getAbsolutePath()
|
String bodyFilePath = moduleDir.getAbsolutePath()
|
||||||
+ java.io.File.separator + currentCase.getName() + "-" + datenotime + ".txt";
|
+ java.io.File.separator + currentCase.getName() + "-" + datenotime + ".txt";
|
||||||
@ -845,34 +861,39 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
String filesAndDirs = "type = '" + TskData.TSK_DB_FILES_TYPE_ENUM.FS.getFileType() + "' "
|
String filesAndDirs = "type = '" + TskData.TSK_DB_FILES_TYPE_ENUM.FS.getFileType() + "' "
|
||||||
+ "AND name != '.' "
|
+ "AND name != '.' "
|
||||||
+ "AND name != '..'";
|
+ "AND name != '..'";
|
||||||
List<FsContent> fs = Collections.EMPTY_LIST;
|
List<FsContent> fs = null;
|
||||||
try {
|
try {
|
||||||
fs = skCase.findFilesWhere(filesAndDirs);
|
fs = skCase.findFilesWhere(filesAndDirs);
|
||||||
} catch (TskCoreException ex) {
|
} catch (TskCoreException ex) {
|
||||||
Exceptions.printStackTrace(ex);
|
logger.log(Level.SEVERE, "Error querying image files to make a body file: " + bodyFilePath, ex);
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Loop files and write info to report
|
// Loop files and write info to report
|
||||||
|
FileWriter fileWriter = null;
|
||||||
|
try {
|
||||||
|
fileWriter = new FileWriter(bodyFilePath, true);
|
||||||
|
} catch (IOException ex) {
|
||||||
|
logger.log(Level.SEVERE, "Error creating output stream to write body file to: " + bodyFilePath, ex);
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
BufferedWriter out = null;
|
BufferedWriter out = null;
|
||||||
try {
|
try {
|
||||||
out = new BufferedWriter(new FileWriter(bodyFilePath, true));
|
out = new BufferedWriter(fileWriter);
|
||||||
} catch (IOException ex) {
|
for (FsContent file : fs) {
|
||||||
logger.log(Level.WARNING, "Could not create new BufferedWriter for body file.", ex);
|
// try {
|
||||||
}
|
|
||||||
for (FsContent file : fs) {
|
|
||||||
try {
|
|
||||||
// MD5|name|inode|mode_as_string|ObjId|GID|size|atime|mtime|ctime|crtime
|
// MD5|name|inode|mode_as_string|ObjId|GID|size|atime|mtime|ctime|crtime
|
||||||
//out = new BufferedWriter(new FileWriter(bodyFilePath, true));
|
|
||||||
|
|
||||||
if (file.getMd5Hash() != null) {
|
if (file.getMd5Hash() != null) {
|
||||||
out.write(file.getMd5Hash());
|
out.write(file.getMd5Hash());
|
||||||
}
|
}
|
||||||
out.write("|");
|
out.write("|");
|
||||||
String path = "";
|
String path = null;
|
||||||
try {
|
try {
|
||||||
path = file.getUniquePath();
|
path = file.getUniquePath();
|
||||||
} catch (TskCoreException e) {
|
} catch (TskCoreException e) {
|
||||||
logger.log(Level.WARNING, "Failed to get the unique path.", e);
|
logger.log(Level.SEVERE, "Failed to get the unique path of: " + file + " and writing body file.", e);
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
out.write(path);
|
out.write(path);
|
||||||
@ -899,18 +920,21 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
out.write("|");
|
out.write("|");
|
||||||
out.write(Long.toString(file.getCrtime()));
|
out.write(Long.toString(file.getCrtime()));
|
||||||
out.write("\n");
|
out.write("\n");
|
||||||
} catch (IOException ex) {
|
}
|
||||||
logger.log(Level.WARNING, "Probelm while trying to write data to the body file.", ex);
|
} catch (IOException ex) {
|
||||||
break;
|
logger.log(Level.WARNING, "Error while trying to write data to the body file.", ex);
|
||||||
|
return null;
|
||||||
|
} finally {
|
||||||
|
if (out != null) {
|
||||||
|
try {
|
||||||
|
out.flush();
|
||||||
|
out.close();
|
||||||
|
} catch (IOException ex1) {
|
||||||
|
logger.log(Level.WARNING, "Could not flush and/or close body file.", ex1);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
|
||||||
out.flush();
|
|
||||||
out.close();
|
|
||||||
} catch (IOException ex1) {
|
|
||||||
logger.log(Level.WARNING, "Could not flush and/or close body file.", ex1);
|
|
||||||
}
|
|
||||||
|
|
||||||
return bodyFilePath;
|
return bodyFilePath;
|
||||||
}
|
}
|
||||||
@ -952,11 +976,13 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
final Case currentCase = Case.getCurrentCase();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
if (Case.getCurrentCase().getImages().isEmpty()) {
|
if (currentCase.getImages().isEmpty()) {
|
||||||
logger.log(Level.INFO, "Error creating timeline, there are no images to parse");
|
logger.log(Level.INFO, "Error creating timeline, there are no images to parse");
|
||||||
} else {
|
} else {
|
||||||
|
|
||||||
if (IngestManager.getDefault().isIngestRunning()) {
|
if (IngestManager.getDefault().isIngestRunning()) {
|
||||||
int answer = JOptionPane.showConfirmDialog(new JFrame(),
|
int answer = JOptionPane.showConfirmDialog(new JFrame(),
|
||||||
"You are trying to generate a timeline before "
|
"You are trying to generate a timeline before "
|
||||||
@ -967,25 +993,24 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
logger.log(Level.INFO, "Beginning generation of timeline");
|
logger.log(Level.INFO, "Beginning generation of timeline");
|
||||||
|
|
||||||
// if the timeline window is already open, do nothing
|
// if the timeline window is already open, do nothing
|
||||||
if (jf != null && jf.isVisible()) {
|
if (jf != null && jf.isVisible()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
Platform.setImplicitExit(false);
|
Platform.setImplicitExit(false);
|
||||||
|
|
||||||
// listen for case changes (specifically images being added).
|
// listen for case changes (specifically images being added).
|
||||||
Case currcase = Case.getCurrentCase();
|
if (Case.isCaseOpen() && !listeningToAddImage) {
|
||||||
if (currcase != null && !listeningToAddImage) {
|
Case.addPropertyChangeListener(this);
|
||||||
currcase.addPropertyChangeListener(this);
|
|
||||||
listeningToAddImage = true;
|
listeningToAddImage = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
// create the modal dialog
|
// create the modal dialog
|
||||||
SwingUtilities.invokeLater(new Runnable () {
|
SwingUtilities.invokeLater(new Runnable() {
|
||||||
@Override
|
@Override
|
||||||
public void run() {
|
public void run() {
|
||||||
dialog = new TimelineProgressDialog(jf, true);
|
dialog = new TimelineProgressDialog(jf, true);
|
||||||
@ -994,11 +1019,11 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
});
|
});
|
||||||
|
|
||||||
// initialize mactimeFileName
|
// initialize mactimeFileName
|
||||||
mactimeFileName = Case.getCurrentCase().getName() + "-MACTIME.txt";
|
mactimeFileName = currentCase.getName() + "-MACTIME.txt";
|
||||||
|
|
||||||
// see if data has been added to the database since the last
|
// see if data has been added to the database since the last
|
||||||
// time timeline ran
|
// time timeline ran
|
||||||
long objId = Case.getCurrentCase().getSleuthkitCase().getLastObjectId();
|
long objId = currentCase.getSleuthkitCase().getLastObjectId();
|
||||||
if (objId != lastObjectId && lastObjectId != -1) {
|
if (objId != lastObjectId && lastObjectId != -1) {
|
||||||
clearMactimeData();
|
clearMactimeData();
|
||||||
}
|
}
|
||||||
@ -1008,7 +1033,9 @@ public class Simile2 extends CallableSystemAction implements Presenter.Toolbar,
|
|||||||
customize();
|
customize();
|
||||||
}
|
}
|
||||||
} catch (TskCoreException ex) {
|
} catch (TskCoreException ex) {
|
||||||
Exceptions.printStackTrace(ex);
|
logger.log(Level.SEVERE, "Error when generating timeline, ", ex);
|
||||||
|
} catch (Exception ex) {
|
||||||
|
logger.log(Level.SEVERE, "Unexpected error when generating timeline, ", ex);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user