📄 trtrackerbtannouncerimpl.java
字号:
last_failure_resp.setPeers( cached_peers );
}
return( last_failure_resp );
}
private byte[]
updateOld(
URL[] tracker_url,
URL reqUrl )
throws Exception
{
// set context in case authentication dialog is required
TorrentUtils.setTLSTorrentHash( torrent_hash );
// loop to possibly retry update on SSL certificate install
for (int i=0;i<2;i++){
String failure_reason = null;
try{
String protocol = reqUrl.getProtocol();
if (Logger.isEnabled())
Logger.log(new LogEvent(torrent, LOGID,
"Tracker Announcer is Requesting: " + reqUrl));
ByteArrayOutputStream message = new ByteArrayOutputStream();
if ( protocol.equalsIgnoreCase("udp")){
failure_reason = announceUDP( reqUrl, message );
}else{
failure_reason = announceHTTP( tracker_url, reqUrl, message );
}
// if we've got some kind of response then return it
if ( message.size() > 0 ){
return( message.toByteArray());
}
if ( failure_reason == null ){
failure_reason = "No data received from tracker";
}
}catch( SSLException e ){
// e.printStackTrace();
// try and install certificate regardless of error (as this changed in JDK1.5
// and broke this...)
if ( i == 0 ){//&& e.getMessage().indexOf("No trusted certificate found") != -1 ){
if ( SESecurityManager.installServerCertificates( reqUrl ) != null ){
// certificate has been installed
continue; // retry with new certificate
}
failure_reason = exceptionToString( e );
}else{
failure_reason = exceptionToString( e );
}
}catch (Exception e){
// e.printStackTrace();
failure_reason = exceptionToString( e );
}
if ( failure_reason.indexOf("401" ) != -1 ){
failure_reason = "Tracker authentication failed";
}
if (Logger.isEnabled())
Logger.log(new LogEvent(torrent, LOGID, LogEvent.LT_ERROR,
"Exception while processing the Tracker Request : "
+ failure_reason));
throw( new Exception( failure_reason));
}
// should never get here as second iteration of loop will always cause an exit
throw( new Exception( "Internal Error: should never get here" ));
}
protected String
announceHTTP(
URL[] tracker_url, // overwritten if redirected
URL reqUrl,
ByteArrayOutputStream message )
throws IOException
{
TRTrackerUtils.checkForBlacklistedURLs( reqUrl );
reqUrl = TRTrackerUtils.adjustURLForHosting( reqUrl );
reqUrl = AddressUtils.adjustURL( reqUrl );
String failure_reason = null;
HttpURLConnection con;
Properties http_properties = new Properties();
http_properties.put( ClientIDGenerator.PR_URL, reqUrl );
try{
ClientIDManagerImpl.getSingleton().generateHTTPProperties( http_properties );
}catch( ClientIDException e ){
throw( new IOException( e.getMessage()));
}
reqUrl = (URL)http_properties.get( ClientIDGenerator.PR_URL );
if ( reqUrl.getProtocol().equalsIgnoreCase("https")){
// see ConfigurationChecker for SSL client defaults
HttpsURLConnection ssl_con = (HttpsURLConnection)reqUrl.openConnection();
// allow for certs that contain IP addresses rather than dns names
ssl_con.setHostnameVerifier(
new HostnameVerifier()
{
public boolean
verify(
String host,
SSLSession session )
{
return( true );
}
});
con = ssl_con;
}else{
con = (HttpURLConnection) reqUrl.openConnection();
}
String user_agent = (String)http_properties.get( ClientIDGenerator.PR_USER_AGENT );
if ( user_agent != null ){
con.setRequestProperty("User-Agent", user_agent );
}
con.setRequestProperty("Connection", "close" );
// some trackers support gzip encoding of replies
con.addRequestProperty("Accept-Encoding","gzip");
try{
con.connect();
InputStream is = null;
try{
is = con.getInputStream();
String resulting_url_str = con.getURL().toString();
if ( !reqUrl.toString().equals( resulting_url_str )){
// some kind of redirect has occurred. Unfortunately we can't get at the underlying
// redirection reason (temp, perm etc) so we support the use of an explicit indicator
// in the resulting url
String marker = "permredirect=1";
int pos = resulting_url_str.indexOf( marker );
if ( pos != -1 ){
pos = pos-1; // include the '&' or '?'
try{
URL redirect_url =
new URL( resulting_url_str.substring(0,pos));
tracker_url[0] = redirect_url;
}catch( Throwable e ){
Debug.printStackTrace(e);
}
}
}
String encoding = con.getHeaderField( "content-encoding");
boolean gzip = encoding != null && encoding.equalsIgnoreCase("gzip");
// System.out.println( "encoding = " + encoding );
if ( gzip ){
is = new GZIPInputStream( is );
}
// there are some trackers out there that don't set content length correctly
// so we can't reliably use it :(
int content_length = -1; //con.getContentLength();
// System.out.println(length);
byte[] data = new byte[1024];
int num_read = 0;
// some trackers don't return content-length
while ( content_length <= 0 || num_read < content_length ){
try{
int len = is.read(data);
if ( len > 0 ){
message.write(data, 0, len);
num_read += len;
if ( num_read > 128*1024 ){
// someone's sending us junk, bail out
message.reset();
throw( new Exception( "Tracker response invalid (too large)" ));
}
}else if ( len == 0 ){
Thread.sleep(20);
}else{
break;
}
}catch (Exception e){
if (Logger.isEnabled()) {
Logger.log(new LogEvent(torrent, LOGID,
"Exception while Requesting Tracker", e));
Logger.log(new LogEvent(torrent, LOGID, LogEvent.LT_ERROR,
"Message Received was : " + message));
}
failure_reason = exceptionToString( e );
break;
}
}
if (Logger.isEnabled())
Logger.log(new LogEvent(torrent, LOGID, "Tracker Announcer ["
+ lastUsedUrl + "] has received : " + message));
}catch (Exception e){
// e.printStackTrace();
failure_reason = exceptionToString( e );
}finally{
if (is != null) {
try {
is.close();
}catch (Exception e) {
}
is = null;
}
}
}finally{
con.disconnect();
}
return( failure_reason );
}
protected String
announceUDP(
URL reqUrl,
ByteArrayOutputStream message )
throws IOException
{
reqUrl = TRTrackerUtils.adjustURLForHosting( reqUrl );
String failure_reason = null;
PasswordAuthentication auth = null;
try{
if ( reqUrl.getQuery().toLowerCase().indexOf("auth") != -1 ){
auth = SESecurityManager.getPasswordAuthentication( UDP_REALM, reqUrl );
}
PRUDPPacketHandler handler = PRUDPPacketHandlerFactory.getHandler( UDPNetworkManager.getSingleton().getUDPNonDataListeningPortNumber());
InetSocketAddress destination = new InetSocketAddress(reqUrl.getHost(),reqUrl.getPort()==-1?80:reqUrl.getPort());
for (int retry_loop=0;retry_loop<PRUDPPacketTracker.DEFAULT_RETRY_COUNT;retry_loop++){
try{
PRUDPPacket connect_request = new PRUDPPacketRequestConnect();
PRUDPPacket reply = handler.sendAndReceive( auth, connect_request, destination );
if ( reply.getAction() == PRUDPPacketTracker.ACT_REPLY_CONNECT ){
PRUDPPacketReplyConnect connect_reply = (PRUDPPacketReplyConnect)reply;
long my_connection = connect_reply.getConnectionId();
PRUDPPacketRequest request;
if ( PRUDPPacketTracker.VERSION == 1 ){
PRUDPPacketRequestAnnounce announce_request = new PRUDPPacketRequestAnnounce( my_connection );
request = announce_request;
// bit of a hack this...
String url_str = reqUrl.toString();
int p_pos = url_str.indexOf("?");
url_str = url_str.substring(p_pos+1);
String event_str = getURLParam( url_str, "event" );
int event = PRUDPPacketRequestAnnounce.EV_UPDATE;
if ( event_str != null ){
if ( event_str.equals( "started" )){
event = PRUDPPacketRequestAnnounce.EV_STARTED;
}else if ( event_str.equals( "stopped" )){
event = PRUDPPacketRequestAnnounce.EV_STOPPED;
}else if ( event_str.equals( "completed" )){
event = PRUDPPacketRequestAnnounce.EV_COMPLETED;
}
}
String ip_str = getURLParam( url_str, "ip" );
int ip = 0;
if ( ip_str != null ){
ip = PRHelpers.addressToInt( ip_str);
}
announce_request.setDetails(
torrent_hash.getBytes(),
tracker_peer_id,
getLongURLParam( url_str, "downloaded" ),
event,
ip,
(int)getLongURLParam( url_str, "numwant" ),
getLongURLParam( url_str, "left" ),
(short)getLongURLParam( url_str, "port" ),
getLongURLParam( url_str, "uploaded" ));
}else{
PRUDPPacketRequestAnnounce2 announce_request = new PRUDPPacketRequestAnnounce2( my_connection );
request = announce_request;
// bit of a hack this...
String url_str = reqUrl.toString();
int p_pos = url_str.indexOf("?");
url_str = url_str.substring(p_pos+1);
String event_str = getURLParam( url_str, "event" );
int event = PRUDPPacketRequestAnnounce.EV_UPDATE;
if ( event_str != null ){
if ( event_str.equals( "started" )){
event = PRUDPPacketRequestAnnounce.EV_STARTED;
}else if ( event_str.equals( "stopped" )){
event = PRUDPPacketRequestAnnounce.EV_STOPPED;
}else if ( event_str.equals( "completed" )){
event = PRUDPPacketRequestAnnounce.EV_COMPLETED;
}
}
String ip_str = getURLParam( url_str, "ip" );
int ip = 0;
if ( ip_str != null ){
ip = PRHelpers.addressToInt( ip_str);
}
announce_request.setDetails(
torrent_hash.getBytes(),
tracker_peer_id,
getLongURLParam( url_str, "downloaded" ),
event,
ip,
key_udp,
(int)getLongURLParam( url_str, "numwant" ),
getLongURLParam( url_str, "left" ),
(short)getLongURLParam( url_str, "port" ),
getLongURLParam( url_str, "uploaded" ));
}
reply = handler.sendAndReceive( auth, request, destination );
if ( reply.getAction() == PRUDPPacketTracker.ACT_REPLY_ANNOUNCE ){
if ( auth != null ){
SESecurityManager.setPasswordAuthenticationOutcome( UDP_REALM, reqUrl, true );
}
if ( PRUDPPacketTracker.VERSION == 1 ){
PRUDPPacketReplyAnnounce announce_reply = (PRUDPPacketReplyAnnounce)reply;
Map map = new HashMap();
map.put( "interval", new Long( announce_reply.getInterval()));
int[] addresses = announce_reply.getAddresses();
short[] ports = announce_reply.getPorts();
List peers = new ArrayList();
map.put( "peers", peers );
for (int i=0;i<addresses.length;i++){
Map peer = new HashMap();
peers.add( peer );
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -