use of com.biglybt.core.download.DownloadManager in project BiglyBT by BiglySoftware.
the class NameItem method refresh.
@Override
public void refresh(TableCell cell, boolean sortOnlyRefresh) {
String name = null;
DownloadManager dm = (DownloadManager) cell.getDataSource();
if (dm != null)
name = dm.getDisplayName();
if (name == null)
name = "";
// setText returns true only if the text is updated
if ((cell.setText(name) || !cell.isValid())) {
if (dm != null && isShowIcon() && !sortOnlyRefresh && (cell instanceof TableCellSWT)) {
DiskManagerFileInfo fileInfo = dm.getDownloadState().getPrimaryFile();
if (fileInfo != null) {
// Don't ever dispose of PathIcon, it's cached and may be used elsewhere
TOTorrent torrent = dm.getTorrent();
Image icon = ImageRepository.getPathIcon(fileInfo.getFile(false).getName(), false, torrent != null && !torrent.isSimpleTorrent());
((TableCellSWT) cell).setIcon(icon);
}
}
}
}
use of com.biglybt.core.download.DownloadManager in project BiglyBT by BiglySoftware.
the class NetworksItem method refresh.
@Override
public void refresh(TableCell cell) {
String networks = "";
DownloadManager dm = (DownloadManager) cell.getDataSource();
if (dm != null) {
String[] nets = dm.getDownloadState().getNetworks();
for (int i = 0; i < nets.length; i++) {
networks += (i == 0 ? "" : ",") + nets[i];
}
}
cell.setText(networks);
}
use of com.biglybt.core.download.DownloadManager in project BiglyBT by BiglySoftware.
the class CategoryItem method refresh.
@Override
public void refresh(TableCell cell) {
TRHostTorrent tr_torrent = (TRHostTorrent) cell.getDataSource();
if (tr_torrent == null) {
cell.setText("");
} else {
TOTorrent torrent = tr_torrent.getTorrent();
if (gm == null) {
if (CoreFactory.isCoreRunning()) {
return;
}
gm = CoreFactory.getSingleton().getGlobalManager();
}
DownloadManager dm = gm.getDownloadManager(torrent);
String cat_str = null;
if (dm != null) {
Category cat = dm.getDownloadState().getCategory();
if (cat != null) {
cat_str = cat.getName();
}
} else {
// pick up specific torrent category, bit 'o' a hack tis
cat_str = TorrentUtils.getPluginStringProperty(torrent, "azcoreplugins.category");
}
cell.setText(cat_str == null ? "" : cat_str);
}
}
use of com.biglybt.core.download.DownloadManager in project BiglyBT by BiglySoftware.
the class ManagerUtils method asyncPauseForPeriod.
public static void asyncPauseForPeriod(final List<DownloadManager> dms, final int seconds) {
CoreWaiterSWT.waitForCore(TriggerInThread.NEW_THREAD, new CoreRunningListener() {
@Override
public void coreRunning(Core core) {
final List<DownloadManager> paused = new ArrayList<>();
final DownloadManagerListener listener = new DownloadManagerAdapter() {
@Override
public void stateChanged(DownloadManager manager, int state) {
synchronized (paused) {
if (!paused.remove(manager)) {
return;
}
}
manager.removeListener(this);
}
};
long target_time = SystemTime.getOffsetTime(seconds * 1000);
String time_str = new SimpleDateFormat("HH:mm:ss").format(new Date(target_time));
String reason = MessageText.getString("label.resuming.at", new String[] { time_str });
for (DownloadManager dm : dms) {
if (!isPauseable(dm)) {
continue;
}
if (dm.pause(target_time)) {
dm.setStopReason(reason);
synchronized (paused) {
paused.add(dm);
}
dm.addListener(listener, false);
}
}
if (paused.size() > 0) {
SimpleTimer.addEvent("ManagerUtils.resumer", target_time, new TimerEventPerformer() {
@Override
public void perform(TimerEvent event) {
List<DownloadManager> to_resume = new ArrayList<>();
synchronized (paused) {
to_resume.addAll(paused);
paused.clear();
}
for (DownloadManager dm : to_resume) {
dm.removeListener(listener);
try {
dm.resume();
} catch (Throwable e) {
Debug.out(e);
}
}
}
});
}
}
});
}
use of com.biglybt.core.download.DownloadManager in project BiglyBT by BiglySoftware.
the class ManagerUtils method locateFiles.
public static void locateFiles(final DownloadManager[] dms, final DiskManagerFileInfo[][] dm_files, Shell shell) {
DirectoryDialog dd = new DirectoryDialog(shell);
dd.setFilterPath(TorrentOpener.getFilterPathData());
dd.setText(MessageText.getString("MyTorrentsView.menu.locatefiles.dialog"));
String path = dd.open();
if (path != null) {
TorrentOpener.setFilterPathData(path);
final File dir = new File(path);
final TextViewerWindow viewer = new TextViewerWindow(MessageText.getString("locatefiles.view.title"), null, "", true, true);
viewer.setEditable(false);
viewer.setOKEnabled(true);
new AEThread2("FileLocator") {
@Override
public void run() {
final int MAX_LINKS = DownloadManagerStateFactory.MAX_FILES_FOR_INCOMPLETE_AND_DND_LINKAGE;
final String LINK_LIMIT_MSG = "Link limit of " + MAX_LINKS + " exceeded. See Tools->Options->Files to increase this";
try {
Map<Long, Set<File>> file_map = new HashMap<>();
final boolean[] quit = { false };
viewer.addListener(new TextViewerWindow.TextViewerWindowListener() {
@Override
public void closed() {
synchronized (quit) {
quit[0] = true;
}
}
});
logLine(viewer, new SimpleDateFormat().format(new Date()) + ": Enumerating files in " + dir);
long bfm_start = SystemTime.getMonotonousTime();
long[] last_log = { bfm_start };
int file_count = buildFileMap(viewer, dir, file_map, last_log, quit);
logLine(viewer, (bfm_start == last_log[0] ? "" : "\r\n") + "Found " + file_count + " files with " + file_map.size() + " distinct sizes");
Set<String> all_dm_incomplete_files = null;
ConcurrentHasher hasher = ConcurrentHasher.getSingleton();
int downloads_modified = 0;
for (int i = 0; i < dms.length; i++) {
DownloadManager dm = dms[i];
synchronized (quit) {
if (quit[0]) {
break;
}
}
if (!dm.isPersistent()) {
continue;
}
TOTorrent torrent = dm.getTorrent();
if (torrent == null) {
continue;
}
DiskManagerFileInfo[] selected_files = dm_files == null ? null : dm_files[i];
Set<Integer> selected_file_indexes;
if (selected_files == null) {
selected_file_indexes = null;
} else {
selected_file_indexes = new HashSet<>();
for (DiskManagerFileInfo f : selected_files) {
selected_file_indexes.add(f.getIndex());
}
}
TOTorrentFile[] to_files = torrent.getFiles();
long piece_size = torrent.getPieceLength();
byte[][] pieces = torrent.getPieces();
logLine(viewer, "Processing '" + dm.getDisplayName() + "', piece size=" + DisplayFormatters.formatByteCountToKiBEtc(piece_size));
int dm_state = dm.getState();
if (!(dm_state == DownloadManager.STATE_STOPPED || dm_state == DownloadManager.STATE_ERROR)) {
logLine(viewer, " Download must be stopped");
continue;
}
DiskManagerFileInfo[] files = dm.getDiskManagerFileInfoSet().getFiles();
Set<String> dm_files = null;
Map<DiskManagerFileInfo, File> links_established = new HashMap<>();
Map<DiskManagerFileInfo, Set<String>> unmatched_files = new TreeMap<>(new Comparator<DiskManagerFileInfo>() {
@Override
public int compare(DiskManagerFileInfo o1, DiskManagerFileInfo o2) {
long diff = o2.getLength() - o1.getLength();
if (diff < 0) {
return (-1);
} else if (diff > 0) {
return (1);
} else {
return (0);
}
}
});
int no_candidates = 0;
int already_complete = 0;
int link_count = 0;
try {
download_loop: for (final DiskManagerFileInfo file : files) {
synchronized (quit) {
if (quit[0]) {
break;
}
}
if (selected_file_indexes != null) {
if (!selected_file_indexes.contains(file.getIndex())) {
continue;
}
}
long file_length = file.getLength();
if (file.getDownloaded() == file_length) {
already_complete++;
continue;
}
Set<File> candidates = file_map.get(file_length);
if (candidates != null) {
if (candidates.size() > 0) {
if (all_dm_incomplete_files == null) {
all_dm_incomplete_files = new HashSet<>();
List<DownloadManager> all_dms = CoreFactory.getSingleton().getGlobalManager().getDownloadManagers();
for (DownloadManager x : all_dms) {
if (!x.isDownloadComplete(false)) {
DiskManagerFileInfo[] fs = x.getDiskManagerFileInfoSet().getFiles();
for (DiskManagerFileInfo f : fs) {
if (f.isSkipped() || f.getDownloaded() != f.getLength()) {
all_dm_incomplete_files.add(f.getFile(true).getAbsolutePath());
}
}
}
}
}
Iterator<File> it = candidates.iterator();
while (it.hasNext()) {
File f = it.next();
if (all_dm_incomplete_files.contains(f.getAbsolutePath())) {
it.remove();
}
}
}
if (candidates.size() > 0) {
// duplicate now as this is download-specific
candidates = new HashSet<>(candidates);
if (dm_files == null) {
dm_files = new HashSet<>();
for (DiskManagerFileInfo f : files) {
dm_files.add(f.getFile(true).getAbsolutePath());
}
}
Iterator<File> it = candidates.iterator();
while (it.hasNext()) {
File f = it.next();
if (dm_files.contains(f.getAbsolutePath())) {
it.remove();
}
}
}
if (candidates.size() > 0) {
boolean matched = false;
Set<String> failed_candidates = new HashSet<>();
TOTorrentFile to_file = file.getTorrentFile();
long offset = 0;
for (TOTorrentFile tf : to_files) {
if (tf == to_file) {
break;
}
offset += tf.getLength();
}
int to_piece_number = to_file.getFirstPieceNumber();
long to_file_offset = offset % piece_size;
if (to_file_offset != 0) {
to_file_offset = piece_size - to_file_offset;
to_piece_number++;
}
long to_stop_at = file_length - piece_size;
if (to_file_offset < to_stop_at) {
logLine(viewer, " " + candidates.size() + " candidate(s) for " + to_file.getRelativePath() + " (size=" + DisplayFormatters.formatByteCountToKiBEtc(to_file.getLength()) + ")");
byte[] buffer = new byte[(int) piece_size];
for (File candidate : candidates) {
synchronized (quit) {
if (quit[0]) {
break;
}
}
log(viewer, " Testing " + candidate);
RandomAccessFile raf = null;
boolean error = false;
boolean hash_failed = false;
long last_ok_log = SystemTime.getMonotonousTime();
try {
raf = new RandomAccessFile(candidate, "r");
long file_offset = to_file_offset;
int piece_number = to_piece_number;
while (file_offset < to_stop_at) {
synchronized (quit) {
if (quit[0]) {
break;
}
}
raf.seek(file_offset);
raf.read(buffer);
ConcurrentHasherRequest req = hasher.addRequest(ByteBuffer.wrap(buffer));
byte[] hash = req.getResult();
boolean match = Arrays.equals(pieces[piece_number], hash);
if (match) {
long now = SystemTime.getMonotonousTime();
if (now - last_ok_log >= 250) {
last_ok_log = now;
log(viewer, ".");
}
file_offset += piece_size;
piece_number++;
} else {
hash_failed = true;
failed_candidates.add(candidate.getAbsolutePath());
logLine(viewer, "X");
break;
}
}
} catch (Throwable e) {
logLine(viewer, "X");
error = true;
} finally {
if (raf != null) {
try {
raf.close();
} catch (Throwable e) {
}
}
}
if (!(error || hash_failed)) {
logLine(viewer, " Matched");
try {
dm.setUserData("set_link_dont_delete_existing", true);
if (file.setLink(candidate)) {
logLine(viewer, " Link successful");
links_established.put(file, candidate);
link_count++;
matched = true;
if (link_count > MAX_LINKS) {
logLine(viewer, " " + LINK_LIMIT_MSG);
break download_loop;
}
} else {
logLine(viewer, " Link failed");
}
} finally {
dm.setUserData("set_link_dont_delete_existing", null);
}
break;
}
}
}
if (!matched) {
unmatched_files.put(file, failed_candidates);
}
} else {
no_candidates++;
}
} else {
no_candidates++;
}
}
logLine(viewer, " Matched=" + links_established.size() + ", complete=" + already_complete + ", no candidates=" + no_candidates + ", remaining=" + unmatched_files.size() + " (total=" + files.length + ")");
if (links_established.size() > 0 && unmatched_files.size() > 0) {
logLine(viewer, " Looking for other potential name-based matches");
File overall_root = null;
for (Map.Entry<DiskManagerFileInfo, File> entry : links_established.entrySet()) {
DiskManagerFileInfo dm_file = entry.getKey();
File root = entry.getValue();
String rel = dm_file.getTorrentFile().getRelativePath();
int pos = 0;
while (root != null) {
root = root.getParentFile();
pos = rel.indexOf(File.separatorChar, pos);
if (pos >= 0) {
pos = pos + 1;
} else {
break;
}
}
if (root == null) {
logLine(viewer, " No usable root folder found");
break;
}
if (overall_root == null) {
overall_root = root;
} else {
if (!overall_root.equals(root)) {
overall_root = null;
logLine(viewer, " Inconsistent root folder found");
break;
}
}
}
if (overall_root != null) {
logLine(viewer, " Root folder is " + overall_root.getAbsolutePath());
int links_ok = 0;
for (Map.Entry<DiskManagerFileInfo, Set<String>> entry : unmatched_files.entrySet()) {
synchronized (quit) {
if (quit[0]) {
break;
}
}
DiskManagerFileInfo file = entry.getKey();
if (selected_file_indexes != null) {
if (!selected_file_indexes.contains(file.getIndex())) {
continue;
}
}
File expected_file = new File(overall_root, file.getTorrentFile().getRelativePath());
if (expected_file.exists() && expected_file.length() == file.getLength()) {
if (!entry.getValue().contains(expected_file.getAbsolutePath())) {
try {
dm.setUserData("set_link_dont_delete_existing", true);
if (file.setLink(expected_file)) {
links_ok++;
link_count++;
if (link_count > MAX_LINKS) {
logLine(viewer, " " + LINK_LIMIT_MSG);
break;
}
}
} finally {
dm.setUserData("set_link_dont_delete_existing", null);
}
}
}
}
logLine(viewer, " Linked " + links_ok + " of " + unmatched_files.size());
}
}
} finally {
if (link_count > 0) {
dm.forceRecheck();
downloads_modified++;
}
}
}
logLine(viewer, new SimpleDateFormat().format(new Date()) + ": Complete, downloads updated=" + downloads_modified);
} catch (Throwable e) {
log(viewer, "\r\n" + new SimpleDateFormat().format(new Date()) + ": Failed: " + Debug.getNestedExceptionMessage(e) + "\r\n");
}
}
}.start();
viewer.goModal();
}
}
Aggregations