Sleuth Kit Java Bindings (JNI)  4.12.1
Java bindings for using The Sleuth Kit
SleuthkitJNI.java
Go to the documentation of this file.
1 /*
2  * Sleuth Kit Data Model
3  *
4  * Copyright 2011-2018 Basis Technology Corp.
5  * Contact: carrier <at> sleuthkit <dot> org
6  *
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  * http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  */
19 package org.sleuthkit.datamodel;
20 
21 import com.google.common.annotations.Beta;
22 import java.io.BufferedReader;
23 import java.io.FileReader;
24 import java.io.IOException;
25 import java.text.DateFormat;
26 import java.text.SimpleDateFormat;
27 import java.util.ArrayList;
28 import java.util.Arrays;
29 import java.util.GregorianCalendar;
30 import java.util.HashMap;
31 import java.util.HashSet;
32 import java.util.List;
33 import java.util.Map;
34 import java.util.Set;
35 import java.util.TimeZone;
36 import java.util.UUID;
37 import java.util.concurrent.locks.ReadWriteLock;
38 import java.util.concurrent.locks.ReentrantReadWriteLock;
39 import java.util.logging.Level;
40 import java.util.logging.Logger;
41 import org.apache.commons.lang3.StringUtils;
44 
53 public class SleuthkitJNI {
54 
55  private static final Logger logger = Logger.getLogger(SleuthkitJNI.class.getName());
56 
63  private static final ReadWriteLock tskLock = new ReentrantReadWriteLock();
64 
65  /*
66  * Loads the SleuthKit libraries.
67  */
68  static {
70  }
71 
76  private SleuthkitJNI() {
77  }
78 
82  private static class CaseHandles {
83  /*
84  * A SleuthKit image handle cache implemented as a mappng of
85  * concatenated image file paths to image handles.
86  */
87  private final Map<String, Long> imageHandleCache = new HashMap<>();
88 
89  /*
90  * A SleuthKit file system handles cache implemented as a mapping of
91  * image handles to image offset and file system handle pairs.
92  */
93  private final Map<Long, Map<Long, Long>> fsHandleCache = new HashMap<>();
94 
95  /*
96  * The collection of open file handles. We will only allow requests
97  * through to the C code if the file handle exists in this collection.
98  */
99  private final Set<Long> fileHandleCache = new HashSet<>();
100 
101  private final Map<Long, List<Long>> fileSystemToFileHandles = new HashMap<>();
102 
103  private final Map<Long, Map<Long, Long>> poolHandleCache = new HashMap<>();
104 
105  // The poolImgCache is only used to close the images later.
106  private final List<Long> poolImgCache = new ArrayList<>();
107 
108  /*
109  * Currently, our APFS code is not thread-safe and it is the only code
110  * that uses pools. To prevent crashes, we make any reads to a file system
111  * contained in a pool single-threaded. This cache keeps track of which
112  * open file system handles are contained in a pool so we can set the locks
113  * appropriately.
114  */
115  private final List<Long> poolFsList = new ArrayList<>();
116 
117  private CaseHandles() {
118  // Nothing to do here
119  }
120  }
121 
128  private static class HandleCache {
129 
130  /*
131  * A monitor used to guard access to cached Sleuthkit JNI handles.
132  */
133  private static final Object cacheLock = new Object();
134 
135  private static final Map<String, CaseHandles> caseHandlesCache = new HashMap<>();
136 
137  private static final String INVALID_FILE_HANDLE = "Invalid file handle."; //NON-NLS
138 
139  /*
140  * Currently, our APFS code is not thread-safe and it is the only code
141  * that uses pools. To prevent crashes, we make any reads to a file system
142  * contained in a pool single-threaded. This cache keeps track of which
143  * open file handles are contained in a pool so we can set the locks
144  * appropriately.
145  *
146  * Access to this list should be guarded by cacheLock.
147  */
148  private static final List<Long> poolFileHandles = new ArrayList<>();
149 
155  private static void createCaseHandleCache(String caseIdentifier) {
156  caseHandlesCache.put(caseIdentifier, new CaseHandles());
157  }
158 
167  private static String getDefaultCaseIdentifier() throws TskCoreException {
168  synchronized (cacheLock) {
169  if (caseHandlesCache.keySet().size() > 1) {
170  throw new TskCoreException("Can not get default case identifier with multiple open cases");
171  } else if (caseHandlesCache.keySet().isEmpty()) {
172  throw new TskCoreException("Can not get default case identifier with no open case");
173  }
174 
175  return (caseHandlesCache.keySet().iterator().next());
176  }
177  }
178 
188  private static CaseHandles getCaseHandles(String caseIdentifier) throws TskCoreException {
189  synchronized (cacheLock) {
190  if (caseHandlesCache.containsKey(caseIdentifier)) {
191  return caseHandlesCache.get(caseIdentifier);
192  }
193  // If the CaseHandles object isn't in there, it should mean the case has been closed.
194  throw new TskCoreException("No entry for case " + caseIdentifier + " in cache. Case may have been closed");
195  }
196  }
197 
203  private static void removeCaseHandlesCache(String caseIdentifier) {
204  synchronized (cacheLock) {
205  if (caseHandlesCache.containsKey(caseIdentifier)) {
206  caseHandlesCache.get(caseIdentifier).fsHandleCache.clear();
207  caseHandlesCache.get(caseIdentifier).imageHandleCache.clear();
208  caseHandlesCache.get(caseIdentifier).fileHandleCache.clear();
209  caseHandlesCache.get(caseIdentifier).fileSystemToFileHandles.clear();
210  caseHandlesCache.get(caseIdentifier).poolHandleCache.clear();
211  caseHandlesCache.remove(caseIdentifier);
212  }
213  }
214  }
215 
223  private static boolean isImageInAnyCache(long imgHandle) {
224  synchronized (cacheLock) {
225  for (String caseIdentifier:caseHandlesCache.keySet()) {
226  if (caseHandlesCache.get(caseIdentifier).fsHandleCache.keySet().contains(imgHandle)) {
227  return true;
228  }
229  }
230  return false;
231  }
232  }
233 
241  private static void addFileHandle(String caseIdentifier, long fileHandle, long fsHandle) {
242  try {
243  synchronized (cacheLock) {
244  // Add to collection of open file handles.
245  getCaseHandles(caseIdentifier).fileHandleCache.add(fileHandle);
246 
247  // Add to map of file system to file handles.
248  if (getCaseHandles(caseIdentifier).fileSystemToFileHandles.containsKey(fsHandle)) {
249  getCaseHandles(caseIdentifier).fileSystemToFileHandles.get(fsHandle).add(fileHandle);
250  } else {
251  getCaseHandles(caseIdentifier).fileSystemToFileHandles.put(fsHandle, new ArrayList<>(Arrays.asList(fileHandle)));
252  }
253  }
254  } catch (TskCoreException ex) {
255  logger.log(Level.WARNING, "Error caching file handle for case {0}", caseIdentifier);
256  }
257  }
258 
265  private static void removeFileHandle(long fileHandle, SleuthkitCase skCase) {
266  synchronized (cacheLock) {
267  // Remove from collection of open file handles.
268  if (skCase != null) {
269  try {
270  getCaseHandles(skCase.getCaseHandleIdentifier()).fileHandleCache.remove(fileHandle);
271  } catch (TskCoreException ex) {
272  // If the call to getCaseHandles() failed, we've already cleared the cache.
273  }
274  } else {
275  // If we don't know what case the handle is from, delete the first one we find
276  for (String caseIdentifier:caseHandlesCache.keySet()) {
277  if (caseHandlesCache.get(caseIdentifier).fileHandleCache.contains(fileHandle)) {
278  caseHandlesCache.get(caseIdentifier).fileHandleCache.remove(fileHandle);
279  return;
280  }
281  }
282  }
283  }
284  }
285 
293  private static boolean isValidFileHandle(long fileHandle) {
294  synchronized (cacheLock) {
295  for (String caseIdentifier:caseHandlesCache.keySet()) {
296  if (caseHandlesCache.get(caseIdentifier).fileHandleCache.contains(fileHandle)) {
297  return true;
298  }
299  }
300  return false;
301  }
302  }
303 
304  private static void closeHandlesAndClearCache(String caseIdentifier) throws TskCoreException {
305  synchronized (cacheLock) {
306  /*
307  * Close any cached file system handles.
308  */
309  for (Map<Long, Long> imageToFsMap : getCaseHandles(caseIdentifier).fsHandleCache.values()) {
310  for (Long fsHandle : imageToFsMap.values()) {
311  // First close all open file handles for the file system.
312  if (getCaseHandles(caseIdentifier).fileSystemToFileHandles.containsKey(fsHandle)) {
313  for (Long fileHandle : getCaseHandles(caseIdentifier).fileSystemToFileHandles.get(fsHandle)) {
314  // Update the cache of file handles contained in pools
315  if (poolFileHandles.contains(fileHandle)) {
316  poolFileHandles.remove(fileHandle);
317  }
318  closeFile(fileHandle);
319  }
320  }
321  // Then close the file system handle.
322  closeFsNat(fsHandle);
323  }
324  }
325 
326  /*
327  * Clear out the list of pool file systems.
328  */
329  getCaseHandles(caseIdentifier).poolFsList.clear();
330 
331  /*
332  * Close any cached pools
333  */
334  for (Long imgHandle : getCaseHandles(caseIdentifier).poolHandleCache.keySet()) {
335  for (Long poolHandle : getCaseHandles(caseIdentifier).poolHandleCache.get(imgHandle).values()) {
336  closePoolNat(poolHandle);
337  }
338  }
339 
340  /*
341  * Close any open pool images
342  */
343  for (Long imageHandle : getCaseHandles(caseIdentifier).poolImgCache) {
344  closeImgNat(imageHandle);
345  }
346 
347  /*
348  * Close any cached image handles.
349  */
350  for (Long imageHandle : getCaseHandles(caseIdentifier).imageHandleCache.values()) {
351  closeImgNat(imageHandle);
352  }
353 
354  removeCaseHandlesCache(caseIdentifier);
355  }
356 
357  }
358  }
359 
364  public static class CaseDbHandle {
365 
366  /*
367  * A unique indentifier for a case
368  */
369  private final String caseDbIdentifier;
370 
377  private CaseDbHandle(String databaseName) {
378  this.caseDbIdentifier = "SingleUser:" + databaseName; // NON-NLS
379  HandleCache.createCaseHandleCache(caseDbIdentifier);
380  }
381 
389  private CaseDbHandle(String databaseName, CaseDbConnectionInfo info) {
390  this.caseDbIdentifier = "MultiUser:" + info.getHost() + ":" + databaseName;
391  HandleCache.createCaseHandleCache(caseDbIdentifier);
392  }
393 
399  String getCaseDbIdentifier() {
400  return caseDbIdentifier;
401  }
402 
409  void free() throws TskCoreException {
410  tskLock.writeLock().lock();
411  try {
412  HandleCache.closeHandlesAndClearCache(caseDbIdentifier);
413  //SleuthkitJNI.closeCaseDbNat(caseDbIdentifier);
414  } finally {
415  tskLock.writeLock().unlock();
416  }
417  }
418 
437  long addImageInfo(long deviceObjId, List<String> imageFilePaths, String timeZone, Host host, String password, SleuthkitCase skCase) throws TskCoreException {
438 
439  try {
440  if (host == null) {
441  String hostName;
442  if (imageFilePaths.size() > 0) {
443  String path = imageFilePaths.get(0);
444  hostName = (new java.io.File(path)).getName() + " Host";
445  } else {
446  hostName = "Image_" + deviceObjId + " Host";
447  }
448  host = skCase.getHostManager().newHost(hostName);
449  }
450  TskCaseDbBridge dbHelper = new TskCaseDbBridge(skCase, new DefaultAddDataSourceCallbacks(), host);
451  long tskAutoDbPointer = initializeAddImgPasswordNat(dbHelper, timezoneLongToShort(timeZone), false, false, false, password);
452  runOpenAndAddImgNat(tskAutoDbPointer, UUID.randomUUID().toString(), imageFilePaths.toArray(new String[0]), imageFilePaths.size(), timeZone);
453  long id = finishAddImgNat(tskAutoDbPointer);
454  dbHelper.finish();
455  skCase.addDataSourceToHasChildrenMap();
456  return id;
457  } catch (TskDataException ex) {
458  throw new TskCoreException("Error adding image to case database", ex);
459  }
460  }
461 
480  AddImageProcess initAddImageProcess(String timeZone, boolean addUnallocSpace, boolean skipFatFsOrphans, String imageCopyPath, String password, SleuthkitCase skCase) {
481  return new AddImageProcess(timeZone, addUnallocSpace, skipFatFsOrphans, imageCopyPath, password, skCase);
482  }
483 
488  public class AddImageProcess {
489 
490  private final String timeZone;
491  private final boolean addUnallocSpace;
492  private final boolean skipFatFsOrphans;
493  private final String imageWriterPath;
494  private volatile long tskAutoDbPointer;
495  private long imageId = 0;
496  private boolean isCanceled;
497  private final SleuthkitCase skCase;
498  private TskCaseDbBridge dbHelper;
499  private final String password;
500 
516  private AddImageProcess(String timeZone, boolean addUnallocSpace, boolean skipFatFsOrphans, String imageWriterPath, String password, SleuthkitCase skCase) {
517  this.timeZone = timeZone;
518  this.addUnallocSpace = addUnallocSpace;
519  this.skipFatFsOrphans = skipFatFsOrphans;
520  this.imageWriterPath = imageWriterPath;
521  tskAutoDbPointer = 0;
522  this.isCanceled = false;
523  this.skCase = skCase;
524  this.password = password;
525 
526  }
527 
544  public void run(String deviceId, String[] imageFilePaths, int sectorSize) throws TskCoreException, TskDataException {
545  Image img = addImageToDatabase(skCase, imageFilePaths, sectorSize, "", "", "", "", deviceId, password, null);
546  run(deviceId, img, sectorSize, new DefaultAddDataSourceCallbacks());
547  }
548 
566  public void run(String deviceId, Image image, int sectorSize,
567  AddDataSourceCallbacks addDataSourceCallbacks) throws TskCoreException, TskDataException {
568 
569  dbHelper = new TskCaseDbBridge(skCase, addDataSourceCallbacks, image.getHost());
570  getTSKReadLock();
571  try {
572  long imageHandle = 0;
573  synchronized (this) {
574  if (0 != tskAutoDbPointer) {
575  throw new TskCoreException("Add image process already started");
576  }
577  if (!isCanceled) { //with isCanceled being guarded by this it will have the same value everywhere in this synchronized block
578  imageHandle = image.getImageHandle();
579  tskAutoDbPointer = initAddImgNatPassword(dbHelper, timezoneLongToShort(timeZone), addUnallocSpace, skipFatFsOrphans, password);
580  }
581  if (0 == tskAutoDbPointer) {
582  throw new TskCoreException("initAddImgNat returned a NULL TskAutoDb pointer");
583  }
584  }
585  if (imageHandle != 0) {
586  runAddImgNat(tskAutoDbPointer, deviceId, imageHandle, image.getId(), timeZone, imageWriterPath);
587  }
588  } finally {
589  finishAddImageProcess();
590  releaseTSKReadLock();
591  }
592  }
593 
603  public synchronized void stop() throws TskCoreException {
604  getTSKReadLock();
605  try {
606  isCanceled = true;
607  if (tskAutoDbPointer != 0) {
608  stopAddImgNat(tskAutoDbPointer);
609  }
610  } finally {
611  releaseTSKReadLock();
612  }
613  }
614 
625  private synchronized void finishAddImageProcess() throws TskCoreException {
626  if (tskAutoDbPointer == 0) {
627  return;
628  }
629 
630  // If the process wasn't cancelled, finish up processing the
631  // remaining files.
632  if (! this.isCanceled && dbHelper != null) {
633  dbHelper.finish();
634  }
635 
636  // Free the auto DB pointer and get the image ID
637  imageId = finishAddImgNat(tskAutoDbPointer);
638  tskAutoDbPointer = 0;
639 
640  skCase.addDataSourceToHasChildrenMap();
641  }
642 
651  @Deprecated
652  public synchronized void revert() throws TskCoreException {
653  // No-op
654  }
655 
667  @Deprecated
668  public synchronized long commit() throws TskCoreException {
669  return imageId;
670  }
671 
678  public synchronized String currentDirectory() {
679  return tskAutoDbPointer == 0 ? "" : getCurDirNat(tskAutoDbPointer); //NON-NLS
680  }
681 
697  @Deprecated
698  public void run(String[] imageFilePaths) throws TskCoreException, TskDataException {
699  run(null, imageFilePaths, 0);
700  }
701 
717  public void run(String deviceId, String[] imageFilePaths) throws TskCoreException, TskDataException {
718  run(deviceId, imageFilePaths, 0);
719  }
720  }
721 
722  }
723 
735  static CaseDbHandle newCaseDb(String path) throws TskCoreException {
736  return new CaseDbHandle(path);
737  }
738 
751  static CaseDbHandle newCaseDb(String databaseName, CaseDbConnectionInfo info) throws TskCoreException {
752  return new CaseDbHandle(databaseName, info);
753  }
754 
766  static CaseDbHandle openCaseDb(String path) throws TskCoreException {
767  return new CaseDbHandle(path);
768  }
769 
782  static CaseDbHandle openCaseDb(String databaseName, CaseDbConnectionInfo info) throws TskCoreException {
783  return new CaseDbHandle(databaseName, info);
784  }
785 
791  public static String getVersion() {
792  return getVersionNat();
793  }
794 
800  public static void startVerboseLogging(String logPath) {
801  startVerboseLoggingNat(logPath);
802  }
803 
815  public static long openImage(String[] imageFiles, SleuthkitCase skCase) throws TskCoreException {
816  if (skCase == null) {
817  throw new TskCoreException("SleuthkitCase can not be null");
818  }
819  return openImage(imageFiles, 0, true, skCase.getCaseHandleIdentifier());
820  }
821 
835  public static long openImage(String[] imageFiles, int sSize, SleuthkitCase skCase) throws TskCoreException {
836  if (skCase == null) {
837  throw new TskCoreException("SleuthkitCase can not be null");
838  }
839  return openImage(imageFiles, sSize, true, skCase.getCaseHandleIdentifier());
840  }
841 
859  private static long openImage(String[] imageFiles, int sSize, boolean useCache, String caseIdentifer) throws TskCoreException {
860  getTSKReadLock();
861  try {
862  long imageHandle;
863 
864  StringBuilder keyBuilder = new StringBuilder();
865  for (int i = 0; i < imageFiles.length; ++i) {
866  keyBuilder.append(imageFiles[i]);
867  }
868  final String imageKey = keyBuilder.toString();
869 
870  synchronized (HandleCache.cacheLock) {
871  String nonNullCaseIdentifer = caseIdentifer;
872  if (nonNullCaseIdentifer == null) {
873  nonNullCaseIdentifer = HandleCache.getDefaultCaseIdentifier();
874  }
875 
876  // If we're getting a fresh copy and an image with this path is already
877  // in the cache, move the existing cache reference so it won't be used by
878  // any subsequent calls to openImage but will still be valid if any objects
879  // have it cached. This happens in the case where the user adds the same data
880  // source twice (see JIRA-5868).
881  if (!useCache && HandleCache.getCaseHandles(nonNullCaseIdentifer).imageHandleCache.containsKey(imageKey)) {
882  long tempImageHandle = HandleCache.getCaseHandles(nonNullCaseIdentifer).imageHandleCache.get(imageKey);
883 
884  // Store the old image handle in a fake path. This way it will no longer be found but will
885  // still be valid and the image and its file systems will be closed with the case.
886  String newPath = "Image_" + UUID.randomUUID().toString();
887  HandleCache.getCaseHandles(nonNullCaseIdentifer).imageHandleCache.put(newPath, tempImageHandle);
888  HandleCache.getCaseHandles(nonNullCaseIdentifer).imageHandleCache.remove(imageKey);
889  }
890 
891  if (useCache && HandleCache.getCaseHandles(nonNullCaseIdentifer).imageHandleCache.containsKey(imageKey)) //get from cache
892  {
893  imageHandle = HandleCache.getCaseHandles(nonNullCaseIdentifer).imageHandleCache.get(imageKey);
894  } else {
895  //open new handle and cache it
896  imageHandle = openImgNat(imageFiles, imageFiles.length, sSize);
897  HandleCache.getCaseHandles(nonNullCaseIdentifer).fsHandleCache.put(imageHandle, new HashMap<>());
898  HandleCache.getCaseHandles(nonNullCaseIdentifer).imageHandleCache.put(imageKey, imageHandle);
899  }
900  }
901  return imageHandle;
902  } finally {
903  releaseTSKReadLock();
904  }
905  }
906 
920  private static void cacheImageHandle(SleuthkitCase skCase, List<String> imagePaths, long imageHandle) throws TskCoreException {
921 
922  // Construct the hash key from the image paths
923  StringBuilder keyBuilder = new StringBuilder();
924  for (int i = 0; i < imagePaths.size(); ++i) {
925  keyBuilder.append(imagePaths.get(i));
926  }
927  final String imageKey = keyBuilder.toString();
928 
929  // Get the case identifier
930  String caseIdentifier = skCase.getCaseHandleIdentifier();
931 
932  synchronized (HandleCache.cacheLock) {
933  HandleCache.getCaseHandles(caseIdentifier).fsHandleCache.put(imageHandle, new HashMap<>());
934  HandleCache.getCaseHandles(caseIdentifier).imageHandleCache.put(imageKey, imageHandle);
935  }
936  }
937 
954  public static Image addImageToDatabase(SleuthkitCase skCase, String[] imagePaths, int sectorSize,
955  String timeZone, String md5fromSettings, String sha1fromSettings, String sha256fromSettings, String deviceId) throws TskCoreException {
956 
957  return addImageToDatabase(skCase, imagePaths, sectorSize, timeZone, md5fromSettings, sha1fromSettings, sha256fromSettings, deviceId, null);
958  }
959 
977  public static Image addImageToDatabase(SleuthkitCase skCase, String[] imagePaths, int sectorSize,
978  String timeZone, String md5fromSettings, String sha1fromSettings, String sha256fromSettings, String deviceId, Host host) throws TskCoreException {
979 
980  return addImageToDatabase(skCase, imagePaths, sectorSize, timeZone, md5fromSettings, sha1fromSettings, sha256fromSettings, deviceId, null, host);
981  }
982 
1001  @Beta
1002  public static Image addImageToDatabase(SleuthkitCase skCase, String[] imagePaths, int sectorSize,
1003  String timeZone, String md5fromSettings, String sha1fromSettings, String sha256fromSettings, String deviceId, String password, Host host) throws TskCoreException {
1004 
1005  // Open the image
1006  long imageHandle = openImgNat(imagePaths, 1, sectorSize);
1007 
1008  // Get the fields stored in the native code
1009  List<String> computedPaths = Arrays.asList(getPathsForImageNat(imageHandle));
1010  long size = getSizeForImageNat(imageHandle);
1011  long type = getTypeForImageNat(imageHandle);
1012  long computedSectorSize = getSectorSizeForImageNat(imageHandle);
1013  String md5 = md5fromSettings;
1014  if (StringUtils.isEmpty(md5)) {
1015  md5 = getMD5HashForImageNat(imageHandle);
1016  }
1017  String sha1 = sha1fromSettings;
1018  if (StringUtils.isEmpty(sha1)) {
1019  sha1 = getSha1HashForImageNat(imageHandle);
1020  }
1021  // Sleuthkit does not currently generate any SHA256 hashes. Set to empty
1022  // string for consistency.
1023  String sha256 = sha256fromSettings;
1024  if (sha256 == null) {
1025  sha256 = "";
1026  }
1027  String collectionDetails = getCollectionDetailsForImageNat(imageHandle);
1028 
1029  // Now save to database
1030  CaseDbTransaction transaction = skCase.beginTransaction();
1031  try {
1032  Image img = skCase.addImage(TskData.TSK_IMG_TYPE_ENUM.valueOf(type), computedSectorSize,
1033  size, null, computedPaths,
1034  timeZone, md5, sha1, sha256,
1035  deviceId, host, password, transaction);
1036  if (!StringUtils.isEmpty(collectionDetails)) {
1037  skCase.setAcquisitionDetails(img, collectionDetails);
1038  }
1039  transaction.commit();
1040 
1041  img.setImageHandle(imageHandle);
1042  cacheImageHandle(skCase, computedPaths, imageHandle);
1043  return img;
1044  } catch (TskCoreException ex) {
1045  transaction.rollback();
1046  throw(ex);
1047  }
1048  }
1049 
1050 
1051 
1064  public static long openVs(long imgHandle, long vsOffset) throws TskCoreException {
1065  getTSKReadLock();
1066  try {
1067  if(! imgHandleIsValid(imgHandle)) {
1068  throw new TskCoreException("Image handle " + imgHandle + " is closed");
1069  }
1070  return openVsNat(imgHandle, vsOffset);
1071  } finally {
1072  releaseTSKReadLock();
1073  }
1074  }
1075 
1076  //get pointers
1088  public static long openVsPart(long vsHandle, long volId) throws TskCoreException {
1089  getTSKReadLock();
1090  try {
1091  //returned long is ptr to vs Handle object in tsk
1092  return openVolNat(vsHandle, volId);
1093  } finally {
1094  releaseTSKReadLock();
1095  }
1096  }
1097 
1109  static long openPool(long imgHandle, long offset, SleuthkitCase skCase) throws TskCoreException {
1110  getTSKReadLock();
1111  try {
1112  if(! imgHandleIsValid(imgHandle)) {
1113  throw new TskCoreException("Image handle " + imgHandle + " is closed");
1114  }
1115 
1116  synchronized (HandleCache.cacheLock) {
1117  String caseIdentifier;
1118  if (skCase == null) {
1119  caseIdentifier = HandleCache.getDefaultCaseIdentifier();
1120  } else {
1121  caseIdentifier = skCase.getCaseHandleIdentifier();
1122  }
1123 
1124  // If a pool handle cache for this image does not exist, make one
1125  if (! HandleCache.getCaseHandles(caseIdentifier).poolHandleCache.containsKey(imgHandle)) {
1126  HandleCache.getCaseHandles(caseIdentifier).poolHandleCache.put(imgHandle, new HashMap<>());
1127  }
1128 
1129  // Get the pool handle cache for this image
1130  Map<Long, Long> poolCacheForImage = HandleCache.getCaseHandles(caseIdentifier).poolHandleCache.get(imgHandle);
1131 
1132  if (poolCacheForImage.containsKey(offset)) {
1133  return poolCacheForImage.get(offset);
1134  } else {
1135  //returned long is ptr to pool Handle object in tsk
1136  long poolHandle = openPoolNat(imgHandle, offset);
1137  poolCacheForImage.put(offset, poolHandle);
1138  return poolHandle;
1139  }
1140  }
1141  } finally {
1142  releaseTSKReadLock();
1143  }
1144  }
1145 
1159  public static long openFs(long imgHandle, long fsOffset, SleuthkitCase skCase) throws TskCoreException {
1160  return openFs(imgHandle, fsOffset, "", skCase);
1161  }
1162 
1177  public static long openFs(long imgHandle, long fsOffset, String password, SleuthkitCase skCase) throws TskCoreException {
1178  getTSKReadLock();
1179  try {
1180  long fsHandle;
1181  synchronized (HandleCache.cacheLock) {
1182  String caseIdentifier;
1183  if (skCase == null) {
1184  caseIdentifier = HandleCache.getDefaultCaseIdentifier();
1185  } else {
1186  caseIdentifier = skCase.getCaseHandleIdentifier();
1187  }
1188  final Map<Long, Long> imgOffSetToFsHandle = HandleCache.getCaseHandles(caseIdentifier).fsHandleCache.get(imgHandle);
1189  if (imgOffSetToFsHandle == null) {
1190  throw new TskCoreException("Missing image offset to file system handle cache for image handle " + imgHandle);
1191  }
1192  if (imgOffSetToFsHandle.containsKey(fsOffset)) {
1193  //return cached
1194  fsHandle = imgOffSetToFsHandle.get(fsOffset);
1195  } else {
1196  fsHandle = openFsDecryptNat(imgHandle, fsOffset, password);
1197  //cache it
1198  imgOffSetToFsHandle.put(fsOffset, fsHandle);
1199  }
1200  }
1201  return fsHandle;
1202  } finally {
1203  releaseTSKReadLock();
1204  }
1205  }
1206 
1223  static long openFsPool(long imgHandle, long fsOffset, long poolHandle, long poolBlock, SleuthkitCase skCase) throws TskCoreException {
1224  /*
1225  * Currently, our APFS code is not thread-safe and it is the only code
1226  * that uses pools. To prevent crashes, we make any reads to a file system
1227  * contained in a pool single-threaded.
1228  */
1229  getTSKWriteLock();
1230  try {
1231  long fsHandle;
1232  synchronized (HandleCache.cacheLock) {
1233  String caseIdentifier;
1234  if (skCase == null) {
1235  caseIdentifier = HandleCache.getDefaultCaseIdentifier();
1236  } else {
1237  caseIdentifier = skCase.getCaseHandleIdentifier();
1238  }
1239  final Map<Long, Long> imgOffSetToFsHandle = HandleCache.getCaseHandles(caseIdentifier).fsHandleCache.get(imgHandle);
1240  if (imgOffSetToFsHandle == null) {
1241  throw new TskCoreException("Missing image offset to file system handle cache for image handle " + imgHandle);
1242  }
1243 
1244  if (imgOffSetToFsHandle.containsKey(poolBlock)) {
1245  //return cached
1246  fsHandle = imgOffSetToFsHandle.get(poolBlock);
1247  } else {
1248  long poolImgHandle = getImgInfoForPoolNat(poolHandle, poolBlock);
1249  HandleCache.getCaseHandles(caseIdentifier).poolImgCache.add(poolImgHandle);
1250  fsHandle = openFsNat(poolImgHandle, fsOffset);
1251  //cache it
1252  imgOffSetToFsHandle.put(poolBlock, fsHandle);
1253  HandleCache.getCaseHandles(caseIdentifier).poolFsList.add(fsHandle);
1254  }
1255  }
1256  return fsHandle;
1257  } finally {
1258  releaseTSKWriteLock();
1259  }
1260  }
1261 
1276  public static long openFile(long fsHandle, long fileId, TSK_FS_ATTR_TYPE_ENUM attrType, int attrId, SleuthkitCase skCase) throws TskCoreException {
1277  /*
1278  * NOTE: previously attrId used to be stored in AbstractFile as (signed)
1279  * short even though it is stored as uint16 in TSK. In extremely rare
1280  * occurrences attrId can be larger than what a signed short can hold
1281  * (2^15). Changes were made to AbstractFile to store attrId as integer.
1282  * However, a depricated method still exists in AbstractFile to get
1283  * attrId as short. In that method we convert attribute ids that are
1284  * larger than 32K to a negative number. Therefore if encountered, we
1285  * need to convert negative attribute id to uint16 which is what TSK is
1286  * using to store attribute id.
1287  */
1288  boolean withinPool = false;
1289  synchronized (HandleCache.cacheLock) {
1290  String caseIdentifier;
1291  if (skCase == null) {
1292  caseIdentifier = HandleCache.getDefaultCaseIdentifier();
1293  } else {
1294  caseIdentifier = skCase.getCaseHandleIdentifier();
1295  }
1296  if (HandleCache.getCaseHandles(caseIdentifier).poolFsList.contains(fsHandle)) {
1297  withinPool = true;
1298  }
1299  }
1300 
1301  /*
1302  * The current APFS code is not thread-safe. To compensate, we make any
1303  * reads to the APFS pool single-threaded by obtaining a write
1304  * lock instead of a read lock.
1305  */
1306  if (withinPool) {
1307  getTSKWriteLock();
1308  } else {
1309  getTSKReadLock();
1310  }
1311  try {
1312  long fileHandle = openFileNat(fsHandle, fileId, attrType.getValue(), convertSignedToUnsigned(attrId));
1313  synchronized (HandleCache.cacheLock) {
1314  String caseIdentifier;
1315  if (skCase == null) {
1316  caseIdentifier = HandleCache.getDefaultCaseIdentifier();
1317  } else {
1318  caseIdentifier = skCase.getCaseHandleIdentifier();
1319  }
1320  HandleCache.addFileHandle(caseIdentifier, fileHandle, fsHandle);
1321 
1322  // If this file is in a pool file system, record it so the locks
1323  // can be set appropriately when reading it.
1324  if (withinPool) {
1325  HandleCache.poolFileHandles.add(fileHandle);
1326  }
1327  }
1328  return fileHandle;
1329  } finally {
1330  if (withinPool) {
1331  releaseTSKWriteLock();
1332  } else {
1333  releaseTSKReadLock();
1334  }
1335  }
1336  }
1337 
1345  private static int convertSignedToUnsigned(int val) {
1346  if (val >= 0) {
1347  return val;
1348  }
1349 
1350  return val & 0xffff; // convert negative value to positive value
1351  }
1352 
1358  private static boolean imgHandleIsValid(long imgHandle) {
1359  synchronized(HandleCache.cacheLock) {
1360  return HandleCache.isImageInAnyCache(imgHandle);
1361  }
1362  }
1363 
1364  //do reads
1379  public static int readImg(long imgHandle, byte[] readBuffer, long offset, long len) throws TskCoreException {
1380  getTSKReadLock();
1381  try {
1382  if(! imgHandleIsValid(imgHandle)) {
1383  throw new TskCoreException("Image handle " + imgHandle + " is closed");
1384  }
1385  //returned byte[] is the data buffer
1386  return readImgNat(imgHandle, readBuffer, offset, len);
1387  } finally {
1388  releaseTSKReadLock();
1389  }
1390  }
1391 
1406  public static int readVs(long vsHandle, byte[] readBuffer, long offset, long len) throws TskCoreException {
1407  getTSKReadLock();
1408  try {
1409  return readVsNat(vsHandle, readBuffer, offset, len);
1410  } finally {
1411  releaseTSKReadLock();
1412  }
1413  }
1414 
1427  static int readPool(long poolHandle, byte[] readBuffer, long offset, long len) throws TskCoreException {
1428  getTSKReadLock();
1429  try {
1430  return readPoolNat(poolHandle, readBuffer, offset, len);
1431  } finally {
1432  releaseTSKReadLock();
1433  }
1434  }
1435 
1450  public static int readVsPart(long volHandle, byte[] readBuffer, long offset, long len) throws TskCoreException {
1451  getTSKReadLock();
1452  try {
1453  //returned byte[] is the data buffer
1454  return readVolNat(volHandle, readBuffer, offset, len);
1455  } finally {
1456  releaseTSKReadLock();
1457  }
1458  }
1459 
1474  public static int readFs(long fsHandle, byte[] readBuffer, long offset, long len) throws TskCoreException {
1475  getTSKReadLock();
1476  try {
1477  //returned byte[] is the data buffer
1478  return readFsNat(fsHandle, readBuffer, offset, len);
1479  } finally {
1480  releaseTSKReadLock();
1481  }
1482  }
1483 
1488  private enum TSK_FS_FILE_READ_OFFSET_TYPE_ENUM {
1489  START_OF_FILE(0),
1490  START_OF_SLACK(1);
1491 
1492  private final int val;
1493 
1494  TSK_FS_FILE_READ_OFFSET_TYPE_ENUM(int val) {
1495  this.val = val;
1496  }
1497 
1498  int getValue() {
1499  return val;
1500  }
1501  }
1502 
1517  public static int readFile(long fileHandle, byte[] readBuffer, long offset, long len) throws TskCoreException {
1518  boolean withinPool = false;
1519  synchronized (HandleCache.cacheLock) {
1520  if (HandleCache.poolFileHandles.contains(fileHandle)) {
1521  withinPool = true;
1522  }
1523  }
1524 
1525  /*
1526  * The current APFS code is not thread-safe. To compensate, we make any
1527  * reads to the APFS pool single-threaded by obtaining a write
1528  * lock instead of a read lock.
1529  */
1530  if (withinPool) {
1531  getTSKWriteLock();
1532  } else {
1533  getTSKReadLock();
1534  }
1535  try {
1536  if (!HandleCache.isValidFileHandle(fileHandle)) {
1537  throw new TskCoreException(HandleCache.INVALID_FILE_HANDLE);
1538  }
1539 
1540  return readFileNat(fileHandle, readBuffer, offset, TSK_FS_FILE_READ_OFFSET_TYPE_ENUM.START_OF_FILE.getValue(), len);
1541  } finally {
1542  if (withinPool) {
1543  releaseTSKWriteLock();
1544  } else {
1545  releaseTSKReadLock();
1546  }
1547  }
1548  }
1549 
1564  public static int readFileSlack(long fileHandle, byte[] readBuffer, long offset, long len) throws TskCoreException {
1565  getTSKReadLock();
1566  try {
1567  if (!HandleCache.isValidFileHandle(fileHandle)) {
1568  throw new TskCoreException(HandleCache.INVALID_FILE_HANDLE);
1569  }
1570 
1571  return readFileNat(fileHandle, readBuffer, offset, TSK_FS_FILE_READ_OFFSET_TYPE_ENUM.START_OF_SLACK.getValue(), len);
1572  } finally {
1573  releaseTSKReadLock();
1574  }
1575  }
1576 
1587  public static List<String> getFileMetaDataText(long fileHandle) throws TskCoreException {
1588  getTSKReadLock();
1589  try {
1590  if (!HandleCache.isValidFileHandle(fileHandle)) {
1591  throw new TskCoreException(HandleCache.INVALID_FILE_HANDLE);
1592  }
1593 
1594  try {
1595  java.io.File tmp = java.io.File.createTempFile("tsk", ".txt");
1596 
1597  saveFileMetaDataTextNat(fileHandle, tmp.getAbsolutePath());
1598 
1599  FileReader fr = new FileReader(tmp.getAbsolutePath());
1600  BufferedReader textReader = new BufferedReader(fr);
1601 
1602  List<String> lines = new ArrayList<String>();
1603  while (true) {
1604  String line = textReader.readLine();
1605  if (line == null) {
1606  break;
1607  }
1608  lines.add(line);
1609  }
1610  textReader.close();
1611  fr.close();
1612  tmp.delete();
1613  return lines;
1614  } catch (IOException ex) {
1615  throw new TskCoreException("Error reading istat output: " + ex.getLocalizedMessage());
1616  }
1617  } finally {
1618  releaseTSKReadLock();
1619  }
1620  }
1621 
1627  public static void closeFile(long fileHandle) {
1628  closeFile(fileHandle, null);
1629  }
1630 
1637  public static void closeFile(long fileHandle, SleuthkitCase skCase) {
1638  boolean withinPool = false;
1639  synchronized (HandleCache.cacheLock) {
1640  if (HandleCache.poolFileHandles.contains(fileHandle)) {
1641  withinPool = true;
1642  }
1643  }
1644 
1645  /*
1646  * The current APFS code is not thread-safe. To compensate, we make any
1647  * reads to the APFS pool single-threaded by obtaining a write
1648  * lock instead of a read lock.
1649  */
1650  if (withinPool) {
1651  getTSKWriteLock();
1652  } else {
1653  getTSKReadLock();
1654  }
1655  try {
1656  synchronized (HandleCache.cacheLock) {
1657  if (!HandleCache.isValidFileHandle(fileHandle)) {
1658  // File handle is not open so this is a no-op.
1659  return;
1660  }
1661  closeFileNat(fileHandle);
1662  HandleCache.removeFileHandle(fileHandle, skCase);
1663  if (HandleCache.poolFileHandles.contains(fileHandle)) {
1664  HandleCache.poolFileHandles.remove(fileHandle);
1665  }
1666  }
1667  } finally {
1668  if (withinPool) {
1669  releaseTSKWriteLock();
1670  } else {
1671  releaseTSKReadLock();
1672  }
1673  }
1674  }
1675 
1683  public static void createLookupIndexForHashDatabase(int dbHandle) throws TskCoreException {
1684  hashDbCreateIndexNat(dbHandle);
1685  }
1686 
1696  public static boolean hashDatabaseHasLookupIndex(int dbHandle) throws TskCoreException {
1697  return hashDbIndexExistsNat(dbHandle);
1698  }
1699 
1710  public static boolean hashDatabaseCanBeReindexed(int dbHandle) throws TskCoreException {
1711  return hashDbIsReindexableNat(dbHandle);
1712  }
1713 
1723  public static String getHashDatabasePath(int dbHandle) throws TskCoreException {
1724  return hashDbPathNat(dbHandle);
1725  }
1726 
1736  public static String getHashDatabaseIndexPath(int dbHandle) throws TskCoreException {
1737  return hashDbIndexPathNat(dbHandle);
1738  }
1739 
1746  public static int openHashDatabase(String path) throws TskCoreException {
1747  return hashDbOpenNat(path);
1748  }
1749 
1759  public static int createHashDatabase(String path) throws TskCoreException {
1760  return hashDbNewNat(path);
1761  }
1762 
1769  public static void closeAllHashDatabases() throws TskCoreException {
1770  hashDbCloseAll();
1771  }
1772 
1782  public static void closeHashDatabase(int dbHandle) throws TskCoreException {
1783  hashDbClose(dbHandle);
1784  }
1785 
1795  public static String getHashDatabaseDisplayName(int dbHandle) throws TskCoreException {
1796  return hashDbGetDisplayName(dbHandle);
1797  }
1798 
1809  public static boolean lookupInHashDatabase(String hash, int dbHandle) throws TskCoreException {
1810  return hashDbLookup(hash, dbHandle);
1811  }
1812 
1824  public static HashHitInfo lookupInHashDatabaseVerbose(String hash, int dbHandle) throws TskCoreException {
1825  return hashDbLookupVerbose(hash, dbHandle);
1826  }
1827 
1840  public static void addToHashDatabase(String filename, String md5, String sha1, String sha256, String comment, int dbHandle) throws TskCoreException {
1841  hashDbAddEntryNat(filename, md5, sha1, sha256, comment, dbHandle);
1842  }
1843 
1844  public static void addToHashDatabase(List<HashEntry> hashes, int dbHandle) throws TskCoreException {
1845  hashDbBeginTransactionNat(dbHandle);
1846  try {
1847  for (HashEntry entry : hashes) {
1848  hashDbAddEntryNat(entry.getFileName(), entry.getMd5Hash(), entry.getSha1Hash(), entry.getSha256Hash(), entry.getComment(), dbHandle);
1849  }
1850  hashDbCommitTransactionNat(dbHandle);
1851  } catch (TskCoreException ex) {
1852  try {
1853  hashDbRollbackTransactionNat(dbHandle);
1854  } catch (TskCoreException ex2) {
1855  ex2.initCause(ex);
1856  throw ex2;
1857  }
1858  throw ex;
1859  }
1860  }
1861 
1862  public static boolean isUpdateableHashDatabase(int dbHandle) throws TskCoreException {
1863  return hashDbIsUpdateableNat(dbHandle);
1864  }
1865 
1866  public static boolean hashDatabaseIsIndexOnly(int dbHandle) throws TskCoreException {
1867  return hashDbIsIdxOnlyNat(dbHandle);
1868  }
1869 
1879  private static String timezoneLongToShort(String timezoneLongForm) {
1880  if (timezoneLongForm == null || timezoneLongForm.isEmpty()) {
1881  return "";
1882  }
1883 
1884  String timezoneShortForm;
1885  TimeZone zone = TimeZone.getTimeZone(timezoneLongForm);
1886  int offset = zone.getRawOffset() / 1000;
1887  int hour = offset / 3600;
1888  int min = (offset % 3600) / 60;
1889  DateFormat dfm = new SimpleDateFormat("z");
1890  dfm.setTimeZone(zone);
1891  boolean hasDaylight = zone.useDaylightTime();
1892  String first = dfm.format(new GregorianCalendar(2010, 1, 1).getTime()).substring(0, 3); // make it only 3 letters code
1893  String second = dfm.format(new GregorianCalendar(2011, 6, 6).getTime()).substring(0, 3); // make it only 3 letters code
1894  int mid = hour * -1;
1895  timezoneShortForm = first + Integer.toString(mid);
1896  if (min != 0) {
1897  timezoneShortForm = timezoneShortForm + ":" + (min < 10 ? "0" : "") + Integer.toString(min);
1898  }
1899  if (hasDaylight) {
1900  timezoneShortForm += second;
1901  }
1902  return timezoneShortForm;
1903  }
1904 
1915  public static int finishImageWriter(long imgHandle) throws TskCoreException {
1916  getTSKReadLock();
1917  try {
1918  if(! imgHandleIsValid(imgHandle)) {
1919  throw new TskCoreException("Image handle " + imgHandle + " is closed");
1920  }
1921  return finishImageWriterNat(imgHandle);
1922  } finally {
1923  releaseTSKReadLock();
1924  }
1925  }
1926 
1934  public static int getFinishImageProgress(long imgHandle) {
1935  getTSKReadLock();
1936  try {
1937  if (imgHandleIsValid(imgHandle)) {
1938  return getFinishImageProgressNat(imgHandle);
1939  } else {
1940  return 0;
1941  }
1942  } finally {
1943  releaseTSKReadLock();
1944  }
1945  }
1946 
1952  public static void cancelFinishImage(long imgHandle) {
1953  getTSKReadLock();
1954  try {
1955  if (imgHandleIsValid(imgHandle)) {
1956  cancelFinishImageNat(imgHandle);
1957  }
1958  } finally {
1959  releaseTSKReadLock();
1960  }
1961  }
1962 
1974  public static long findDeviceSize(String devPath) throws TskCoreException {
1975  return findDeviceSizeNat(devPath);
1976  }
1977 
1978  public static boolean isImageSupported(String imagePath) {
1979  // isImageSupportedStringNat returns a blank string if the image is supported or
1980  // an error message if the file systems could not be opened
1981  return isImageSupportedStringNat(imagePath, "").isBlank();
1982  }
1983 
1987  public static class TestOpenImageResult {
1988  boolean testSuccess;
1989  String message;
1990 
1991  TestOpenImageResult(boolean testSuccess, String message) {
1992  this.testSuccess = testSuccess;
1993  this.message = message;
1994  }
1995 
1996  // True if we were able to open at least one file system in the given image
1997  public boolean wasSuccessful() {
1998  return testSuccess;
1999  }
2000 
2001  // Contains a user-friendly status message. On success, will contain "Image opened successfully".
2002  // Otherwise it will give our best effort to explain why we were unsuccessful.
2003  public String getMessage() {
2004  return message;
2005  }
2006  }
2007 
2016  public static TestOpenImageResult testOpenImage(String imagePath, String password) {
2017  String resultStr = isImageSupportedStringNat(imagePath, password);
2018  if (resultStr.isBlank()) {
2019  return new TestOpenImageResult(true, "Image opened successfully");
2020  }
2021  return new TestOpenImageResult(false, resultStr);
2022  }
2023 
2037  static long getSleuthkitVersion() {
2038  return getSleuthkitVersionNat();
2039  }
2040 
2045  private static void getTSKReadLock() {
2046  tskLock.readLock().lock();
2047  }
2048 
2052  private static void releaseTSKReadLock() {
2053  tskLock.readLock().unlock();
2054  }
2055 
2063  private static void getTSKWriteLock() {
2064  tskLock.writeLock().lock();
2065  }
2066 
2070  private static void releaseTSKWriteLock() {
2071  tskLock.writeLock().unlock();
2072  }
2073 
2074  //free pointers
2081  @Deprecated
2082  public static void closeImg(long imgHandle) {
2083  //closeImgNat(imgHandle);
2084  }
2085 
2091  @Deprecated
2092  public static void closeVs(long vsHandle) {
2093  // closeVsNat(vsHandle); TODO JIRA-3829
2094  }
2095 
2102  @Deprecated
2103  public static void closeFs(long fsHandle) {
2104  //closeFsNat(fsHandle);
2105  }
2106 
2118  @Deprecated
2119  public static long openImage(String[] imageFiles) throws TskCoreException {
2120 
2121  return openImage(imageFiles, 0, true, null);
2122  }
2123 
2137  @Deprecated
2138  public static long openImage(String[] imageFiles, int sSize) throws TskCoreException {
2139  return openImage(imageFiles, sSize, true, null);
2140  }
2141 
2142 
2156  @Deprecated
2157  public static long openFs(long imgHandle, long fsOffset) throws TskCoreException {
2158  return openFs(imgHandle, fsOffset, null);
2159  }
2160 
2175  @Deprecated
2176  public static long openFile(long fsHandle, long fileId, TSK_FS_ATTR_TYPE_ENUM attrType, int attrId) throws TskCoreException {
2177  return openFile(fsHandle, fileId, attrType, attrId, null);
2178  }
2179 
2180 
2181  private static native String getVersionNat();
2182 
2183  private static native void startVerboseLoggingNat(String logPath);
2184 
2185  private static native int hashDbOpenNat(String hashDbPath) throws TskCoreException;
2186 
2187  private static native int hashDbNewNat(String hashDbPath) throws TskCoreException;
2188 
2189  private static native int hashDbBeginTransactionNat(int dbHandle) throws TskCoreException;
2190 
2191  private static native int hashDbCommitTransactionNat(int dbHandle) throws TskCoreException;
2192 
2193  private static native int hashDbRollbackTransactionNat(int dbHandle) throws TskCoreException;
2194 
2195  private static native int hashDbAddEntryNat(String filename, String hashMd5, String hashSha1, String hashSha256, String comment, int dbHandle) throws TskCoreException;
2196 
2197  private static native boolean hashDbIsUpdateableNat(int dbHandle);
2198 
2199  private static native boolean hashDbIsReindexableNat(int dbHandle);
2200 
2201  private static native String hashDbPathNat(int dbHandle);
2202 
2203  private static native String hashDbIndexPathNat(int dbHandle);
2204 
2205  private static native String hashDbGetDisplayName(int dbHandle) throws TskCoreException;
2206 
2207  private static native void hashDbCloseAll() throws TskCoreException;
2208 
2209  private static native void hashDbClose(int dbHandle) throws TskCoreException;
2210 
2211  private static native void hashDbCreateIndexNat(int dbHandle) throws TskCoreException;
2212 
2213  private static native boolean hashDbIndexExistsNat(int dbHandle) throws TskCoreException;
2214 
2215  private static native boolean hashDbIsIdxOnlyNat(int dbHandle) throws TskCoreException;
2216 
2217  private static native boolean hashDbLookup(String hash, int dbHandle) throws TskCoreException;
2218 
2219  private static native HashHitInfo hashDbLookupVerbose(String hash, int dbHandle) throws TskCoreException;
2220 
2221  private static native long initAddImgNat(TskCaseDbBridge dbHelperObj, String timezone, boolean addUnallocSpace, boolean skipFatFsOrphans) throws TskCoreException;
2222 
2223  private static native long initAddImgNatPassword(TskCaseDbBridge dbHelperObj, String timezone, boolean addUnallocSpace, boolean skipFatFsOrphans, String password) throws TskCoreException;
2224 
2225  private static native long initializeAddImgNat(TskCaseDbBridge dbHelperObj, String timezone, boolean addFileSystems, boolean addUnallocSpace, boolean skipFatFsOrphans) throws TskCoreException;
2226 
2227  private static native long initializeAddImgPasswordNat(TskCaseDbBridge dbHelperObj, String timezone, boolean addFileSystems, boolean addUnallocSpace, boolean skipFatFsOrphans, String password) throws TskCoreException;
2228 
2229  private static native void runOpenAndAddImgNat(long process, String deviceId, String[] imgPath, int splits, String timezone) throws TskCoreException, TskDataException;
2230 
2231  private static native void runAddImgNat(long process, String deviceId, long a_img_info, long image_id, String timeZone, String imageWriterPath) throws TskCoreException, TskDataException;
2232 
2233  private static native void stopAddImgNat(long process) throws TskCoreException;
2234 
2235  private static native long finishAddImgNat(long process) throws TskCoreException;
2236 
2237  private static native long openImgNat(String[] imgPath, int splits, int sSize) throws TskCoreException;
2238 
2239  private static native long openVsNat(long imgHandle, long vsOffset) throws TskCoreException;
2240 
2241  private static native long openVolNat(long vsHandle, long volId) throws TskCoreException;
2242 
2243  private static native long openPoolNat(long imgHandle, long offset) throws TskCoreException;
2244 
2245  private static native long getImgInfoForPoolNat(long poolHandle, long poolOffset) throws TskCoreException;
2246 
2247  private static native long openFsNat(long imgHandle, long fsId) throws TskCoreException;
2248 
2249  private static native long openFsDecryptNat(long imgHandle, long fsId, String password) throws TskCoreException;
2250 
2251  private static native long openFileNat(long fsHandle, long fileId, int attrType, int attrId) throws TskCoreException;
2252 
2253  private static native int readImgNat(long imgHandle, byte[] readBuffer, long offset, long len) throws TskCoreException;
2254 
2255  private static native int readVsNat(long vsHandle, byte[] readBuffer, long offset, long len) throws TskCoreException;
2256 
2257  private static native int readPoolNat(long poolHandle, byte[] readBuffer, long offset, long len) throws TskCoreException;
2258 
2259  private static native int readVolNat(long volHandle, byte[] readBuffer, long offset, long len) throws TskCoreException;
2260 
2261  private static native int readFsNat(long fsHandle, byte[] readBuffer, long offset, long len) throws TskCoreException;
2262 
2263  private static native int readFileNat(long fileHandle, byte[] readBuffer, long offset, int offset_type, long len) throws TskCoreException;
2264 
2265  private static native int saveFileMetaDataTextNat(long fileHandle, String fileName) throws TskCoreException;
2266 
2267  private static native String[] getPathsForImageNat(long imgHandle);
2268 
2269  private static native long getSizeForImageNat(long imgHandle);
2270 
2271  private static native long getTypeForImageNat(long imgHandle);
2272 
2273  private static native long getSectorSizeForImageNat(long imgHandle);
2274 
2275  private static native String getMD5HashForImageNat(long imgHandle);
2276 
2277  private static native String getSha1HashForImageNat(long imgHandle);
2278 
2279  private static native String getCollectionDetailsForImageNat(long imgHandle);
2280 
2281  private static native void closeImgNat(long imgHandle);
2282 
2283  private static native void closePoolNat(long poolHandle);
2284 
2285  private static native void closeVsNat(long vsHandle);
2286 
2287  private static native void closeFsNat(long fsHandle);
2288 
2289  private static native void closeFileNat(long fileHandle);
2290 
2291  private static native long findDeviceSizeNat(String devicePath) throws TskCoreException;
2292 
2293  private static native String getCurDirNat(long process);
2294 
2295  private static native String isImageSupportedStringNat(String imagePath, String password);
2296 
2297  private static native long getSleuthkitVersionNat();
2298 
2299  private static native int finishImageWriterNat(long a_img_info);
2300 
2301  private static native int getFinishImageProgressNat(long a_img_info);
2302 
2303  private static native void cancelFinishImageNat(long a_img_info);
2304 
2305 }
static int readImg(long imgHandle, byte[] readBuffer, long offset, long len)
static String getHashDatabaseIndexPath(int dbHandle)
static int readVs(long vsHandle, byte[] readBuffer, long offset, long len)
static void createLookupIndexForHashDatabase(int dbHandle)
void run(String deviceId, Image image, int sectorSize, AddDataSourceCallbacks addDataSourceCallbacks)
static void addToHashDatabase(String filename, String md5, String sha1, String sha256, String comment, int dbHandle)
static long openFs(long imgHandle, long fsOffset, String password, SleuthkitCase skCase)
static long openFile(long fsHandle, long fileId, TSK_FS_ATTR_TYPE_ENUM attrType, int attrId, SleuthkitCase skCase)
static int createHashDatabase(String path)
static void closeFs(long fsHandle)
static void cancelFinishImage(long imgHandle)
static long openFile(long fsHandle, long fileId, TSK_FS_ATTR_TYPE_ENUM attrType, int attrId)
void run(String deviceId, String[] imageFilePaths)
static int readFile(long fileHandle, byte[] readBuffer, long offset, long len)
static int finishImageWriter(long imgHandle)
static HashHitInfo lookupInHashDatabaseVerbose(String hash, int dbHandle)
static long openVs(long imgHandle, long vsOffset)
static long openImage(String[] imageFiles, SleuthkitCase skCase)
static boolean hashDatabaseIsIndexOnly(int dbHandle)
static boolean isImageSupported(String imagePath)
static int readVsPart(long volHandle, byte[] readBuffer, long offset, long len)
static void closeFile(long fileHandle, SleuthkitCase skCase)
static long openImage(String[] imageFiles, int sSize)
static void closeVs(long vsHandle)
static long openImage(String[] imageFiles)
static long openFs(long imgHandle, long fsOffset, SleuthkitCase skCase)
static long openImage(String[] imageFiles, int sSize, SleuthkitCase skCase)
void run(String deviceId, String[] imageFilePaths, int sectorSize)
Definition: HashEntry.java:25
static Image addImageToDatabase(SleuthkitCase skCase, String[] imagePaths, int sectorSize, String timeZone, String md5fromSettings, String sha1fromSettings, String sha256fromSettings, String deviceId, Host host)
static long findDeviceSize(String devPath)
static String getHashDatabaseDisplayName(int dbHandle)
static TestOpenImageResult testOpenImage(String imagePath, String password)
static List< String > getFileMetaDataText(long fileHandle)
static void closeImg(long imgHandle)
static long openFs(long imgHandle, long fsOffset)
Image addImage(TskData.TSK_IMG_TYPE_ENUM type, long sectorSize, long size, String displayName, List< String > imagePaths, String timezone, String md5, String sha1, String sha256, String deviceId, CaseDbTransaction transaction)
static int getFinishImageProgress(long imgHandle)
static int openHashDatabase(String path)
static void closeFile(long fileHandle)
static boolean lookupInHashDatabase(String hash, int dbHandle)
static TSK_IMG_TYPE_ENUM valueOf(long imgType)
Definition: TskData.java:549
static boolean hashDatabaseHasLookupIndex(int dbHandle)
static Image addImageToDatabase(SleuthkitCase skCase, String[] imagePaths, int sectorSize, String timeZone, String md5fromSettings, String sha1fromSettings, String sha256fromSettings, String deviceId)
static Image addImageToDatabase(SleuthkitCase skCase, String[] imagePaths, int sectorSize, String timeZone, String md5fromSettings, String sha1fromSettings, String sha256fromSettings, String deviceId, String password, Host host)
static long openVsPart(long vsHandle, long volId)
static int readFileSlack(long fileHandle, byte[] readBuffer, long offset, long len)
static boolean isUpdateableHashDatabase(int dbHandle)
static void addToHashDatabase(List< HashEntry > hashes, int dbHandle)
static boolean hashDatabaseCanBeReindexed(int dbHandle)
static void startVerboseLogging(String logPath)
static int readFs(long fsHandle, byte[] readBuffer, long offset, long len)
static String getHashDatabasePath(int dbHandle)
static void closeHashDatabase(int dbHandle)

Copyright © 2011-2024 Brian Carrier. (carrier -at- sleuthkit -dot- org)
This work is licensed under a Creative Commons Attribution-Share Alike 3.0 United States License.