use of com.biglybt.plugin.dht.DHTPluginOperationListener in project BiglyBT by BiglySoftware.
the class DHTTrackerPlugin method processNonRegistrations.
protected void processNonRegistrations() {
Download ready_download = null;
long ready_download_next_check = -1;
long now = plugin_interface.getUtilities().getCurrentSystemTime();
// unfortunately getting scrape results can acquire locks and there is a vague
// possibility of deadlock here, so pre-fetch the scrape results
List<Download> to_scrape = new ArrayList<>();
try {
this_mon.enter();
Iterator<Download> it = interesting_downloads.keySet().iterator();
while (it.hasNext() && ready_download == null) {
Download download = it.next();
Torrent torrent = download.getTorrent();
if (torrent == null) {
continue;
}
int[] run_data = running_downloads.get(download);
if (run_data == null || run_data[0] == REG_TYPE_DERIVED) {
// looks like we'll need the scrape below
to_scrape.add(download);
}
}
} finally {
this_mon.exit();
}
Map<Download, DownloadScrapeResult> scrapes = new HashMap<>();
for (int i = 0; i < to_scrape.size(); i++) {
Download download = (Download) to_scrape.get(i);
scrapes.put(download, download.getLastScrapeResult());
}
try {
this_mon.enter();
Iterator<Download> it = interesting_downloads.keySet().iterator();
while (it.hasNext() && ready_download == null) {
Download download = it.next();
Torrent torrent = download.getTorrent();
if (torrent == null) {
continue;
}
int[] run_data = running_downloads.get(download);
if (run_data == null || run_data[0] == REG_TYPE_DERIVED) {
boolean force = torrent.wasCreatedByUs();
if (!force) {
if (interesting_pub_max > 0 && interesting_published > interesting_pub_max) {
continue;
}
DownloadScrapeResult scrape = (DownloadScrapeResult) scrapes.get(download);
if (scrape == null) {
continue;
}
if (scrape.getSeedCount() + scrape.getNonSeedCount() > NUM_WANT) {
continue;
}
}
long target = ((Long) interesting_downloads.get(download)).longValue();
long check_period = TorrentUtils.isDecentralised(torrent.getAnnounceURL()) ? INTERESTING_DHT_CHECK_PERIOD : INTERESTING_CHECK_PERIOD;
if (target <= now) {
ready_download = download;
ready_download_next_check = now + check_period;
interesting_downloads.put(download, new Long(ready_download_next_check));
} else if (target - now > check_period) {
interesting_downloads.put(download, new Long(now + (target % check_period)));
}
}
}
} finally {
this_mon.exit();
}
if (ready_download != null) {
final Download f_ready_download = ready_download;
final Torrent torrent = ready_download.getTorrent();
if (ready_download.getFlag(Download.FLAG_METADATA_DOWNLOAD)) {
try {
this_mon.enter();
interesting_downloads.remove(f_ready_download);
} finally {
this_mon.exit();
}
} else if (dht.isDiversified(torrent.getHash())) {
try {
this_mon.enter();
interesting_downloads.remove(f_ready_download);
} finally {
this_mon.exit();
}
} else {
// System.out.println( "presence query for " + ready_download.getName());
final long start = now;
final long f_next_check = ready_download_next_check;
dht.get(torrent.getHash(), "Presence query for '" + ready_download.getName() + "'", (byte) 0, INTERESTING_AVAIL_MAX, ANNOUNCE_TIMEOUT, false, false, new DHTPluginOperationListener() {
private boolean diversified;
private int leechers = 0;
private int seeds = 0;
private int i2p_leechers = 0;
private int i2p_seeds = 0;
@Override
public boolean diversified() {
diversified = true;
return (false);
}
@Override
public void starts(byte[] key) {
}
@Override
public void valueRead(DHTPluginContact originator, DHTPluginValue value) {
boolean is_leecher = (value.getFlags() & DHTPlugin.FLAG_DOWNLOADING) == 1;
if (is_leecher) {
leechers++;
} else {
seeds++;
}
try {
String[] tokens = new String(value.getValue()).split(";");
for (int i = 1; i < tokens.length; i++) {
String token = tokens[i].trim();
if (token.length() > 0) {
if (!Character.isDigit(token.charAt(0))) {
String flag_str = token;
if (flag_str.contains("I")) {
if (is_leecher) {
i2p_leechers++;
} else {
i2p_seeds++;
}
}
}
}
}
} catch (Throwable e) {
}
}
@Override
public void valueWritten(DHTPluginContact target, DHTPluginValue value) {
}
@Override
public void complete(byte[] key, boolean timeout_occurred) {
// System.out.println( " presence query for " + f_ready_download.getName() + "->" + total + "/div = " + diversified );
int total = leechers + seeds;
log(torrent, "Presence query: availability=" + (total == INTERESTING_AVAIL_MAX ? (INTERESTING_AVAIL_MAX + "+") : (total + "")) + ",div=" + diversified + " (elapsed=" + TimeFormatter.formatColonMillis(SystemTime.getCurrentTime() - start) + ")");
if (diversified) {
try {
this_mon.enter();
interesting_downloads.remove(f_ready_download);
} finally {
this_mon.exit();
}
} else if (total < INTERESTING_AVAIL_MAX) {
try {
this_mon.enter();
interesting_downloads.remove(f_ready_download);
} finally {
this_mon.exit();
}
interesting_published++;
if (!disable_put) {
dht.put(torrent.getHash(), "Presence store '" + f_ready_download.getName() + "'", // port 0, no connections
"0".getBytes(), (byte) 0, new DHTPluginOperationListener() {
@Override
public boolean diversified() {
return (true);
}
@Override
public void starts(byte[] key) {
}
@Override
public void valueRead(DHTPluginContact originator, DHTPluginValue value) {
}
@Override
public void valueWritten(DHTPluginContact target, DHTPluginValue value) {
}
@Override
public void complete(byte[] key, boolean timeout_occurred) {
}
});
}
}
try {
this_mon.enter();
int[] run_data = running_downloads.get(f_ready_download);
if (run_data == null) {
run_data = run_data_cache.get(f_ready_download);
}
if (run_data != null) {
if (total < INTERESTING_AVAIL_MAX) {
run_data[1] = seeds;
run_data[2] = leechers;
run_data[3] = total;
} else {
run_data[1] = Math.max(run_data[1], seeds);
run_data[2] = Math.max(run_data[2], leechers);
}
run_data[4] = (int) (SystemTime.getCurrentTime() / 1000);
}
} finally {
this_mon.exit();
}
if (i2p_seeds + i2p_leechers > 0) {
int[] details = (int[]) f_ready_download.getUserData(DOWNLOAD_USER_DATA_I2P_SCRAPE_KEY);
if (details == null) {
details = new int[] { i2p_seeds, i2p_leechers };
f_ready_download.setUserData(DOWNLOAD_USER_DATA_I2P_SCRAPE_KEY, details);
} else {
details[0] = Math.max(details[0], i2p_seeds);
details[1] = Math.max(details[1], i2p_leechers);
}
}
f_ready_download.setScrapeResult(new DownloadScrapeResult() {
@Override
public Download getDownload() {
return (null);
}
@Override
public int getResponseType() {
return (DownloadScrapeResult.RT_SUCCESS);
}
@Override
public int getSeedCount() {
return (seeds);
}
@Override
public int getNonSeedCount() {
return (leechers);
}
@Override
public long getScrapeStartTime() {
return (SystemTime.getCurrentTime());
}
@Override
public void setNextScrapeStartTime(long nextScrapeStartTime) {
}
@Override
public long getNextScrapeStartTime() {
return (f_next_check);
}
@Override
public String getStatus() {
return ("OK");
}
@Override
public URL getURL() {
URL url_to_report = torrent.isDecentralised() ? torrent.getAnnounceURL() : DEFAULT_URL;
return (url_to_report);
}
});
}
});
}
}
}
use of com.biglybt.plugin.dht.DHTPluginOperationListener in project BiglyBT by BiglySoftware.
the class DHTTrackerPlugin method trackerRemove.
protected void trackerRemove(final Download download, final trackerTarget target) {
if (disable_put) {
return;
}
if (download.getFlag(Download.FLAG_METADATA_DOWNLOAD)) {
return;
}
final long start = SystemTime.getCurrentTime();
if (dht.hasLocalKey(target.getHash())) {
increaseActive(download);
dht.remove(target.getHash(), "Tracker dereg of '" + download.getName() + "'" + target.getDesc(), new DHTPluginOperationListener() {
@Override
public boolean diversified() {
return (true);
}
@Override
public void starts(byte[] key) {
}
@Override
public void valueRead(DHTPluginContact originator, DHTPluginValue value) {
}
@Override
public void valueWritten(DHTPluginContact target, DHTPluginValue value) {
}
@Override
public void complete(byte[] key, boolean timeout_occurred) {
if (target.getType() == REG_TYPE_FULL) {
log(download, "Unregistration of '" + target.getDesc() + "' completed (elapsed=" + TimeFormatter.formatColonMillis(SystemTime.getCurrentTime() - start) + ")");
}
decreaseActive(download);
}
});
}
}
use of com.biglybt.plugin.dht.DHTPluginOperationListener in project BiglyBT by BiglySoftware.
the class DHTTrackerPlugin method scrape.
/**
* This is used by the dhtscraper plugin
*/
public DownloadScrapeResult scrape(byte[] hash) {
final int[] seeds = { 0 };
final int[] leechers = { 0 };
final AESemaphore sem = new AESemaphore("DHTTrackerPlugin:scrape");
dht.get(hash, "Scrape for " + ByteFormatter.encodeString(hash).substring(0, 16), DHTPlugin.FLAG_DOWNLOADING, NUM_WANT, SCRAPE_TIMEOUT, false, false, new DHTPluginOperationListener() {
@Override
public boolean diversified() {
return (true);
}
@Override
public void starts(byte[] key) {
}
@Override
public void valueRead(DHTPluginContact originator, DHTPluginValue value) {
if ((value.getFlags() & DHTPlugin.FLAG_DOWNLOADING) == 1) {
leechers[0]++;
} else {
seeds[0]++;
}
}
@Override
public void valueWritten(DHTPluginContact target, DHTPluginValue value) {
}
@Override
public void complete(byte[] key, boolean timeout_occurred) {
sem.release();
}
});
sem.reserve();
return (new DownloadScrapeResult() {
@Override
public Download getDownload() {
return (null);
}
@Override
public int getResponseType() {
return (DownloadScrapeResult.RT_SUCCESS);
}
@Override
public int getSeedCount() {
return (seeds[0]);
}
@Override
public int getNonSeedCount() {
return (leechers[0]);
}
@Override
public long getScrapeStartTime() {
return (0);
}
@Override
public void setNextScrapeStartTime(long nextScrapeStartTime) {
}
@Override
public long getNextScrapeStartTime() {
return (0);
}
@Override
public String getStatus() {
return ("OK");
}
@Override
public URL getURL() {
return (null);
}
});
}
use of com.biglybt.plugin.dht.DHTPluginOperationListener in project BiglyBT by BiglySoftware.
the class DHTTrackerPlugin method trackerPut.
protected void trackerPut(final Download download, RegistrationDetails details) {
final long start = SystemTime.getCurrentTime();
trackerTarget[] targets = details.getTargets(true);
byte flags = details.getFlags();
for (int i = 0; i < targets.length; i++) {
final trackerTarget target = targets[i];
int target_type = target.getType();
// don't let a put block an announce as we don't want to be waiting for
// this at start of day to get a torrent running
// increaseActive( dl );
String encoded = details.getPutDetails().getEncoded();
byte[] encoded_bytes = encoded.getBytes();
DHTPluginValue existing = dht.getLocalValue(target.getHash());
if (existing != null && existing.getFlags() == flags && Arrays.equals(existing.getValue(), encoded_bytes)) {
continue;
}
if (disable_put) {
if (target_type == REG_TYPE_FULL) {
log(download, "Registration of '" + target.getDesc() + "' skipped as disabled due to use of SOCKS proxy");
}
} else if (download.getFlag(Download.FLAG_METADATA_DOWNLOAD)) {
log(download, "Registration of '" + target.getDesc() + "' skipped as metadata download");
} else if (target_type == REG_TYPE_DERIVED && dht.isSleeping()) {
log(download, "Registration of '" + target.getDesc() + "' skipped as sleeping");
} else {
dht.put(target.getHash(), "Tracker reg of '" + download.getName() + "'" + target.getDesc() + " -> " + encoded, encoded_bytes, flags, false, new DHTPluginOperationListener() {
@Override
public boolean diversified() {
return (true);
}
@Override
public void starts(byte[] key) {
}
@Override
public void valueRead(DHTPluginContact originator, DHTPluginValue value) {
}
@Override
public void valueWritten(DHTPluginContact target, DHTPluginValue value) {
}
@Override
public void complete(byte[] key, boolean timeout_occurred) {
if (target.getType() == REG_TYPE_FULL) {
log(download, "Registration of '" + target.getDesc() + "' completed (elapsed=" + TimeFormatter.formatColonMillis((SystemTime.getCurrentTime() - start)) + ")");
}
// decreaseActive( dl );
}
});
}
}
}
use of com.biglybt.plugin.dht.DHTPluginOperationListener in project BiglyBT by BiglySoftware.
the class DHTTrackerPlugin method trackerRemove.
protected void trackerRemove(final Download download, RegistrationDetails details) {
if (disable_put) {
return;
}
if (download.getFlag(Download.FLAG_METADATA_DOWNLOAD)) {
return;
}
final long start = SystemTime.getCurrentTime();
trackerTarget[] targets = details.getTargets(true);
for (int i = 0; i < targets.length; i++) {
final trackerTarget target = targets[i];
if (dht.hasLocalKey(target.getHash())) {
increaseActive(download);
dht.remove(target.getHash(), "Tracker dereg of '" + download.getName() + "'" + target.getDesc(), new DHTPluginOperationListener() {
@Override
public boolean diversified() {
return (true);
}
@Override
public void starts(byte[] key) {
}
@Override
public void valueRead(DHTPluginContact originator, DHTPluginValue value) {
}
@Override
public void valueWritten(DHTPluginContact target, DHTPluginValue value) {
}
@Override
public void complete(byte[] key, boolean timeout_occurred) {
if (target.getType() == REG_TYPE_FULL) {
log(download, "Unregistration of '" + target.getDesc() + "' completed (elapsed=" + TimeFormatter.formatColonMillis(SystemTime.getCurrentTime() - start) + ")");
}
decreaseActive(download);
}
});
}
}
}
Aggregations